From 61c0d2a10a7e3e51b8b4854f0add202943980964 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 13 Sep 2024 13:22:38 -0500 Subject: [PATCH 01/59] Fix up some bugs. --- .../IkvmReflectionSymbolTests.cs | 8 + .../Reflection/ReflectionSymbolTests.cs | 8 + .../Symbols/ICustomAttributeSymbolProvider.cs | 17 +- .../IkvmReflectionAssemblySymbol.cs | 16 +- .../IkvmReflectionMemberSymbol.cs | 107 ++++++++++++- .../IkvmReflectionModuleSymbol.cs | 18 ++- .../IkvmReflectionParameterSymbol.cs | 20 ++- .../Reflection/ReflectionAssemblySymbol.cs | 37 ++++- .../Reflection/ReflectionMemberSymbol.cs | 149 ++++++++++++++---- .../Reflection/ReflectionModuleSymbol.cs | 22 +-- .../Reflection/ReflectionParameterSymbol.cs | 23 ++- .../Symbols/Reflection/ReflectionSymbol.cs | 14 ++ src/IKVM.Runtime/RuntimeManagedJavaType.cs | 2 - 13 files changed, 362 insertions(+), 79 deletions(-) diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index c683fdbb12..8e933cc672 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -194,6 +194,14 @@ public void CanGetMethod() m.IsPrivate.Should().BeFalse(); } + [TestMethod] + public void CanReadCustomAttributes() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(coreAssembly!.GetType("System.AttributeUsageAttribute")); + var a = s.GetCustomAttribute(s); + } + } } diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index 37b66bf096..a63114293c 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -142,6 +142,14 @@ public void CanGetMethod() m.IsPrivate.Should().BeFalse(); } + [TestMethod] + public void CanReadCustomAttributes() + { + var c = new ReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(typeof(AttributeUsageAttribute)); + var a = s.GetCustomAttributes(); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/ICustomAttributeSymbolProvider.cs b/src/IKVM.CoreLib/Symbols/ICustomAttributeSymbolProvider.cs index d7354b219e..7659f048f8 100644 --- a/src/IKVM.CoreLib/Symbols/ICustomAttributeSymbolProvider.cs +++ b/src/IKVM.CoreLib/Symbols/ICustomAttributeSymbolProvider.cs @@ -10,22 +10,33 @@ interface ICustomAttributeSymbolProvider /// /// Returns an array of all of the custom attributes defined on this member, excluding named attributes, or an empty array if there are no custom attributes. /// + /// /// - CustomAttributeSymbol[] GetCustomAttributes(); + CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false); /// /// Returns an array of custom attributes defined on this member, identified by type, or an empty array if there are no custom attributes of that type. /// /// + /// /// - CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType); + CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false); + + /// + /// Retrieves a custom attribute of a specified type that is applied to a specified member. + /// + /// + /// + /// + CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false); /// /// Indicates whether one or more instance of is defined on this member. /// /// + /// /// - bool IsDefined(ITypeSymbol attributeType); + bool IsDefined(ITypeSymbol attributeType, bool inherit = false); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 12920dd971..987c8af156 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using System.Diagnostics; +using System.Linq; using System.Runtime.CompilerServices; using Assembly = IKVM.Reflection.Assembly; @@ -135,17 +136,26 @@ public ITypeSymbol[] GetTypes() return ResolveTypeSymbols(_assembly.GetTypes()); } - public CustomAttributeSymbol[] GetCustomAttributes() + /// + public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); } - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + /// + public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_assembly.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false)); } - public bool IsDefined(ITypeSymbol attributeType) + /// + public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { return _assembly.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index e32966d91f..70fcc692f6 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Linq; using ConstructorInfo = IKVM.Reflection.ConstructorInfo; @@ -15,10 +16,41 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection abstract class IkvmReflectionMemberSymbol : IkvmReflectionSymbol, IMemberSymbol { + /// + /// Concatinates the list of arrays. + /// + /// + /// + static T[] Concat(List? list) + { + if (list == null) + return []; + + var c = 0; + foreach (var i in list) + c += i.Length; + + if (c == 0) + return []; + + var t = 0; + var a = new T[c]; + foreach (var i in list) + { + Array.Copy(i, 0, a, t, i.Length); + t += i.Length; + } + + return a; + } + readonly IkvmReflectionModuleSymbol _module; readonly IkvmReflectionTypeSymbol? _type; readonly MemberInfo _member; + CustomAttributeSymbol[]? _customAttributes; + CustomAttributeSymbol[]? _inheritedCustomAttributes; + /// /// Initializes a new instance. /// @@ -126,37 +158,100 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn return base.ResolveEventSymbol(@event); } + /// internal MemberInfo ReflectionObject => _member; + /// internal IkvmReflectionModuleSymbol ContainingModule => _module; + /// internal IkvmReflectionTypeSymbol? ContainingType => _type; + /// public virtual ITypeSymbol? DeclaringType => _member.DeclaringType is Type t ? Context.GetOrCreateTypeSymbol(t) : null; + /// public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)_member.MemberType; + /// public virtual int MetadataToken => _member.MetadataToken; + /// public virtual IModuleSymbol Module => Context.GetOrCreateModuleSymbol(_member.Module); + /// public virtual string Name => _member.Name; + /// public override bool IsMissing => _member.__IsMissing; - public virtual CustomAttributeSymbol[] GetCustomAttributes() + /// + public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + { + if (inherit) + { + // check that we've already processed this + if (_inheritedCustomAttributes != null) + return _inheritedCustomAttributes; + + var self = _member; + var list = default(List?); + for (; ; ) + { + // get attribute for current member and append to list + var attr = ResolveMemberSymbol(self).GetCustomAttributes(false); + if (attr.Length > 0) + { + list ??= []; + list.Add(attr); + } + + var type = self as Type; + if (type != null) + { + type = type.BaseType; + if (type == null) + return _inheritedCustomAttributes ??= Concat(list); + + self = type; + continue; + } + + var method = self as MethodInfo; + if (method != null) + { + var prev = self; + method = method.GetBaseDefinition(); + if (method == null || method == prev) + return _inheritedCustomAttributes ??= Concat(list); + + self = method; + continue; + } + + return _inheritedCustomAttributes ??= Concat(list); + } + } + + return _customAttributes ??= ResolveCustomAttributes(_member.GetCustomAttributesData()); + } + + /// + public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_member.GetCustomAttributesData()); + return ResolveCustomAttributes(_member.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit)); } - public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + /// + public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_member.GetCustomAttributesData()).Where(i => i.AttributeType == attributeType).ToArray(); + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } - public virtual bool IsDefined(ITypeSymbol attributeType) + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _member.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); + return _member.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index 9c30b305a4..f1a88c6574 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -2,6 +2,7 @@ using System.Diagnostics; using System.Linq; using System.Reflection.Metadata.Ecma335; +using System.Runtime.InteropServices; using System.Threading; using IKVM.Reflection; @@ -83,10 +84,7 @@ internal IkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) _types ??= new IkvmReflectionTypeSymbol?[_typesSource.Length]; // index of current record is specified row - base - var idx = row - _typesBaseRow; - if (idx < 0) - throw new Exception(); - + var idx = row - _typesBaseRow - 1; Debug.Assert(idx >= 0); Debug.Assert(idx < _typesSource.Length); @@ -335,19 +333,25 @@ public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArgu } /// - public CustomAttributeSymbol[] GetCustomAttributes() + public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_module.GetCustomAttributesData()); } /// - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_module.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false)); } /// - public bool IsDefined(ITypeSymbol attributeType) + public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { return _module.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs index c63d92cad6..80a558f4b6 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs @@ -1,4 +1,6 @@ using System; +using System.Linq; +using System.Runtime.InteropServices; using ParameterInfo = IKVM.Reflection.ParameterInfo; @@ -52,21 +54,29 @@ public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IkvmRe public int Position => _parameter.Position; - public CustomAttributeSymbol[] GetCustomAttributes() + /// + public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_parameter.GetCustomAttributesData()); } - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + /// + public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_parameter.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false)); + return ResolveCustomAttributes(_parameter.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit)); } - public bool IsDefined(ITypeSymbol attributeType) + /// + public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return _parameter.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return _parameter.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit); + } } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index 5165146189..bd5721750e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -39,88 +39,115 @@ internal ReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) return _modules.GetValue(module, _ => new ReflectionModuleSymbol(Context, _)); } + /// public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); + /// public IMethodSymbol? EntryPoint => _assembly.EntryPoint is { } m ? ResolveMethodSymbol(m) : null; + /// public IEnumerable ExportedTypes => ResolveTypeSymbols(_assembly.ExportedTypes); + /// public string? FullName => _assembly.FullName; + /// public string ImageRuntimeVersion => _assembly.ImageRuntimeVersion; + /// public IModuleSymbol ManifestModule => ResolveModuleSymbol(_assembly.ManifestModule); + /// public IEnumerable Modules => ResolveModuleSymbols(_assembly.Modules); + /// public ITypeSymbol[] GetExportedTypes() { return ResolveTypeSymbols(_assembly.GetExportedTypes()); } + /// public IModuleSymbol? GetModule(string name) { return _assembly.GetModule(name) is Module m ? GetOrCreateModuleSymbol(m) : null; } + /// public IModuleSymbol[] GetModules() { return ResolveModuleSymbols(_assembly.GetModules()); } + /// public IModuleSymbol[] GetModules(bool getResourceModules) { return ResolveModuleSymbols(_assembly.GetModules(getResourceModules)); } + /// public AssemblyName GetName() { return _assembly.GetName(); } + /// public AssemblyName GetName(bool copiedName) { return _assembly.GetName(copiedName); } + /// public AssemblyName[] GetReferencedAssemblies() { return _assembly.GetReferencedAssemblies(); } + /// public ITypeSymbol? GetType(string name, bool throwOnError) { return _assembly.GetType(name, throwOnError) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; } + /// public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) { return _assembly.GetType(name, throwOnError, ignoreCase) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; } + /// public ITypeSymbol? GetType(string name) { return _assembly.GetType(name) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; } + /// public ITypeSymbol[] GetTypes() { return ResolveTypeSymbols(_assembly.GetTypes()); } - public CustomAttributeSymbol[] GetCustomAttributes() + /// + public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); } - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + /// + public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_assembly.GetCustomAttributesData()).Where(i => i.AttributeType == attributeType).ToArray(); + return ResolveCustomAttributes(_assembly.GetCustomAttributesData().Where(i => i.AttributeType == ((ReflectionTypeSymbol)attributeType).ReflectionObject)); } - public bool IsDefined(ITypeSymbol attributeType) + /// + public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return _assembly.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject); + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return _assembly.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, false); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 28e417cab8..850276ccf6 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Linq; using System.Reflection; @@ -11,22 +12,53 @@ namespace IKVM.CoreLib.Symbols.Reflection abstract class ReflectionMemberSymbol : ReflectionSymbol, IMemberSymbol { - readonly ReflectionModuleSymbol _module; - readonly ReflectionTypeSymbol? _type; + /// + /// Concatinates the list of arrays. + /// + /// + /// + static T[] Concat(List? list) + { + if (list == null) + return []; + + var c = 0; + foreach (var i in list) + c += i.Length; + + if (c == 0) + return []; + + var t = 0; + var a = new T[c]; + foreach (var i in list) + { + Array.Copy(i, 0, a, t, i.Length); + t += i.Length; + } + + return a; + } + + readonly ReflectionModuleSymbol _containingModule; + readonly ReflectionTypeSymbol? _containingType; readonly MemberInfo _member; + CustomAttributeSymbol[]? _customAttributes; + CustomAttributeSymbol[]? _inheritedCustomAttributes; + /// /// Initializes a new instance. /// /// - /// - /// + /// + /// /// - public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, ReflectionTypeSymbol? type, MemberInfo member) : + public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol containingModule, ReflectionTypeSymbol? containingType, MemberInfo member) : base(context) { - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type; + _containingModule = containingModule ?? throw new ArgumentNullException(nameof(containingModule)); + _containingType = containingType; _member = member ?? throw new ArgumentNullException(nameof(member)); } @@ -37,10 +69,10 @@ public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionModuleS /// protected internal override ReflectionTypeSymbol ResolveTypeSymbol(Type type) { - if (_type != null && type == _type.ReflectionObject) - return _type; + if (_containingType != null && type == _containingType.ReflectionObject) + return _containingType; else if (type.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(type); + return _containingModule.GetOrCreateTypeSymbol(type); else return base.ResolveTypeSymbol(type); } @@ -52,10 +84,10 @@ protected internal override ReflectionTypeSymbol ResolveTypeSymbol(Type type) /// protected internal override ReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) { - if (_type != null && ctor.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateConstructorSymbol(ctor); + if (_containingType != null && ctor.DeclaringType == _containingType.ReflectionObject) + return _containingType.GetOrCreateConstructorSymbol(ctor); else if (ctor.DeclaringType != null && ctor.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(ctor.DeclaringType).GetOrCreateConstructorSymbol(ctor); + return _containingModule.GetOrCreateTypeSymbol(ctor.DeclaringType).GetOrCreateConstructorSymbol(ctor); else return base.ResolveConstructorSymbol(ctor); } @@ -67,10 +99,10 @@ protected internal override ReflectionConstructorSymbol ResolveConstructorSymbol /// protected internal override ReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) { - if (_type != null && method.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateMethodSymbol(method); + if (_containingType != null && method.DeclaringType == _containingType.ReflectionObject) + return _containingType.GetOrCreateMethodSymbol(method); else if (method.DeclaringType != null && method.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(method.DeclaringType).GetOrCreateMethodSymbol(method); + return _containingModule.GetOrCreateTypeSymbol(method.DeclaringType).GetOrCreateMethodSymbol(method); else return base.ResolveMethodSymbol(method); } @@ -82,10 +114,10 @@ protected internal override ReflectionMethodSymbol ResolveMethodSymbol(MethodInf /// protected internal override ReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) { - if (_type != null && field.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateFieldSymbol(field); + if (_containingType != null && field.DeclaringType == _containingType.ReflectionObject) + return _containingType.GetOrCreateFieldSymbol(field); else if (field.DeclaringType != null && field.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(field.DeclaringType).GetOrCreateFieldSymbol(field); + return _containingModule.GetOrCreateTypeSymbol(field.DeclaringType).GetOrCreateFieldSymbol(field); else return base.ResolveFieldSymbol(field); } @@ -99,10 +131,10 @@ protected internal override ReflectionFieldSymbol ResolveFieldSymbol(FieldInfo f protected internal override ReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) { - if (_type != null && property.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreatePropertySymbol(property); + if (_containingType != null && property.DeclaringType == _containingType.ReflectionObject) + return _containingType.GetOrCreatePropertySymbol(property); else if (property.DeclaringType != null && property.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(property.DeclaringType).GetOrCreatePropertySymbol(property); + return _containingModule.GetOrCreateTypeSymbol(property.DeclaringType).GetOrCreatePropertySymbol(property); else return base.ResolvePropertySymbol(property); } @@ -114,10 +146,10 @@ protected internal override ReflectionPropertySymbol ResolvePropertySymbol(Prope /// protected internal override ReflectionEventSymbol ResolveEventSymbol(EventInfo @event) { - if (_type != null && @event.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateEventSymbol(@event); + if (_containingType != null && @event.DeclaringType == _containingType.ReflectionObject) + return _containingType.GetOrCreateEventSymbol(@event); else if (@event.DeclaringType != null && @event.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(@event.DeclaringType).GetOrCreateEventSymbol(@event); + return _containingModule.GetOrCreateTypeSymbol(@event.DeclaringType).GetOrCreateEventSymbol(@event); else return base.ResolveEventSymbol(@event); } @@ -130,12 +162,12 @@ protected internal override ReflectionEventSymbol ResolveEventSymbol(EventInfo @ /// /// Gets the which contains the metadata of this member. /// - internal ReflectionModuleSymbol ContainingModule => _module; + internal ReflectionModuleSymbol ContainingModule => _containingModule; /// /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. /// - internal ReflectionTypeSymbol? ContainingType => _type; + internal ReflectionTypeSymbol? ContainingType => _containingType; /// public virtual IModuleSymbol Module => Context.GetOrCreateModuleSymbol(_member.Module); @@ -153,21 +185,72 @@ protected internal override ReflectionEventSymbol ResolveEventSymbol(EventInfo @ public virtual string Name => _member.Name; /// - public virtual CustomAttributeSymbol[] GetCustomAttributes() + public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + { + if (inherit) + { + // check that we've already processed this + if (_inheritedCustomAttributes != null) + return _inheritedCustomAttributes; + + var self = _member; + var list = default(List?); + for (; ; ) + { + // get attribute for current member and append to list + var attr = ResolveMemberSymbol(self).GetCustomAttributes(false); + if (attr.Length > 0) + { + list ??= []; + list.Add(attr); + } + + var type = self as Type; + if (type != null) + { + type = type.BaseType; + if (type == null) + return _inheritedCustomAttributes ??= Concat(list); + + self = type; + continue; + } + + var method = self as MethodInfo; + if (method != null) + { + var prev = self; + method = method.GetBaseDefinition(); + if (method == null || method == prev) + return _inheritedCustomAttributes ??= Concat(list); + + self = method; + continue; + } + + return _inheritedCustomAttributes ??= Concat(list); + } + } + + return _customAttributes ??= ResolveCustomAttributes(_member.GetCustomAttributesData()); + } + + /// + public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_member.GetCustomAttributesData()); + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); } /// - public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_member.GetCustomAttributesData()).Where(i => i.AttributeType == attributeType).ToArray(); + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } /// - public virtual bool IsDefined(ITypeSymbol attributeType) + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _member.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject); + return _member.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 3b96124816..0e8bc370fc 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -3,6 +3,7 @@ using System.Linq; using System.Reflection; using System.Reflection.Metadata.Ecma335; +using System.Runtime.InteropServices; using System.Threading; namespace IKVM.CoreLib.Symbols.Reflection @@ -84,10 +85,7 @@ internal ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) Interlocked.CompareExchange(ref _types, new ReflectionTypeSymbol?[_typesSource.Length], null); // index of current record is specified row - base - var idx = row - _typesBaseRow; - if (idx < 0) - throw new Exception(); - + var idx = row - _typesBaseRow - 1; Debug.Assert(idx >= 0); Debug.Assert(idx < _typesSource.Length); @@ -330,21 +328,27 @@ public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArgu } /// - public CustomAttributeSymbol[] GetCustomAttributes() + public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_module.GetCustomAttributesData()); } /// - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(_module.GetCustomAttributesData().Where(i => i.AttributeType == ((ReflectionTypeSymbol)attributeType).ReflectionObject)); + } + + /// + public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_module.GetCustomAttributesData()).Where(i => i.AttributeType == attributeType).ToArray(); + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } /// - public bool IsDefined(ITypeSymbol attributeType) + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _module.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject); + return _module.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, false); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index 1bf805672e..2ad73f2602 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -11,6 +11,8 @@ class ReflectionParameterSymbol : ReflectionSymbol, IParameterSymbol readonly ParameterInfo _parameter; readonly ReflectionMethodBaseSymbol _method; + CustomAttributeSymbol[]? _customAttributes; + /// /// Initializes a new instance. /// @@ -52,19 +54,28 @@ public ReflectionParameterSymbol(ReflectionSymbolContext context, ReflectionMeth public int Position => _parameter.Position; - public CustomAttributeSymbol[] GetCustomAttributes() + /// + public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + { + return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); + } + + /// + public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_parameter.GetCustomAttributesData()); + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); } - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType) + /// + public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_parameter.GetCustomAttributesData()).Where(i => i.AttributeType == attributeType).ToArray(); + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } - public bool IsDefined(ITypeSymbol attributeType) + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _parameter.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject); + return _parameter.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index 03ad96cf32..f0aa2a89a5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -350,6 +350,20 @@ protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IList + /// Transforms a custom set of custom attribute data records to a symbol record. + /// + /// + /// + protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IEnumerable attributes) + { + var a = new List(); + foreach (var i in attributes) + a.Add(ResolveCustomAttribute(i)); + + return a.ToArray(); + } + /// /// Transforms a custom attribute data record to a symbol record. /// diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index 04a159d570..c864042dad 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -26,8 +26,6 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; -using System.Collections.Concurrent; -using System.Runtime.CompilerServices; #if IMPORTER || EXPORTER using IKVM.Reflection; From 4119fcb2430e1f2eccbcd414c5fb78c78b13463c Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 15 Sep 2024 13:58:04 -0500 Subject: [PATCH 02/59] Builder infrastructure mostly in place. --- Directory.Build.props | 4 + IKVM.deps.targets | 1 + .../Collections/IndexRangeDictionaryTests.cs | 56 + .../IkvmReflectionSymbolTests.cs | 27 +- .../Reflection/ReflectionSymbolTests.cs | 298 +- .../Collections/IndexRangeDictionary.cs | 140 + src/IKVM.CoreLib/IKVM.CoreLib.csproj | 1 + src/IKVM.CoreLib/Symbols/CustomAttribute.cs | 13 + ...ent.cs => CustomAttributeNamedArgument.cs} | 4 +- .../Symbols/CustomAttributeSymbol.cs | 12 - ...ent.cs => CustomAttributeTypedArgument.cs} | 2 +- .../Symbols/Emit/IAssemblySymbolBuilder.cs | 29 + .../Symbols/Emit/IConstructorSymbolBuilder.cs | 50 + .../Symbols/Emit/ICustomAttributeBuilder.cs | 11 + .../Symbols/Emit/IEventSymbolBuilder.cs | 46 + .../Symbols/Emit/IFieldSymbolBuilder.cs | 34 + .../IGenericTypeParameterSymbolBuilder.cs | 11 + src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs | 11 + .../Symbols/Emit/IMethodSymbolBuilder.cs | 80 + .../Symbols/Emit/IModuleSymbolBuilder.cs | 90 + .../Symbols/Emit/IParameterSymbolBuilder.cs | 27 + .../Symbols/Emit/IPropertySymbolBuilder.cs | 22 + .../Symbols/Emit/ISymbolBuilder.cs | 32 + .../Symbols/Emit/ITypeSymbolBuilder.cs | 326 ++ src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs | 2 +- ...rovider.cs => ICustomAttributeProvider.cs} | 8 +- src/IKVM.CoreLib/Symbols/IMemberSymbol.cs | 2 +- src/IKVM.CoreLib/Symbols/IMethodSymbol.cs | 2 +- src/IKVM.CoreLib/Symbols/IModuleSymbol.cs | 2 +- src/IKVM.CoreLib/Symbols/IParameterSymbol.cs | 14 +- src/IKVM.CoreLib/Symbols/ISymbol.cs | 5 + src/IKVM.CoreLib/Symbols/ISymbolResolver.cs | 2 +- src/IKVM.CoreLib/Symbols/ITypeSymbol.cs | 50 +- .../IkvmReflectionAssemblySymbol.cs | 31 +- .../IkvmReflectionMemberSymbol.cs | 16 +- .../IkvmReflectionMethodBaseSymbol.cs | 30 + .../IkvmReflectionMethodSymbol.cs | 2 +- .../IkvmReflectionModuleSymbol.cs | 9 +- .../IkvmReflectionParameterSymbol.cs | 43 +- .../IkvmReflection/IkvmReflectionSymbol.cs | 48 +- .../IkvmReflectionTypeSymbol.cs | 135 +- .../Emit/ReflectionAssemblySymbolBuilder.cs | 49 + .../ReflectionConstructorSymbolBuilder.cs | 74 + .../Emit/ReflectionCustomAttributeBuilder.cs | 29 + .../Emit/ReflectionEventBuilderInfo.cs | 81 + .../Emit/ReflectionEventSymbolBuilder.cs | 72 + .../Emit/ReflectionFieldSymbolBuilder.cs | 88 + .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 49 + .../Emit/ReflectionMethodSymbolBuilder.cs | 107 + .../Emit/ReflectionModuleSymbolBuilder.cs | 86 + .../Emit/ReflectionParameterSymbolBuilder.cs | 102 + .../Emit/ReflectionPropertySymbolBuilder.cs | 47 + .../Emit/ReflectionSymbolBuilder.cs | 94 + .../Emit/ReflectionTypeSymbolBuilder.cs | 238 ++ .../Reflection/ReflectionAssemblySymbol.cs | 24 +- .../Reflection/ReflectionEventSymbol.cs | 2 +- .../Reflection/ReflectionFieldSymbol.cs | 18 +- .../Reflection/ReflectionMemberSymbol.cs | 59 +- .../Reflection/ReflectionMethodBaseSymbol.cs | 55 +- .../Reflection/ReflectionMethodSymbol.cs | 27 +- .../Reflection/ReflectionModuleSymbol.cs | 319 +- .../Reflection/ReflectionParameterSymbol.cs | 125 +- .../Symbols/Reflection/ReflectionSymbol.cs | 144 +- .../Reflection/ReflectionSymbolContext.cs | 50 +- .../Reflection/ReflectionTypeSymbol.cs | 560 ++-- .../Symbols/Reflection/ReflectionUtil.cs | 146 + src/IKVM.CoreLib/System/TypeExtensions.cs | 450 +++ .../ReaderWriterLockSlimExtensions.cs | 99 + src/IKVM.Reflection/ArrayType.cs | 2 +- src/IKVM.Reflection/CustomAttributeData.cs | 4 +- src/IKVM.Reflection/Emit/ModuleBuilder.cs | 2 +- src/IKVM.Reflection/Signature.cs | 2 +- src/IKVM.Reflection/Type.cs | 13 +- src/IKVM.Runtime/Annotation.cs | 49 +- src/IKVM.Runtime/AttributeHelper.cs | 1596 +++++----- .../Attributes/LineNumberTableAttribute.cs | 425 +-- src/IKVM.Runtime/ByteCodeHelperMethods.cs | 181 +- src/IKVM.Runtime/CodeEmitter.cs | 130 +- src/IKVM.Runtime/CodeEmitterLocal.cs | 15 +- src/IKVM.Runtime/DefineMethodHelper.cs | 2 +- src/IKVM.Runtime/DynamicClassLoader.cs | 4 +- src/IKVM.Runtime/EnumHelper.cs | 28 +- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 28 + src/IKVM.Runtime/JNI/JNIEnv.cs | 2 +- src/IKVM.Runtime/JVM.Resolver.cs | 12 +- .../Java/Externs/java/lang/Class.cs | 41 +- .../Externs/sun/reflect/ReflectionFactory.cs | 20 +- src/IKVM.Runtime/LambdaMetafactory.cs | 4 +- src/IKVM.Runtime/MethodHandleUtil.root.cs | 83 +- src/IKVM.Runtime/ReflectUtil.cs | 67 +- .../RuntimeAccessStubJavaMethod.cs | 11 +- src/IKVM.Runtime/RuntimeAnonymousJavaType.cs | 13 +- src/IKVM.Runtime/RuntimeArrayJavaType.cs | 10 +- .../RuntimeAssemblyClassLoader.cs | 109 +- .../RuntimeAssemblyClassLoaderFactory.cs | 13 +- .../RuntimeByteCodeJavaType.FinishContext.cs | 22 +- ...ypeImpl.DelegateInvokeStubMethodWrapper.cs | 50 +- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 2813 +++++++++-------- src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 2 +- .../RuntimeByteCodePropertyJavaField.cs | 4 +- src/IKVM.Runtime/RuntimeClassLoader.cs | 2 +- src/IKVM.Runtime/RuntimeClassLoaderFactory.cs | 29 +- src/IKVM.Runtime/RuntimeConstantJavaField.cs | 4 +- .../RuntimeConstructorAccessStubJavaMethod.cs | 9 +- src/IKVM.Runtime/RuntimeContext.cs | 28 +- .../RuntimeDefaultInterfaceJavaMethod.cs | 13 +- src/IKVM.Runtime/RuntimeGhostJavaMethod.cs | 15 +- src/IKVM.Runtime/RuntimeJavaField.cs | 39 +- src/IKVM.Runtime/RuntimeJavaMethod.cs | 65 +- src/IKVM.Runtime/RuntimeJavaType.cs | 224 +- src/IKVM.Runtime/RuntimeJavaTypeFactory.cs | 11 +- ...ntimeManagedByteCodeAccessStubJavaField.cs | 14 +- ...eJavaType.DelegateConstructorJavaMethod.cs | 13 +- ...meManagedByteCodeJavaType.GhostJavaType.cs | 42 +- ...agedByteCodeJavaType.RemappedJavaMethod.cs | 25 +- ...anagedByteCodeJavaType.RemappedJavaType.cs | 44 +- .../RuntimeManagedByteCodeJavaType.cs | 305 +- ...RuntimeManagedByteCodePropertyJavaField.cs | 11 +- ...tionJavaType.MultipleAnnotationJavaType.cs | 2 +- ...gedJavaType.AttributeAnnotationJavaType.cs | 148 +- .../RuntimeManagedJavaType.ByRefJavaMethod.cs | 9 +- .../RuntimeManagedJavaType.CloneJavaMethod.cs | 2 +- ...agedJavaType.DelegateInnerClassJavaType.cs | 23 +- ...RuntimeManagedJavaType.EnumEnumJavaType.cs | 27 +- ...timeManagedJavaType.OpenGenericJavaType.cs | 9 +- src/IKVM.Runtime/RuntimeManagedJavaType.cs | 114 +- .../RuntimeManagedJavaTypeFactory.cs | 10 +- src/IKVM.Runtime/RuntimePrimitiveJavaType.cs | 10 +- .../RuntimePrivateInterfaceJavaMethod.cs | 7 +- src/IKVM.Runtime/RuntimeSimpleJavaField.cs | 10 +- src/IKVM.Runtime/RuntimeSmartJavaMethod.cs | 3 +- src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs | 4 +- src/IKVM.Runtime/RuntimeUnloadableJavaType.cs | 20 +- .../RuntimeVolatileLongDoubleJavaField.cs | 4 +- src/IKVM.Runtime/SymbolExtensions.cs | 60 + src/IKVM.Runtime/Types.cs | 115 +- .../Vfs/VfsAssemblyClassDirectory.cs | 2 +- src/IKVM.Runtime/compiler.cs | 6 +- .../IKVM.Tools.Exporter.csproj | 1 + src/IKVM.Tools.Importer/FakeTypes.cs | 49 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 13 +- src/IKVM.Tools.Importer/StaticCompiler.cs | 14 +- 142 files changed, 7824 insertions(+), 4410 deletions(-) create mode 100644 src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs create mode 100644 src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs create mode 100644 src/IKVM.CoreLib/Symbols/CustomAttribute.cs rename src/IKVM.CoreLib/Symbols/{CustomAttributeSymbolNamedArgument.cs => CustomAttributeNamedArgument.cs} (50%) delete mode 100644 src/IKVM.CoreLib/Symbols/CustomAttributeSymbol.cs rename src/IKVM.CoreLib/Symbols/{CustomAttributeSymbolTypedArgument.cs => CustomAttributeTypedArgument.cs} (60%) create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs rename src/IKVM.CoreLib/Symbols/{ICustomAttributeSymbolProvider.cs => ICustomAttributeProvider.cs} (81%) create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs create mode 100644 src/IKVM.CoreLib/System/TypeExtensions.cs create mode 100644 src/IKVM.CoreLib/Threading/ReaderWriterLockSlimExtensions.cs create mode 100644 src/IKVM.Runtime/IRuntimeSymbolResolver.cs diff --git a/Directory.Build.props b/Directory.Build.props index bde86f5e56..bc21f1c585 100644 --- a/Directory.Build.props +++ b/Directory.Build.props @@ -7,6 +7,10 @@ win-x64;win-x86;win-arm64;linux-x64;linux-arm;linux-arm64;linux-musl-x64;linux-musl-arm;linux-musl-arm64;osx-x64;osx-arm64 $(SupportedImageRuntimes) + win-x64;win-x86 + win-x64;win-x86 + win-x64;win-x86 + <_SupportedRuntimes>;$(SupportedRuntimes); <_EnabledRuntimes>;$(EnabledRuntimes); <_SupportedToolRuntimes>;$(SupportedToolRuntimes); diff --git a/IKVM.deps.targets b/IKVM.deps.targets index 7f0a15af2b..e12e969497 100644 --- a/IKVM.deps.targets +++ b/IKVM.deps.targets @@ -16,6 +16,7 @@ + diff --git a/src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs b/src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs new file mode 100644 index 0000000000..b42cc97a80 --- /dev/null +++ b/src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs @@ -0,0 +1,56 @@ +using FluentAssertions; + +using IKVM.CoreLib.Collections; + +using Microsoft.VisualStudio.TestTools.UnitTesting; + +namespace IKVM.CoreLib.Tests.Collections +{ + + [TestClass] + public class IndexRangeDictionaryTests + { + + [TestMethod] + public void CanAddBasicItem() + { + var d = new IndexRangeDictionary(); + d[0] = "Item1"; + d[0].Should().Be("Item1"); + } + + [TestMethod] + public void CanAddOffsetItem() + { + var d = new IndexRangeDictionary(); + d[10] = "Item1"; + d[10].Should().Be("Item1"); + } + + [TestMethod] + public void CanAddSparseRange() + { + var d = new IndexRangeDictionary(); + d[10] = "Item1"; + d[20] = "Item2"; + d[9].Should().BeNull(); + d[10].Should().Be("Item1"); + d[11].Should().BeNull(); + d[19].Should().BeNull(); + d[20].Should().Be("Item2"); + d[21].Should().BeNull(); + } + + [TestMethod] + public void CanAddMaxBeforeMin() + { + var d = new IndexRangeDictionary(); + d[20] = "Item1"; + d[10] = "Item2"; + d[20].Should().Be("Item1"); + d[10].Should().Be("Item2"); + } + + } + +} diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index 8e933cc672..22936c64dd 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -192,14 +192,37 @@ public void CanGetMethod() m.IsGenericMethodDefinition.Should().BeFalse(); m.IsPublic.Should().BeTrue(); m.IsPrivate.Should().BeFalse(); + } + + [System.AttributeUsage(System.AttributeTargets.Class)] + class AttributeWithType : System.Attribute + { + + public AttributeWithType(System.Type type) + { + Type = type; + } + + public System.Type Type { get; } + + } + + [AttributeWithType(typeof(object))] + class ClassWithAttributeWithType + { + + + } [TestMethod] public void CanReadCustomAttributes() { var c = new IkvmReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(coreAssembly!.GetType("System.AttributeUsageAttribute")); - var a = s.GetCustomAttribute(s); + var s = c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); + var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); + var v = a.Value.ConstructorArguments[0].Value; + v.Should().BeOfType(); } } diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index a63114293c..efbd5e2846 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -1,8 +1,11 @@ using System; +using System.Reflection; +using System.Reflection.Emit; using FluentAssertions; using IKVM.CoreLib.Symbols.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; using Microsoft.VisualStudio.TestTools.UnitTesting; @@ -92,7 +95,7 @@ public void EnumTypeShouldBeSame() } [TestMethod] - public void CanGetType() + public void CanResolveType() { var c = new ReflectionSymbolContext(); var s = c.GetOrCreateTypeSymbol(typeof(object)); @@ -101,7 +104,7 @@ public void CanGetType() } [TestMethod] - public void CanGetFieldOfGenericTypeDefinition() + public void CanResolveFieldOfGenericTypeDefinition() { var c = new ReflectionSymbolContext(); var s = c.GetOrCreateTypeSymbol(typeof(Foo<>)); @@ -114,7 +117,7 @@ public void CanGetFieldOfGenericTypeDefinition() } [TestMethod] - public void CanGetFieldOfGenericType() + public void CanResolveFieldOfGenericType() { var c = new ReflectionSymbolContext(); var s = c.GetOrCreateTypeSymbol(typeof(Foo)); @@ -128,7 +131,7 @@ public void CanGetFieldOfGenericType() } [TestMethod] - public void CanGetMethod() + public void CanResolveMethod() { var c = new ReflectionSymbolContext(); var s = c.GetOrCreateTypeSymbol(typeof(object)); @@ -140,14 +143,297 @@ public void CanGetMethod() m.IsGenericMethodDefinition.Should().BeFalse(); m.IsPublic.Should().BeTrue(); m.IsPrivate.Should().BeFalse(); + } + + [TestMethod] + public void CanResolveParameters() + { + var c = new ReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(typeof(object)); + var m = s.GetMethod("ReferenceEquals"); + m.Name.Should().Be("ReferenceEquals"); + m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(bool))); + m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(bool))); + m.IsGenericMethod.Should().BeFalse(); + m.IsGenericMethodDefinition.Should().BeFalse(); + m.IsPublic.Should().BeTrue(); + m.IsPrivate.Should().BeFalse(); + var p = m.GetParameters(); + p.Length.Should().Be(2); + p[0].Name.Should().Be("objA"); + p[0].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(typeof(object))); + p[1].Name.Should().Be("objB"); + p[1].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(typeof(object))); + } + + [AttributeUsage(AttributeTargets.Class)] + class AttributeWithType : Attribute + { + + public AttributeWithType(Type type) + { + Type = type; + } + + public Type Type { get; } + + } + + [AttributeWithType(typeof(object))] + class ClassWithAttributeWithType + { + + + } [TestMethod] public void CanReadCustomAttributes() { var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(AttributeUsageAttribute)); - var a = s.GetCustomAttributes(); + var s = c.GetOrCreateTypeSymbol(typeof(ClassWithAttributeWithType)); + var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithType))); + var v = a.Value.ConstructorArguments[0].Value; + v.Should().BeOfType(); + } + + [TestMethod] + public void CanResolveAssemblyBuilder() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var assemblySymbol = c.GetOrCreateAssemblySymbol(a); + assemblySymbol.Should().BeOfType(); + assemblySymbol.Should().BeSameAs(c.GetOrCreateAssemblySymbol(a)); + } + + [TestMethod] + public void CanResolveModuleBuilder() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var module = a.DefineDynamicModule("Test"); + var moduleSymbol = c.GetOrCreateModuleSymbol(module); + moduleSymbol.Should().BeOfType(); + moduleSymbol.Should().BeSameAs(c.GetOrCreateModuleSymbol(module)); + } + + [TestMethod] + public void CanResolveTypeBuilder() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + + var type1 = m.DefineType("DynamicType1"); + var type1Symbol = c.GetOrCreateTypeSymbol(type1); + type1Symbol.Should().BeOfType(); + type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); + } + + [TestMethod] + public void CanResolveMultipleTypeBuilders() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + + var type1 = m.DefineType("DynamicType1"); + var type1Symbol = c.GetOrCreateTypeSymbol(type1); + type1Symbol.Should().BeOfType(); + type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); + type1.CreateType(); + + var type2 = m.DefineType("DynamicType2"); + var type2Symbol = c.GetOrCreateTypeSymbol(type2); + type2Symbol.Should().BeOfType(); + type2Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type2)); + } + + [TestMethod] + public void CanResolveMethodBuilder() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + } + + [TestMethod] + public void CanResolveMultipleMethodBuilders() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + + var method2 = t.DefineMethod("DynamicMethod2", MethodAttributes.Public | MethodAttributes.Static); + var method2Symbol = c.GetOrCreateMethodSymbol(method2); + method2Symbol.Should().BeOfType(); + method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); + } + + [TestMethod] + public void CanResolveFieldBuilder() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var field = t.DefineField("dynamicField", typeof(object), FieldAttributes.Public); + var fieldSymbol = c.GetOrCreateFieldSymbol(field); + fieldSymbol.Should().BeOfType(); + fieldSymbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field)); + } + + [TestMethod] + public void CanResolveMultipleFieldBuilders() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var field1 = t.DefineField("dynamicField1", typeof(object), FieldAttributes.Public); + var field1Symbol = c.GetOrCreateFieldSymbol(field1); + field1Symbol.Should().BeOfType(); + field1Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field1)); + + var field2 = t.DefineField("dynamicField2", typeof(object), FieldAttributes.Public); + var field2Symbol = c.GetOrCreateFieldSymbol(field2); + field2Symbol.Should().BeOfType(); + field2Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field2)); + } + + [TestMethod] + public void CanResolvePropertyBuilder() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var property = t.DefineProperty("DynamicProperty", PropertyAttributes.None, typeof(object), []); + var propertySymbol = c.GetOrCreatePropertySymbol(property); + propertySymbol.Should().BeOfType(); + propertySymbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property)); + } + + [TestMethod] + public void CanResolveMultiplePropertyBuilders() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var property1 = t.DefineProperty("DynamicProperty1", PropertyAttributes.None, typeof(object), []); + var property1Symbol = c.GetOrCreatePropertySymbol(property1); + property1Symbol.Should().BeOfType(); + property1Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property1)); + + var property2 = t.DefineProperty("DynamicProperty2", PropertyAttributes.None, typeof(object), []); + var property2Symbol = c.GetOrCreatePropertySymbol(property2); + property2Symbol.Should().BeOfType(); + property2Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property2)); + } + + [TestMethod] + public void CanResolveEventBuilder() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); + var event1Symbol = c.GetOrCreateEventSymbol(event1); + event1Symbol.Should().BeOfType(); + event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); + } + + [TestMethod] + public void CanResolveMultipleEventBuilders() + { + var c = new ReflectionSymbolContext(); + var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); + var m = a.DefineDynamicModule("DynamicModule"); + var t = m.DefineType("DynamicType"); + + var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); + var event1Symbol = c.GetOrCreateEventSymbol(event1); + event1Symbol.Should().BeOfType(); + event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); + + var event2 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); + var event2Symbol = c.GetOrCreateEventSymbol(event2); + event2Symbol.Should().BeOfType(); + event2Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event2)); + } + + [TestMethod] + public void CanCreateAndResolveDynamicMethodOnModule() + { + var c = new ReflectionSymbolContext(); + + var method1 = new DynamicMethod("DynamicMethod1", null, null, typeof(ReflectionSymbolTests).Module); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + } + + [TestMethod] + public void CanCreateAndResolveMultipleDynamicMethodsOnModule() + { + var c = new ReflectionSymbolContext(); + + var method1 = new DynamicMethod("DynamicMethod1", null, null, typeof(ReflectionSymbolTests).Module); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + + var method2 = new DynamicMethod("DynamicMethod2", null, null, typeof(ReflectionSymbolTests).Module); + var method2Symbol = c.GetOrCreateMethodSymbol(method2); + method2Symbol.Should().BeOfType(); + method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); + } + + [TestMethod] + public void CanCreateAndResolveDynamicMethodOnType() + { + var c = new ReflectionSymbolContext(); + + var method1 = new DynamicMethod("DynamicMethod", null, null, typeof(ReflectionSymbolTests)); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + } + + [TestMethod] + public void CanCreateAndResolveMultipleDynamicMethodsOnType() + { + var c = new ReflectionSymbolContext(); + + var method1 = new DynamicMethod("DynamicMethod1", null, null, typeof(ReflectionSymbolTests)); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + + var method2 = new DynamicMethod("DynamicMethod2", null, null, typeof(ReflectionSymbolTests)); + var method2Symbol = c.GetOrCreateMethodSymbol(method2); + method2Symbol.Should().BeOfType(); + method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); } } diff --git a/src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs b/src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs new file mode 100644 index 0000000000..deae4e8aed --- /dev/null +++ b/src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs @@ -0,0 +1,140 @@ +using System; +using System.Diagnostics; + +namespace IKVM.CoreLib.Collections +{ + + /// + /// Represents a dictionary that can store int keys mapped to values, where the underlying storage is an array that + /// holds the minimum number of items for the minimum and maximum key values. + /// + struct IndexRangeDictionary + { + + int _initialCapacity; + int _maxCapacity; + int _minKey; + T?[]? _items; + + /// + /// Initializes a new instance. + /// + public IndexRangeDictionary() : this(initialCapacity: 4, maxCapacity: int.MaxValue) + { + + } + + /// + /// Initializes a new instance. + /// + public IndexRangeDictionary(int initialCapacity = 4, int maxCapacity = int.MaxValue) + { + if (initialCapacity < 0) + throw new ArgumentOutOfRangeException(nameof(initialCapacity)); + if (maxCapacity < 0) + throw new ArgumentOutOfRangeException(nameof(maxCapacity)); + + _initialCapacity = initialCapacity; + _maxCapacity = maxCapacity; + } + + /// + /// Gets the capacity of the dictionary. + /// + public readonly int Capacity => _items?.Length ?? 0; + + /// + /// Gets or sets the item with the specified key, optionally growing the list to accomidate. + /// + /// + /// + public T? this[int key] + { + readonly get => Get(key); + set => Set(key, value); + } + + /// + /// Ensures the list is sized such that it can hold the specified key. + /// + /// + /// + public void EnsureCapacity(int key) + { + // initial state, first item, hold only that + if (_items == null) + { + _minKey = key; + _items = new T[_initialCapacity]; + } + + // key is less than minKey, grow and shift by difference + if (key < _minKey) + { + // increase length until we encompass key + var len = _items.Length; + while (key - _minKey + len - _items.Length < 0) + len *= 2; + + if (len > _maxCapacity || len < 0) + throw new InvalidOperationException(); + + var end = _items.Length - 1; + Array.Resize(ref _items, len); + for (int i = end; i >= 0; i--) + _items[i + _minKey - key] = _items[i]; + Array.Clear(_items, 0, end); + + _minKey = key; + } + + // desired position if after the end of the array, we need to grow, but no copies needed + if (key - _minKey >= _items.Length) + { + // increase length until we encompass key + var len = _items.Length; + while (key - _minKey >= len) + len *= 2; + + if (len > _maxCapacity || len < 0) + throw new InvalidOperationException(); + + Array.Resize(ref _items, len); + } + + Debug.Assert(key - _minKey >= 0); + Debug.Assert(key - _minKey < _items.Length); + } + + /// + /// Adds a new item to the list. + /// + /// + readonly T? Get(int key) + { + var pos = key - _minKey; + if (_items == null || pos < 0 || pos >= _items.Length) + return default; + else + return _items[pos]; + } + + /// + /// Adds a new item to the list. + /// + /// + /// + void Set(int key, T? value) + { + EnsureCapacity(key); + if (_items == null) + throw new InvalidOperationException(); + + Debug.Assert(key - _minKey >= 0); + Debug.Assert(key - _minKey < _items.Length); + _items[key - _minKey] = value; + } + + } + +} diff --git a/src/IKVM.CoreLib/IKVM.CoreLib.csproj b/src/IKVM.CoreLib/IKVM.CoreLib.csproj index cede1bd120..5e31c90e3d 100644 --- a/src/IKVM.CoreLib/IKVM.CoreLib.csproj +++ b/src/IKVM.CoreLib/IKVM.CoreLib.csproj @@ -25,6 +25,7 @@ + diff --git a/src/IKVM.CoreLib/Symbols/CustomAttribute.cs b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs new file mode 100644 index 0000000000..7b1af0a9d5 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs @@ -0,0 +1,13 @@ +using System.Collections.Immutable; + +namespace IKVM.CoreLib.Symbols +{ + + readonly record struct CustomAttribute( + ITypeSymbol AttributeType, + IConstructorSymbol Constructor, + ImmutableArray ConstructorArguments, + ImmutableArray NamedArguments); + + +} diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeSymbolNamedArgument.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs similarity index 50% rename from src/IKVM.CoreLib/Symbols/CustomAttributeSymbolNamedArgument.cs rename to src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs index c01598e24c..9ba5842e8d 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeSymbolNamedArgument.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs @@ -1,10 +1,10 @@ namespace IKVM.CoreLib.Symbols { - readonly record struct CustomAttributeSymbolNamedArgument( + readonly record struct CustomAttributeNamedArgument( bool IsField, IMemberSymbol MemberInfo, string MemberName, - CustomAttributeSymbolTypedArgument TypedValue); + CustomAttributeTypedArgument TypedValue); } diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeSymbol.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeSymbol.cs deleted file mode 100644 index dbdab0f3cb..0000000000 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeSymbol.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System.Collections.Immutable; - -namespace IKVM.CoreLib.Symbols -{ - - readonly record struct CustomAttributeSymbol( - ITypeSymbol AttributeType, - IConstructorSymbol Constructor, - ImmutableArray ConstructorArguments, - ImmutableArray NamedArguments); - -} diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeSymbolTypedArgument.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs similarity index 60% rename from src/IKVM.CoreLib/Symbols/CustomAttributeSymbolTypedArgument.cs rename to src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs index 0f56df5a32..d19aebfddb 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeSymbolTypedArgument.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs @@ -1,7 +1,7 @@ namespace IKVM.CoreLib.Symbols { - readonly record struct CustomAttributeSymbolTypedArgument( + readonly record struct CustomAttributeTypedArgument( ITypeSymbol ArgumentType, object? Value); diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs new file mode 100644 index 0000000000..c89940b3a4 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs @@ -0,0 +1,29 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IAssemblySymbolBuilder : ISymbolBuilder + { + + /// + /// Defines a named module in this assembly. + /// + /// + /// + IModuleSymbolBuilder DefineModule(string name); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs new file mode 100644 index 0000000000..72d628579c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs @@ -0,0 +1,50 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IConstructorSymbolBuilder : ISymbolBuilder + { + + /// + /// Sets the method implementation flags for this constructor. + /// + /// + void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes); + + /// + /// Defines a parameter of this constructor. + /// + /// + /// + /// + /// + IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection.ParameterAttributes attributes, string? strParamName); + + /// + /// Gets an ILGenerator object, with the specified MSIL stream size, that can be used to build a method body for this constructor. + /// + /// + /// + System.Reflection.Emit.ILGenerator GetILGenerator(int streamSize); + + /// + /// Gets an ILGenerator for this constructor. + /// + /// + System.Reflection.Emit.ILGenerator GetILGenerator(); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs new file mode 100644 index 0000000000..e30a02e211 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface ICustomAttributeBuilder + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs new file mode 100644 index 0000000000..b5378a41d9 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs @@ -0,0 +1,46 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IEventSymbolBuilder : ISymbolBuilder + { + + /// + /// Sets the method used to subscribe to this event. + /// + /// + void SetAddOnMethod(IMethodSymbolBuilder mdBuilder); + + /// + /// Sets the method used to unsubscribe to this event. + /// + /// + void SetRemoveOnMethod(IMethodSymbolBuilder mdBuilder); + + /// + /// Sets the method used to raise this event. + /// + /// + void SetRaiseMethod(IMethodSymbolBuilder mdBuilder); + + /// + /// Adds one of the "other" methods associated with this event. "Other" methods are methods other than the "on" and "raise" methods associated with an event. This function can be called many times to add as many "other" methods. + /// + /// + void AddOtherMethod(IMethodSymbolBuilder mdBuilder); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs new file mode 100644 index 0000000000..5b6706e3f2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs @@ -0,0 +1,34 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IFieldSymbolBuilder : ISymbolBuilder + { + + /// + /// Sets the default value of this field. + /// + /// + void SetConstant(object? defaultValue); + + /// + /// Specifies the field layout. + /// + /// + void SetOffset(int iOffset); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs new file mode 100644 index 0000000000..38bcde8376 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IGenericTypeParameterSymbolBuilder : ISymbolBuilder + { + + + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs new file mode 100644 index 0000000000..69f29dfa36 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IILGenerator + { + + + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs new file mode 100644 index 0000000000..9e251bed28 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs @@ -0,0 +1,80 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IMethodSymbolBuilder : ISymbolBuilder + { + + /// + /// Sets the implementation flags for this method. + /// + /// + void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes); + + /// + /// Sets the number and types of parameters for a method. + /// + /// + void SetParameters(params ITypeSymbol[] parameterTypes); + + /// + /// Sets the return type of the method. + /// + /// + void SetReturnType(ITypeSymbol? returnType); + + /// + /// Sets the method signature, including the return type, the parameter types, and the required and optional custom modifiers of the return type and parameter types. + /// + /// + /// + /// + /// + /// + /// + void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); + + /// + /// Sets the number of generic type parameters for the current method, specifies their names, and returns an array of GenericTypeParameterBuilder objects that can be used to define their constraints. + /// + /// + /// + IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names); + + /// + /// Sets the parameter attributes and the name of a parameter of this method, or of the return value of this method. Returns a ParameterBuilder that can be used to apply custom attributes. + /// + /// + /// + /// + /// + IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName); + + /// + /// Returns an ILGenerator for this method with a default Microsoft intermediate language (MSIL) stream size of 64 bytes. + /// + /// + IILGenerator GetILGenerator(); + + /// + /// Returns an ILGenerator for this method with the specified Microsoft intermediate language (MSIL) stream size. + /// + /// + /// + IILGenerator GetILGenerator(int size); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs new file mode 100644 index 0000000000..5d059cc092 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -0,0 +1,90 @@ +using System.Reflection; +using System.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IModuleSymbolBuilder : ISymbolBuilder + { + + /// + /// Constructs a TypeBuilder for a private type with the specified name in this module. + /// + /// + /// + ITypeSymbolBuilder DefineType(string name); + + /// + /// Constructs a TypeBuilder given the type name, the attributes, the type that the defined type extends, and the total size of the type. + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, int typesize); + + /// + /// Constructs a TypeBuilder given type name, its attributes, and the type that the defined type extends. + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent); + + /// + /// Constructs a TypeBuilder given the type name and the type attributes. + /// + /// + /// + /// + ITypeSymbolBuilder DefineType(string name, TypeAttributes attr); + + /// + /// Constructs a TypeBuilder given the type name, the attributes, the type that the defined type extends, and the packing size of the type. + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packsize); + + /// + /// Constructs a TypeBuilder given the type name, attributes, the type that the defined type extends, the packing size of the defined type, and the total size of the defined type. + /// + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packingSize, int typesize); + + /// + /// Constructs a TypeBuilder given the type name, attributes, the type that the defined type extends, and the interfaces that the defined type implements. + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs new file mode 100644 index 0000000000..9ac13b3847 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs @@ -0,0 +1,27 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IParameterSymbolBuilder : ISymbolBuilder + { + /// + /// Sets the default value of the parameter. + /// + /// + void SetConstant(object? defaultValue); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs new file mode 100644 index 0000000000..6c2d9ade91 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs @@ -0,0 +1,22 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IPropertySymbolBuilder : ISymbolBuilder + { + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs new file mode 100644 index 0000000000..8b7b295feb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs @@ -0,0 +1,32 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + /// + /// Base interface for a builder of symbols. + /// + interface ISymbolBuilder + { + + /// + /// Gets the that is currently being built. Portions of this interface will be non-functional until the build is completed. + /// + ISymbol Symbol { get; } + + } + + /// + /// Base interface for a builder of symbols. + /// + /// + interface ISymbolBuilder : ISymbolBuilder + where TSymbol : ISymbol + { + + /// + /// Gets the that is currently being built. Portions of this interface will be non-functional until the build is completed. + /// + new TSymbol Symbol { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs new file mode 100644 index 0000000000..ebe0c59156 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs @@ -0,0 +1,326 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface ITypeSymbolBuilder : ISymbolBuilder + { + + /// + /// Sets the base type of the type currently under construction. + /// + /// + void SetParent(ITypeSymbol? parent); + + /// + /// Defines the generic type parameters for the current type, specifying their number and their names, and returns an array of GenericTypeParameterBuilder objects that can be used to set their constraints. + /// + /// + /// + IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names); + + /// + /// Defines the initializer for this type. + /// + /// + IConstructorSymbolBuilder DefineTypeInitializer(); + + /// + /// Adds an interface that this type implements. + /// + /// + void AddInterfaceImplementation(ITypeSymbol interfaceType); + + /// + /// Adds a new constructor to the type, with the given attributes and signature. + /// + /// + /// + /// + /// + IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes); + + /// + /// Adds a new constructor to the type, with the given attributes, signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredCustomModifiers, ITypeSymbol[][]? optionalCustomModifiers); + + /// + /// Defines the parameterless constructor. The constructor defined here will simply call the parameterless constructor of the parent. + /// + /// + /// + IConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes); + + /// + /// Adds a new event to the type, with the given name, attributes and event type. + /// + /// + /// + /// + /// + IEventSymbolBuilder DefineEvent(string name, EventAttributes attributes, ITypeSymbol eventtype); + + /// + /// Adds a new field to the type, with the given name, attributes, and field type. + /// + /// + /// + /// + /// + IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, FieldAttributes attributes); + + /// + /// Adds a new field to the type, with the given name, attributes, field type, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, FieldAttributes attributes); + + /// + /// Adds a new method to the type, with the specified name, method attributes, calling convention, method signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); + + /// + /// Adds a new method to the type, with the specified name, method attributes, calling convention, and method signature. + /// + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + + /// + /// Adds a new method to the type, with the specified name, method attributes, and calling convention. + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention); + + /// + /// Adds a new method to the type, with the specified name and method attributes. + /// + /// + /// + /// + IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes); + + /// + /// Adds a new method to the type, with the specified name, method attributes, and method signature. + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + + /// + /// Defines a nested type, given its name, attributes, the type that it extends, and the interfaces that it implements. + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces); + + /// + /// Defines a nested type, given its name, attributes, size, and the type that it extends. + /// + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize, int typeSize); + + /// + /// Defines a nested type, given its name, attributes, the type that it extends, and the packing size. + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize); + + /// + /// Defines a nested type, given its name. + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(string name); + + /// + /// Defines a nested type, given its name, attributes, and the type that it extends. + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent); + + /// + /// Defines a nested type, given its name and attributes. + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr); + + /// + /// Defines a nested type, given its name, attributes, the total size of the type, and the type that it extends. + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typeSize); + + /// + /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); + + /// + /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); + + /// + /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, the PInvoke flags, and custom modifiers for the parameters and return type. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); + + /// + /// Adds a new property to the type, with the given name and property signature. + /// + /// + /// + /// + /// + /// + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes); + + /// + /// Adds a new property to the type, with the given name, attributes, calling convention, and property signature. + /// + /// + /// + /// + /// + /// + /// + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes); + + /// + /// Adds a new property to the type, with the given name, property signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); + + /// + /// Adds a new property to the type, with the given name, calling convention, property signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + /// + /// Finishes the type, updating the associated symbol. + /// + void Finish(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs index 1b0817f280..a87909ae33 100644 --- a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols { - interface IAssemblySymbol : ISymbol, ICustomAttributeSymbolProvider + interface IAssemblySymbol : ISymbol, ICustomAttributeProvider { IEnumerable DefinedTypes { get; } diff --git a/src/IKVM.CoreLib/Symbols/ICustomAttributeSymbolProvider.cs b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs similarity index 81% rename from src/IKVM.CoreLib/Symbols/ICustomAttributeSymbolProvider.cs rename to src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs index 7659f048f8..447839f6a3 100644 --- a/src/IKVM.CoreLib/Symbols/ICustomAttributeSymbolProvider.cs +++ b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs @@ -4,7 +4,7 @@ /// /// Provides custom attributes for reflection objects that support them. /// - interface ICustomAttributeSymbolProvider + interface ICustomAttributeProvider { /// @@ -12,7 +12,7 @@ interface ICustomAttributeSymbolProvider /// /// /// - CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false); + CustomAttribute[] GetCustomAttributes(bool inherit = false); /// /// Returns an array of custom attributes defined on this member, identified by type, or an empty array if there are no custom attributes of that type. @@ -20,7 +20,7 @@ interface ICustomAttributeSymbolProvider /// /// /// - CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false); + CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false); /// /// Retrieves a custom attribute of a specified type that is applied to a specified member. @@ -28,7 +28,7 @@ interface ICustomAttributeSymbolProvider /// /// /// - CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false); + CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false); /// /// Indicates whether one or more instance of is defined on this member. diff --git a/src/IKVM.CoreLib/Symbols/IMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IMemberSymbol.cs index 0613ff1000..f54d6c3ffa 100644 --- a/src/IKVM.CoreLib/Symbols/IMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IMemberSymbol.cs @@ -6,7 +6,7 @@ namespace IKVM.CoreLib.Symbols /// /// Obtains information about the attributes of a member and provides access to member metadata. /// - interface IMemberSymbol : ISymbol, ICustomAttributeSymbolProvider + interface IMemberSymbol : ISymbol, ICustomAttributeProvider { /// diff --git a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs index 08d2f8dcb6..c3c8d5c9e0 100644 --- a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs @@ -20,7 +20,7 @@ interface IMethodSymbol : IMethodBaseSymbol /// /// Gets the custom attributes for the return type. /// - ICustomAttributeSymbolProvider ReturnTypeCustomAttributes { get; } + ICustomAttributeProvider ReturnTypeCustomAttributes { get; } /// /// When overridden in a derived class, returns the object for the method on the direct or indirect base class in which the method represented by this instance was first declared. diff --git a/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs index 771d4263c2..bcd76ad225 100644 --- a/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs @@ -7,7 +7,7 @@ namespace IKVM.CoreLib.Symbols /// /// Performs reflection on a module. /// - interface IModuleSymbol : ISymbol, ICustomAttributeSymbolProvider + interface IModuleSymbol : ISymbol, ICustomAttributeProvider { /// diff --git a/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs index 033015ae7f..18e855157e 100644 --- a/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs @@ -6,7 +6,7 @@ namespace IKVM.CoreLib.Symbols /// /// Discovers the attributes of a parameter and provides access to parameter metadata. /// - interface IParameterSymbol : ISymbol, ICustomAttributeSymbolProvider + interface IParameterSymbol : ISymbol, ICustomAttributeProvider { /// @@ -74,6 +74,18 @@ interface IParameterSymbol : ISymbol, ICustomAttributeSymbolProvider /// int MetadataToken { get; } + /// + /// Returns an array of types representing the optional custom modifiers of the parameter. + /// + /// + ITypeSymbol[] GetOptionalCustomModifiers(); + + /// + /// Returns an array of types representing the required custom modifiers of the parameter. + /// + /// + ITypeSymbol[] GetRequiredCustomModifiers(); + } } diff --git a/src/IKVM.CoreLib/Symbols/ISymbol.cs b/src/IKVM.CoreLib/Symbols/ISymbol.cs index 91abe16390..7fae6f73ea 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbol.cs @@ -12,6 +12,11 @@ interface ISymbol /// bool IsMissing { get; } + /// + /// Returns true if the symbol contains a missing symbol. + /// + bool ContainsMissing { get; } + } } diff --git a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs index 5a4815f8d0..2976d5bbb9 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs @@ -2,7 +2,7 @@ { /// - /// Provides an interface to resolve a maaged type symbols. + /// Provides an interface to resolve a managed type symbols. /// interface ISymbolResolver { diff --git a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs index 377a82aa6f..0df2185f3e 100644 --- a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs @@ -1,4 +1,5 @@ -using System.Reflection; +using System; +using System.Reflection; namespace IKVM.CoreLib.Symbols { @@ -39,6 +40,11 @@ interface ITypeSymbol : IMemberSymbol /// string? Namespace { get; } + /// + /// Gets the underlying type code of the specified Type. + /// + TypeCode TypeCode { get; } + /// /// Gets the type from which the current directly inherits. /// @@ -70,14 +76,19 @@ interface ITypeSymbol : IMemberSymbol bool IsConstructedGenericType { get; } /// - /// Gets a value indicating whether the current represents a type parameter in the definition of a generic type or method. + /// Gets a value indicating whether the current type is a generic type. /// - bool IsGenericParameter { get; } + bool IsGenericType { get; } /// - /// Gets a value indicating whether the current type is a generic type. + /// Gets a value indicating whether the current Type represents a generic type definition, from which other generic types can be constructed. /// - bool IsGenericType { get; } + bool IsGenericTypeDefinition { get; } + + /// + /// Gets a value indicating whether the current represents a type parameter in the definition of a generic type or method. + /// + bool IsGenericParameter { get; } /// /// Gets a value indicating whether the fields of the current type are laid out automatically by the common language runtime. @@ -119,6 +130,11 @@ interface ITypeSymbol : IMemberSymbol /// bool IsPrimitive { get; } + /// + /// Gets a value that indicates whether the type is an array type that can represent only a single-dimensional array with a zero lower bound. + /// + bool IsSZArray { get; } + /// /// Gets a value that indicates whether the type is an array. /// @@ -134,6 +150,16 @@ interface ITypeSymbol : IMemberSymbol /// bool IsPointer { get; } + /// + /// Gets a value that indicates whether the current is an unmanaged function pointer. + /// + bool IsFunctionPointer { get; } + + /// + /// Gets a value that indicates whether the current is an unmanaged function pointer. + /// + bool IsUnmanagedFunctionPointer { get; } + /// /// Gets a value indicating whether the is passed by reference. /// @@ -204,6 +230,16 @@ interface ITypeSymbol : IMemberSymbol /// bool IsSerializable { get; } + /// + /// Gets a value that indicates whether the type is a signature type. + /// + bool IsSignatureType { get; } + + /// + /// Gets a value indicating whether the type has a name that requires special handling. + /// + bool IsSpecialName { get; } + /// /// Gets the initializer for the type. /// @@ -280,10 +316,10 @@ interface ITypeSymbol : IMemberSymbol ITypeSymbol? GetInterface(string name, bool ignoreCase); /// - /// When overridden in a derived class, gets all the interfaces implemented or inherited by the current . + /// When overridden in a derived class, gets all the interfaces implemented or if specified,inherited by the current . /// /// - ITypeSymbol[] GetInterfaces(); + ITypeSymbol[] GetInterfaces(bool inherit = true); /// /// Returns an interface mapping for the specified interface type. diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 987c8af156..19b75b9931 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -43,39 +43,57 @@ internal IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) return _modules.GetValue(module, _ => new IkvmReflectionModuleSymbol(Context, _)); } + /// + /// Gets the wrapped . + /// internal Assembly ReflectionObject => _assembly; + /// public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); + /// public IMethodSymbol? EntryPoint => _assembly.EntryPoint is { } m ? ResolveMethodSymbol(m) : null; + /// public IEnumerable ExportedTypes => ResolveTypeSymbols(_assembly.ExportedTypes); + /// public string? FullName => _assembly.FullName; + /// public string ImageRuntimeVersion => _assembly.ImageRuntimeVersion; + /// public IModuleSymbol ManifestModule => ResolveModuleSymbol(_assembly.ManifestModule); + /// public IEnumerable Modules => ResolveModuleSymbols(_assembly.Modules); + /// public override bool IsMissing => _assembly.__IsMissing; + /// + public override bool ContainsMissing => GetModules().Any(i => i.IsMissing || i.ContainsMissing); + + /// public ITypeSymbol[] GetExportedTypes() { return ResolveTypeSymbols(_assembly.GetExportedTypes()); } + /// public IModuleSymbol? GetModule(string name) { return _assembly.GetModule(name) is Module m ? GetOrCreateModuleSymbol(m) : null; } + /// public IModuleSymbol[] GetModules() { return ResolveModuleSymbols(_assembly.GetModules()); } + /// public IModuleSymbol[] GetModules(bool getResourceModules) { return ResolveModuleSymbols(_assembly.GetModules(getResourceModules)); @@ -96,16 +114,19 @@ System.Reflection.AssemblyName ToName(AssemblyName src) #pragma warning restore SYSLIB0037 // Type or member is obsolete } + /// public System.Reflection.AssemblyName GetName() { return _assemblyName ??= ToName(_assembly.GetName()); } + /// public System.Reflection.AssemblyName GetName(bool copiedName) { return ToName(_assembly.GetName()); } + /// public System.Reflection.AssemblyName[] GetReferencedAssemblies() { var l = _assembly.GetReferencedAssemblies(); @@ -116,40 +137,44 @@ public System.Reflection.AssemblyName[] GetReferencedAssemblies() return a; } + /// public ITypeSymbol? GetType(string name, bool throwOnError) { return _assembly.GetType(name, throwOnError) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; } + /// public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) { return _assembly.GetType(name, throwOnError, ignoreCase) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; } + /// public ITypeSymbol? GetType(string name) { return _assembly.GetType(name) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; } + /// public ITypeSymbol[] GetTypes() { return ResolveTypeSymbols(_assembly.GetTypes()); } /// - public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); } /// - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_assembly.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false)); } /// - public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index 70fcc692f6..c01581bda7 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -48,8 +48,8 @@ static T[] Concat(List? list) readonly IkvmReflectionTypeSymbol? _type; readonly MemberInfo _member; - CustomAttributeSymbol[]? _customAttributes; - CustomAttributeSymbol[]? _inheritedCustomAttributes; + CustomAttribute[]? _customAttributes; + CustomAttribute[]? _inheritedCustomAttributes; /// /// Initializes a new instance. @@ -158,7 +158,9 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn return base.ResolveEventSymbol(@event); } - /// + /// + /// Gets the wrapped . + /// internal MemberInfo ReflectionObject => _member; /// @@ -186,7 +188,7 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn public override bool IsMissing => _member.__IsMissing; /// - public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) { if (inherit) { @@ -195,7 +197,7 @@ public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) return _inheritedCustomAttributes; var self = _member; - var list = default(List?); + var list = default(List?); for (; ; ) { // get attribute for current member and append to list @@ -237,13 +239,13 @@ public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) } /// - public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_member.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit)); } /// - public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs index 644d3f05c1..f62f4d444c 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs @@ -71,54 +71,84 @@ internal IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo return sym; } + /// + /// Gets the wrapped . + /// + internal new MethodBase ReflectionObject => _method; + + /// public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)_method.Attributes; + /// public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)_method.CallingConvention; + /// public bool ContainsGenericParameters => _method.ContainsGenericParameters; + /// public bool IsAbstract => _method.IsAbstract; + /// public bool IsAssembly => _method.IsAssembly; + /// public bool IsConstructor => _method.IsConstructor; + /// public bool IsFamily => _method.IsFamily; + /// public bool IsFamilyAndAssembly => _method.IsFamilyAndAssembly; + /// public bool IsFamilyOrAssembly => _method.IsFamilyOrAssembly; + /// public bool IsFinal => _method.IsFinal; + /// public bool IsGenericMethod => _method.IsGenericMethod; + /// public bool IsGenericMethodDefinition => _method.IsGenericMethodDefinition; + /// public bool IsHideBySig => _method.IsHideBySig; + /// public bool IsPrivate => _method.IsPrivate; + /// public bool IsPublic => _method.IsPublic; + /// public bool IsSpecialName => _method.IsSpecialName; + /// public bool IsStatic => _method.IsStatic; + /// public bool IsVirtual => _method.IsVirtual; + /// public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)_method.MethodImplementationFlags; + /// + public override bool ContainsMissing => GetGenericArguments().Any(i => i.IsMissing || i.ContainsMissing) || GetParameters().Any(i => i.IsMissing || i.ContainsMissing); + + /// public ITypeSymbol[] GetGenericArguments() { return ResolveTypeSymbols(_method.GetGenericArguments()); } + /// public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() { return (System.Reflection.MethodImplAttributes)_method.GetMethodImplementationFlags(); } + /// public IParameterSymbol[] GetParameters() { return ResolveParameterSymbols(_method.GetParameters()); diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs index 51fbc6a326..c18969aa21 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs @@ -109,7 +109,7 @@ internal IkvmReflectionMethodSymbol GetOrCreateGenericTypeSymbol(Type[] genericM public ITypeSymbol ReturnType => ResolveTypeSymbol(_method.ReturnType); - public ICustomAttributeSymbolProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); public IMethodSymbol GetBaseDefinition() { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index f1a88c6574..eacc58c3b0 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -177,6 +177,9 @@ IkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) /// public override bool IsMissing => _module.__IsMissing; + /// + public override bool ContainsMissing => GetTypes().Any(t => t.IsMissing || t.ContainsMissing); + /// public IFieldSymbol? GetField(string name) { @@ -333,19 +336,19 @@ public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArgu } /// - public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_module.GetCustomAttributesData()); } /// - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_module.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false)); } /// - public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs index 80a558f4b6..cc3e18be62 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs @@ -1,6 +1,5 @@ using System; using System.Linq; -using System.Runtime.InteropServices; using ParameterInfo = IKVM.Reflection.ParameterInfo; @@ -10,64 +9,77 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionParameterSymbol : IkvmReflectionSymbol, IParameterSymbol { + readonly IkvmReflectionMethodBaseSymbol _containingMethod; readonly ParameterInfo _parameter; - readonly IkvmReflectionMethodBaseSymbol _method; /// /// Initializes a new instance. /// /// - /// + /// /// - public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IkvmReflectionMethodBaseSymbol method, ParameterInfo parameter) : + public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IkvmReflectionMethodBaseSymbol containingMethod, ParameterInfo parameter) : base(context) { - _method = method ?? throw new ArgumentNullException(nameof(method)); + _containingMethod = containingMethod ?? throw new ArgumentNullException(nameof(containingMethod)); _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); } - internal IkvmReflectionMethodBaseSymbol ContainingMethod => _method; + internal IkvmReflectionMethodBaseSymbol ContainingMethod => _containingMethod; + /// public System.Reflection.ParameterAttributes Attributes => (System.Reflection.ParameterAttributes)_parameter.Attributes; + /// public object DefaultValue => _parameter.RawDefaultValue; + /// public bool HasDefaultValue => _parameter.HasDefaultValue; + /// public bool IsIn => _parameter.IsIn; + /// public bool IsLcid => _parameter.IsLcid; + /// public bool IsOptional => _parameter.IsOptional; + /// public bool IsOut => _parameter.IsOut; + /// public bool IsRetval => _parameter.IsRetval; + /// public IMemberSymbol Member => ResolveMemberSymbol(_parameter.Member); + /// public int MetadataToken => _parameter.MetadataToken; + /// public string? Name => _parameter.Name; + /// public ITypeSymbol ParameterType => ResolveTypeSymbol(_parameter.ParameterType); + /// public int Position => _parameter.Position; /// - public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_parameter.GetCustomAttributesData()); } /// - public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_parameter.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit)); } /// - public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } @@ -77,6 +89,19 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { return _parameter.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit); } + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(_parameter.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(_parameter.GetRequiredCustomModifiers()); + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index e1bf81bf8c..f0d642b569 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -40,6 +40,9 @@ public IkvmReflectionSymbol(IkvmReflectionSymbolContext context) /// public virtual bool IsMissing => false; + /// + public virtual bool ContainsMissing => false; + /// /// Resolves the symbol for the specified type. /// @@ -350,9 +353,9 @@ protected internal IkvmReflectionEventSymbol[] ResolveEventSymbols(EventInfo[] e /// /// /// - protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IList attributes) + protected internal CustomAttribute[] ResolveCustomAttributes(IList attributes) { - var a = new CustomAttributeSymbol[attributes.Count]; + var a = new CustomAttribute[attributes.Count]; for (int i = 0; i < attributes.Count; i++) a[i] = ResolveCustomAttribute(attributes[i]); @@ -365,9 +368,9 @@ protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IList /// /// - protected internal CustomAttributeSymbol ResolveCustomAttribute(CustomAttributeData customAttributeData) + protected internal CustomAttribute ResolveCustomAttribute(CustomAttributeData customAttributeData) { - return new CustomAttributeSymbol( + return new CustomAttribute( ResolveTypeSymbol(customAttributeData.AttributeType), ResolveConstructorSymbol(customAttributeData.Constructor), ResolveCustomAttributeTypedArguments(customAttributeData.ConstructorArguments), @@ -375,13 +378,13 @@ protected internal CustomAttributeSymbol ResolveCustomAttribute(CustomAttributeD } /// - /// Transforms a list of values into symbols. + /// Transforms a list of values into symbols. /// /// /// - ImmutableArray ResolveCustomAttributeTypedArguments(IList args) + ImmutableArray ResolveCustomAttributeTypedArguments(IList args) { - var a = new CustomAttributeSymbolTypedArgument[args.Count]; + var a = new CustomAttributeTypedArgument[args.Count]; for (int i = 0; i < args.Count; i++) a[i] = ResolveCustomAttributeTypedArgument(args[i]); @@ -389,23 +392,36 @@ ImmutableArray ResolveCustomAttributeTypedAr } /// - /// Transforms a values into a symbol. + /// Transforms a values into a symbol. /// /// /// - CustomAttributeSymbolTypedArgument ResolveCustomAttributeTypedArgument(CustomAttributeTypedArgument arg) + CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Reflection.CustomAttributeTypedArgument arg) { - return new CustomAttributeSymbolTypedArgument(ResolveTypeSymbol(arg.ArgumentType), arg.Value); + return new CustomAttributeTypedArgument(ResolveTypeSymbol(arg.ArgumentType), ResolveCustomAttributeTypedValue(arg.Value)); + } + + /// + /// Transforms the type as appropriate. + /// + /// + /// + object? ResolveCustomAttributeTypedValue(object? value) + { + if (value is IKVM.Reflection.Type v) + return ResolveTypeSymbol(v); + + return value; } /// - /// Transforms a list of values into symbols. + /// Transforms a list of values into symbols. /// /// /// - ImmutableArray ResolveCustomAttributeNamedArguments(IList args) + ImmutableArray ResolveCustomAttributeNamedArguments(IList args) { - var a = new CustomAttributeSymbolNamedArgument[args.Count]; + var a = new CustomAttributeNamedArgument[args.Count]; for (int i = 0; i < args.Count; i++) a[i] = ResolveCustomAttributeNamedArgument(args[i]); @@ -413,13 +429,13 @@ ImmutableArray ResolveCustomAttributeNamedAr } /// - /// Transforms a values into a symbol. + /// Transforms a values into a symbol. /// /// /// - CustomAttributeSymbolNamedArgument ResolveCustomAttributeNamedArgument(CustomAttributeNamedArgument arg) + CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(IKVM.Reflection.CustomAttributeNamedArgument arg) { - return new CustomAttributeSymbolNamedArgument(arg.IsField, ResolveMemberSymbol(arg.MemberInfo), arg.MemberName, ResolveCustomAttributeTypedArgument(arg.TypedValue)); + return new CustomAttributeNamedArgument(arg.IsField, ResolveMemberSymbol(arg.MemberInfo), arg.MemberName, ResolveCustomAttributeTypedArgument(arg.TypedValue)); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index 84c73c8988..aad2c19796 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -461,260 +461,363 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn /// internal new Type ReflectionObject => _type; + /// public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_type.Assembly); + /// public string? AssemblyQualifiedName => _type.AssemblyQualifiedName; + /// public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)(int)_type.Attributes; + /// public ITypeSymbol? BaseType => _type.BaseType != null ? ResolveTypeSymbol(_type.BaseType) : null; + /// public bool ContainsGenericParameters => _type.ContainsGenericParameters; + /// public IMethodBaseSymbol? DeclaringMethod => _type.DeclaringMethod is MethodInfo m ? ResolveMethodSymbol(m) : null; + /// public string? FullName => _type.FullName; + /// + public string? Namespace => _type.Namespace; + + /// public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)(int)_type.GenericParameterAttributes; + /// public int GenericParameterPosition => _type.GenericParameterPosition; + /// public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(_type.GenericTypeArguments); + /// public bool HasElementType => _type.HasElementType; + /// public bool IsAbstract => _type.IsAbstract; + /// + public bool IsSZArray => _type.IsSZArray; + + /// public bool IsArray => _type.IsArray; + /// public bool IsAutoLayout => _type.IsAutoLayout; + /// + public bool IsExplicitLayout => _type.IsExplicitLayout; + + /// public bool IsByRef => _type.IsByRef; + /// public bool IsClass => _type.IsClass; + /// public bool IsConstructedGenericType => _type.IsConstructedGenericType; + /// public bool IsEnum => _type.IsEnum; - public bool IsExplicitLayout => _type.IsExplicitLayout; - + /// public bool IsGenericParameter => _type.IsGenericParameter; + /// public bool IsGenericType => _type.IsGenericType; + /// public bool IsGenericTypeDefinition => _type.IsGenericTypeDefinition; + /// public bool IsInterface => _type.IsInterface; + /// public bool IsLayoutSequential => _type.IsLayoutSequential; + /// public bool IsNested => _type.IsNested; + /// public bool IsNestedAssembly => _type.IsNestedAssembly; + /// public bool IsNestedFamANDAssem => _type.IsNestedFamANDAssem; + /// public bool IsNestedFamORAssem => _type.IsNestedFamORAssem; + /// public bool IsNestedFamily => _type.IsNestedFamily; + /// public bool IsNestedPrivate => _type.IsNestedPrivate; + /// public bool IsNestedPublic => _type.IsNestedPublic; + /// public bool IsNotPublic => _type.IsNotPublic; + /// public bool IsPointer => _type.IsPointer; + /// + public bool IsFunctionPointer => _type.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _type.IsUnmanagedFunctionPointer; + + /// public bool IsPrimitive => _type.IsPrimitive; + /// public bool IsPublic => _type.IsPublic; + /// public bool IsSealed => _type.IsSealed; #pragma warning disable SYSLIB0050 // Type or member is obsolete + /// public bool IsSerializable => _type.IsSerializable; #pragma warning restore SYSLIB0050 // Type or member is obsolete + /// public bool IsValueType => _type.IsValueType; + /// public bool IsVisible => _type.IsVisible; - public string? Namespace => _type.Namespace; + /// + public bool IsSignatureType => throw new NotImplementedException(); + + /// + public bool IsSpecialName => _type.IsSpecialName; + + /// + public TypeCode TypeCode => Type.GetTypeCode(_type); + /// public IConstructorSymbol? TypeInitializer => _type.TypeInitializer is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; + /// + public override bool IsMissing => _type.__IsMissing; + + /// + public override bool ContainsMissing => _type.__ContainsMissingType; + + /// public int GetArrayRank() { return _type.GetArrayRank(); } + /// public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { return _type.GetConstructor((BindingFlags)bindingAttr, binder: null, UnpackTypeSymbols(types), modifiers: null) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; } + /// public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { return _type.GetConstructor(UnpackTypeSymbols(types)) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; } + /// public IConstructorSymbol[] GetConstructors() { return ResolveConstructorSymbols(_type.GetConstructors()); } + /// public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { return ResolveConstructorSymbols(_type.GetConstructors((BindingFlags)bindingAttr)); } + /// public IMemberSymbol[] GetDefaultMembers() { return ResolveMemberSymbols(_type.GetDefaultMembers()); } + /// public ITypeSymbol? GetElementType() { return _type.GetElementType() is Type t ? ResolveTypeSymbol(t) : null; } + /// public string? GetEnumName(object value) { return _type.GetEnumName(value); } + /// public string[] GetEnumNames() { return _type.GetEnumNames(); } + /// public ITypeSymbol GetEnumUnderlyingType() { return ResolveTypeSymbol(_type.GetEnumUnderlyingType()); } + /// public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { return _type.GetEvent(name, (BindingFlags)bindingAttr) is { } f ? ResolveEventSymbol(f) : null; } + /// public IEventSymbol? GetEvent(string name) { return _type.GetEvent(name) is { } f ? ResolveEventSymbol(f) : null; } + /// public IEventSymbol[] GetEvents() { return ResolveEventSymbols(_type.GetEvents()); } + /// public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { return ResolveEventSymbols(_type.GetEvents((BindingFlags)bindingAttr)); } + /// public IFieldSymbol? GetField(string name) { return _type.GetField(name) is FieldInfo f ? ResolveFieldSymbol(f) : null; } + /// public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { return _type.GetField(name, (BindingFlags)bindingAttr) is FieldInfo f ? ResolveFieldSymbol(f) : null; } + /// public IFieldSymbol[] GetFields() { return ResolveFieldSymbols(_type.GetFields()); } + /// public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { return ResolveFieldSymbols(_type.GetFields((BindingFlags)bindingAttr)); } + /// public ITypeSymbol[] GetGenericArguments() { return ResolveTypeSymbols(_type.GetGenericArguments()); } + /// public ITypeSymbol[] GetGenericParameterConstraints() { return ResolveTypeSymbols(_type.GetGenericParameterConstraints()); } + /// public ITypeSymbol GetGenericTypeDefinition() { return ResolveTypeSymbol(_type.GetGenericTypeDefinition()); } + /// public ITypeSymbol? GetInterface(string name) { return _type.GetInterface(name) is { } i ? ResolveTypeSymbol(i) : null; } + /// public ITypeSymbol? GetInterface(string name, bool ignoreCase) { return _type.GetInterface(name, ignoreCase) is { } i ? ResolveTypeSymbol(i) : null; } + /// public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { throw new NotImplementedException(); } - public ITypeSymbol[] GetInterfaces() + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return ResolveTypeSymbols(_type.GetInterfaces()); + if (inherit) + return ResolveTypeSymbols(_type.GetInterfaces()); + else + return ResolveTypeSymbols(_type.__GetDeclaredInterfaces()); } + /// public IMemberSymbol[] GetMember(string name) { return ResolveMemberSymbols(_type.GetMember(name)); } + /// public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(_type.GetMember(name, (BindingFlags)bindingAttr)); } + /// public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(_type.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } + /// public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(_type.GetMembers((BindingFlags)bindingAttr)); } + /// public IMemberSymbol[] GetMembers() { return ResolveMemberSymbols(_type.GetMembers()); } + /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { return _type.GetMethod(name, (BindingFlags)bindingAttr) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { return _type.GetMethod(name, (BindingFlags)bindingAttr, null, UnpackTypeSymbols(types), null) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { return _type.GetMethod(name, UnpackTypeSymbols(types)) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetMethod(string name) { return _type.GetMethod(name) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { if (modifiers != null) @@ -723,46 +826,55 @@ public IMemberSymbol[] GetMembers() return _type.GetMethod(name, UnpackTypeSymbols(types), null) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { return ResolveMethodSymbols(_type.GetMethods((BindingFlags)bindingAttr)); } + /// public IMethodSymbol[] GetMethods() { return ResolveMethodSymbols(_type.GetMethods()); } + /// public ITypeSymbol? GetNestedType(string name) { return _type.GetNestedType(name) is Type t ? ResolveTypeSymbol(t) : null; } + /// public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { return _type.GetNestedType(name, (BindingFlags)bindingAttr) is Type t ? ResolveTypeSymbol(t) : null; } + /// public ITypeSymbol[] GetNestedTypes() { return ResolveTypeSymbols(_type.GetNestedTypes()); } + /// public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { return ResolveTypeSymbols(_type.GetNestedTypes((BindingFlags)bindingAttr)); } + /// public IPropertySymbol[] GetProperties() { return ResolvePropertySymbols(_type.GetProperties()); } + /// public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { return ResolvePropertySymbols(_type.GetProperties((BindingFlags)bindingAttr)); } + /// public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { if (modifiers != null) @@ -772,27 +884,32 @@ public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAtt return _type.GetProperty(name, _returnType, UnpackTypeSymbols(types), null) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { return _type.GetProperty(name, UnpackTypeSymbols(types)) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { var _returnType = returnType != null ? ((IkvmReflectionTypeSymbol)returnType).ReflectionObject : null; return _type.GetProperty(name, _returnType, UnpackTypeSymbols(types)) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { return _type.GetProperty(name, (BindingFlags)bindingAttr) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name) { return _type.GetProperty(name) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { var _returnType = returnType != null ? ((IkvmReflectionTypeSymbol)returnType).ReflectionObject : null; @@ -800,21 +917,25 @@ public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAtt return _type.GetProperty(name, _returnType) is { } p ? ResolvePropertySymbol(p) : null; } + /// public bool IsAssignableFrom(ITypeSymbol? c) { return _type.IsAssignableFrom(c != null ? ((IkvmReflectionTypeSymbol)c).ReflectionObject : null); } + /// public bool IsEnumDefined(object value) { return _type.IsEnumDefined(value); } + /// public bool IsSubclassOf(ITypeSymbol c) { return _type.IsSubclassOf(((IkvmReflectionTypeSymbol)c).ReflectionObject); } + /// public ITypeSymbol MakeArrayType() { if (_asSZArray == null) @@ -823,6 +944,7 @@ public ITypeSymbol MakeArrayType() return _asSZArray; } + /// public ITypeSymbol MakeArrayType(int rank) { if (rank == 1) @@ -838,6 +960,7 @@ public ITypeSymbol MakeArrayType(int rank) return asArray; } + /// public ITypeSymbol MakeByRefType() { if (_asByRef == null) @@ -846,11 +969,13 @@ public ITypeSymbol MakeByRefType() return _asByRef; } + /// public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { throw new NotImplementedException(); } + /// public ITypeSymbol MakePointerType() { if (_asPointer == null) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs new file mode 100644 index 0000000000..ee8c1f6873 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -0,0 +1,49 @@ +using System; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionAssemblySymbolBuilder : ReflectionSymbolBuilder, IAssemblySymbolBuilder + { + + readonly AssemblyBuilder _builder; + ReflectionAssemblySymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReflectionAssemblySymbolBuilder(ReflectionSymbolContext context, AssemblyBuilder builder) : + base(context) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + internal sealed override ReflectionAssemblySymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateAssemblySymbol(_builder); + + /// + public IModuleSymbolBuilder DefineModule(string name) + { + return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name)); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs new file mode 100644 index 0000000000..e351e1813c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -0,0 +1,74 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder + { + + readonly ConstructorBuilder _builder; + ReflectionConstructorSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, ConstructorBuilder builder) : + base(context, containingTypeBuilder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the containing . + /// + protected internal new ReflectionTypeSymbolBuilder ContainingTypeBuilder => base.ContainingTypeBuilder ?? throw new NullReferenceException(); + + /// + internal override ReflectionConstructorSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateConstructorSymbol(_builder); + + /// + public void SetImplementationFlags(MethodImplAttributes attributes) + { + _builder.SetImplementationFlags(attributes); + } + + /// + public IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) + { + return new ReflectionParameterSymbolBuilder(Context, this, _builder.DefineParameter(iSequence, attributes, strParamName)); + } + + /// + public ILGenerator GetILGenerator() + { + throw new NotImplementedException(); + } + + /// + public ILGenerator GetILGenerator(int streamSize) + { + throw new NotImplementedException(); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs new file mode 100644 index 0000000000..bb1978ec30 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs @@ -0,0 +1,29 @@ +using System; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionCustomAttributeBuilder : ICustomAttributeBuilder + { + + readonly CustomAttributeBuilder _builder; + + /// + /// Initializes a new instance. + /// + public ReflectionCustomAttributeBuilder(CustomAttributeBuilder builder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the underlying reflection . + /// + internal CustomAttributeBuilder ReflectionBuilder => _builder; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs new file mode 100644 index 0000000000..771ff97570 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs @@ -0,0 +1,81 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + /// + /// Fake implementation that wraps a , which does not extend . + /// + class ReflectionEventBuilderInfo : EventInfo + { + + readonly EventBuilder _builder; + + /// + /// Initialies a new instance. + /// + /// + /// + public ReflectionEventBuilderInfo(EventBuilder builder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + public override Module Module => _builder.GetModuleBuilder(); + + /// + public override Type? DeclaringType => _builder.GetTypeBuilder(); + + /// + public override EventAttributes Attributes => _builder.GetEventAttributes(); + + /// + public override string Name => _builder.GetEventName(); + + /// + public override Type? ReflectedType => DeclaringType; + + /// + public override int MetadataToken => _builder.GetMetadataToken(); + + /// + public override MethodInfo? GetAddMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override MethodInfo? GetRemoveMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override MethodInfo? GetRaiseMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override object[] GetCustomAttributes(bool inherit) + { + throw new NotImplementedException(); + } + + /// + public override object[] GetCustomAttributes(Type attributeType, bool inherit) + { + throw new NotImplementedException(); + } + + /// + public override bool IsDefined(Type attributeType, bool inherit) + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs new file mode 100644 index 0000000000..fbc7ea865b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs @@ -0,0 +1,72 @@ +using System; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionEventSymbolBuilder : ReflectionSymbolBuilder, IEventSymbolBuilder + { + + readonly ReflectionTypeSymbolBuilder _containingTypeBuilder; + readonly EventBuilder _builder; + readonly ReflectionEventBuilderInfo _info; + ReflectionEventSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionEventSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, EventBuilder builder) : + base(context) + { + _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _info = new ReflectionEventBuilderInfo(_builder); + } + + /// + internal override ReflectionEventSymbol ReflectionSymbol => _symbol ??= _containingTypeBuilder.ReflectionSymbol.ResolveEventSymbol(_info); + + /// + public void SetAddOnMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.SetAddOnMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void SetRemoveOnMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.SetRemoveOnMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void SetRaiseMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.SetRaiseMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.AddOtherMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs new file mode 100644 index 0000000000..241fbf8ed8 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs @@ -0,0 +1,88 @@ +using System; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionFieldSymbolBuilder : ReflectionSymbolBuilder, IFieldSymbolBuilder + { + + readonly ReflectionModuleSymbolBuilder _containingModuleBuilder; + readonly ReflectionTypeSymbolBuilder? _containingTypeBuilder; + readonly FieldBuilder _builder; + ReflectionFieldSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder, FieldBuilder builder) : + base(context) + { + _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, FieldBuilder builder) : + base(context) + { + _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); + _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the containing . + /// + internal ReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; + + /// + /// Gets the containing . + /// + internal ReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; + + /// + /// Gets the underlying + /// + internal FieldBuilder ReflectionBuilder => _builder; + + /// + internal override ReflectionFieldSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateFieldSymbol(_builder); + + /// + public void SetConstant(object? defaultValue) + { + _builder.SetConstant(defaultValue); + } + + /// + public void SetOffset(int iOffset) + { + _builder.SetOffset(iOffset); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs new file mode 100644 index 0000000000..f260f68197 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs @@ -0,0 +1,49 @@ +using System; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + abstract class ReflectionMethodBaseSymbolBuilder : ReflectionSymbolBuilder + where TSymbol : ISymbol + where TReflectionSymbol : ReflectionSymbol, TSymbol + { + + readonly ReflectionModuleSymbolBuilder _containingModuleBuilder; + readonly ReflectionTypeSymbolBuilder? _containingTypeBuilder; + + /// + /// Initializes a new instance. + /// + /// + /// + protected ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder) : + base(context) + { + _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); + _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; + } + + /// + /// Initializes a new instance. + /// + /// + /// + protected ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder) : + base(context) + { + _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); + } + + /// + /// Gets the containing . + /// + protected internal ReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; + + /// + /// Gets the containing . + /// + protected internal ReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs new file mode 100644 index 0000000000..ce4b912945 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -0,0 +1,107 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder + { + + readonly MethodBuilder _builder; + ReflectionMethodSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder, MethodBuilder builder) : + base(context, containingModuleBuilder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, MethodBuilder builder) : + base(context, containingTypeBuilder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the that underlies this instance. + /// + internal MethodBuilder ReflectionBuilder => _builder; + + /// + internal override ReflectionMethodSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateMethodSymbol(_builder); + + /// + public void SetImplementationFlags(MethodImplAttributes attributes) + { + _builder.SetImplementationFlags(attributes); + } + + /// + public void SetParameters(params ITypeSymbol[] parameterTypes) + { + _builder.SetParameters(parameterTypes.Unpack()); + } + + /// + public void SetReturnType(ITypeSymbol? returnType) + { + _builder.SetReturnType(returnType?.Unpack()); + } + + /// + public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + _builder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); + } + + public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) + { + throw new NotImplementedException(); + } + + /// + public IParameterSymbolBuilder DefineParameter(int position, ParameterAttributes attributes, string? strParamName) + { + return new ReflectionParameterSymbolBuilder(Context, this, _builder.DefineParameter(position, attributes, strParamName)); + } + + public IILGenerator GetILGenerator() + { + throw new NotImplementedException(); + } + + public IILGenerator GetILGenerator(int size) + { + throw new NotImplementedException(); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs new file mode 100644 index 0000000000..83f3a6ea19 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -0,0 +1,86 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionModuleSymbolBuilder : ReflectionSymbolBuilder, IModuleSymbolBuilder + { + + readonly ModuleBuilder _builder; + ReflectionModuleSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, ModuleBuilder builder) : + base(context) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + internal override ReflectionModuleSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateModuleSymbol(_builder); + + /// + public ITypeSymbolBuilder DefineType(string name) + { + return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, int typesize) + { + return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), typesize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent) + { + return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr) + { + return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packsize) + { + return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), packsize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packingSize, int typesize) + { + return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), packingSize, typesize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) + { + return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), interfaces?.Unpack())); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs new file mode 100644 index 0000000000..fa908dac80 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs @@ -0,0 +1,102 @@ +using System; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + abstract class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder, IParameterSymbolBuilder + { + + readonly ParameterBuilder _builder; + readonly ReflectionParameterBuilderInfo _info; + ReflectionParameterSymbol? _symbol; + + object? _constant; + + /// + /// Initializes a new instance. + /// + /// + protected ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, ParameterBuilder builder) : + base(context) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _info = new ReflectionParameterBuilderInfo(_builder); + } + + /// + /// Gets the wrapped . + /// + internal ParameterBuilder ReflectionBuilder => _builder; + + /// + internal override ReflectionParameterSymbol ReflectionSymbol => _symbol ??= GetOrCreateSymbol(_info); + + /// + /// Gets or creates the . + /// + /// + protected internal abstract ReflectionParameterSymbol GetOrCreateSymbol(ReflectionParameterBuilderInfo info); + + /// + public void SetConstant(object? defaultValue) + { + _builder.SetConstant(_constant = defaultValue); + } + + /// + /// Saves the constant value so it can be retrieved as a symbol. + /// + /// + internal object? GetConstant() + { + return _constant; + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + + class ReflectionParameterSymbolBuilder : ReflectionParameterSymbolBuilder + where TContainingSymbol : IMethodBaseSymbol + where TContainingReflectionSymbol : ReflectionMethodBaseSymbol, TContainingSymbol + where TContainingBuilder : ReflectionMethodBaseSymbolBuilder + { + + readonly TContainingBuilder _containingMethodBuilder; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, TContainingBuilder containingMethodBuilder, ParameterBuilder builder) : + base(context, builder) + { + _containingMethodBuilder = containingMethodBuilder ?? throw new ArgumentNullException(nameof(containingMethodBuilder)); + } + + /// + /// Gets the containing . + /// + internal TContainingBuilder ContainingMethodBuilder => _containingMethodBuilder; + + /// + protected internal override ReflectionParameterSymbol GetOrCreateSymbol(ReflectionParameterBuilderInfo info) => ContainingMethodBuilder.ReflectionSymbol.ResolveParameterSymbol(info); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs new file mode 100644 index 0000000000..1d9a57c4b0 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs @@ -0,0 +1,47 @@ +using System; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionPropertySymbolBuilder : ReflectionSymbolBuilder, IPropertySymbolBuilder + { + + readonly ReflectionTypeSymbolBuilder _containingTypeBuilder; + readonly PropertyBuilder _builder; + ReflectionPropertySymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, PropertyBuilder builder) : + base(context) + { + _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + internal PropertyBuilder ReflectionBuilder => _builder; + + internal override ReflectionPropertySymbol ReflectionSymbol => _symbol ??= _containingTypeBuilder.ReflectionSymbol.ResolvePropertySymbol(_builder); + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs new file mode 100644 index 0000000000..3ff29a8b2c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs @@ -0,0 +1,94 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + /// + /// Reflection-specific implementation of . + /// + abstract class ReflectionSymbolBuilder : ISymbolBuilder + { + + readonly ReflectionSymbolContext _context; + + /// + /// Initializes a new instance. + /// + /// + protected ReflectionSymbolBuilder(ReflectionSymbolContext context) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + } + + /// + /// Gets the associated . + /// + public ReflectionSymbolContext Context => _context; + + /// + public ISymbol Symbol => GetSymbol(); + + /// + /// Implement to get the symbol. + /// + /// + protected abstract ISymbol GetSymbol(); + + } + + /// + /// Reflection-specific implementation of . + /// + abstract class ReflectionSymbolBuilder : ReflectionSymbolBuilder, ISymbolBuilder + where TSymbol : ISymbol + { + + /// + /// Initializes a new instance. + /// + /// + protected ReflectionSymbolBuilder(ReflectionSymbolContext context) : + base(context) + { + + } + + /// + public abstract new TSymbol Symbol { get; } + + /// + protected sealed override ISymbol GetSymbol() => Symbol; + + } + + /// + /// Base implementation for reflection symbol builders. + /// + abstract class ReflectionSymbolBuilder : ReflectionSymbolBuilder + where TSymbol : ISymbol + where TReflectionSymbol : ReflectionSymbol, TSymbol + { + + /// + /// Initializes a new instance. + /// + /// + protected ReflectionSymbolBuilder(ReflectionSymbolContext context) : + base(context) + { + + } + + /// + public sealed override TSymbol Symbol => ReflectionSymbol; + + /// + /// Gets the that is currently being built. Portions of this interface will be non-functional until the build is completed. + /// + internal abstract TReflectionSymbol ReflectionSymbol { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs new file mode 100644 index 0000000000..197211f65a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -0,0 +1,238 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; +using System.Runtime.InteropServices; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionTypeSymbolBuilder : ReflectionSymbolBuilder, ITypeSymbolBuilder + { + + readonly ReflectionModuleSymbolBuilder _containingModuleBuilder; + readonly TypeBuilder _builder; + ReflectionTypeSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder, TypeBuilder builder) : + base(context) + { + _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the containing . + /// + internal ReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; + + /// + /// Gets the underlying . + /// + internal TypeBuilder ReflectionBuilder => _builder; + + /// + internal override ReflectionTypeSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateTypeSymbol(_builder); + + /// + public void SetParent(ITypeSymbol? parent) + { + _builder.SetParent(parent?.Unpack()); + } + + /// + public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) + { + throw new NotImplementedException(); + } + + /// + public void AddInterfaceImplementation(ITypeSymbol interfaceType) + { + _builder.AddInterfaceImplementation(interfaceType.Unpack()); + } + + /// + public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes) + { + return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack())); + } + + /// + public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredCustomModifiers, ITypeSymbol[][]? optionalCustomModifiers) + { + return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack())); + } + + /// + public IConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes) + { + return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineDefaultConstructor(attributes)); + } + + /// + public IEventSymbolBuilder DefineEvent(string name, EventAttributes attributes, ITypeSymbol eventtype) + { + return new ReflectionEventSymbolBuilder(Context, this, _builder.DefineEvent(name, attributes, eventtype.Unpack())); + } + + /// + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, FieldAttributes attributes) + { + return new ReflectionFieldSymbolBuilder(Context, this, _builder.DefineField(fieldName, type.Unpack(), attributes)); + } + + /// + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, FieldAttributes attributes) + { + return new ReflectionFieldSymbolBuilder(Context, this, _builder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), attributes)); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + { + return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention) + { + return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, callingConvention)); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes) + { + return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes)); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + { + return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) + { + return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), interfaces?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize) + { + return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), packSize, typeSize)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize) + { + return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), packSize)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name) + { + return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent) + { + return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr) + { + return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize) + { + return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), typeSize)); + } + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + return new ReflectionMethodSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefinePInvokeMethod(name, dllName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + } + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + return new ReflectionMethodSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + } + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + return new ReflectionMethodSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack(), nativeCallConv, nativeCharSet)); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) + { + return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, returnType.Unpack(), parameterTypes?.Unpack())); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) + { + return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), parameterTypes?.Unpack())); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + } + + /// + public IConstructorSymbolBuilder DefineTypeInitializer() + { + return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineTypeInitializer()); + } + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + /// + public void Finish() + { + var sym = ReflectionSymbol; + sym.FinishType(_builder.CreateType()); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index bd5721750e..8f51202536 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -5,6 +5,8 @@ using System.Reflection; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Symbols.Reflection.Emit; + namespace IKVM.CoreLib.Symbols.Reflection { @@ -35,10 +37,26 @@ public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly assemb /// internal ReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) { + if (module is null) + throw new ArgumentNullException(nameof(module)); + Debug.Assert(module.Assembly == _assembly); return _modules.GetValue(module, _ => new ReflectionModuleSymbol(Context, _)); } + /// + /// Gets or creates the cached for the module. + /// + /// + /// + internal ReflectionModuleSymbol GetOrCreateModuleSymbol(ReflectionModuleSymbolBuilder module) + { + if (module is null) + throw new ArgumentNullException(nameof(module)); + + throw new NotImplementedException(); + } + /// public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); @@ -127,19 +145,19 @@ public ITypeSymbol[] GetTypes() } /// - public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); } /// - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_assembly.GetCustomAttributesData().Where(i => i.AttributeType == ((ReflectionTypeSymbol)attributeType).ReflectionObject)); } /// - public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs index 7c4a37a7b2..080785635e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs @@ -16,7 +16,7 @@ class ReflectionEventSymbol : ReflectionMemberSymbol, IEventSymbol /// /// public ReflectionEventSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, EventInfo @event) : - base(context, type.ContainingModule, type, @event) + base(context, type, @event) { _event = @event ?? throw new ArgumentNullException(nameof(@event)); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index 8ba9a0eb66..61bfb54769 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -13,10 +13,22 @@ class ReflectionFieldSymbol : ReflectionMemberSymbol, IFieldSymbol /// Initializes a new instance. /// /// - /// + /// /// - public ReflectionFieldSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, FieldInfo field) : - base(context, type.ContainingModule, type, field) + public ReflectionFieldSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol containingModule, FieldInfo field) : + base(context, containingModule, field) + { + _field = field ?? throw new ArgumentNullException(nameof(field)); + } + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionFieldSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol containingType, FieldInfo field) : + base(context, containingType, field) { _field = field ?? throw new ArgumentNullException(nameof(field)); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 850276ccf6..f4bbd6c78a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -44,24 +44,34 @@ static T[] Concat(List? list) readonly ReflectionTypeSymbol? _containingType; readonly MemberInfo _member; - CustomAttributeSymbol[]? _customAttributes; - CustomAttributeSymbol[]? _inheritedCustomAttributes; + CustomAttribute[]? _customAttributes; + CustomAttribute[]? _inheritedCustomAttributes; /// /// Initializes a new instance. /// /// /// - /// /// - public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol containingModule, ReflectionTypeSymbol? containingType, MemberInfo member) : + public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol containingModule, MemberInfo member) : base(context) { _containingModule = containingModule ?? throw new ArgumentNullException(nameof(containingModule)); - _containingType = containingType; _member = member ?? throw new ArgumentNullException(nameof(member)); } + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol containingType, MemberInfo member) : + this(context, containingType.ContainingModule, member) + { + _containingType = containingType ?? throw new ArgumentNullException(nameof(containingType)); + } + /// /// Resolves the symbol for the specified type. /// @@ -84,10 +94,8 @@ protected internal override ReflectionTypeSymbol ResolveTypeSymbol(Type type) /// protected internal override ReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) { - if (_containingType != null && ctor.DeclaringType == _containingType.ReflectionObject) - return _containingType.GetOrCreateConstructorSymbol(ctor); - else if (ctor.DeclaringType != null && ctor.Module == _member.Module) - return _containingModule.GetOrCreateTypeSymbol(ctor.DeclaringType).GetOrCreateConstructorSymbol(ctor); + if (ctor.Module == _member.Module) + return _containingModule.GetOrCreateConstructorSymbol(ctor); else return base.ResolveConstructorSymbol(ctor); } @@ -99,10 +107,8 @@ protected internal override ReflectionConstructorSymbol ResolveConstructorSymbol /// protected internal override ReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) { - if (_containingType != null && method.DeclaringType == _containingType.ReflectionObject) - return _containingType.GetOrCreateMethodSymbol(method); - else if (method.DeclaringType != null && method.Module == _member.Module) - return _containingModule.GetOrCreateTypeSymbol(method.DeclaringType).GetOrCreateMethodSymbol(method); + if (method.Module == _member.Module) + return _containingModule.GetOrCreateMethodSymbol(method); else return base.ResolveMethodSymbol(method); } @@ -114,10 +120,8 @@ protected internal override ReflectionMethodSymbol ResolveMethodSymbol(MethodInf /// protected internal override ReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) { - if (_containingType != null && field.DeclaringType == _containingType.ReflectionObject) - return _containingType.GetOrCreateFieldSymbol(field); - else if (field.DeclaringType != null && field.Module == _member.Module) - return _containingModule.GetOrCreateTypeSymbol(field.DeclaringType).GetOrCreateFieldSymbol(field); + if (field.Module == _member.Module) + return _containingModule.GetOrCreateFieldSymbol(field); else return base.ResolveFieldSymbol(field); } @@ -130,11 +134,8 @@ protected internal override ReflectionFieldSymbol ResolveFieldSymbol(FieldInfo f /// protected internal override ReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) { - - if (_containingType != null && property.DeclaringType == _containingType.ReflectionObject) - return _containingType.GetOrCreatePropertySymbol(property); - else if (property.DeclaringType != null && property.Module == _member.Module) - return _containingModule.GetOrCreateTypeSymbol(property.DeclaringType).GetOrCreatePropertySymbol(property); + if (property.Module == _member.Module) + return _containingModule.GetOrCreatePropertySymbol(property); else return base.ResolvePropertySymbol(property); } @@ -146,10 +147,8 @@ protected internal override ReflectionPropertySymbol ResolvePropertySymbol(Prope /// protected internal override ReflectionEventSymbol ResolveEventSymbol(EventInfo @event) { - if (_containingType != null && @event.DeclaringType == _containingType.ReflectionObject) - return _containingType.GetOrCreateEventSymbol(@event); - else if (@event.DeclaringType != null && @event.Module == _member.Module) - return _containingModule.GetOrCreateTypeSymbol(@event.DeclaringType).GetOrCreateEventSymbol(@event); + if (@event.Module == _member.Module) + return _containingModule.GetOrCreateEventSymbol(@event); else return base.ResolveEventSymbol(@event); } @@ -185,7 +184,7 @@ protected internal override ReflectionEventSymbol ResolveEventSymbol(EventInfo @ public virtual string Name => _member.Name; /// - public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) { if (inherit) { @@ -194,7 +193,7 @@ public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) return _inheritedCustomAttributes; var self = _member; - var list = default(List?); + var list = default(List?); for (; ; ) { // get attribute for current member and append to list @@ -236,13 +235,13 @@ public virtual CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) } /// - public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); } /// - public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs index 5f1aaa9aa4..8bd357f1dc 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs @@ -1,8 +1,5 @@ using System; -using System.Diagnostics; -using System.Linq; using System.Reflection; -using System.Threading; namespace IKVM.CoreLib.Symbols.Reflection { @@ -12,61 +9,29 @@ abstract class ReflectionMethodBaseSymbol : ReflectionMemberSymbol, IMethodBaseS readonly MethodBase _method; - ParameterInfo[]? _parametersSource; - ReflectionParameterSymbol?[]? _parameters; - ReflectionParameterSymbol? _returnParameter; - /// /// Initializes a new instance. /// /// /// - /// /// - public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, ReflectionTypeSymbol? type, MethodBase method) : - base(context, module, type, method) + public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, MethodBase method) : + base(context, module, method) { _method = method ?? throw new ArgumentNullException(nameof(method)); } /// - /// Gets or creates the cached for the type by method. + /// Initializes a new instance. /// - /// - /// - internal ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + /// + /// + /// + /// + public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, MethodBase method) : + this(context, type.ContainingModule, method) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - Debug.Assert(parameter.Member == _method); - - if (_parametersSource == null) - Interlocked.CompareExchange(ref _parametersSource, _method.GetParameters().OrderBy(i => i.Position).ToArray(), null); - if (_parameters == null) - Interlocked.CompareExchange(ref _parameters, new ReflectionParameterSymbol?[_parametersSource.Length], null); - - // index of current record - var idx = parameter.Position; - Debug.Assert(idx >= -1); - Debug.Assert(idx < _parametersSource.Length); - - // check that our list is long enough to contain the entire table - if (idx >= 0 && _parameters.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _returnParameter; - if (idx >= 0) - rec = ref _parameters[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new ReflectionParameterSymbol(Context, this, parameter), null); - - // this should never happen - if (rec is not ReflectionParameterSymbol sym) - throw new InvalidOperationException(); - return sym; } /// @@ -151,4 +116,4 @@ public IParameterSymbol[] GetParameters() } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index fdbb45b38b..56030a0d76 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -24,12 +24,24 @@ class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IMethodSymbol /// /// /// - public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, ReflectionTypeSymbol? type, MethodInfo method) : - base(context, module, type, method) + public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, MethodInfo method) : + base(context, module, method) { _method = method ?? throw new ArgumentNullException(nameof(method)); } + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, MethodInfo method) : + this(context, type.ContainingModule, method) + { + + } + /// /// Gets or creates the cached for the generic parameter type. /// @@ -98,7 +110,12 @@ internal ReflectionMethodSymbol GetOrCreateGenericTypeSymbol(Type[] genericMetho return i.Symbol; // generate new symbol - var sym = new ReflectionMethodSymbol(Context, ContainingModule, ContainingType, _method.MakeGenericMethod(genericMethodArguments)); + ReflectionMethodSymbol sym; + if (ContainingType != null) + sym = new ReflectionMethodSymbol(Context, ContainingType, _method.MakeGenericMethod(genericMethodArguments)); + else + sym = new ReflectionMethodSymbol(Context, ContainingModule, _method.MakeGenericMethod(genericMethodArguments)); + _genericTypes.Add((genericMethodArguments, sym)); return sym; } @@ -116,7 +133,7 @@ internal ReflectionMethodSymbol GetOrCreateGenericTypeSymbol(Type[] genericMetho public ITypeSymbol ReturnType => ResolveTypeSymbol(_method.ReturnType); /// - public ICustomAttributeSymbolProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); /// public IMethodSymbol GetBaseDefinition() @@ -133,7 +150,7 @@ public IMethodSymbol GetGenericMethodDefinition() /// public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) { - return ResolveMethodSymbol(_method.MakeGenericMethod(UnpackTypeSymbols(typeArguments))); + return ResolveMethodSymbol(_method.MakeGenericMethod(typeArguments.Unpack())); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 0e8bc370fc..2f7a1cff79 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -2,10 +2,11 @@ using System.Diagnostics; using System.Linq; using System.Reflection; -using System.Reflection.Metadata.Ecma335; -using System.Runtime.InteropServices; using System.Threading; +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Threading; + namespace IKVM.CoreLib.Symbols.Reflection { @@ -23,17 +24,41 @@ class ReflectionModuleSymbol : ReflectionSymbol, IModuleSymbol static bool IsTypeDefinition(Type type) { #if NET - return type.IsTypeDefinition; + return type.IsTypeDefinition; #else return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; #endif } + const int MAX_CAPACITY = 65536 * 2; + + const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; + readonly Module _module; - Type[]? _typesSource; - int _typesBaseRow; - ReflectionTypeSymbol?[]? _types; + IndexRangeDictionary _typeTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _typeLock; + + IndexRangeDictionary _methodTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _methodLock; + + IndexRangeDictionary _fieldTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _fieldLock; + + IndexRangeDictionary _propertyTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _propertyLock; + + IndexRangeDictionary _eventTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _eventLock; + + IndexRangeDictionary _parameterTable = new(); + IndexRangeDictionary _parameterSymbols = new(); + ReaderWriterLockSlim? _parameterLock; /// /// Initializes a new instance. @@ -50,7 +75,7 @@ public ReflectionModuleSymbol(ReflectionSymbolContext context, Module module) : /// /// Gets the wrapped . /// - internal Module ReflectionModule => _module; + internal Module ReflectionObject => _module; /// /// Gets or creates the cached for the module by type. @@ -69,46 +94,33 @@ internal ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) if (IsTypeDefinition(type) == false) return GetOrCreateTypeSymbolForSpecification(type); - // look up handle and row - var hnd = MetadataTokens.TypeDefinitionHandle(type.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); + // create lock on demand + if (_typeLock == null) + lock (this) + _typeLock ??= new ReaderWriterLockSlim(); - // initialize source table - if (_typesSource == null) + using (_typeLock.CreateUpgradeableReadLock()) { - Interlocked.CompareExchange(ref _typesSource, _module.GetTypes().OrderBy(i => i.MetadataToken).ToArray(), null); - _typesBaseRow = _typesSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_typesSource[0].MetadataToken)) : 0; + var row = type.GetMetadataTokenRowNumberSafe(); + if (_typeTable[row] != type) + using (_typeLock.CreateWriteLock()) + _typeTable[row] = type; + + if (_typeSymbols[row] == null) + using (_typeLock.CreateWriteLock()) + return _typeSymbols[row] ??= new ReflectionTypeSymbol(Context, this, type); + else + return _typeSymbols[row] ?? throw new InvalidOperationException(); } - - // initialize cache table - if (_types == null) - Interlocked.CompareExchange(ref _types, new ReflectionTypeSymbol?[_typesSource.Length], null); - - // index of current record is specified row - base - var idx = row - _typesBaseRow - 1; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _typesSource.Length); - - // check that our type list is long enough to contain the entire table - if (_types.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - if (_types[idx] == null) - Interlocked.CompareExchange(ref _types[idx], new ReflectionTypeSymbol(Context, this, type), null); - - // this should never happen - if (_types[idx] is not ReflectionTypeSymbol sym) - throw new InvalidOperationException(); - - return sym; } /// - /// For a given + /// Gets or creates a for the specification type: array, pointer, etc. /// /// - /// + /// + /// + /// ReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) { if (type is null) @@ -118,7 +130,7 @@ ReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) if (type.GetElementType() is { } elementType) { - var elementTypeSymbol = GetOrCreateTypeSymbol(elementType); + var elementTypeSymbol = ResolveTypeSymbol(elementType); // handles both SZ arrays and normal arrays if (type.IsArray) @@ -135,28 +147,221 @@ ReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) if (type.IsGenericType) { - var definitionType = type.GetGenericTypeDefinition(); - var definitionTypeSymbol = GetOrCreateTypeSymbol(definitionType); + var definitionTypeSymbol = ResolveTypeSymbol(type.GetGenericTypeDefinition()); return definitionTypeSymbol.GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); } // generic type parameter if (type.IsGenericParameter && type.DeclaringMethod is null && type.DeclaringType is not null) { - var declaringType = GetOrCreateTypeSymbol(type.DeclaringType); + var declaringType = ResolveTypeSymbol(type.DeclaringType); return declaringType.GetOrCreateGenericParameterSymbol(type); } // generic method parameter if (type.IsGenericParameter && type.DeclaringMethod is not null && type.DeclaringMethod.DeclaringType is not null) { - var declaringMethod = GetOrCreateTypeSymbol(type.DeclaringMethod.DeclaringType); + var declaringMethod = ResolveTypeSymbol(type.DeclaringMethod.DeclaringType); return declaringMethod.GetOrCreateGenericParameterSymbol(type); } throw new InvalidOperationException(); } + /// + /// Gets or creates the cached fqor the type by method. + /// + /// + /// + internal ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + Debug.Assert(method.Module == _module); + + // create lock on demand + if (_methodLock == null) + lock (this) + _methodLock ??= new ReaderWriterLockSlim(); + + using (_methodLock.CreateUpgradeableReadLock()) + { + var row = method.GetMetadataTokenRowNumberSafe(); + if (_methodTable[row] != method) + using (_methodLock.CreateWriteLock()) + _methodTable[row] = method; + + if (_methodSymbols[row] == null) + using (_methodLock.CreateWriteLock()) + if (method is ConstructorInfo c) + return _methodSymbols[row] ??= new ReflectionConstructorSymbol(Context, ResolveTypeSymbol(c.DeclaringType ?? throw new InvalidOperationException()), c); + else if (method is MethodInfo m) + if (method.DeclaringType is { } dt) + return _methodSymbols[row] ??= new ReflectionMethodSymbol(Context, ResolveTypeSymbol(dt), m); + else + return _methodSymbols[row] ??= new ReflectionMethodSymbol(Context, this, m); + else + throw new InvalidOperationException(); + else + return _methodSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by ctor. + /// + /// + /// + internal ReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return (ReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + internal ReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return (ReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + /// + internal ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + + Debug.Assert(field.Module == _module); + + // create lock on demand + if (_fieldLock == null) + lock (this) + _fieldLock ??= new ReaderWriterLockSlim(); + + using (_fieldLock.CreateUpgradeableReadLock()) + { + var row = field.GetMetadataTokenRowNumberSafe(); + if (_fieldTable[row] != field) + using (_fieldLock.CreateWriteLock()) + _fieldTable[row] = field; + + if (_fieldSymbols[row] == null) + using (_fieldLock.CreateWriteLock()) + if (field.DeclaringType is { } dt) + return _fieldSymbols[row] ??= new ReflectionFieldSymbol(Context, ResolveTypeSymbol(dt), field); + else + return _fieldSymbols[row] ??= new ReflectionFieldSymbol(Context, this, field); + else + return _fieldSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + /// + internal ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + Debug.Assert(property.Module == _module); + + // create lock on demand + if (_propertyLock == null) + lock (this) + _propertyLock ??= new ReaderWriterLockSlim(); + + using (_propertyLock.CreateUpgradeableReadLock()) + { + var row = property.GetMetadataTokenRowNumberSafe(); + if (_propertyTable[row] != property) + using (_propertyLock.CreateWriteLock()) + _propertyTable[row] = property; + + if (_propertySymbols[row] == null) + using (_propertyLock.CreateWriteLock()) + return _propertySymbols[row] ??= new ReflectionPropertySymbol(Context, ResolveTypeSymbol(property.DeclaringType!), property); + else + return _propertySymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + /// + internal ReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + Debug.Assert(@event.Module == _module); + + // create lock on demand + if (_eventLock == null) + lock (this) + _eventLock ??= new ReaderWriterLockSlim(); + + using (_eventLock.CreateUpgradeableReadLock()) + { + var row = @event.GetMetadataTokenRowNumberSafe(); + if (_eventTable[row] is not EventInfo i || i != @event) + using (_eventLock.CreateWriteLock()) + _eventTable[row] = @event; + + if (_eventSymbols[row] == null) + using (_eventLock.CreateWriteLock()) + return _eventSymbols[row] ??= new ReflectionEventSymbol(Context, ResolveTypeSymbol(@event.DeclaringType!), @event); + else + return _eventSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + internal ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + Debug.Assert(parameter.Member.Module == _module); + + // create lock on demand + if (_parameterLock == null) + lock (this) + _parameterLock ??= new ReaderWriterLockSlim(); + + using (_parameterLock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_parameterTable[position] != parameter) + using (_parameterLock.CreateWriteLock()) + _parameterTable[position] = parameter; + + if (_parameterSymbols[position] == null) + using (_parameterLock.CreateWriteLock()) + return _parameterSymbols[position] ??= new ReflectionParameterSymbol(Context, ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); + else + return _parameterSymbols[position] ?? throw new InvalidOperationException(); + } + } + /// public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_module.Assembly); @@ -208,13 +413,13 @@ public IFieldSymbol[] GetFields() /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _module.GetMethod(name, UnpackTypeSymbols(types)) is { } m ? ResolveMethodSymbol(m) : null; + return _module.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; } /// public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - return _module.GetMethod(name, bindingAttr, null, callConvention, UnpackTypeSymbols(types), modifiers) is { } m ? ResolveMethodSymbol(m) : null; + return _module.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; } /// @@ -268,9 +473,7 @@ public bool IsResource() /// public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return _module.ResolveField(metadataToken, _genericTypeArguments, _genericMethodArguments) is { } f ? ResolveFieldSymbol(f) : null; + return _module.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } f ? ResolveFieldSymbol(f) : null; } /// @@ -282,17 +485,13 @@ public bool IsResource() /// public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return _module.ResolveMember(metadataToken, _genericTypeArguments, _genericMethodArguments) is { } m ? ResolveMemberSymbol(m) : null; + return _module.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMemberSymbol(m) : null; } /// public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return _module.ResolveMethod(metadataToken, _genericTypeArguments, _genericMethodArguments) is { } m ? ResolveMethodBaseSymbol(m) : null; + return _module.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMethodBaseSymbol(m) : null; } /// @@ -322,25 +521,23 @@ public ITypeSymbol ResolveType(int metadataToken) /// public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return ResolveTypeSymbol(_module.ResolveType(metadataToken, _genericTypeArguments, _genericMethodArguments)); + return ResolveTypeSymbol(_module.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); } /// - public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { return ResolveCustomAttributes(_module.GetCustomAttributesData()); } /// - public CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return ResolveCustomAttributes(_module.GetCustomAttributesData().Where(i => i.AttributeType == ((ReflectionTypeSymbol)attributeType).ReflectionObject)); } /// - public CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index 2ad73f2602..d891bd5488 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -2,72 +2,113 @@ using System.Linq; using System.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; + namespace IKVM.CoreLib.Symbols.Reflection { class ReflectionParameterSymbol : ReflectionSymbol, IParameterSymbol { - readonly ParameterInfo _parameter; - readonly ReflectionMethodBaseSymbol _method; + readonly ReflectionMethodBaseSymbol _containingMethod; + ParameterInfo? _parameter; + ReflectionParameterSymbolBuilder? _builder; - CustomAttributeSymbol[]? _customAttributes; + CustomAttribute[]? _customAttributes; /// /// Initializes a new instance. /// /// - /// + /// /// - public ReflectionParameterSymbol(ReflectionSymbolContext context, ReflectionMethodBaseSymbol method, ParameterInfo parameter) : + public ReflectionParameterSymbol(ReflectionSymbolContext context, ReflectionMethodBaseSymbol containingMethod, ParameterInfo parameter) : base(context) { - _method = method ?? throw new ArgumentNullException(nameof(method)); + _containingMethod = containingMethod ?? throw new ArgumentNullException(nameof(containingMethod)); _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); } - internal ReflectionMethodBaseSymbol ContainingMethod => _method; + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionParameterSymbol(ReflectionSymbolContext context, ReflectionMethodBaseSymbol containingMethod, ReflectionParameterSymbolBuilder builder) : + base(context) + { + _containingMethod = containingMethod ?? throw new ArgumentNullException(nameof(containingMethod)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } - public ParameterAttributes Attributes => _parameter.Attributes; + internal ReflectionMethodBaseSymbol ContainingMethod => _containingMethod; - public object? DefaultValue => _parameter.DefaultValue; + /// + public ParameterAttributes Attributes => _parameter is { } p ? p.Attributes : _builder is { } b ? (ParameterAttributes)b.ReflectionBuilder.Attributes : throw new InvalidOperationException(); - public bool HasDefaultValue => _parameter.HasDefaultValue; + /// + public object? DefaultValue => _parameter is { } p ? p.DefaultValue : _builder is { } b ? b.GetConstant() : throw new InvalidOperationException(); - public bool IsIn => _parameter.IsIn; + /// + public bool HasDefaultValue => (Attributes & ParameterAttributes.HasDefault) != 0; - public bool IsLcid => _parameter.IsLcid; + /// + public bool IsIn => (Attributes & ParameterAttributes.In) != 0; - public bool IsOptional => _parameter.IsOptional; + /// + public bool IsLcid => (Attributes & ParameterAttributes.Lcid) != 0; + + /// + public bool IsOptional => (Attributes & ParameterAttributes.Optional) != 0; - public bool IsOut => _parameter.IsOut; + /// + public bool IsOut => (Attributes & ParameterAttributes.Out) != 0; + + /// + public bool IsRetval => (Attributes & ParameterAttributes.Retval) != 0; + + /// + public IMemberSymbol Member => _parameter is { } p ? ResolveMemberSymbol(p.Member) : _containingMethod; + +#if NETFRAMEWORK + + /// + public int MetadataToken => _parameter is { } p ? p.MetadataToken : _builder is { } b ? b.ReflectionBuilder.GetToken().Token : throw new InvalidOperationException(); - public bool IsRetval => _parameter.IsRetval; +#else - public IMemberSymbol Member => ResolveMemberSymbol(_parameter.Member); + /// + public int MetadataToken => _parameter is { } p ? p.MetadataToken : _builder is { } b ? throw new NotSupportedException() : throw new InvalidOperationException(); - public int MetadataToken => _parameter.MetadataToken; +#endif - public string? Name => _parameter.Name; + /// + public string? Name => _parameter is { } p ? p.Name : _builder is { } b ? b.ReflectionBuilder.Name : throw new InvalidOperationException(); - public ITypeSymbol ParameterType => ResolveTypeSymbol(_parameter.ParameterType); + /// + public ITypeSymbol ParameterType => _parameter is { } p ? ResolveTypeSymbol(p.ParameterType) : _builder is { } b ? throw new NotSupportedException() : throw new InvalidOperationException(); - public int Position => _parameter.Position; + /// + public int Position => _parameter is { } p ? p.Position : _builder is { } b ? b.ReflectionBuilder.Position : throw new InvalidOperationException(); /// - public CustomAttributeSymbol[] GetCustomAttributes(bool inherit = false) + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); + if (_parameter is not null) + return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); + + throw new NotSupportedException(); } /// - public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); } /// - public virtual CustomAttributeSymbol? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); } @@ -75,9 +116,41 @@ public virtual CustomAttributeSymbol[] GetCustomAttributes(ITypeSymbol attribute /// public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _parameter.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); + if (_parameter is not null) + return _parameter.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); + + throw new NotSupportedException(); + } + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + if (_parameter is not null) + return ResolveTypeSymbols(_parameter.GetOptionalCustomModifiers()); + + throw new NotSupportedException(); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + if (_parameter is not null) + return ResolveTypeSymbols(_parameter.GetRequiredCustomModifiers()); + + throw new NotSupportedException(); + } + + /// + /// Finishes the symbol by replacing the builder. + /// + /// + /// + internal void Finish(ParameterInfo parameter) + { + _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); + _builder = null; } } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index f0aa2a89a5..8ee7be1096 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -29,7 +29,10 @@ public ReflectionSymbol(ReflectionSymbolContext context) protected ReflectionSymbolContext Context => _context; /// - public virtual bool IsMissing => false; + public bool IsMissing => false; + + /// + public bool ContainsMissing => false; /// /// Resolves the symbol for the specified type. @@ -66,20 +69,6 @@ protected internal IEnumerable ResolveModuleSymbols(IEnu yield return ResolveModuleSymbol(module); } - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - protected internal Module[] UnpackModuleSymbols(IModuleSymbol[] modules) - { - var a = new Module[modules.Length]; - for (int i = 0; i < modules.Length; i++) - a[i] = ((ReflectionModuleSymbol)modules[i]).ReflectionModule; - - return a; - } - /// /// Resolves the symbol for the specified type. /// @@ -116,20 +105,6 @@ protected internal ReflectionMemberSymbol[] ResolveMemberSymbols(MemberInfo[] ty return a; } - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - protected internal MemberInfo[] UnpackMemberSymbols(IMemberSymbol[] members) - { - var a = new MemberInfo[members.Length]; - for (int i = 0; i < members.Length; i++) - a[i] = ((ReflectionMemberSymbol)members[i]).ReflectionObject; - - return a; - } - /// /// Resolves the symbol for the specified type. /// @@ -165,20 +140,6 @@ protected internal IEnumerable ResolveTypeSymbols(IEnumera yield return ResolveTypeSymbol(type); } - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - protected internal Type[] UnpackTypeSymbols(ITypeSymbol[] types) - { - var a = new Type[types.Length]; - for (int i = 0; i < types.Length; i++) - a[i] = ((ReflectionTypeSymbol)types[i]).ReflectionObject; - - return a; - } - /// /// Resolves the symbol for the specified method. /// @@ -240,30 +201,6 @@ protected internal ReflectionMethodSymbol[] ResolveMethodSymbols(MethodInfo[] me return a; } - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - protected virtual internal ReflectionParameterSymbol ResolveParameterSymbol(ParameterInfo parameter) - { - return _context.GetOrCreateParameterSymbol(parameter); - } - - /// - /// Resolves the symbols for the specified parameters. - /// - /// - /// - protected internal ReflectionParameterSymbol[] ResolveParameterSymbols(ParameterInfo[] parameters) - { - var a = new ReflectionParameterSymbol[parameters.Length]; - for (int i = 0; i < parameters.Length; i++) - a[i] = ResolveParameterSymbol(parameters[i]); - - return a; - } - /// /// Resolves the symbol for the specified field. /// @@ -336,14 +273,38 @@ protected internal ReflectionEventSymbol[] ResolveEventSymbols(EventInfo[] event return a; } + /// + /// Resolves the symbol for the specified parameter. + /// + /// + /// + protected virtual internal ReflectionParameterSymbol ResolveParameterSymbol(ParameterInfo parameter) + { + return _context.GetOrCreateParameterSymbol(parameter); + } + + /// + /// Resolves the symbols for the specified parameters. + /// + /// + /// + protected internal ReflectionParameterSymbol[] ResolveParameterSymbols(ParameterInfo[] parameters) + { + var a = new ReflectionParameterSymbol[parameters.Length]; + for (int i = 0; i < parameters.Length; i++) + a[i] = ResolveParameterSymbol(parameters[i]); + + return a; + } + /// /// Transforms a custom set of custom attribute data records to a symbol record. /// /// /// - protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IList attributes) + protected internal CustomAttribute[] ResolveCustomAttributes(IList attributes) { - var a = new CustomAttributeSymbol[attributes.Count]; + var a = new CustomAttribute[attributes.Count]; for (int i = 0; i < attributes.Count; i++) a[i] = ResolveCustomAttribute(attributes[i]); @@ -355,9 +316,9 @@ protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IList /// /// - protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IEnumerable attributes) + protected internal CustomAttribute[] ResolveCustomAttributes(IEnumerable attributes) { - var a = new List(); + var a = new List(); foreach (var i in attributes) a.Add(ResolveCustomAttribute(i)); @@ -370,9 +331,9 @@ protected internal CustomAttributeSymbol[] ResolveCustomAttributes(IEnumerable /// /// - protected internal CustomAttributeSymbol ResolveCustomAttribute(CustomAttributeData customAttributeData) + protected internal CustomAttribute ResolveCustomAttribute(CustomAttributeData customAttributeData) { - return new CustomAttributeSymbol( + return new CustomAttribute( ResolveTypeSymbol(customAttributeData.AttributeType), ResolveConstructorSymbol(customAttributeData.Constructor), ResolveCustomAttributeTypedArguments(customAttributeData.ConstructorArguments), @@ -380,13 +341,13 @@ protected internal CustomAttributeSymbol ResolveCustomAttribute(CustomAttributeD } /// - /// Transforms a list of values into symbols. + /// Transforms a list of values into symbols. /// /// /// - ImmutableArray ResolveCustomAttributeTypedArguments(IList args) + ImmutableArray ResolveCustomAttributeTypedArguments(IList args) { - var a = new CustomAttributeSymbolTypedArgument[args.Count]; + var a = new CustomAttributeTypedArgument[args.Count]; for (int i = 0; i < args.Count; i++) a[i] = ResolveCustomAttributeTypedArgument(args[i]); @@ -394,23 +355,36 @@ ImmutableArray ResolveCustomAttributeTypedAr } /// - /// Transforms a values into a symbol. + /// Transforms a values into a symbol. /// /// /// - CustomAttributeSymbolTypedArgument ResolveCustomAttributeTypedArgument(CustomAttributeTypedArgument arg) + CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg) + { + return new CustomAttributeTypedArgument(ResolveTypeSymbol(arg.ArgumentType), ResolveCustomAttributeTypedValue(arg.Value)); + } + + /// + /// Transforms the type as appropriate. + /// + /// + /// + object? ResolveCustomAttributeTypedValue(object? value) { - return new CustomAttributeSymbolTypedArgument(ResolveTypeSymbol(arg.ArgumentType), arg.Value); + if (value is System.Type v) + return ResolveTypeSymbol(v); + + return value; } /// - /// Transforms a list of values into symbols. + /// Transforms a list of values into symbols. /// /// /// - ImmutableArray ResolveCustomAttributeNamedArguments(IList args) + ImmutableArray ResolveCustomAttributeNamedArguments(IList args) { - var a = new CustomAttributeSymbolNamedArgument[args.Count]; + var a = new CustomAttributeNamedArgument[args.Count]; for (int i = 0; i < args.Count; i++) a[i] = ResolveCustomAttributeNamedArgument(args[i]); @@ -418,13 +392,13 @@ ImmutableArray ResolveCustomAttributeNamedAr } /// - /// Transforms a values into a symbol. + /// Transforms a values into a symbol. /// /// /// - CustomAttributeSymbolNamedArgument ResolveCustomAttributeNamedArgument(CustomAttributeNamedArgument arg) + CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg) { - return new CustomAttributeSymbolNamedArgument(arg.IsField, ResolveMemberSymbol(arg.MemberInfo), arg.MemberName, ResolveCustomAttributeTypedArgument(arg.TypedValue)); + return new CustomAttributeNamedArgument(arg.IsField, ResolveMemberSymbol(arg.MemberInfo), arg.MemberName, ResolveCustomAttributeTypedArgument(arg.TypedValue)); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index b88ecdf06a..6a65e95473 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -1,7 +1,10 @@ using System; using System.Reflection; +using System.Reflection.Emit; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Symbols.Reflection.Emit; + namespace IKVM.CoreLib.Symbols.Reflection { @@ -51,6 +54,19 @@ public ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); } + /// + /// Gets or creates a for the specified . + /// + /// + /// + public ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is ConstructorInfo ctor) + return GetOrCreateConstructorSymbol(ctor); + else + return GetOrCreateMethodSymbol((MethodInfo)method); + } + /// /// Gets or creates a for the specified . /// @@ -58,17 +74,17 @@ public ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) /// public ReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { - return GetOrCreateAssemblySymbol(ctor.Module.Assembly).GetOrCreateModuleSymbol(ctor.Module).GetOrCreateTypeSymbol(ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); + return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// public ReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { - return GetOrCreateAssemblySymbol(method.Module.Assembly).GetOrCreateModuleSymbol(method.Module).GetOrCreateTypeSymbol(method.DeclaringType!).GetOrCreateMethodSymbol(method); + return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); } /// @@ -78,7 +94,7 @@ public ReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) /// public ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { - return GetOrCreateAssemblySymbol(parameter.Member.Module.Assembly).GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateTypeSymbol(parameter.Member.DeclaringType!).GetOrCreateMethodBaseSymbol((MethodBase)parameter.Member).GetOrCreateParameterSymbol(parameter); + return GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateParameterSymbol(parameter); } /// @@ -88,7 +104,7 @@ public ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parame /// public ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - return GetOrCreateAssemblySymbol(field.Module.Assembly).GetOrCreateModuleSymbol(field.Module).GetOrCreateTypeSymbol(field.DeclaringType!).GetOrCreateFieldSymbol(field); + return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); } /// @@ -98,7 +114,7 @@ public ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) /// public ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { - return GetOrCreateAssemblySymbol(property.Module.Assembly).GetOrCreateModuleSymbol(property.Module).GetOrCreateTypeSymbol(property.DeclaringType!).GetOrCreatePropertySymbol(property); + return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); } /// @@ -108,7 +124,27 @@ public ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) /// public ReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { - return GetOrCreateAssemblySymbol(@event.Module.Assembly).GetOrCreateModuleSymbol(@event.Module).GetOrCreateTypeSymbol(@event.DeclaringType!).GetOrCreateEventSymbol(@event); + return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public ReflectionEventSymbol GetOrCreateEventSymbol(EventBuilder @event) + { + return GetOrCreateEventSymbol(new ReflectionEventBuilderInfo(@event)); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return GetOrCreateParameterSymbol(new ReflectionParameterBuilderInfo(parameter)); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index df9b1ffe70..b49dbe0287 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -3,46 +3,30 @@ using System.Diagnostics; using System.Linq; using System.Reflection; -using System.Reflection.Metadata.Ecma335; using System.Threading; -using IKVM.CoreLib.Symbols.IkvmReflection; - namespace IKVM.CoreLib.Symbols.Reflection { class ReflectionTypeSymbol : ReflectionMemberSymbol, ITypeSymbol { - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - - readonly Type _type; - - MethodBase[]? _methodsSource; - int _methodsBaseRow; - ReflectionMethodBaseSymbol?[]? _methods; + const int MAX_CAPACITY = 65536 * 2; - FieldInfo[]? _fieldsSource; - int _fieldsBaseRow; - ReflectionFieldSymbol?[]? _fields; - - PropertyInfo[]? _propertiesSource; - int _propertiesBaseRow; - ReflectionPropertySymbol?[]? _properties; + const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - EventInfo[]? _eventsSource; - int _eventsBaseRow; - ReflectionEventSymbol?[]? _events; + Type _type; ReflectionTypeSymbol?[]? _asArray; ReflectionTypeSymbol? _asSZArray; ReflectionTypeSymbol? _asPointer; ReflectionTypeSymbol? _asByRef; - Type[]? _genericParametersSource; - ReflectionTypeSymbol?[]? _genericParameters; - List<(Type[] Arguments, ReflectionTypeSymbol Symbol)>? _genericTypes; - ReaderWriterLockSlim? _genericTypesLock; + Type[]? _genericParameterList; + ReflectionTypeSymbol?[]? _genericParameterSymbols; + + List<(Type[] Arguments, ReflectionTypeSymbol Symbol)>? _genericTypeSymbols; + ReaderWriterLockSlim? _genericTypeLock; /// /// Initializes a new instance. @@ -51,233 +35,12 @@ class ReflectionTypeSymbol : ReflectionMemberSymbol, ITypeSymbol /// /// public ReflectionTypeSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, Type type) : - base(context, module, null, type) + base(context, module, type) { - Debug.Assert(module.ReflectionModule == type.Module); + Debug.Assert(module.ReflectionObject == type.Module); _type = type ?? throw new ArgumentNullException(nameof(type)); } - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal ReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return (ReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - internal ReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return (ReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - Debug.Assert(method.DeclaringType == _type); - - var hnd = MetadataTokens.MethodDefinitionHandle(method.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source table - if (_methodsSource == null) - { - Interlocked.CompareExchange(ref _methodsSource, _type.GetConstructors(DefaultBindingFlags).Cast().Concat(_type.GetMethods(DefaultBindingFlags)).OrderBy(i => i.MetadataToken).ToArray(), null); - _methodsBaseRow = _methodsSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_methodsSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_methods == null) - Interlocked.CompareExchange(ref _methods, new ReflectionMethodBaseSymbol?[_methodsSource.Length], null); - - // index of current record is specified row - base - var idx = row - _methodsBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _methodsSource.Length); - - // check that our list is long enough to contain the entire table - if (_methods.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _methods[idx]; - if (rec == null) - { - switch (method) - { - case ConstructorInfo c: - Interlocked.CompareExchange(ref rec, new ReflectionConstructorSymbol(Context, ContainingModule, this, c), null); - break; - case MethodInfo m: - Interlocked.CompareExchange(ref rec, new ReflectionMethodSymbol(Context, ContainingModule, this, m), null); - break; - } - } - - // this should never happen - if (rec is not ReflectionMethodBaseSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - /// - internal ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - Debug.Assert(field.DeclaringType == _type); - - var hnd = MetadataTokens.FieldDefinitionHandle(field.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source table - if (_fieldsSource == null) - { - Interlocked.CompareExchange(ref _fieldsSource, _type.GetFields(DefaultBindingFlags).OrderBy(i => i.MetadataToken).ToArray(), null); - _fieldsBaseRow = _fieldsSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_fieldsSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_fields == null) - Interlocked.CompareExchange(ref _fields, new ReflectionFieldSymbol?[_fieldsSource.Length], null); - - // index of current field is specified row - base - var idx = row - _fieldsBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _fieldsSource.Length); - - // check that our list is long enough to contain the entire table - if (_fields.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _fields[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new ReflectionFieldSymbol(Context, this, field), null); - - // this should never happen - if (rec is not ReflectionFieldSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - /// - internal ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - Debug.Assert(property.DeclaringType == _type); - - var hnd = MetadataTokens.PropertyDefinitionHandle(property.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source table - if (_propertiesSource == null) - { - Interlocked.CompareExchange(ref _propertiesSource, _type.GetProperties(DefaultBindingFlags).OrderBy(i => i.MetadataToken).ToArray(), null); - _propertiesBaseRow = _propertiesSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_propertiesSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_properties == null) - Interlocked.CompareExchange(ref _properties, new ReflectionPropertySymbol?[_propertiesSource.Length], null); - - // index of current property is specified row - base - var idx = row - _propertiesBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _propertiesSource.Length); - - // check that our list is long enough to contain the entire table - if (_properties.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _properties[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new ReflectionPropertySymbol(Context, this, property), null); - - // this should never happen - if (rec is not ReflectionPropertySymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - /// - internal ReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - Debug.Assert(@event.DeclaringType == _type); - - var hnd = MetadataTokens.PropertyDefinitionHandle(@event.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source events - if (_eventsSource == null) - { - Interlocked.CompareExchange(ref _eventsSource, _type.GetEvents(DefaultBindingFlags).OrderBy(i => i.MetadataToken).ToArray(), null); - _eventsBaseRow = _eventsSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(_eventsSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_events == null) - Interlocked.CompareExchange(ref _events, new ReflectionEventSymbol?[_eventsSource.Length], null); - - // index of current event is specified row - base - var idx = row - _eventsBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _eventsSource.Length); - - // check that our list is long enough to contain the entire table - if (_events.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _events[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new ReflectionEventSymbol(Context, this, @event), null); - - // this should never happen - if (rec is not ReflectionEventSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - /// /// Gets or creates the cached for the generic parameter type. /// @@ -292,20 +55,20 @@ internal ReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericType Debug.Assert(genericTypeParameterType.DeclaringType == _type); // initialize tables - if (_genericParametersSource == null) - Interlocked.CompareExchange(ref _genericParametersSource, _type.GetGenericArguments(), null); - if (_genericParameters == null) - Interlocked.CompareExchange(ref _genericParameters, new ReflectionTypeSymbol?[_genericParametersSource.Length], null); + if (_genericParameterList == null) + Interlocked.CompareExchange(ref _genericParameterList, _type.GetGenericArguments(), null); + if (_genericParameterSymbols == null) + Interlocked.CompareExchange(ref _genericParameterSymbols, new ReflectionTypeSymbol?[_genericParameterList.Length], null); // position of the parameter in the list var idx = genericTypeParameterType.GenericParameterPosition; // check that our list is long enough to contain the entire table - if (_genericParameters.Length < idx) + if (_genericParameterSymbols.Length < idx) throw new IndexOutOfRangeException(); // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _genericParameters[idx]; + ref var rec = ref _genericParameterSymbols[idx]; if (rec == null) Interlocked.CompareExchange(ref rec, new ReflectionTypeSymbol(Context, ContainingModule, genericTypeParameterType), null); @@ -331,43 +94,43 @@ internal ReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArg throw new InvalidOperationException(); // initialize the available parameters - if (_genericParametersSource == null) - Interlocked.CompareExchange(ref _genericParametersSource, _type.GetGenericArguments(), null); - if (_genericParametersSource.Length != genericTypeArguments.Length) + if (_genericParameterList == null) + Interlocked.CompareExchange(ref _genericParameterList, _type.GetGenericArguments(), null); + if (_genericParameterList.Length != genericTypeArguments.Length) throw new InvalidOperationException(); // initialize generic type map, and lock on it since we're potentially adding items - if (_genericTypes == null) - Interlocked.CompareExchange(ref _genericTypes, [], null); - if (_genericTypesLock == null) - Interlocked.CompareExchange(ref _genericTypesLock, new(), null); + if (_genericTypeSymbols == null) + Interlocked.CompareExchange(ref _genericTypeSymbols, [], null); + if (_genericTypeLock == null) + Interlocked.CompareExchange(ref _genericTypeLock, new(), null); try { - _genericTypesLock.EnterUpgradeableReadLock(); + _genericTypeLock.EnterUpgradeableReadLock(); // find existing entry - foreach (var i in _genericTypes) + foreach (var i in _genericTypeSymbols) if (i.Arguments.SequenceEqual(genericTypeArguments)) return i.Symbol; try { - _genericTypesLock.EnterWriteLock(); + _genericTypeLock.EnterWriteLock(); // generate new symbol var sym = new ReflectionTypeSymbol(Context, ContainingModule, _type.MakeGenericType(genericTypeArguments)); - _genericTypes.Add((genericTypeArguments, sym)); + _genericTypeSymbols.Add((genericTypeArguments, sym)); return sym; } finally { - _genericTypesLock.ExitWriteLock(); + _genericTypeLock.ExitWriteLock(); } } finally { - _genericTypesLock.ExitUpgradeableReadLock(); + _genericTypeLock.ExitUpgradeableReadLock(); } } @@ -384,418 +147,499 @@ protected internal override ReflectionTypeSymbol ResolveTypeSymbol(Type type) return base.ResolveTypeSymbol(type); } - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - protected internal override ReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) - { - if (ctor.DeclaringType == _type) - return GetOrCreateConstructorSymbol(ctor); - else - return base.ResolveConstructorSymbol(ctor); - } - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected internal override ReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) - { - if (method.DeclaringType == _type) - return GetOrCreateMethodSymbol(method); - else - return base.ResolveMethodSymbol(method); - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override ReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) - { - if (field.DeclaringType == _type) - return GetOrCreateFieldSymbol(field); - else - return base.ResolveFieldSymbol(field); - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override ReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) - { - if (property.DeclaringType == _type) - return GetOrCreatePropertySymbol(property); - else - return base.ResolvePropertySymbol(property); - } - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - protected internal override ReflectionEventSymbol ResolveEventSymbol(EventInfo @event) - { - if (@event.DeclaringType == _type) - return GetOrCreateEventSymbol(@event); - else - return base.ResolveEventSymbol(@event); - } - /// /// Gets the wrapped . /// internal new Type ReflectionObject => _type; + /// public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_type.Assembly); + /// public string? AssemblyQualifiedName => _type.AssemblyQualifiedName; + /// public TypeAttributes Attributes => _type.Attributes; + /// public ITypeSymbol? BaseType => _type.BaseType != null ? ResolveTypeSymbol(_type.BaseType) : null; + /// public bool ContainsGenericParameters => _type.ContainsGenericParameters; + /// public IMethodBaseSymbol? DeclaringMethod => _type.DeclaringMethod is MethodInfo m ? ResolveMethodSymbol(m) : null; + /// public string? FullName => _type.FullName; + /// + public string? Namespace => _type.Namespace; + + /// public GenericParameterAttributes GenericParameterAttributes => _type.GenericParameterAttributes; + /// public int GenericParameterPosition => _type.GenericParameterPosition; + /// public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(_type.GenericTypeArguments); + /// public bool HasElementType => _type.HasElementType; + /// + public TypeCode TypeCode => Type.GetTypeCode(_type); + + /// public bool IsAbstract => _type.IsAbstract; +#if NETFRAMEWORK + + /// + /// + /// There's no API to distinguish an array of rank 1 from a vector, + /// so we check if the type name ends in [], which indicates it's a vector + /// (non-vectors will have [*] or [,]). + /// + public bool IsSZArray => _type.IsArray && _type.Name.EndsWith("[]"); + +#else + + /// + public bool IsSZArray => _type.IsSZArray; + +#endif + + /// public bool IsArray => _type.IsArray; + /// public bool IsAutoLayout => _type.IsAutoLayout; + /// + public bool IsExplicitLayout => _type.IsExplicitLayout; + + /// public bool IsByRef => _type.IsByRef; + /// public bool IsClass => _type.IsClass; - public bool IsConstructedGenericType => _type.IsConstructedGenericType; - + /// public bool IsEnum => _type.IsEnum; - public bool IsExplicitLayout => _type.IsExplicitLayout; + /// + public bool IsInterface => _type.IsInterface; + /// + public bool IsConstructedGenericType => _type.IsConstructedGenericType; + + /// public bool IsGenericParameter => _type.IsGenericParameter; + /// public bool IsGenericType => _type.IsGenericType; + /// public bool IsGenericTypeDefinition => _type.IsGenericTypeDefinition; - public bool IsInterface => _type.IsInterface; - + /// public bool IsLayoutSequential => _type.IsLayoutSequential; + /// public bool IsNested => _type.IsNested; + /// public bool IsNestedAssembly => _type.IsNestedAssembly; + /// public bool IsNestedFamANDAssem => _type.IsNestedFamANDAssem; + /// public bool IsNestedFamORAssem => _type.IsNestedFamORAssem; + /// public bool IsNestedFamily => _type.IsNestedFamily; + /// public bool IsNestedPrivate => _type.IsNestedPrivate; + /// public bool IsNestedPublic => _type.IsNestedPublic; + /// public bool IsNotPublic => _type.IsNotPublic; + /// public bool IsPointer => _type.IsPointer; +#if NET8_0_OR_GREATER + + /// + public bool IsFunctionPointer => _type.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _type.IsUnmanagedFunctionPointer; + +#else + + /// + public bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif + + /// public bool IsPrimitive => _type.IsPrimitive; + /// public bool IsPublic => _type.IsPublic; + /// public bool IsSealed => _type.IsSealed; #pragma warning disable SYSLIB0050 // Type or member is obsolete + /// public bool IsSerializable => _type.IsSerializable; #pragma warning restore SYSLIB0050 // Type or member is obsolete + /// public bool IsValueType => _type.IsValueType; + /// public bool IsVisible => _type.IsVisible; - public string? Namespace => _type.Namespace; +#if NET6_0_OR_GREATER + + /// + public bool IsSignatureType => _type.IsSignatureType; +#else + + /// + public bool IsSignatureType => throw new NotImplementedException(); + +#endif + + /// + public bool IsSpecialName => _type.IsSpecialName; + + /// public IConstructorSymbol? TypeInitializer => _type.TypeInitializer is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; + /// public int GetArrayRank() { return _type.GetArrayRank(); } + /// public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) { - return _type.GetConstructor(bindingAttr, binder: null, UnpackTypeSymbols(types), modifiers: null) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; + return _type.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; } + /// public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _type.GetConstructor(UnpackTypeSymbols(types)) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; + return _type.GetConstructor(types.Unpack()) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; } + /// public IConstructorSymbol[] GetConstructors() { return ResolveConstructorSymbols(_type.GetConstructors()); } + /// public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) { return ResolveConstructorSymbols(_type.GetConstructors(bindingAttr)); } + /// public IMemberSymbol[] GetDefaultMembers() { return ResolveMemberSymbols(_type.GetDefaultMembers()); } + /// public ITypeSymbol? GetElementType() { return _type.GetElementType() is Type t ? ResolveTypeSymbol(t) : null; } + /// public string? GetEnumName(object value) { return _type.GetEnumName(value); } + /// public string[] GetEnumNames() { return _type.GetEnumNames(); } + /// public ITypeSymbol GetEnumUnderlyingType() { return ResolveTypeSymbol(_type.GetEnumUnderlyingType()); } + /// public Array GetEnumValues() { return _type.GetEnumValues(); } + /// public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) { throw new NotImplementedException(); } + /// public IEventSymbol? GetEvent(string name) { return _type.GetEvent(name) is { } f ? ResolveEventSymbol(f) : null; } + /// public IEventSymbol[] GetEvents() { return ResolveEventSymbols(_type.GetEvents()); } + /// public IEventSymbol[] GetEvents(BindingFlags bindingAttr) { return ResolveEventSymbols(_type.GetEvents(bindingAttr)); } + /// public IFieldSymbol? GetField(string name) { return _type.GetField(name) is FieldInfo f ? ResolveFieldSymbol(f) : null; } + /// public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) { return _type.GetField(name, bindingAttr) is FieldInfo f ? ResolveFieldSymbol(f) : null; } + /// public IFieldSymbol[] GetFields() { return ResolveFieldSymbols(_type.GetFields()); } + /// public IFieldSymbol[] GetFields(BindingFlags bindingAttr) { return ResolveFieldSymbols(_type.GetFields(bindingAttr)); } + /// public ITypeSymbol[] GetGenericArguments() { return ResolveTypeSymbols(_type.GetGenericArguments()); } + /// public ITypeSymbol[] GetGenericParameterConstraints() { return ResolveTypeSymbols(_type.GetGenericParameterConstraints()); } + /// public ITypeSymbol GetGenericTypeDefinition() { return ResolveTypeSymbol(_type.GetGenericTypeDefinition()); } + /// public ITypeSymbol? GetInterface(string name) { return _type.GetInterface(name) is { } i ? ResolveTypeSymbol(i) : null; } + /// public ITypeSymbol? GetInterface(string name, bool ignoreCase) { return _type.GetInterface(name, ignoreCase) is { } i ? ResolveTypeSymbol(i) : null; } + /// public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { throw new NotImplementedException(); } - public ITypeSymbol[] GetInterfaces() + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return ResolveTypeSymbols(_type.GetInterfaces()); + if (inherit) + return ResolveTypeSymbols(_type.GetInterfaces()); + else + throw new NotImplementedException(); } + /// public IMemberSymbol[] GetMember(string name) { return ResolveMemberSymbols(_type.GetMember(name)); } + /// public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) { return ResolveMemberSymbols(_type.GetMember(name, bindingAttr)); } + /// public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) { return ResolveMemberSymbols(_type.GetMember(name, type, bindingAttr)); } + /// public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) { return ResolveMemberSymbols(_type.GetMembers(bindingAttr)); } + /// public IMemberSymbol[] GetMembers() { return ResolveMemberSymbols(_type.GetMembers()); } + /// public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) { return _type.GetMethod(name, bindingAttr) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _type.GetMethod(name, UnpackTypeSymbols(types)) is { } m ? ResolveMethodSymbol(m) : null; + return _type.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) { - return _type.GetMethod(name, bindingAttr, null, UnpackTypeSymbols(types), null) is { } m ? ResolveMethodSymbol(m) : null; + return _type.GetMethod(name, bindingAttr, null, types.Unpack(), null) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetMethod(string name) { return _type.GetMethod(name) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) { return ResolveMethodSymbols(_type.GetMethods(bindingAttr)); } + /// public IMethodSymbol[] GetMethods() { return ResolveMethodSymbols(_type.GetMethods()); } + /// public ITypeSymbol? GetNestedType(string name) { return _type.GetNestedType(name) is Type t ? ResolveTypeSymbol(t) : null; } + /// public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) { return _type.GetNestedType(name, bindingAttr) is Type t ? ResolveTypeSymbol(t) : null; } + /// public ITypeSymbol[] GetNestedTypes() { return ResolveTypeSymbols(_type.GetNestedTypes()); } + /// public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) { return ResolveTypeSymbols(_type.GetNestedTypes(bindingAttr)); } + /// public IPropertySymbol[] GetProperties() { return ResolvePropertySymbols(_type.GetProperties()); } + /// public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) { return ResolvePropertySymbols(_type.GetProperties(bindingAttr)); } + /// public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _type.GetProperty(name, UnpackTypeSymbols(types)) is { } p ? ResolvePropertySymbol(p) : null; + return _type.GetProperty(name, types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - var _returnType = returnType != null ? ((ReflectionTypeSymbol)returnType).ReflectionObject : null; - return _type.GetProperty(name, _returnType, UnpackTypeSymbols(types)) is { } p ? ResolvePropertySymbol(p) : null; + return _type.GetProperty(name, returnType?.Unpack(), types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) { return _type.GetProperty(name, bindingAttr) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name) { return _type.GetProperty(name) is { } p ? ResolvePropertySymbol(p) : null; } + /// public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - var _returnType = returnType != null ? ((ReflectionTypeSymbol)returnType).ReflectionObject : null; - - return _type.GetProperty(name, _returnType) is { } p ? ResolvePropertySymbol(p) : null; + return _type.GetProperty(name, returnType?.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; } + /// public bool IsAssignableFrom(ITypeSymbol? c) { - return _type.IsAssignableFrom(c != null ? ((ReflectionTypeSymbol)c).ReflectionObject : null); + return _type.IsAssignableFrom(c?.Unpack()); } + /// public bool IsEnumDefined(object value) { return _type.IsEnumDefined(value); } + /// public bool IsSubclassOf(ITypeSymbol c) { - return _type.IsSubclassOf(((ReflectionTypeSymbol)c).ReflectionObject); + return _type.IsSubclassOf(c.Unpack()); } + /// public ITypeSymbol MakeArrayType() { if (_asSZArray == null) @@ -804,6 +648,7 @@ public ITypeSymbol MakeArrayType() return _asSZArray; } + /// public ITypeSymbol MakeArrayType(int rank) { if (rank == 1) @@ -819,6 +664,7 @@ public ITypeSymbol MakeArrayType(int rank) return asArray; } + /// public ITypeSymbol MakeByRefType() { if (_asByRef == null) @@ -827,11 +673,13 @@ public ITypeSymbol MakeByRefType() return _asByRef; } + /// public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { throw new NotImplementedException(); } + /// public ITypeSymbol MakePointerType() { if (_asPointer == null) @@ -840,6 +688,16 @@ public ITypeSymbol MakePointerType() return _asPointer; } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + /// + internal void FinishType(Type type) + { + _type = type; + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs new file mode 100644 index 0000000000..30d9881679 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -0,0 +1,146 @@ +using System; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + static class ReflectionUtil + { + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static Module Unpack(this IModuleSymbol module) + { + return ((ReflectionModuleSymbol)module).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Module[] Unpack(this IModuleSymbol[] modules) + { + var a = new Module[modules.Length]; + for (int i = 0; i < modules.Length; i++) + a[i] = modules[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static Type Unpack(this ITypeSymbol type) + { + return ((ReflectionTypeSymbol)type).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Type[] Unpack(this ITypeSymbol[] types) + { + var a = new Type[types.Length]; + for (int i = 0; i < types.Length; i++) + a[i] = types[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Type[][] Unpack(this ITypeSymbol[][] types) + { + var a = new Type[types.Length][]; + for (int i = 0; i < types.Length; i++) + a[i] = types[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static MemberInfo Unpack(this IMemberSymbol member) + { + return ((ReflectionMemberSymbol)member).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static MemberInfo[] Unpack(this IMemberSymbol[] members) + { + var a = new MemberInfo[members.Length]; + for (int i = 0; i < members.Length; i++) + a[i] = members[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static ConstructorInfo Unpack(this IConstructorSymbol ctor) + { + return ((ReflectionConstructorSymbol)ctor).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static ConstructorInfo[] Unpack(this IConstructorSymbol[] ctor) + { + var a = new ConstructorInfo[ctor.Length]; + for (int i = 0; i < ctor.Length; i++) + a[i] = ctor[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static MethodInfo Unpack(this IMethodSymbol ctor) + { + return ((ReflectionMethodSymbol)ctor).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static MethodInfo[] Unpack(this IMethodSymbol[] ctor) + { + var a = new MethodInfo[ctor.Length]; + for (int i = 0; i < ctor.Length; i++) + a[i] = ctor[i].Unpack(); + + return a; + } + + } + +} diff --git a/src/IKVM.CoreLib/System/TypeExtensions.cs b/src/IKVM.CoreLib/System/TypeExtensions.cs new file mode 100644 index 0000000000..1abd007c2b --- /dev/null +++ b/src/IKVM.CoreLib/System/TypeExtensions.cs @@ -0,0 +1,450 @@ +using System.Linq.Expressions; +using System.Reflection; +using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; + +using IKVM.CoreLib.Symbols.Reflection.Emit; + +namespace System +{ + + static class TypeExtensions + { + + static readonly ParameterExpression _propertyBuilderParameter = Expression.Parameter(typeof(PropertyBuilder), "p"); + static readonly ParameterExpression _eventBuilderParameter = Expression.Parameter(typeof(EventBuilder), "p"); + static readonly ParameterExpression _parameterBuilderParameter = Expression.Parameter(typeof(ParameterBuilder), "p"); + +#if NET + + static readonly Type _propertyBuilderType = typeof(PropertyBuilder).Assembly.GetType("System.Reflection.Emit.RuntimePropertyBuilder", true)!; + static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.RuntimeEventBuilder", true)!; + static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.RuntimeParameterBuilder", true)!; + + static readonly Func _getPropertyMetadataTokenFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_propertyBuilderParameter, _propertyBuilderType), + _propertyBuilderType.GetField("m_tkProperty", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _propertyBuilderParameter) + .Compile(); + + + static readonly Func _getEventMetadataTokenFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_eventBuilderParameter, _eventBuilderType), + _eventBuilderType.GetField("m_evToken", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _eventBuilderParameter) + .Compile(); + + static readonly Func _getParameterMethodBuilderFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_parameterBuilderParameter, _parameterBuilderType), + _parameterBuilderType.GetField("_methodBuilder", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _parameterBuilderParameter) + .Compile(); + + static readonly Func _getParameterMetadataTokenFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_parameterBuilderParameter, _parameterBuilderType), + _parameterBuilderType.GetField("_token", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _parameterBuilderParameter) + .Compile(); + +#else + + static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.EventBuilder", true)!; + static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.ParameterBuilder", true)!; + + static readonly Func _getParameterMethodBuilderFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_parameterBuilderParameter, _parameterBuilderType), + _parameterBuilderType.GetField("m_methodBuilder", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _parameterBuilderParameter) + .Compile(); + +#endif + + static readonly Func _getEventModuleBuilderFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_eventBuilderParameter, _eventBuilderType), + _eventBuilderType.GetField("m_module", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _eventBuilderParameter) + .Compile(); + + static readonly Func _getEventTypeBuilderFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_eventBuilderParameter, _eventBuilderType), + _eventBuilderType.GetField("m_type", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _eventBuilderParameter) + .Compile(); + + static readonly Func _getEventNameFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_eventBuilderParameter, _eventBuilderType), + _eventBuilderType.GetField("m_name", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _eventBuilderParameter) + .Compile(); + + static readonly Func _getEventAttributesFunc = Expression.Lambda>( + Expression.ConvertChecked( + Expression.Field( + Expression.ConvertChecked(_eventBuilderParameter, _eventBuilderType), + _eventBuilderType.GetField("m_attributes", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + typeof(EventAttributes)), + _eventBuilderParameter) + .Compile(); + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + public static int GetMetadataTokenSafe(this Type type) + { +#if NETFRAMEWORK + if (type is TypeBuilder b) + { + var t = b.TypeToken.Token; + if (t == 0) + throw new InvalidOperationException(); + + return t; + } +#endif + + return type.GetMetadataToken(); + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this Type type) + { + return MetadataTokens.GetRowNumber(MetadataTokens.TypeDefinitionHandle(type.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + public static int GetMetadataTokenSafe(this FieldInfo field) + { +#if NETFRAMEWORK + if (field is FieldBuilder b) + { + var t = b.GetToken().Token; + if (t == 0) + throw new InvalidOperationException(); + + return t; + } +#endif + + return field.GetMetadataToken(); + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this FieldInfo field) + { + return MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(field.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + /// + public static int GetMetadataTokenSafe(this MethodBase method) + { + return method switch + { + ConstructorInfo c => c.GetMetadataTokenSafe(), + MethodInfo m => m.GetMetadataTokenSafe(), + _ => throw new InvalidOperationException(), + }; + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this MethodBase method) + { + return method switch + { + ConstructorInfo c => c.GetMetadataTokenRowNumberSafe(), + MethodInfo m => m.GetMetadataTokenRowNumberSafe(), + _ => throw new InvalidOperationException(), + }; + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + public static int GetMetadataTokenSafe(this ConstructorInfo ctor) + { +#if NETFRAMEWORK + if (ctor is ConstructorBuilder b) + { + var t = b.GetToken().Token; + if (t == 0) + throw new InvalidOperationException(); + + return t; + } +#endif + + return ctor.GetMetadataToken(); + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this ConstructorInfo ctor) + { + return MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(ctor.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + public static int GetMetadataTokenSafe(this MethodInfo method) + { +#if NETFRAMEWORK + if (method is MethodBuilder b) + { + var t = b.GetToken().Token; + if (t == 0) + throw new InvalidOperationException(); + + return t; + } +#endif + + return method.GetMetadataToken(); + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this MethodInfo ctor) + { + return MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(ctor.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + /// + public static int GetMetadataTokenSafe(this PropertyInfo property) + { + if (property is PropertyBuilder b) + { +#if NETFRAMEWORK + var t = b.PropertyToken.Token; +#else + var t = _getPropertyMetadataTokenFunc(b); +#endif + if (t == 0) + throw new InvalidOperationException(); + + return t; + } + + return property.GetMetadataToken(); + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this PropertyInfo property) + { + return MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(property.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + /// + public static int GetMetadataTokenSafe(this EventInfo @event) + { + if (@event is ReflectionEventBuilderInfo b) + { + var t = b.GetMetadataToken(); + if (t == 0) + throw new InvalidOperationException(); + } + + return @event.GetMetadataToken(); + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this EventInfo @event) + { + return MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + /// + /// + public static int GetMetadataToken(this EventBuilder @event) + { +#if NETFRAMEWORK + return @event.GetEventToken().Token; +#else + return _getEventMetadataTokenFunc(@event); +#endif + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + /// + /// + public static int GetMetadataTokenSafe(this EventBuilder @event) + { + var t = GetMetadataToken(@event); + if (t == 0) + throw new InvalidOperationException(); + + return t; + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this EventBuilder @event) + { + return MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + /// + public static int GetMetadataTokenSafe(this ParameterInfo parameter) + { + var t = parameter.MetadataToken; + if (t == 0) + throw new InvalidOperationException(); + + return t; + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this ParameterInfo parameter) + { + return MetadataTokens.GetRowNumber(MetadataTokens.ParameterHandle(parameter.GetMetadataTokenSafe())); + } + + /// + /// Gets the metadata token for the specified . + /// + /// + /// + /// + /// + public static int GetMetadataToken(this ParameterBuilder parameter) + { +#if NETFRAMEWORK + return parameter.GetToken().Token; +#else + return _getParameterMetadataTokenFunc(parameter); +#endif + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static ModuleBuilder GetModuleBuilder(this EventBuilder @event) + { + return _getEventModuleBuilderFunc(@event); + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static TypeBuilder GetTypeBuilder(this EventBuilder @event) + { + return _getEventTypeBuilderFunc(@event); + } + + /// + /// Gets the name associated with a . + /// + /// + /// + public static string GetEventName(this EventBuilder @event) + { + return _getEventNameFunc(@event); + } + + /// + /// Gets the attributes associated with a . + /// + /// + /// + public static EventAttributes GetEventAttributes(this EventBuilder @event) + { + return _getEventAttributesFunc(@event); + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static MemberInfo GetMethodBuilder(this ParameterBuilder parameter) + { + return _getParameterMethodBuilderFunc(parameter); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Threading/ReaderWriterLockSlimExtensions.cs b/src/IKVM.CoreLib/Threading/ReaderWriterLockSlimExtensions.cs new file mode 100644 index 0000000000..4d41fc658c --- /dev/null +++ b/src/IKVM.CoreLib/Threading/ReaderWriterLockSlimExtensions.cs @@ -0,0 +1,99 @@ +using System; +using System.Threading; + +namespace IKVM.CoreLib.Threading +{ + + static class ReaderWriterLockSlimExtensions + { + + public readonly struct ReaderWriterLockSlimReadLock : IDisposable + { + + readonly ReaderWriterLockSlim @lock; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReaderWriterLockSlimReadLock(ReaderWriterLockSlim @lock) + { + this.@lock = @lock ?? throw new ArgumentNullException(nameof(@lock)); + @lock.EnterReadLock(); + } + + /// + public readonly void Dispose() + { + @lock.ExitReadLock(); + } + + } + + public readonly struct ReaderWriterLockSlimUpradeableReadLock : IDisposable + { + + readonly ReaderWriterLockSlim @lock; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReaderWriterLockSlimUpradeableReadLock(ReaderWriterLockSlim @lock) + { + this.@lock = @lock ?? throw new ArgumentNullException(nameof(@lock)); + @lock.EnterUpgradeableReadLock(); + } + + /// + public readonly void Dispose() + { + @lock.ExitUpgradeableReadLock(); + } + + } + + public readonly struct ReaderWriterLockSlimWriteLock : IDisposable + { + + readonly ReaderWriterLockSlim @lock; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReaderWriterLockSlimWriteLock(ReaderWriterLockSlim @lock) + { + this.@lock = @lock ?? throw new ArgumentNullException(nameof(@lock)); + @lock.EnterWriteLock(); + } + + /// + public readonly void Dispose() + { + @lock.ExitWriteLock(); + } + + } + + public static ReaderWriterLockSlimReadLock CreateReadLock(this ReaderWriterLockSlim @lock) + { + return new ReaderWriterLockSlimReadLock(@lock); + } + + public static ReaderWriterLockSlimUpradeableReadLock CreateUpgradeableReadLock(this ReaderWriterLockSlim @lock) + { + return new ReaderWriterLockSlimUpradeableReadLock(@lock); + } + + public static ReaderWriterLockSlimWriteLock CreateWriteLock(this ReaderWriterLockSlim @lock) + { + return new ReaderWriterLockSlimWriteLock(@lock); + } + + } + +} diff --git a/src/IKVM.Reflection/ArrayType.cs b/src/IKVM.Reflection/ArrayType.cs index 78f02ab4f4..e53eafac85 100644 --- a/src/IKVM.Reflection/ArrayType.cs +++ b/src/IKVM.Reflection/ArrayType.cs @@ -69,7 +69,7 @@ public override MethodBase[] __GetDeclaredMethods() list.Add(new BuiltinArrayMethod(Module, this, "Get", CallingConventions.Standard | CallingConventions.HasThis, elementType, int32)); list.Add(new ConstructorInfoImpl(new BuiltinArrayMethod(Module, this, ".ctor", CallingConventions.Standard | CallingConventions.HasThis, Module.Universe.System_Void, int32))); - for (var type = elementType; type.__IsVector; type = type.GetElementType()) + for (var type = elementType; type.IsSZArray; type = type.GetElementType()) { Array.Resize(ref int32, int32.Length + 1); int32[int32.Length - 1] = int32[0]; diff --git a/src/IKVM.Reflection/CustomAttributeData.cs b/src/IKVM.Reflection/CustomAttributeData.cs index 7ac1afeb9d..fa7754c622 100644 --- a/src/IKVM.Reflection/CustomAttributeData.cs +++ b/src/IKVM.Reflection/CustomAttributeData.cs @@ -435,11 +435,9 @@ static Type ReadType(Module context, ByteReader br) if (typeName == null) return null; + // there are broken compilers that emit an extra NUL character after the type name if (typeName.Length > 0 && typeName[typeName.Length - 1] == 0) - { - // there are broken compilers that emit an extra NUL character after the type name typeName = typeName.Substring(0, typeName.Length - 1); - } return TypeNameParser.Parse(typeName, true).GetType(context.Universe, context, true, typeName, true, false); } diff --git a/src/IKVM.Reflection/Emit/ModuleBuilder.cs b/src/IKVM.Reflection/Emit/ModuleBuilder.cs index d00b52c81b..2f540520e3 100644 --- a/src/IKVM.Reflection/Emit/ModuleBuilder.cs +++ b/src/IKVM.Reflection/Emit/ModuleBuilder.cs @@ -978,7 +978,7 @@ internal int ImportType(Type type) { if (typeTokens.TryGetValue(type, out var token) == false) { - if (type.HasElementType || type.IsConstructedGenericType || type.__IsFunctionPointer) + if (type.HasElementType || type.IsConstructedGenericType || type.IsFunctionPointer) { var spec = new ByteBuffer(5); Signature.WriteTypeSpec(this, spec, type); diff --git a/src/IKVM.Reflection/Signature.cs b/src/IKVM.Reflection/Signature.cs index 2af7852d29..7f1e3dd749 100644 --- a/src/IKVM.Reflection/Signature.cs +++ b/src/IKVM.Reflection/Signature.cs @@ -378,7 +378,7 @@ protected static void WriteType(ModuleBuilder module, ByteBuffer bb, Type type) { WriteGenericSignature(module, bb, type); } - else if (type.__IsFunctionPointer) + else if (type.IsFunctionPointer) { bb.Write(ELEMENT_TYPE_FNPTR); WriteStandAloneMethodSig(module, bb, type.__MethodSignature); diff --git a/src/IKVM.Reflection/Type.cs b/src/IKVM.Reflection/Type.cs index 839e48e33f..4d90961cf6 100644 --- a/src/IKVM.Reflection/Type.cs +++ b/src/IKVM.Reflection/Type.cs @@ -200,7 +200,7 @@ public bool IsArray get { return sigElementType == Signature.ELEMENT_TYPE_ARRAY || sigElementType == Signature.ELEMENT_TYPE_SZARRAY; } } - public bool __IsVector + public bool IsSZArray { get { return sigElementType == Signature.ELEMENT_TYPE_SZARRAY; } } @@ -215,11 +215,16 @@ public bool IsPointer get { return sigElementType == Signature.ELEMENT_TYPE_PTR; } } - public bool __IsFunctionPointer + public bool IsFunctionPointer { get { return sigElementType == Signature.ELEMENT_TYPE_FNPTR; } } + public bool IsUnmanagedFunctionPointer + { + get { throw new NotSupportedException(); } + } + public bool IsValueType { get @@ -1173,7 +1178,7 @@ internal byte SigElementType get { // this property can only be called after __IsBuiltIn, HasElementType, __IsFunctionPointer or IsGenericParameter returned true - System.Diagnostics.Debug.Assert((typeFlags & TypeFlags.BuiltIn) != 0 || HasElementType || __IsFunctionPointer || IsGenericParameter); + System.Diagnostics.Debug.Assert((typeFlags & TypeFlags.BuiltIn) != 0 || HasElementType || IsFunctionPointer || IsGenericParameter); return sigElementType; } } @@ -1642,7 +1647,7 @@ public bool IsAssignableFrom(Type type) { return false; } - else if (this.__IsVector && !type.__IsVector) + else if (this.IsSZArray && !type.IsSZArray) { return false; } diff --git a/src/IKVM.Runtime/Annotation.cs b/src/IKVM.Runtime/Annotation.cs index 5ceea4735a..9a53b8cb65 100644 --- a/src/IKVM.Runtime/Annotation.cs +++ b/src/IKVM.Runtime/Annotation.cs @@ -25,27 +25,15 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; - - +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; - -using System.Collections; -using System.Collections.Generic; - #else using System.Reflection; using System.Reflection.Emit; #endif -#if IMPORTER -using IKVM.Tools.Importer; -#endif - namespace IKVM.Runtime { @@ -119,49 +107,47 @@ internal static Annotation Load(RuntimeJavaType owner, object[] def) #endif - private static object LookupEnumValue(RuntimeContext context, Type enumType, string value) + static object LookupEnumValue(RuntimeContext context, ITypeSymbol enumType, string value) { - FieldInfo field = enumType.GetField(value, BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic); + var field = enumType.GetField(value, System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic); if (field != null) - { return field.GetRawConstantValue(); - } + // both __unspecified and missing values end up here - return EnumHelper.GetPrimitiveValue(context, EnumHelper.GetUnderlyingType(enumType), 0); + return EnumHelper.GetPrimitiveValue(context, enumType.GetEnumUnderlyingType(), 0); } - protected static object ConvertValue(RuntimeClassLoader loader, Type targetType, object obj) + protected static object ConvertValue(RuntimeClassLoader loader, ITypeSymbol targetType, object obj) { if (targetType.IsEnum) { // TODO check the obj descriptor matches the type we expect if (((object[])obj)[0].Equals(AnnotationDefaultAttribute.TAG_ARRAY)) { - object[] arr = (object[])obj; + var arr = (object[])obj; + object value = null; for (int i = 1; i < arr.Length; i++) { // TODO check the obj descriptor matches the type we expect - string s = ((object[])arr[i])[2].ToString(); - object newval = LookupEnumValue(loader.Context, targetType, s); + var s = ((object[])arr[i])[2].ToString(); + var newval = LookupEnumValue(loader.Context, targetType, s); if (value == null) - { value = newval; - } else - { value = EnumHelper.OrBoxedIntegrals(loader.Context, value, newval); - } } + return value; } else { - string s = ((object[])obj)[2].ToString(); + var s = ((object[])obj)[2].ToString(); if (s == "__unspecified") { // TODO we should probably return null and handle that } + return LookupEnumValue(loader.Context, targetType, s); } } @@ -173,13 +159,12 @@ protected static object ConvertValue(RuntimeClassLoader loader, Type targetType, else if (targetType.IsArray) { // TODO check the obj descriptor matches the type we expect - object[] arr = (object[])obj; - Type elementType = targetType.GetElementType(); - object[] targetArray = new object[arr.Length - 1]; + var arr = (object[])obj; + var elementType = targetType.GetElementType(); + var targetArray = new object[arr.Length - 1]; for (int i = 1; i < arr.Length; i++) - { targetArray[i - 1] = ConvertValue(loader, elementType, arr[i]); - } + return targetArray; } else diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index ea8b43babf..12e0e0bbc6 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -32,6 +32,7 @@ Jeroen Frijters using IKVM.ByteCode.Buffers; using IKVM.ByteCode.Decoding; using IKVM.ByteCode.Encoding; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -60,125 +61,125 @@ class AttributeHelper #if IMPORTER - CustomAttributeBuilder compilerGeneratedAttribute; - CustomAttributeBuilder ghostInterfaceAttribute; - CustomAttributeBuilder deprecatedAttribute; - CustomAttributeBuilder editorBrowsableNever; - ConstructorInfo implementsAttribute; - ConstructorInfo throwsAttribute; - ConstructorInfo sourceFileAttribute; - ConstructorInfo lineNumberTableAttribute1; - ConstructorInfo lineNumberTableAttribute2; - ConstructorInfo enclosingMethodAttribute; - ConstructorInfo signatureAttribute; - ConstructorInfo methodParametersAttribute; - ConstructorInfo runtimeVisibleTypeAnnotationsAttribute; - ConstructorInfo constantPoolAttribute; - CustomAttributeBuilder paramArrayAttribute; - ConstructorInfo nonNestedInnerClassAttribute; - ConstructorInfo nonNestedOuterClassAttribute; - - Type typeofModifiers; - Type typeofSourceFileAttribute; - Type typeofLineNumberTableAttribute; + CustomAttributeBuilder compilerGeneratedAttribute; + CustomAttributeBuilder ghostInterfaceAttribute; + CustomAttributeBuilder deprecatedAttribute; + CustomAttributeBuilder editorBrowsableNever; + IConstructorSymbol implementsAttribute; + IConstructorSymbol throwsAttribute; + IConstructorSymbol sourceFileAttribute; + IConstructorSymbol lineNumberTableAttribute1; + IConstructorSymbol lineNumberTableAttribute2; + IConstructorSymbol enclosingMethodAttribute; + IConstructorSymbol signatureAttribute; + IConstructorSymbol methodParametersAttribute; + IConstructorSymbol runtimeVisibleTypeAnnotationsAttribute; + IConstructorSymbol constantPoolAttribute; + CustomAttributeBuilder paramArrayAttribute; + IConstructorSymbol nonNestedInnerClassAttribute; + IConstructorSymbol nonNestedOuterClassAttribute; + + ITypeSymbol typeofModifiers; + ITypeSymbol typeofSourceFileAttribute; + ITypeSymbol typeofLineNumberTableAttribute; #endif - Type typeofRemappedClassAttribute; - Type typeofRemappedTypeAttribute; - Type typeofModifiersAttribute; - Type typeofRemappedInterfaceMethodAttribute; - Type typeofNameSigAttribute; - Type typeofJavaModuleAttribute; - Type typeofSignatureAttribute; - Type typeofInnerClassAttribute; - Type typeofImplementsAttribute; - Type typeofGhostInterfaceAttribute; - Type typeofExceptionIsUnsafeForMappingAttribute; - Type typeofThrowsAttribute; - Type typeofHideFromJavaAttribute; - Type typeofHideFromJavaFlags; - Type typeofNoPackagePrefixAttribute; - Type typeofAnnotationAttributeAttribute; - Type typeofNonNestedInnerClassAttribute; - Type typeofNonNestedOuterClassAttribute; - Type typeofEnclosingMethodAttribute; - Type typeofMethodParametersAttribute; - Type typeofRuntimeVisibleTypeAnnotationsAttribute; - Type typeofConstantPoolAttribute; - Type typeofDebuggableAttribute; + ITypeSymbol typeofRemappedClassAttribute; + ITypeSymbol typeofRemappedTypeAttribute; + ITypeSymbol typeofModifiersAttribute; + ITypeSymbol typeofRemappedInterfaceMethodAttribute; + ITypeSymbol typeofNameSigAttribute; + ITypeSymbol typeofJavaModuleAttribute; + ITypeSymbol typeofSignatureAttribute; + ITypeSymbol typeofInnerClassAttribute; + ITypeSymbol typeofImplementsAttribute; + ITypeSymbol typeofGhostInterfaceAttribute; + ITypeSymbol typeofExceptionIsUnsafeForMappingAttribute; + ITypeSymbol typeofThrowsAttribute; + ITypeSymbol typeofHideFromJavaAttribute; + ITypeSymbol typeofHideFromJavaFlags; + ITypeSymbol typeofNoPackagePrefixAttribute; + ITypeSymbol typeofAnnotationAttributeAttribute; + ITypeSymbol typeofNonNestedInnerClassAttribute; + ITypeSymbol typeofNonNestedOuterClassAttribute; + ITypeSymbol typeofEnclosingMethodAttribute; + ITypeSymbol typeofMethodParametersAttribute; + ITypeSymbol typeofRuntimeVisibleTypeAnnotationsAttribute; + ITypeSymbol typeofConstantPoolAttribute; + ITypeSymbol typeofDebuggableAttribute; CustomAttributeBuilder hideFromJavaAttribute; CustomAttributeBuilder hideFromReflection; - ConstructorInfo debuggableAttribute; + IConstructorSymbol debuggableAttribute; #if IMPORTER - Type TypeOfModifiers => typeofModifiers ??= LoadType(typeof(Modifiers)); + ITypeSymbol TypeOfModifiers => typeofModifiers ??= LoadType(typeof(Modifiers)); - Type TypeOfSourceFileAttribute => typeofSourceFileAttribute ??= LoadType(typeof(IKVM.Attributes.SourceFileAttribute)); + ITypeSymbol TypeOfSourceFileAttribute => typeofSourceFileAttribute ??= LoadType(typeof(IKVM.Attributes.SourceFileAttribute)); - Type TypeOfLineNumberTableAttribute => typeofLineNumberTableAttribute ??= LoadType(typeof(IKVM.Attributes.LineNumberTableAttribute)); + ITypeSymbol TypeOfLineNumberTableAttribute => typeofLineNumberTableAttribute ??= LoadType(typeof(IKVM.Attributes.LineNumberTableAttribute)); #endif - Type TypeOfRemappedClassAttribute => typeofRemappedClassAttribute ??= LoadType(typeof(RemappedClassAttribute)); + ITypeSymbol TypeOfRemappedClassAttribute => typeofRemappedClassAttribute ??= LoadType(typeof(RemappedClassAttribute)); - Type TypeOfRemappedTypeAttribute => typeofRemappedTypeAttribute ??= LoadType(typeof(RemappedTypeAttribute)); + ITypeSymbol TypeOfRemappedTypeAttribute => typeofRemappedTypeAttribute ??= LoadType(typeof(RemappedTypeAttribute)); - Type TypeOfModifiersAttribute => typeofModifiersAttribute ??= LoadType(typeof(ModifiersAttribute)); + ITypeSymbol TypeOfModifiersAttribute => typeofModifiersAttribute ??= LoadType(typeof(ModifiersAttribute)); - Type TypeOfRemappedInterfaceMethodAttribute => typeofRemappedInterfaceMethodAttribute ??= LoadType(typeof(RemappedInterfaceMethodAttribute)); + ITypeSymbol TypeOfRemappedInterfaceMethodAttribute => typeofRemappedInterfaceMethodAttribute ??= LoadType(typeof(RemappedInterfaceMethodAttribute)); - Type TypeOfNameSigAttribute => typeofNameSigAttribute ??= LoadType(typeof(NameSigAttribute)); + ITypeSymbol TypeOfNameSigAttribute => typeofNameSigAttribute ??= LoadType(typeof(NameSigAttribute)); - Type TypeOfJavaModuleAttribute => typeofJavaModuleAttribute ??= LoadType(typeof(JavaModuleAttribute)); + ITypeSymbol TypeOfJavaModuleAttribute => typeofJavaModuleAttribute ??= LoadType(typeof(JavaModuleAttribute)); - Type TypeOfSignatureAttribute => typeofSignatureAttribute ??= LoadType(typeof(IKVM.Attributes.SignatureAttribute)); + ITypeSymbol TypeOfSignatureAttribute => typeofSignatureAttribute ??= LoadType(typeof(IKVM.Attributes.SignatureAttribute)); - Type TypeOfInnerClassAttribute => typeofInnerClassAttribute ??= LoadType(typeof(InnerClassAttribute)); + ITypeSymbol TypeOfInnerClassAttribute => typeofInnerClassAttribute ??= LoadType(typeof(InnerClassAttribute)); - Type TypeOfImplementsAttribute => typeofImplementsAttribute ??= LoadType(typeof(ImplementsAttribute)); + ITypeSymbol TypeOfImplementsAttribute => typeofImplementsAttribute ??= LoadType(typeof(ImplementsAttribute)); - Type TypeOfGhostInterfaceAttribute => typeofGhostInterfaceAttribute ??= LoadType(typeof(GhostInterfaceAttribute)); + ITypeSymbol TypeOfGhostInterfaceAttribute => typeofGhostInterfaceAttribute ??= LoadType(typeof(GhostInterfaceAttribute)); - Type TypeOfExceptionIsUnsafeForMappingAttribute => typeofExceptionIsUnsafeForMappingAttribute ??= LoadType(typeof(ExceptionIsUnsafeForMappingAttribute)); + ITypeSymbol TypeOfExceptionIsUnsafeForMappingAttribute => typeofExceptionIsUnsafeForMappingAttribute ??= LoadType(typeof(ExceptionIsUnsafeForMappingAttribute)); - Type TypeOfThrowsAttribute => typeofThrowsAttribute ??= LoadType(typeof(ThrowsAttribute)); + ITypeSymbol TypeOfThrowsAttribute => typeofThrowsAttribute ??= LoadType(typeof(ThrowsAttribute)); - Type TypeOfHideFromJavaAttribute => typeofHideFromJavaAttribute ??= LoadType(typeof(HideFromJavaAttribute)); + ITypeSymbol TypeOfHideFromJavaAttribute => typeofHideFromJavaAttribute ??= LoadType(typeof(HideFromJavaAttribute)); - Type TypeOfHideFromJavaFlags => typeofHideFromJavaFlags ??= LoadType(typeof(HideFromJavaFlags)); + ITypeSymbol TypeOfHideFromJavaFlags => typeofHideFromJavaFlags ??= LoadType(typeof(HideFromJavaFlags)); - Type TypeOfNoPackagePrefixAttribute => typeofNoPackagePrefixAttribute ??= LoadType(typeof(NoPackagePrefixAttribute)); + ITypeSymbol TypeOfNoPackagePrefixAttribute => typeofNoPackagePrefixAttribute ??= LoadType(typeof(NoPackagePrefixAttribute)); - Type TypeOfAnnotationAttributeAttribute => typeofAnnotationAttributeAttribute ??= LoadType(typeof(AnnotationAttributeAttribute)); + ITypeSymbol TypeOfAnnotationAttributeAttribute => typeofAnnotationAttributeAttribute ??= LoadType(typeof(AnnotationAttributeAttribute)); - Type TypeOfNonNestedInnerClassAttribute => typeofNonNestedInnerClassAttribute ??= LoadType(typeof(NonNestedInnerClassAttribute)); + ITypeSymbol TypeOfNonNestedInnerClassAttribute => typeofNonNestedInnerClassAttribute ??= LoadType(typeof(NonNestedInnerClassAttribute)); - Type TypeOfNonNestedOuterClassAttribute => typeofNonNestedOuterClassAttribute ??= LoadType(typeof(NonNestedOuterClassAttribute)); + ITypeSymbol TypeOfNonNestedOuterClassAttribute => typeofNonNestedOuterClassAttribute ??= LoadType(typeof(NonNestedOuterClassAttribute)); - Type TypeOfEnclosingMethodAttribute => typeofEnclosingMethodAttribute ??= LoadType(typeof(IKVM.Attributes.EnclosingMethodAttribute)); + ITypeSymbol TypeOfEnclosingMethodAttribute => typeofEnclosingMethodAttribute ??= LoadType(typeof(IKVM.Attributes.EnclosingMethodAttribute)); - Type TypeOfMethodParametersAttribute => typeofMethodParametersAttribute ??= LoadType(typeof(IKVM.Attributes.MethodParametersAttribute)); + ITypeSymbol TypeOfMethodParametersAttribute => typeofMethodParametersAttribute ??= LoadType(typeof(IKVM.Attributes.MethodParametersAttribute)); - Type TypeOfRuntimeVisibleTypeAnnotationsAttribute => typeofRuntimeVisibleTypeAnnotationsAttribute ??= LoadType(typeof(IKVM.Attributes.RuntimeVisibleTypeAnnotationsAttribute)); + ITypeSymbol TypeOfRuntimeVisibleTypeAnnotationsAttribute => typeofRuntimeVisibleTypeAnnotationsAttribute ??= LoadType(typeof(IKVM.Attributes.RuntimeVisibleTypeAnnotationsAttribute)); - Type TypeOfConstantPoolAttribute => typeofConstantPoolAttribute ??= LoadType(typeof(ConstantPoolAttribute)); + ITypeSymbol TypeOfConstantPoolAttribute => typeofConstantPoolAttribute ??= LoadType(typeof(ConstantPoolAttribute)); - Type TypeOfDebuggableAttribute => typeofDebuggableAttribute ??= context.Resolver.ResolveCoreType(typeof(DebuggableAttribute).FullName).AsReflection(); + ITypeSymbol TypeOfDebuggableAttribute => typeofDebuggableAttribute ??= context.Resolver.ResolveCoreType(typeof(DebuggableAttribute).FullName); - CustomAttributeBuilder HideFromJavaAttributeBuilder => hideFromJavaAttribute ??= new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor(Type.EmptyTypes), Array.Empty()); + CustomAttributeBuilder HideFromJavaAttributeBuilder => hideFromJavaAttribute ??= new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor([]).AsReflection(), []); - CustomAttributeBuilder HideFromReflectionBuilder => hideFromReflection ??= new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor(new[] { TypeOfHideFromJavaFlags }), new object[] { HideFromJavaFlags.Reflection | HideFromJavaFlags.StackTrace | HideFromJavaFlags.StackWalk }); + CustomAttributeBuilder HideFromReflectionBuilder => hideFromReflection ??= new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]).AsReflection(), [HideFromJavaFlags.Reflection | HideFromJavaFlags.StackTrace | HideFromJavaFlags.StackWalk]); /// /// Loads the given managed type from the runtime assembly. /// /// /// - Type LoadType(System.Type t) + ITypeSymbol LoadType(System.Type t) { - return context.Resolver.ResolveRuntimeType(t.FullName).AsReflection(); + return context.Resolver.ResolveRuntimeType(t.FullName); } /// @@ -192,314 +193,302 @@ public AttributeHelper(RuntimeContext context) #if IMPORTER - object ParseValue(RuntimeClassLoader loader, RuntimeJavaType tw, string val) - { - if (tw == context.JavaBase.TypeOfJavaLangString) - { - return val; - } - else if (tw.IsUnloadable) - { - throw new FatalCompilerErrorException(DiagnosticEvent.MapFileTypeNotFound(tw.Name)); - } - else if (tw.TypeAsTBD.IsEnum) - { - return EnumHelper.Parse(context, tw.TypeAsTBD, val); - } - else if (tw.TypeAsTBD == context.Types.Type) - { - var valtw = loader.TryLoadClassByName(val); - if (valtw != null) - return valtw.TypeAsBaseType; - - return context.StaticCompiler.Universe.GetType(val, true); - } - else if (tw == context.PrimitiveJavaTypeFactory.BOOLEAN) - { - return bool.Parse(val); - } - else if (tw == context.PrimitiveJavaTypeFactory.BYTE) - { - return (byte)sbyte.Parse(val); - } - else if (tw == context.PrimitiveJavaTypeFactory.CHAR) - { - return char.Parse(val); - } - else if (tw == context.PrimitiveJavaTypeFactory.SHORT) - { - return short.Parse(val); - } - else if (tw == context.PrimitiveJavaTypeFactory.INT) - { - return int.Parse(val); - } - else if (tw == context.PrimitiveJavaTypeFactory.FLOAT) - { - return float.Parse(val); - } - else if (tw == context.PrimitiveJavaTypeFactory.LONG) - { - return long.Parse(val); - } - else if (tw == context.PrimitiveJavaTypeFactory.DOUBLE) - { - return double.Parse(val); - } - else - { - throw new NotImplementedException(); - } - } - - internal void SetCustomAttribute(RuntimeClassLoader loader, TypeBuilder tb, IKVM.Tools.Importer.MapXml.Attribute attr) - { - tb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); - } - - internal void SetCustomAttribute(RuntimeClassLoader loader, FieldBuilder fb, IKVM.Tools.Importer.MapXml.Attribute attr) - { - fb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); - } - - internal void SetCustomAttribute(RuntimeClassLoader loader, ParameterBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) - { - pb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); - } - - internal void SetCustomAttribute(RuntimeClassLoader loader, MethodBuilder mb, IKVM.Tools.Importer.MapXml.Attribute attr) - { - mb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); - } - - internal void SetCustomAttribute(RuntimeClassLoader loader, PropertyBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) - { - pb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); - } - - internal void SetCustomAttribute(RuntimeClassLoader loader, AssemblyBuilder ab, IKVM.Tools.Importer.MapXml.Attribute attr) - { - ab.SetCustomAttribute(CreateCustomAttribute(loader, attr)); - } - - void GetAttributeArgsAndTypes(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr, out Type[] argTypes, out object[] args) - { - // TODO add error handling - var twargs = loader.ArgJavaTypeListFromSig(attr.Sig, LoadMode.Link); - argTypes = new Type[twargs.Length]; - args = new object[argTypes.Length]; - for (int i = 0; i < twargs.Length; i++) - { - argTypes[i] = twargs[i].TypeAsSignatureType; - RuntimeJavaType tw = twargs[i]; - if (tw == context.JavaBase.TypeOfJavaLangObject) - { - tw = loader.FieldTypeWrapperFromSig(attr.Params[i].Sig, LoadMode.Link); - } - if (tw.IsArray) - { - Array arr = Array.CreateInstance(Type.__GetSystemType(Type.GetTypeCode(tw.ElementTypeWrapper.TypeAsArrayType)), attr.Params[i].Elements.Length); - for (int j = 0; j < arr.Length; j++) - { - arr.SetValue(ParseValue(loader, tw.ElementTypeWrapper, attr.Params[i].Elements[j].Value), j); - } - args[i] = arr; - } - else - { - args[i] = ParseValue(loader, tw, attr.Params[i].Value); - } - } - } - - CustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr) - { - // TODO add error handling - Type[] argTypes; - object[] args; - GetAttributeArgsAndTypes(loader, attr, out argTypes, out args); - if (attr.Type != null) - { - var t = context.Resolver.ResolveCoreType(attr.Type).AsReflection(); - var ci = t.GetConstructor(argTypes); - if (ci == null) - throw new InvalidOperationException($"Constructor missing: {attr.Type}::{attr.Sig}"); - - PropertyInfo[] namedProperties; - object[] propertyValues; - if (attr.Properties != null) - { - namedProperties = new PropertyInfo[attr.Properties.Length]; - propertyValues = new object[attr.Properties.Length]; - for (int i = 0; i < namedProperties.Length; i++) - { - namedProperties[i] = t.GetProperty(attr.Properties[i].Name); - propertyValues[i] = ParseValue(loader, loader.FieldTypeWrapperFromSig(attr.Properties[i].Sig, LoadMode.Link), attr.Properties[i].Value); - } - } - else - { - namedProperties = new PropertyInfo[0]; - propertyValues = new object[0]; - } - FieldInfo[] namedFields; - object[] fieldValues; - if (attr.Fields != null) - { - namedFields = new FieldInfo[attr.Fields.Length]; - fieldValues = new object[attr.Fields.Length]; - for (int i = 0; i < namedFields.Length; i++) - { - namedFields[i] = t.GetField(attr.Fields[i].Name); - fieldValues[i] = ParseValue(loader, loader.FieldTypeWrapperFromSig(attr.Fields[i].Sig, LoadMode.Link), attr.Fields[i].Value); - } - } - else - { - namedFields = new FieldInfo[0]; - fieldValues = new object[0]; - } - return new CustomAttributeBuilder(ci, args, namedProperties, propertyValues, namedFields, fieldValues); - } - else - { - if (attr.Properties != null) - { - throw new NotImplementedException("Setting property values on Java attributes is not implemented"); - } - RuntimeJavaType t = loader.LoadClassByName(attr.Class); - FieldInfo[] namedFields; - object[] fieldValues; - if (attr.Fields != null) - { - namedFields = new FieldInfo[attr.Fields.Length]; - fieldValues = new object[attr.Fields.Length]; - for (int i = 0; i < namedFields.Length; i++) - { - RuntimeJavaField fw = t.GetFieldWrapper(attr.Fields[i].Name, attr.Fields[i].Sig); - fw.Link(); - namedFields[i] = fw.GetField(); - fieldValues[i] = ParseValue(loader, loader.FieldTypeWrapperFromSig(attr.Fields[i].Sig, LoadMode.Link), attr.Fields[i].Value); - } - } - else - { - namedFields = new FieldInfo[0]; - fieldValues = new object[0]; - } - var mw = t.GetMethodWrapper("", attr.Sig, false); - if (mw == null) - { - throw new InvalidOperationException(string.Format("Constructor missing: {0}::{1}", attr.Class, attr.Sig)); - } - mw.Link(); - ConstructorInfo ci = (mw.GetMethod() as ConstructorInfo) ?? ((MethodInfo)mw.GetMethod()).__AsConstructorInfo(); - return new CustomAttributeBuilder(ci, args, namedFields, fieldValues); - } - } - - CustomAttributeBuilder GetEditorBrowsableNever() - { - if (editorBrowsableNever == null) - { - var typeofEditorBrowsableAttribute = context.Resolver.ResolveCoreType(typeof(EditorBrowsableAttribute).FullName).AsReflection(); - var typeofEditorBrowsableState = context.Resolver.ResolveCoreType(typeof(EditorBrowsableState).FullName).AsReflection(); - var ctor = (ConstructorInfo)typeofEditorBrowsableAttribute.__CreateMissingMethod(ConstructorInfo.ConstructorName, CallingConventions.Standard | CallingConventions.HasThis, null, default, new Type[] { typeofEditorBrowsableState }, null); - editorBrowsableNever = CustomAttributeBuilder.__FromBlob(ctor, new byte[] { 01, 00, 01, 00, 00, 00, 00, 00 }); - } - - return editorBrowsableNever; - } - - internal void SetCompilerGenerated(TypeBuilder tb) - { - compilerGeneratedAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).AsReflection().GetConstructor(Type.EmptyTypes), Array.Empty()); - tb.SetCustomAttribute(compilerGeneratedAttribute); - } - - internal void SetCompilerGenerated(MethodBuilder mb) - { - compilerGeneratedAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).AsReflection().GetConstructor(Type.EmptyTypes), Array.Empty()); - mb.SetCustomAttribute(compilerGeneratedAttribute); - } - - internal void SetEditorBrowsableNever(TypeBuilder tb) - { - tb.SetCustomAttribute(GetEditorBrowsableNever()); - } - - internal void SetEditorBrowsableNever(MethodBuilder mb) - { - mb.SetCustomAttribute(GetEditorBrowsableNever()); - } - - internal void SetEditorBrowsableNever(PropertyBuilder pb) - { - pb.SetCustomAttribute(GetEditorBrowsableNever()); - } - - internal void SetDeprecatedAttribute(MethodBuilder mb) - { - if (deprecatedAttribute == null) - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); - - mb.SetCustomAttribute(deprecatedAttribute); - } - - internal void SetDeprecatedAttribute(TypeBuilder tb) - { - if (deprecatedAttribute == null) - { - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); - } - - tb.SetCustomAttribute(deprecatedAttribute); - } - - internal void SetDeprecatedAttribute(FieldBuilder fb) - { - if (deprecatedAttribute == null) - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), new object[0]); - - fb.SetCustomAttribute(deprecatedAttribute); - } - - internal void SetDeprecatedAttribute(PropertyBuilder pb) - { - if (deprecatedAttribute == null) - { - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), new object[0]); - } - pb.SetCustomAttribute(deprecatedAttribute); - } - - internal void SetThrowsAttribute(MethodBuilder mb, string[] exceptions) - { - if (exceptions != null && exceptions.Length != 0) - { - throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor(new Type[] { context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType().AsReflection() }); - exceptions = UnicodeUtil.EscapeInvalidSurrogates(exceptions); - mb.SetCustomAttribute(new CustomAttributeBuilder(throwsAttribute, new object[] { exceptions })); - } - } - - internal void SetGhostInterface(TypeBuilder typeBuilder) - { - ghostInterfaceAttribute ??= new CustomAttributeBuilder(TypeOfGhostInterfaceAttribute.GetConstructor(Type.EmptyTypes), new object[0]); - typeBuilder.SetCustomAttribute(ghostInterfaceAttribute); - } - - internal void SetNonNestedInnerClass(TypeBuilder typeBuilder, string className) - { - nonNestedInnerClassAttribute ??= TypeOfNonNestedInnerClassAttribute.GetConstructor(new Type[] { context.Types.String }); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(nonNestedInnerClassAttribute, new object[] { UnicodeUtil.EscapeInvalidSurrogates(className) })); - } - - internal void SetNonNestedOuterClass(TypeBuilder typeBuilder, string className) - { - nonNestedOuterClassAttribute ??= TypeOfNonNestedOuterClassAttribute.GetConstructor(new Type[] { context.Types.String }); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(nonNestedOuterClassAttribute, new object[] { UnicodeUtil.EscapeInvalidSurrogates(className) })); - } + object ParseValue(RuntimeClassLoader loader, RuntimeJavaType tw, string val) + { + if (tw == context.JavaBase.TypeOfJavaLangString) + { + return val; + } + else if (tw.IsUnloadable) + { + throw new FatalCompilerErrorException(DiagnosticEvent.MapFileTypeNotFound(tw.Name)); + } + else if (tw.TypeAsTBD.IsEnum) + { + return EnumHelper.Parse(context, tw.TypeAsTBD, val); + } + else if (tw.TypeAsTBD == context.Types.Type) + { + var valtw = loader.TryLoadClassByName(val); + if (valtw != null) + return valtw.TypeAsBaseType; + + return context.StaticCompiler.Universe.GetType(val, true); + } + else if (tw == context.PrimitiveJavaTypeFactory.BOOLEAN) + { + return bool.Parse(val); + } + else if (tw == context.PrimitiveJavaTypeFactory.BYTE) + { + return (byte)sbyte.Parse(val); + } + else if (tw == context.PrimitiveJavaTypeFactory.CHAR) + { + return char.Parse(val); + } + else if (tw == context.PrimitiveJavaTypeFactory.SHORT) + { + return short.Parse(val); + } + else if (tw == context.PrimitiveJavaTypeFactory.INT) + { + return int.Parse(val); + } + else if (tw == context.PrimitiveJavaTypeFactory.FLOAT) + { + return float.Parse(val); + } + else if (tw == context.PrimitiveJavaTypeFactory.LONG) + { + return long.Parse(val); + } + else if (tw == context.PrimitiveJavaTypeFactory.DOUBLE) + { + return double.Parse(val); + } + else + { + throw new NotImplementedException(); + } + } + + internal void SetCustomAttribute(RuntimeClassLoader loader, TypeBuilder tb, IKVM.Tools.Importer.MapXml.Attribute attr) + { + tb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); + } + + internal void SetCustomAttribute(RuntimeClassLoader loader, FieldBuilder fb, IKVM.Tools.Importer.MapXml.Attribute attr) + { + fb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); + } + + internal void SetCustomAttribute(RuntimeClassLoader loader, ParameterBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) + { + pb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); + } + + internal void SetCustomAttribute(RuntimeClassLoader loader, MethodBuilder mb, IKVM.Tools.Importer.MapXml.Attribute attr) + { + mb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); + } + + internal void SetCustomAttribute(RuntimeClassLoader loader, PropertyBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) + { + pb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); + } + + internal void SetCustomAttribute(RuntimeClassLoader loader, AssemblyBuilder ab, IKVM.Tools.Importer.MapXml.Attribute attr) + { + ab.SetCustomAttribute(CreateCustomAttribute(loader, attr)); + } + + void GetAttributeArgsAndTypes(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr, out ITypeSymbol[] argTypes, out object[] args) + { + // TODO add error handling + var twargs = loader.ArgJavaTypeListFromSig(attr.Sig, LoadMode.Link); + argTypes = new ITypeSymbol[twargs.Length]; + args = new object[argTypes.Length]; + for (int i = 0; i < twargs.Length; i++) + { + argTypes[i] = twargs[i].TypeAsSignatureType; + + var tw = twargs[i]; + if (tw == context.JavaBase.TypeOfJavaLangObject) + tw = loader.FieldTypeWrapperFromSig(attr.Params[i].Sig, LoadMode.Link); + + if (tw.IsArray) + { + var arr = Array.CreateInstance(Type.__GetSystemType(tw.ElementTypeWrapper.TypeAsArrayType.TypeCode), attr.Params[i].Elements.Length); + for (int j = 0; j < arr.Length; j++) + arr.SetValue(ParseValue(loader, tw.ElementTypeWrapper, attr.Params[i].Elements[j].Value), j); + + args[i] = arr; + } + else + { + args[i] = ParseValue(loader, tw, attr.Params[i].Value); + } + } + } + + CustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr) + { + // TODO add error handling + GetAttributeArgsAndTypes(loader, attr, out var argTypes, out var args); + if (attr.Type != null) + { + var t = context.Resolver.ResolveCoreType(attr.Type); + var ci = t.GetConstructor(argTypes); + if (ci == null) + throw new InvalidOperationException($"Constructor missing: {attr.Type}::{attr.Sig}"); + + IPropertySymbol[] namedProperties = []; + object[] propertyValues = []; + + if (attr.Properties != null) + { + namedProperties = new IPropertySymbol[attr.Properties.Length]; + propertyValues = new object[attr.Properties.Length]; + for (int i = 0; i < namedProperties.Length; i++) + { + namedProperties[i] = t.GetProperty(attr.Properties[i].Name); + propertyValues[i] = ParseValue(loader, loader.FieldTypeWrapperFromSig(attr.Properties[i].Sig, LoadMode.Link), attr.Properties[i].Value); + } + } + + IFieldSymbol[] namedFields = []; + object[] fieldValues = []; + + if (attr.Fields != null) + { + namedFields = new IFieldSymbol[attr.Fields.Length]; + fieldValues = new object[attr.Fields.Length]; + for (int i = 0; i < namedFields.Length; i++) + { + namedFields[i] = t.GetField(attr.Fields[i].Name); + fieldValues[i] = ParseValue(loader, loader.FieldTypeWrapperFromSig(attr.Fields[i].Sig, LoadMode.Link), attr.Fields[i].Value); + } + } + + return new CustomAttributeBuilder(ci.AsReflection(), args, namedProperties.AsReflection(), propertyValues, namedFields.AsReflection(), fieldValues); + } + else + { + if (attr.Properties != null) + throw new NotImplementedException("Setting property values on Java attributes is not implemented"); + + var t = loader.LoadClassByName(attr.Class); + + IFieldSymbol[] namedFields = []; + object[] fieldValues = []; + + if (attr.Fields != null) + { + namedFields = new IFieldSymbol[attr.Fields.Length]; + fieldValues = new object[attr.Fields.Length]; + for (int i = 0; i < namedFields.Length; i++) + { + var fw = t.GetFieldWrapper(attr.Fields[i].Name, attr.Fields[i].Sig); + fw.Link(); + namedFields[i] = fw.GetField(); + fieldValues[i] = ParseValue(loader, loader.FieldTypeWrapperFromSig(attr.Fields[i].Sig, LoadMode.Link), attr.Fields[i].Value); + } + } + + var mw = t.GetMethodWrapper("", attr.Sig, false); + if (mw == null) + throw new InvalidOperationException(string.Format("Constructor missing: {0}::{1}", attr.Class, attr.Sig)); + + mw.Link(); + + var ci = (mw.GetMethod() as IConstructorSymbol) ?? ((IConstructorSymbol)mw.GetMethod()); + return new CustomAttributeBuilder(ci.AsReflection(), args, namedFields.AsReflection(), fieldValues); + } + } + + CustomAttributeBuilder GetEditorBrowsableNever() + { + if (editorBrowsableNever == null) + { + var typeofEditorBrowsableAttribute = context.Resolver.ResolveCoreType(typeof(EditorBrowsableAttribute).FullName).AsReflection(); + var typeofEditorBrowsableState = context.Resolver.ResolveCoreType(typeof(EditorBrowsableState).FullName).AsReflection(); + var ctor = (ConstructorInfo)typeofEditorBrowsableAttribute.__CreateMissingMethod(ConstructorInfo.ConstructorName, CallingConventions.Standard | CallingConventions.HasThis, null, default, new Type[] { typeofEditorBrowsableState }, null); + editorBrowsableNever = CustomAttributeBuilder.__FromBlob(ctor, new byte[] { 01, 00, 01, 00, 00, 00, 00, 00 }); + } + + return editorBrowsableNever; + } + + internal void SetCompilerGenerated(TypeBuilder tb) + { + compilerGeneratedAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).AsReflection().GetConstructor([]), Array.Empty()); + tb.SetCustomAttribute(compilerGeneratedAttribute); + } + + internal void SetCompilerGenerated(MethodBuilder mb) + { + compilerGeneratedAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).AsReflection().GetConstructor([]), Array.Empty()); + mb.SetCustomAttribute(compilerGeneratedAttribute); + } + + internal void SetEditorBrowsableNever(TypeBuilder tb) + { + tb.SetCustomAttribute(GetEditorBrowsableNever()); + } + + internal void SetEditorBrowsableNever(MethodBuilder mb) + { + mb.SetCustomAttribute(GetEditorBrowsableNever()); + } + + internal void SetEditorBrowsableNever(PropertyBuilder pb) + { + pb.SetCustomAttribute(GetEditorBrowsableNever()); + } + + internal void SetDeprecatedAttribute(MethodBuilder mb) + { + if (deprecatedAttribute == null) + deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); + + mb.SetCustomAttribute(deprecatedAttribute); + } + + internal void SetDeprecatedAttribute(TypeBuilder tb) + { + if (deprecatedAttribute == null) + { + deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); + } + + tb.SetCustomAttribute(deprecatedAttribute); + } + + internal void SetDeprecatedAttribute(FieldBuilder fb) + { + if (deprecatedAttribute == null) + deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); + + fb.SetCustomAttribute(deprecatedAttribute); + } + + internal void SetDeprecatedAttribute(PropertyBuilder pb) + { + if (deprecatedAttribute == null) + { + deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); + } + pb.SetCustomAttribute(deprecatedAttribute); + } + + internal void SetThrowsAttribute(MethodBuilder mb, string[] exceptions) + { + if (exceptions != null && exceptions.Length != 0) + { + throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); + exceptions = UnicodeUtil.EscapeInvalidSurrogates(exceptions); + mb.SetCustomAttribute(new CustomAttributeBuilder(throwsAttribute.AsReflection(), [exceptions])); + } + } + + internal void SetGhostInterface(TypeBuilder typeBuilder) + { + ghostInterfaceAttribute ??= new CustomAttributeBuilder(TypeOfGhostInterfaceAttribute.GetConstructor([]).AsReflection(), []); + typeBuilder.SetCustomAttribute(ghostInterfaceAttribute); + } + + internal void SetNonNestedInnerClass(TypeBuilder typeBuilder, string className) + { + nonNestedInnerClassAttribute ??= TypeOfNonNestedInnerClassAttribute.GetConstructor([context.Types.String]); + typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(nonNestedInnerClassAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(className)])); + } + + internal void SetNonNestedOuterClass(TypeBuilder typeBuilder, string className) + { + nonNestedOuterClassAttribute ??= TypeOfNonNestedOuterClassAttribute.GetConstructor([context.Types.String]); + typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(nonNestedOuterClassAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(className)])); + } #endif // IMPORTER @@ -530,8 +519,7 @@ internal void HideFromJava(MethodBuilder mb) internal void HideFromJava(MethodBuilder mb, HideFromJavaFlags flags) { - CustomAttributeBuilder cab = new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor(new Type[] { TypeOfHideFromJavaFlags }), new object[] { flags }); - mb.SetCustomAttribute(cab); + mb.SetCustomAttribute(new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]).AsReflection(), [flags])); } internal void HideFromJava(FieldBuilder fb) @@ -541,24 +529,24 @@ internal void HideFromJava(FieldBuilder fb) #if IMPORTER - internal void HideFromJava(PropertyBuilder pb) - { - pb.SetCustomAttribute(HideFromJavaAttributeBuilder); - } + internal void HideFromJava(PropertyBuilder pb) + { + pb.SetCustomAttribute(HideFromJavaAttributeBuilder); + } #endif - internal bool IsHideFromJava(Type type) + internal bool IsHideFromJava(ITypeSymbol type) { return type.IsDefined(TypeOfHideFromJavaAttribute, false) || (type.IsNested && (type.DeclaringType.IsDefined(TypeOfHideFromJavaAttribute, false) || type.Name.StartsWith("__<", StringComparison.Ordinal))); } - internal bool IsHideFromJava(MemberInfo mi) + internal bool IsHideFromJava(IMemberSymbol mi) { return (GetHideFromJavaFlags(mi) & HideFromJavaFlags.Code) != 0; } - internal HideFromJavaFlags GetHideFromJavaFlags(MemberInfo mi) + internal HideFromJavaFlags GetHideFromJavaFlags(IMemberSymbol mi) { // NOTE all privatescope fields and methods are "hideFromJava" // because Java cannot deal with the potential name clashes @@ -572,79 +560,66 @@ internal HideFromJavaFlags GetHideFromJavaFlags(MemberInfo mi) if (mi.Name.StartsWith("__<", StringComparison.Ordinal)) return HideFromJavaFlags.All; -#if !IMPORTER && !EXPORTER - - var attr = mi.GetCustomAttributes(typeofHideFromJavaAttribute, false); + var attr = mi.GetCustomAttributes(TypeOfHideFromJavaAttribute); if (attr.Length == 1) - return ((HideFromJavaAttribute)attr[0]).Flags; + { + var args = attr[0].ConstructorArguments; + if (args.Length == 1) + return (HideFromJavaFlags)args[0].Value; -#else - var attr = CustomAttributeData.__GetCustomAttributes(mi, TypeOfHideFromJavaAttribute, false); - if (attr.Count == 1) - { - var args = attr[0].ConstructorArguments; - if (args.Count == 1) - return (HideFromJavaFlags)args[0].Value; - - return HideFromJavaFlags.All; - } -#endif + return HideFromJavaFlags.All; + } return HideFromJavaFlags.None; } #if IMPORTER - internal void SetImplementsAttribute(TypeBuilder typeBuilder, RuntimeJavaType[] ifaceWrappers) - { - var interfaces = new string[ifaceWrappers.Length]; - for (int i = 0; i < interfaces.Length; i++) - interfaces[i] = UnicodeUtil.EscapeInvalidSurrogates(ifaceWrappers[i].Name); + internal void SetImplementsAttribute(TypeBuilder typeBuilder, RuntimeJavaType[] ifaceWrappers) + { + var interfaces = new string[ifaceWrappers.Length]; + for (int i = 0; i < interfaces.Length; i++) + interfaces[i] = UnicodeUtil.EscapeInvalidSurrogates(ifaceWrappers[i].Name); - if (implementsAttribute == null) - implementsAttribute = TypeOfImplementsAttribute.GetConstructor(new Type[] { context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType().AsReflection() }); + if (implementsAttribute == null) + implementsAttribute = TypeOfImplementsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(implementsAttribute, new object[] { interfaces })); - } + typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(implementsAttribute.AsReflection(), new object[] { interfaces })); + } #endif - internal bool IsGhostInterface(Type type) + internal bool IsGhostInterface(ITypeSymbol type) { return type.IsDefined(TypeOfGhostInterfaceAttribute, false); } - internal bool IsRemappedType(Type type) + internal bool IsRemappedType(ITypeSymbol type) { return type.IsDefined(TypeOfRemappedTypeAttribute, false); } - internal bool IsExceptionIsUnsafeForMapping(Type type) + internal bool IsExceptionIsUnsafeForMapping(ITypeSymbol type) { return type.IsDefined(TypeOfExceptionIsUnsafeForMappingAttribute, false); } - internal ModifiersAttribute GetModifiersAttribute(MemberInfo member) + internal ModifiersAttribute GetModifiersAttribute(IMemberSymbol member) { -#if !IMPORTER && !EXPORTER - var attr = member.GetCustomAttributes(typeof(ModifiersAttribute), false); - return attr.Length == 1 ? (ModifiersAttribute)attr[0] : null; -#else - var attr = CustomAttributeData.__GetCustomAttributes(member, TypeOfModifiersAttribute, false); - if (attr.Count == 1) - { - var args = attr[0].ConstructorArguments; - if (args.Count == 2) - return new ModifiersAttribute((Modifiers)args[0].Value, (bool)args[1].Value); + var attr = member.GetCustomAttributes(TypeOfModifiersAttribute, false); + if (attr.Length == 1) + { + var args = attr[0].ConstructorArguments; + if (args.Length == 2) + return new ModifiersAttribute((Modifiers)args[0].Value, (bool)args[1].Value); - return new ModifiersAttribute((Modifiers)args[0].Value); - } + return new ModifiersAttribute((Modifiers)args[0].Value); + } - return null; -#endif + return null; } - internal ExModifiers GetModifiers(MethodBase mb, bool assemblyIsPrivate) + internal ExModifiers GetModifiers(IMethodBaseSymbol mb, bool assemblyIsPrivate) { var attr = GetModifiersAttribute(mb); if (attr != null) @@ -685,7 +660,7 @@ internal ExModifiers GetModifiers(MethodBase mb, bool assemblyIsPrivate) // Some .NET interfaces (like System._AppDomain) have synchronized methods, // Java doesn't allow synchronized on an abstract methods, so we ignore it for // abstract methods. - if ((mb.GetMethodImplementationFlags() & MethodImplAttributes.Synchronized) != 0) + if ((mb.GetMethodImplementationFlags() & System.Reflection.MethodImplAttributes.Synchronized) != 0) { modifiers |= Modifiers.Synchronized; } @@ -696,19 +671,19 @@ internal ExModifiers GetModifiers(MethodBase mb, bool assemblyIsPrivate) modifiers |= Modifiers.Static; } - if ((mb.Attributes & MethodAttributes.PinvokeImpl) != 0) + if ((mb.Attributes & System.Reflection.MethodAttributes.PinvokeImpl) != 0) { modifiers |= Modifiers.Native; } var parameters = mb.GetParameters(); - if (parameters.Length > 0 && parameters[parameters.Length - 1].IsDefined(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName).AsReflection(), false)) + if (parameters.Length > 0 && parameters[parameters.Length - 1].IsDefined(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName), false)) modifiers |= Modifiers.VarArgs; return new ExModifiers(modifiers, false); } - internal ExModifiers GetModifiers(FieldInfo fi, bool assemblyIsPrivate) + internal ExModifiers GetModifiers(IFieldSymbol fi, bool assemblyIsPrivate) { var attr = GetModifiersAttribute(fi); if (attr != null) @@ -757,439 +732,354 @@ internal ExModifiers GetModifiers(FieldInfo fi, bool assemblyIsPrivate) internal void SetDebuggingModes(AssemblyBuilder assemblyBuilder, DebuggableAttribute.DebuggingModes modes) { - debuggableAttribute ??= TypeOfDebuggableAttribute.GetConstructor(new[] { TypeOfDebuggableAttribute.GetNestedType(nameof(DebuggableAttribute.DebuggingModes)) }); - assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(debuggableAttribute, new object[] { modes })); + debuggableAttribute ??= TypeOfDebuggableAttribute.GetConstructor([TypeOfDebuggableAttribute.GetNestedType(nameof(DebuggableAttribute.DebuggingModes))]); + assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(debuggableAttribute.AsReflection(), [modes])); } #if IMPORTER - internal void SetModifiers(MethodBuilder mb, Modifiers modifiers, bool isInternal) - { - CustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers, context.Types.Boolean }), new object[] { modifiers, isInternal }); - else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers }), new object[] { modifiers }); - - mb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetModifiers(FieldBuilder fb, Modifiers modifiers, bool isInternal) - { - CustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers, context.Types.Boolean }), new object[] { modifiers, isInternal }); - else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers }), new object[] { modifiers }); - - fb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetModifiers(PropertyBuilder pb, Modifiers modifiers, bool isInternal) - { - CustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers, context.Types.Boolean }), new object[] { modifiers, isInternal }); - else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers }), new object[] { modifiers }); - - pb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetModifiers(TypeBuilder tb, Modifiers modifiers, bool isInternal) - { - CustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers, context.Types.Boolean }), new object[] { modifiers, isInternal }); - else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor(new Type[] { TypeOfModifiers }), new object[] { modifiers }); - - tb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetNameSig(MethodBuilder mb, string name, string sig) - { - var customAttributeBuilder = new CustomAttributeBuilder(TypeOfNameSigAttribute.GetConstructor(new Type[] { context.Types.String, context.Types.String }), new object[] { UnicodeUtil.EscapeInvalidSurrogates(name), UnicodeUtil.EscapeInvalidSurrogates(sig) }); - mb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetInnerClass(TypeBuilder typeBuilder, string innerClass, Modifiers modifiers) - { - var argTypes = new Type[] { context.Types.String, TypeOfModifiers }; - var args = new object[] { UnicodeUtil.EscapeInvalidSurrogates(innerClass), modifiers }; - var ci = TypeOfInnerClassAttribute.GetConstructor(argTypes); - var customAttributeBuilder = new CustomAttributeBuilder(ci, args); - typeBuilder.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetSourceFile(TypeBuilder typeBuilder, string filename) - { - sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor(new Type[] { context.Types.String }); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(sourceFileAttribute, new object[] { filename })); - } - - internal void SetSourceFile(ModuleBuilder moduleBuilder, string filename) - { - sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor(new Type[] { context.Types.String }); - moduleBuilder.SetCustomAttribute(new CustomAttributeBuilder(sourceFileAttribute, new object[] { filename })); - } - - internal void SetLineNumberTable(MethodBuilder mb, IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter writer) - { - object arg; - ConstructorInfo con; - if (writer.Count == 1) - { - lineNumberTableAttribute2 ??= TypeOfLineNumberTableAttribute.GetConstructor(new Type[] { context.Types.UInt16 }); - con = lineNumberTableAttribute2; - arg = (ushort)writer.LineNo; - } - else - { - lineNumberTableAttribute1 ??= TypeOfLineNumberTableAttribute.GetConstructor(new Type[] { context.Resolver.ResolveCoreType(typeof(byte).FullName).MakeArrayType().AsReflection() }); - con = lineNumberTableAttribute1; - arg = writer.ToArray(); - } - mb.SetCustomAttribute(new CustomAttributeBuilder(con, new object[] { arg })); - } - - internal void SetEnclosingMethodAttribute(TypeBuilder tb, string className, string methodName, string methodSig) - { - if (enclosingMethodAttribute == null) - { - enclosingMethodAttribute = TypeOfEnclosingMethodAttribute.GetConstructor(new Type[] { context.Types.String, context.Types.String, context.Types.String }); - } - tb.SetCustomAttribute(new CustomAttributeBuilder(enclosingMethodAttribute, - new object[] { UnicodeUtil.EscapeInvalidSurrogates(className), UnicodeUtil.EscapeInvalidSurrogates(methodName), UnicodeUtil.EscapeInvalidSurrogates(methodSig) })); - } - - internal void SetSignatureAttribute(TypeBuilder tb, string signature) - { - signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor(new Type[] { context.Types.String }); - tb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute, new object[] { UnicodeUtil.EscapeInvalidSurrogates(signature) })); - } - - internal void SetSignatureAttribute(FieldBuilder fb, string signature) - { - signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor(new Type[] { context.Types.String }); - fb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute, new object[] { UnicodeUtil.EscapeInvalidSurrogates(signature) })); - } - - internal void SetSignatureAttribute(MethodBuilder mb, string signature) - { - signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor(new Type[] { context.Types.String }); - mb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute, new object[] { UnicodeUtil.EscapeInvalidSurrogates(signature) })); - } - - internal void SetMethodParametersAttribute(MethodBuilder mb, Modifiers[] modifiers) - { - methodParametersAttribute ??= TypeOfMethodParametersAttribute.GetConstructor(new[] { TypeOfModifiers.MakeArrayType() }); - mb.SetCustomAttribute(new CustomAttributeBuilder(methodParametersAttribute, new[] { modifiers })); - } - - internal void SetRuntimeVisibleTypeAnnotationsAttribute(TypeBuilder tb, ref readonly TypeAnnotationTable table) - { - var builder = new BlobBuilder(); - var encoder = new TypeAnnotationTableEncoder(builder); - table.WriteTo(ref encoder); - - runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - tb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); - } - - internal void SetRuntimeVisibleTypeAnnotationsAttribute(FieldBuilder fb, ref readonly TypeAnnotationTable table) - { - var builder = new BlobBuilder(); - var encoder = new TypeAnnotationTableEncoder(builder); - table.WriteTo(ref encoder); - - runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - fb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); - } - - internal void SetRuntimeVisibleTypeAnnotationsAttribute(MethodBuilder mb, ref readonly TypeAnnotationTable table) - { - var builder = new BlobBuilder(); - var encoder = new TypeAnnotationTableEncoder(builder); - table.WriteTo(ref encoder); - - runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - mb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); - } - - internal void SetConstantPoolAttribute(TypeBuilder tb, object[] constantPool) - { - constantPoolAttribute ??= TypeOfConstantPoolAttribute.GetConstructor([context.Types.Object.MakeArrayType()]); - tb.SetCustomAttribute(new CustomAttributeBuilder(constantPoolAttribute, [constantPool])); - } - - internal void SetParamArrayAttribute(ParameterBuilder pb) - { - paramArrayAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName).GetConstructor([]).AsReflection(), []); - pb.SetCustomAttribute(paramArrayAttribute); - } + internal void SetModifiers(MethodBuilder mb, Modifiers modifiers, bool isInternal) + { + CustomAttributeBuilder customAttributeBuilder; + if (isInternal) + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + else + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + + mb.SetCustomAttribute(customAttributeBuilder); + } + + internal void SetModifiers(FieldBuilder fb, Modifiers modifiers, bool isInternal) + { + CustomAttributeBuilder customAttributeBuilder; + if (isInternal) + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + else + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + + fb.SetCustomAttribute(customAttributeBuilder); + } + + internal void SetModifiers(PropertyBuilder pb, Modifiers modifiers, bool isInternal) + { + CustomAttributeBuilder customAttributeBuilder; + if (isInternal) + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + else + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + + pb.SetCustomAttribute(customAttributeBuilder); + } + + internal void SetModifiers(TypeBuilder tb, Modifiers modifiers, bool isInternal) + { + CustomAttributeBuilder customAttributeBuilder; + if (isInternal) + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + else + customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + + tb.SetCustomAttribute(customAttributeBuilder); + } + + internal void SetNameSig(MethodBuilder mb, string name, string sig) + { + var customAttributeBuilder = new CustomAttributeBuilder(TypeOfNameSigAttribute.GetConstructor([context.Types.String, context.Types.String]).AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(name), UnicodeUtil.EscapeInvalidSurrogates(sig)]); + mb.SetCustomAttribute(customAttributeBuilder); + } + + internal void SetInnerClass(TypeBuilder typeBuilder, string innerClass, Modifiers modifiers) + { + var argTypes = new ITypeSymbol[] { context.Types.String, TypeOfModifiers }; + var args = new object[] { UnicodeUtil.EscapeInvalidSurrogates(innerClass), modifiers }; + var ci = TypeOfInnerClassAttribute.GetConstructor(argTypes); + var customAttributeBuilder = new CustomAttributeBuilder(ci.AsReflection(), args); + typeBuilder.SetCustomAttribute(customAttributeBuilder); + } + + internal void SetSourceFile(TypeBuilder typeBuilder, string filename) + { + sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor([context.Types.String]); + typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(sourceFileAttribute.AsReflection(), [filename])); + } + + internal void SetSourceFile(ModuleBuilder moduleBuilder, string filename) + { + sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor([context.Types.String]); + moduleBuilder.SetCustomAttribute(new CustomAttributeBuilder(sourceFileAttribute.AsReflection(), new object[] { filename })); + } + + internal void SetLineNumberTable(MethodBuilder mb, IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter writer) + { + object arg; + IConstructorSymbol con; + if (writer.Count == 1) + { + lineNumberTableAttribute2 ??= TypeOfLineNumberTableAttribute.GetConstructor([context.Types.UInt16]); + con = lineNumberTableAttribute2; + arg = (ushort)writer.LineNo; + } + else + { + lineNumberTableAttribute1 ??= TypeOfLineNumberTableAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(byte).FullName).MakeArrayType()]); + con = lineNumberTableAttribute1; + arg = writer.ToArray(); + } + mb.SetCustomAttribute(new CustomAttributeBuilder(con.AsReflection(), [arg])); + } + + internal void SetEnclosingMethodAttribute(TypeBuilder tb, string className, string methodName, string methodSig) + { + if (enclosingMethodAttribute == null) + { + enclosingMethodAttribute = TypeOfEnclosingMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String]); + } + tb.SetCustomAttribute(new CustomAttributeBuilder(enclosingMethodAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(className), UnicodeUtil.EscapeInvalidSurrogates(methodName), UnicodeUtil.EscapeInvalidSurrogates(methodSig)])); + } + + internal void SetSignatureAttribute(TypeBuilder tb, string signature) + { + signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); + tb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + } + + internal void SetSignatureAttribute(FieldBuilder fb, string signature) + { + signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); + fb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + } + + internal void SetSignatureAttribute(MethodBuilder mb, string signature) + { + signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); + mb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + } + + internal void SetMethodParametersAttribute(MethodBuilder mb, Modifiers[] modifiers) + { + methodParametersAttribute ??= TypeOfMethodParametersAttribute.GetConstructor([TypeOfModifiers.MakeArrayType()]); + mb.SetCustomAttribute(new CustomAttributeBuilder(methodParametersAttribute.AsReflection(), [modifiers])); + } + + internal void SetRuntimeVisibleTypeAnnotationsAttribute(TypeBuilder tb, ref readonly TypeAnnotationTable table) + { + var builder = new BlobBuilder(); + var encoder = new TypeAnnotationTableEncoder(builder); + table.WriteTo(ref encoder); + + runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); + tb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute.AsReflection(), [builder.ToArray()])); + } + + internal void SetRuntimeVisibleTypeAnnotationsAttribute(FieldBuilder fb, ref readonly TypeAnnotationTable table) + { + var builder = new BlobBuilder(); + var encoder = new TypeAnnotationTableEncoder(builder); + table.WriteTo(ref encoder); + + runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); + fb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute.AsReflection(), [builder.ToArray()])); + } + + internal void SetRuntimeVisibleTypeAnnotationsAttribute(MethodBuilder mb, ref readonly TypeAnnotationTable table) + { + var builder = new BlobBuilder(); + var encoder = new TypeAnnotationTableEncoder(builder); + table.WriteTo(ref encoder); + + runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); + mb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute.AsReflection(), [builder.ToArray()])); + } + + internal void SetConstantPoolAttribute(TypeBuilder tb, object[] constantPool) + { + constantPoolAttribute ??= TypeOfConstantPoolAttribute.GetConstructor([context.Types.Object.MakeArrayType()]); + tb.SetCustomAttribute(new CustomAttributeBuilder(constantPoolAttribute.AsReflection(), [constantPool])); + } + + internal void SetParamArrayAttribute(ParameterBuilder pb) + { + paramArrayAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName).GetConstructor([]).AsReflection(), []); + pb.SetCustomAttribute(paramArrayAttribute); + } #endif // IMPORTER - internal NameSigAttribute GetNameSig(MemberInfo member) + internal NameSigAttribute GetNameSig(IMemberSymbol member) { -#if !IMPORTER && !EXPORTER - var attr = member.GetCustomAttributes(typeof(NameSigAttribute), false); - return attr.Length == 1 ? (NameSigAttribute)attr[0] : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(member, TypeOfNameSigAttribute, false)) - { - var args = cad.ConstructorArguments; - return new NameSigAttribute((string)args[0].Value, (string)args[1].Value); - } + foreach (var cad in member.GetCustomAttributes(TypeOfNameSigAttribute)) + { + var args = cad.ConstructorArguments; + return new NameSigAttribute((string)args[0].Value, (string)args[1].Value); + } - return null; -#endif + return null; } - internal T[] DecodeArray(CustomAttributeTypedArgument arg) + internal T[] DecodeArray(CoreLib.Symbols.CustomAttributeTypedArgument arg) { + +/* Unmerged change from project 'IKVM.Tools.Exporter (net8.0)' +Before: var elems = (IList)arg.Value; var arr = new T[elems.Count]; +After: + var elems = (IList)arg.Value; + var arr = new T[elems.Count]; +*/ + var elems = (IList)arg.Value; + var arr = new T[elems.Count]; for (int i = 0; i < arr.Length; i++) arr[i] = (T)elems[i].Value; return arr; } - internal ImplementsAttribute GetImplements(Type type) + internal ImplementsAttribute GetImplements(ITypeSymbol type) { -#if !IMPORTER && !EXPORTER - var attribs = type.GetCustomAttributes(typeof(ImplementsAttribute), false); - return attribs.Length == 1 ? (ImplementsAttribute)attribs[0] : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(type, TypeOfImplementsAttribute, false)) - { - var args = cad.ConstructorArguments; - return new ImplementsAttribute(DecodeArray(args[0])); - } + foreach (var cad in type.GetCustomAttributes(TypeOfImplementsAttribute)) + { + var args = cad.ConstructorArguments; + return new ImplementsAttribute(DecodeArray(args[0])); + } - return null; -#endif + return null; } - internal ThrowsAttribute GetThrows(MethodBase mb) + internal ThrowsAttribute GetThrows(IMethodBaseSymbol mb) { -#if !IMPORTER && !EXPORTER - var attribs = mb.GetCustomAttributes(typeof(ThrowsAttribute), false); - return attribs.Length == 1 ? (ThrowsAttribute)attribs[0] : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(mb, TypeOfThrowsAttribute, false)) - { - var args = cad.ConstructorArguments; - if (args[0].ArgumentType == context.Types.String.MakeArrayType()) - { - return new ThrowsAttribute(DecodeArray(args[0])); - } - else if (args[0].ArgumentType == context.Types.Type.MakeArrayType()) - { - return new ThrowsAttribute(DecodeArray(args[0])); - } - else - { - return new ThrowsAttribute((Type)args[0].Value); - } - } - - return null; -#endif + foreach (var cad in mb.GetCustomAttributes(TypeOfThrowsAttribute)) + { + var args = cad.ConstructorArguments; + if (args[0].ArgumentType == context.Types.String.MakeArrayType()) + { + return new ThrowsAttribute(DecodeArray(args[0])); + } + else if (args[0].ArgumentType == context.Types.Type.MakeArrayType()) + { + return new ThrowsAttribute(DecodeArray(args[0])); + } + else + { + return new ThrowsAttribute((Type)args[0].Value); + } + } + + return null; } - internal string[] GetNonNestedInnerClasses(Type t) + internal string[] GetNonNestedInnerClasses(ITypeSymbol t) { -#if !IMPORTER && !EXPORTER - var attribs = t.GetCustomAttributes(typeof(NonNestedInnerClassAttribute), false); - var classes = new string[attribs.Length]; - for (int i = 0; i < attribs.Length; i++) - classes[i] = ((NonNestedInnerClassAttribute)attribs[i]).InnerClassName; + var list = new List(); + foreach (var cad in t.GetCustomAttributes(TypeOfNonNestedInnerClassAttribute)) + list.Add(UnicodeUtil.UnescapeInvalidSurrogates((string)cad.ConstructorArguments[0].Value)); - return classes; -#else - var list = new List(); - foreach (var cad in CustomAttributeData.__GetCustomAttributes(t, TypeOfNonNestedInnerClassAttribute, false)) - { - var args = cad.ConstructorArguments; - list.Add(UnicodeUtil.UnescapeInvalidSurrogates((string)args[0].Value)); - } - - return list.ToArray(); -#endif + return list.ToArray(); } - internal string GetNonNestedOuterClasses(Type t) + internal string GetNonNestedOuterClasses(ITypeSymbol t) { -#if !IMPORTER && !EXPORTER - var attribs = t.GetCustomAttributes(typeof(NonNestedOuterClassAttribute), false); - return attribs.Length == 1 ? ((NonNestedOuterClassAttribute)attribs[0]).OuterClassName : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(t, TypeOfNonNestedOuterClassAttribute, false)) - { - var args = cad.ConstructorArguments; - return UnicodeUtil.UnescapeInvalidSurrogates((string)args[0].Value); - } - return null; -#endif + foreach (var cad in t.GetCustomAttributes(TypeOfNonNestedOuterClassAttribute)) + return UnicodeUtil.UnescapeInvalidSurrogates((string)cad.ConstructorArguments[0].Value); + + return null; } - internal IKVM.Attributes.SignatureAttribute GetSignature(MemberInfo member) + internal IKVM.Attributes.SignatureAttribute GetSignature(IMemberSymbol member) { -#if !IMPORTER && !EXPORTER - var attribs = member.GetCustomAttributes(typeof(IKVM.Attributes.SignatureAttribute), false); - return attribs.Length == 1 ? (IKVM.Attributes.SignatureAttribute)attribs[0] : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(member, TypeOfSignatureAttribute, false)) - { - var args = cad.ConstructorArguments; - return new IKVM.Attributes.SignatureAttribute((string)args[0].Value); - } + foreach (var cad in member.GetCustomAttributes(TypeOfSignatureAttribute)) + return new IKVM.Attributes.SignatureAttribute((string)cad.ConstructorArguments[0].Value); - return null; -#endif + return null; } - internal IKVM.Attributes.MethodParametersAttribute GetMethodParameters(MethodBase method) + internal IKVM.Attributes.MethodParametersAttribute GetMethodParameters(IMethodBaseSymbol method) { -#if !IMPORTER && !EXPORTER - var attribs = method.GetCustomAttributes(typeof(IKVM.Attributes.MethodParametersAttribute), false); - return attribs.Length == 1 ? (IKVM.Attributes.MethodParametersAttribute)attribs[0] : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(method, TypeOfMethodParametersAttribute, false)) - { - var args = cad.ConstructorArguments; - return new IKVM.Attributes.MethodParametersAttribute(DecodeArray(args[0])); - } - return null; -#endif + foreach (var cad in method.GetCustomAttributes(TypeOfMethodParametersAttribute)) + return new IKVM.Attributes.MethodParametersAttribute(DecodeArray(cad.ConstructorArguments[0])); + + return null; } - internal object[] GetConstantPool(Type type) + internal object[] GetConstantPool(ITypeSymbol type) { -#if !IMPORTER && !EXPORTER - var attribs = type.GetCustomAttributes(typeof(ConstantPoolAttribute), false); - return attribs.Length == 1 ? ((ConstantPoolAttribute)attribs[0]).constantPool : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(type, TypeOfConstantPoolAttribute, false)) - return ConstantPoolAttribute.Decompress(DecodeArray(cad.ConstructorArguments[0])); + foreach (var cad in type.GetCustomAttributes(TypeOfConstantPoolAttribute)) + return ConstantPoolAttribute.Decompress(DecodeArray(cad.ConstructorArguments[0])); - return null; -#endif + return null; } - internal byte[] GetRuntimeVisibleTypeAnnotations(MemberInfo member) + internal byte[] GetRuntimeVisibleTypeAnnotations(IMemberSymbol member) { -#if !IMPORTER && !EXPORTER - object[] attribs = member.GetCustomAttributes(typeof(IKVM.Attributes.RuntimeVisibleTypeAnnotationsAttribute), false); - return attribs.Length == 1 ? ((IKVM.Attributes.RuntimeVisibleTypeAnnotationsAttribute)attribs[0]).data : null; -#else - foreach (CustomAttributeData cad in CustomAttributeData.__GetCustomAttributes(member, TypeOfRuntimeVisibleTypeAnnotationsAttribute, false)) - { - return DecodeArray(cad.ConstructorArguments[0]); - } + foreach (var cad in member.GetCustomAttributes(TypeOfRuntimeVisibleTypeAnnotationsAttribute)) + return DecodeArray(cad.ConstructorArguments[0]); - return null; -#endif + return null; } - internal InnerClassAttribute GetInnerClass(Type type) + internal InnerClassAttribute GetInnerClass(ITypeSymbol type) { -#if !IMPORTER && !EXPORTER - object[] attribs = type.GetCustomAttributes(typeof(InnerClassAttribute), false); - return attribs.Length == 1 ? (InnerClassAttribute)attribs[0] : null; -#else - foreach (CustomAttributeData cad in CustomAttributeData.__GetCustomAttributes(type, TypeOfInnerClassAttribute, false)) - { - IList args = cad.ConstructorArguments; - return new InnerClassAttribute((string)args[0].Value, (Modifiers)args[1].Value); - } - return null; -#endif + foreach (var cad in type.GetCustomAttributes(TypeOfInnerClassAttribute)) + { + var args = cad.ConstructorArguments; + return new InnerClassAttribute((string)args[0].Value, (Modifiers)args[1].Value); + } + + return null; } - internal RemappedInterfaceMethodAttribute[] GetRemappedInterfaceMethods(Type type) + internal RemappedInterfaceMethodAttribute[] GetRemappedInterfaceMethods(ITypeSymbol type) { -#if !IMPORTER && !EXPORTER - var attr = type.GetCustomAttributes(typeof(RemappedInterfaceMethodAttribute), false); - var attr1 = new RemappedInterfaceMethodAttribute[attr.Length]; - Array.Copy(attr, attr1, attr.Length); - return attr1; -#else - var attrs = new List(); - foreach (var cad in CustomAttributeData.__GetCustomAttributes(type, TypeOfRemappedInterfaceMethodAttribute, false)) - { - var args = cad.ConstructorArguments; - attrs.Add(new RemappedInterfaceMethodAttribute((string)args[0].Value, (string)args[1].Value, DecodeArray(args[2]))); - } - - return attrs.ToArray(); -#endif + var attrs = new List(); + foreach (var cad in type.GetCustomAttributes(TypeOfRemappedInterfaceMethodAttribute)) + { + var args = cad.ConstructorArguments; + attrs.Add(new RemappedInterfaceMethodAttribute((string)args[0].Value, (string)args[1].Value, DecodeArray(args[2]))); + } + + return attrs.ToArray(); } - internal RemappedTypeAttribute GetRemappedType(Type type) + internal RemappedTypeAttribute GetRemappedType(ITypeSymbol type) { -#if !IMPORTER && !EXPORTER - var attribs = type.GetCustomAttributes(typeof(RemappedTypeAttribute), false); - return attribs.Length == 1 ? (RemappedTypeAttribute)attribs[0] : null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(type, TypeOfRemappedTypeAttribute, false)) - { - var args = cad.ConstructorArguments; - return new RemappedTypeAttribute((Type)args[0].Value); - } + foreach (var cad in type.GetCustomAttributes(TypeOfRemappedTypeAttribute)) + return new RemappedTypeAttribute((Type)cad.ConstructorArguments[0].Value); - return null; -#endif + return null; } - internal RemappedClassAttribute[] GetRemappedClasses(Assembly coreAssembly) + internal RemappedClassAttribute[] GetRemappedClasses(IAssemblySymbol coreAssembly) { -#if !IMPORTER && !EXPORTER - var attr = coreAssembly.GetCustomAttributes(typeof(RemappedClassAttribute), false); - var attr1 = new RemappedClassAttribute[attr.Length]; - Array.Copy(attr, attr1, attr.Length); - return attr1; -#else - var attrs = new List(); - foreach (var cad in CustomAttributeData.__GetCustomAttributes(coreAssembly, TypeOfRemappedClassAttribute, false)) - { - var args = cad.ConstructorArguments; - attrs.Add(new RemappedClassAttribute((string)args[0].Value, (Type)args[1].Value)); - } - - return attrs.ToArray(); -#endif + var attrs = new List(); + + foreach (var cad in coreAssembly.GetCustomAttributes(TypeOfRemappedClassAttribute)) + { + var args = cad.ConstructorArguments; + attrs.Add(new RemappedClassAttribute((string)args[0].Value, (Type)args[1].Value)); + } + + return attrs.ToArray(); } - internal string GetAnnotationAttributeType(Type type) + internal string GetAnnotationAttributeType(ITypeSymbol type) { -#if !IMPORTER && !EXPORTER - var attr = type.GetCustomAttributes(typeof(AnnotationAttributeAttribute), false); - if (attr.Length == 1) - return ((AnnotationAttributeAttribute)attr[0]).AttributeType; + foreach (var cad in type.GetCustomAttributes(TypeOfAnnotationAttributeAttribute)) + return UnicodeUtil.UnescapeInvalidSurrogates((string)cad.ConstructorArguments[0].Value); return null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(type, TypeOfAnnotationAttributeAttribute, false)) - return UnicodeUtil.UnescapeInvalidSurrogates((string)cad.ConstructorArguments[0].Value); - - return null; -#endif } - internal AssemblyName[] GetInternalsVisibleToAttributes(Assembly assembly) + internal System.Reflection.AssemblyName[] GetInternalsVisibleToAttributes(IAssemblySymbol assembly) { - var list = new List(); - foreach (var cad in CustomAttributeData.GetCustomAttributes(assembly)) + var list = new List(); + + foreach (var cad in assembly.GetCustomAttributes()) { - if (cad.Constructor.DeclaringType == context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName).AsReflection()) + if (cad.Constructor.DeclaringType == context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName)) { try { - list.Add(new AssemblyName((string)cad.ConstructorArguments[0].Value)); + list.Add(new System.Reflection.AssemblyName((string)cad.ConstructorArguments[0].Value)); } catch { @@ -1201,97 +1091,83 @@ internal AssemblyName[] GetInternalsVisibleToAttributes(Assembly assembly) return list.ToArray(); } - internal bool IsJavaModule(Module mod) + internal bool IsJavaModule(IModuleSymbol mod) { return mod.IsDefined(TypeOfJavaModuleAttribute, false); } - internal object[] GetJavaModuleAttributes(Module mod) + internal object[] GetJavaModuleAttributes(IModuleSymbol mod) { -#if !IMPORTER && !EXPORTER - return mod.GetCustomAttributes(TypeOfJavaModuleAttribute, false); -#else - List attrs = new List(); - foreach (CustomAttributeData cad in CustomAttributeData.__GetCustomAttributes(mod, TypeOfJavaModuleAttribute, false)) - { - IList args = cad.ConstructorArguments; - if (args.Count == 0) - { - attrs.Add(new JavaModuleAttribute()); - } - else - { - attrs.Add(new JavaModuleAttribute(DecodeArray(args[0]))); - } - } - return attrs.ToArray(); -#endif + var attrs = new List(); + + foreach (var cad in mod.GetCustomAttributes(TypeOfJavaModuleAttribute)) + { + var args = cad.ConstructorArguments; + if (args.Length == 0) + attrs.Add(new JavaModuleAttribute()); + else + attrs.Add(new JavaModuleAttribute(DecodeArray(args[0]))); + } + + return attrs.ToArray(); } - internal bool IsNoPackagePrefix(Type type) + internal bool IsNoPackagePrefix(ITypeSymbol type) { return type.IsDefined(TypeOfNoPackagePrefixAttribute, false) || type.Assembly.IsDefined(TypeOfNoPackagePrefixAttribute, false); } - internal bool HasEnclosingMethodAttribute(Type type) + internal bool HasEnclosingMethodAttribute(ITypeSymbol type) { return type.IsDefined(TypeOfEnclosingMethodAttribute, false); } - internal IKVM.Attributes.EnclosingMethodAttribute GetEnclosingMethodAttribute(Type type) + internal IKVM.Attributes.EnclosingMethodAttribute GetEnclosingMethodAttribute(ITypeSymbol type) { -#if !IMPORTER && !EXPORTER - var attr = type.GetCustomAttributes(typeof(IKVM.Attributes.EnclosingMethodAttribute), false); - if (attr.Length == 1) - return ((IKVM.Attributes.EnclosingMethodAttribute)attr[0]).SetClassName(context, type); + foreach (var cad in type.GetCustomAttributes(TypeOfEnclosingMethodAttribute)) + return new IKVM.Attributes.EnclosingMethodAttribute((string)cad.ConstructorArguments[0].Value, (string)cad.ConstructorArguments[1].Value, (string)cad.ConstructorArguments[2].Value).SetClassName(context, type.AsReflection()); return null; -#else - foreach (var cad in CustomAttributeData.__GetCustomAttributes(type, TypeOfEnclosingMethodAttribute, false)) - return new IKVM.Attributes.EnclosingMethodAttribute((string)cad.ConstructorArguments[0].Value, (string)cad.ConstructorArguments[1].Value, (string)cad.ConstructorArguments[2].Value).SetClassName(context, type); - - return null; -#endif } #if IMPORTER - internal void SetRemappedClass(AssemblyBuilder assemblyBuilder, string name, Type shadowType) - { - var remappedClassAttribute = TypeOfRemappedClassAttribute.GetConstructor(new Type[] { context.Types.String, context.Types.Type }); - assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(remappedClassAttribute, new object[] { name, shadowType })); - } - - internal void SetRemappedType(TypeBuilder typeBuilder, Type shadowType) - { - var remappedTypeAttribute = TypeOfRemappedTypeAttribute.GetConstructor(new Type[] { context.Types.Type }); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(remappedTypeAttribute, new object[] { shadowType })); - } - - internal void SetRemappedInterfaceMethod(TypeBuilder typeBuilder, string name, string mappedTo, string[] throws) - { - var cab = new CustomAttributeBuilder(TypeOfRemappedInterfaceMethodAttribute.GetConstructor(new Type[] { context.Types.String, context.Types.String, context.Types.String.MakeArrayType() }), new object[] { name, mappedTo, throws }); - typeBuilder.SetCustomAttribute(cab); - } - - internal void SetExceptionIsUnsafeForMapping(TypeBuilder typeBuilder) - { - var cab = new CustomAttributeBuilder(TypeOfExceptionIsUnsafeForMappingAttribute.GetConstructor(Type.EmptyTypes), Array.Empty()); - typeBuilder.SetCustomAttribute(cab); - } + internal void SetRemappedClass(AssemblyBuilder assemblyBuilder, string name, ITypeSymbol shadowType) + { + var remappedClassAttribute = TypeOfRemappedClassAttribute.GetConstructor([context.Types.String, context.Types.Type]); + assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(remappedClassAttribute.AsReflection(), [name, shadowType])); + } + + internal void SetRemappedType(TypeBuilder typeBuilder, ITypeSymbol shadowType) + { + var remappedTypeAttribute = TypeOfRemappedTypeAttribute.GetConstructor([context.Types.Type]); + typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(remappedTypeAttribute.AsReflection(), [shadowType])); + } + + internal void SetRemappedInterfaceMethod(TypeBuilder typeBuilder, string name, string mappedTo, string[] throws) + { + var cab = new CustomAttributeBuilder(TypeOfRemappedInterfaceMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String.MakeArrayType()]).AsReflection(), [name, mappedTo, throws]); + typeBuilder.SetCustomAttribute(cab); + } + + internal void SetExceptionIsUnsafeForMapping(TypeBuilder typeBuilder) + { + var cab = new CustomAttributeBuilder(TypeOfExceptionIsUnsafeForMappingAttribute.GetConstructor([]).AsReflection(), Array.Empty()); + typeBuilder.SetCustomAttribute(cab); + } #endif internal void SetRuntimeCompatibilityAttribute(AssemblyBuilder assemblyBuilder) { - var runtimeCompatibilityAttribute = context.Resolver.ResolveCoreType(typeof(RuntimeCompatibilityAttribute).FullName).AsReflection(); - assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(runtimeCompatibilityAttribute.GetConstructor(Type.EmptyTypes), Array.Empty(), new PropertyInfo[] { runtimeCompatibilityAttribute.GetProperty("WrapNonExceptionThrows") }, new object[] { true }, Array.Empty(), Array.Empty())); + var runtimeCompatibilityAttribute = context.Resolver.ResolveCoreType(typeof(RuntimeCompatibilityAttribute).FullName); + assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(runtimeCompatibilityAttribute.GetConstructor([]).AsReflection(), [], [runtimeCompatibilityAttribute.GetProperty("WrapNonExceptionThrows").AsReflection()], [true], [], [])); } internal void SetInternalsVisibleToAttribute(AssemblyBuilder assemblyBuilder, string assemblyName) { - var internalsVisibleToAttribute = context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName).AsReflection(); - var cab = new CustomAttributeBuilder(internalsVisibleToAttribute.GetConstructor(new Type[] { context.Types.String }), new object[] { assemblyName }); + var internalsVisibleToAttribute = context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName); + var cab = new CustomAttributeBuilder(internalsVisibleToAttribute.GetConstructor([context.Types.String]).AsReflection(), [assemblyName]); assemblyBuilder.SetCustomAttribute(cab); } diff --git a/src/IKVM.Runtime/Attributes/LineNumberTableAttribute.cs b/src/IKVM.Runtime/Attributes/LineNumberTableAttribute.cs index 2ce05c73c9..eeafb50c1c 100644 --- a/src/IKVM.Runtime/Attributes/LineNumberTableAttribute.cs +++ b/src/IKVM.Runtime/Attributes/LineNumberTableAttribute.cs @@ -27,114 +27,115 @@ namespace IKVM.Attributes { [AttributeUsage(AttributeTargets.Method | AttributeTargets.Constructor)] - public sealed class LineNumberTableAttribute : Attribute - { - - private byte[] table; - - public LineNumberTableAttribute(ushort lineno) - { - LineNumberWriter w = new LineNumberWriter(1); - w.AddMapping(0, lineno); - table = w.ToArray(); - } - - public LineNumberTableAttribute(byte[] table) - { - this.table = table; - } - - public sealed class LineNumberWriter - { - private System.IO.MemoryStream stream; - private int prevILOffset; - private int prevLineNum; - private int count; - - public LineNumberWriter(int estimatedCount) - { - stream = new System.IO.MemoryStream(estimatedCount * 2); - } - - public void AddMapping(int ilOffset, int linenumber) - { - if(count == 0) - { - if(ilOffset == 0 && linenumber != 0) - { - prevLineNum = linenumber; - count++; - WritePackedInteger(linenumber - (64 + 50)); - return; - } - else - { - prevLineNum = linenumber & ~3; - WritePackedInteger(((-prevLineNum / 4) - (64 + 50))); - } - } - bool pc_overflow; - bool lineno_overflow; - byte lead; - int deltaPC = ilOffset - prevILOffset; - if(deltaPC >= 0 && deltaPC < 31) - { - lead = (byte)deltaPC; - pc_overflow = false; - } - else - { - lead = (byte)31; - pc_overflow = true; - } - int deltaLineNo = linenumber - prevLineNum; - const int bias = 2; - if(deltaLineNo >= -bias && deltaLineNo < 7 - bias) - { - lead |= (byte)((deltaLineNo + bias) << 5); - lineno_overflow = false; - } - else - { - lead |= (byte)(7 << 5); - lineno_overflow = true; - } - stream.WriteByte(lead); - if(pc_overflow) - { - WritePackedInteger(deltaPC - (64 + 31)); - } - if(lineno_overflow) - { - WritePackedInteger(deltaLineNo); - } - prevILOffset = ilOffset; - prevLineNum = linenumber; - count++; - } - - public int Count - { - get - { - return count; - } - } - - public int LineNo - { - get - { - return prevLineNum; - } - } - - public byte[] ToArray() - { - return stream.ToArray(); - } - - /* + public sealed class LineNumberTableAttribute : Attribute + { + + private byte[] table; + + public LineNumberTableAttribute(ushort lineno) + { + LineNumberWriter w = new LineNumberWriter(1); + w.AddMapping(0, lineno); + table = w.ToArray(); + } + + public LineNumberTableAttribute(byte[] table) + { + this.table = table; + } + + public sealed class LineNumberWriter + { + + System.IO.MemoryStream stream; + int prevILOffset; + int prevLineNum; + int count; + + public LineNumberWriter(int estimatedCount) + { + stream = new System.IO.MemoryStream(estimatedCount * 2); + } + + public void AddMapping(int ilOffset, int linenumber) + { + if (count == 0) + { + if (ilOffset == 0 && linenumber != 0) + { + prevLineNum = linenumber; + count++; + WritePackedInteger(linenumber - (64 + 50)); + return; + } + else + { + prevLineNum = linenumber & ~3; + WritePackedInteger(((-prevLineNum / 4) - (64 + 50))); + } + } + bool pc_overflow; + bool lineno_overflow; + byte lead; + int deltaPC = ilOffset - prevILOffset; + if (deltaPC >= 0 && deltaPC < 31) + { + lead = (byte)deltaPC; + pc_overflow = false; + } + else + { + lead = (byte)31; + pc_overflow = true; + } + int deltaLineNo = linenumber - prevLineNum; + const int bias = 2; + if (deltaLineNo >= -bias && deltaLineNo < 7 - bias) + { + lead |= (byte)((deltaLineNo + bias) << 5); + lineno_overflow = false; + } + else + { + lead |= (byte)(7 << 5); + lineno_overflow = true; + } + stream.WriteByte(lead); + if (pc_overflow) + { + WritePackedInteger(deltaPC - (64 + 31)); + } + if (lineno_overflow) + { + WritePackedInteger(deltaLineNo); + } + prevILOffset = ilOffset; + prevLineNum = linenumber; + count++; + } + + public int Count + { + get + { + return count; + } + } + + public int LineNo + { + get + { + return prevLineNum; + } + } + + public byte[] ToArray() + { + return stream.ToArray(); + } + + /* * packed integer format: * ---------------------- * @@ -145,109 +146,109 @@ public byte[] ToArray() * E0 - FE Reserved * FF Five byte integer */ - private void WritePackedInteger(int val) - { - if(val >= -64 && val < 64) - { - val += 64; - stream.WriteByte((byte)val); - } - else if(val >= -8192 && val < 8192) - { - val += 8192; - stream.WriteByte((byte)(0x80 + (val >> 8))); - stream.WriteByte((byte)val); - } - else if(val >= -1048576 && val < 1048576) - { - val += 1048576; - stream.WriteByte((byte)(0xC0 + (val >> 16))); - stream.WriteByte((byte)(val >> 8)); - stream.WriteByte((byte)val); - } - else - { - stream.WriteByte(0xFF); - stream.WriteByte((byte)(val >> 24)); - stream.WriteByte((byte)(val >> 16)); - stream.WriteByte((byte)(val >> 8)); - stream.WriteByte((byte)(val >> 0)); - } - } - } - - private int ReadPackedInteger(ref int position) - { - byte b = table[position++]; - if(b < 128) - { - return b - 64; - } - else if((b & 0xC0) == 0x80) - { - return ((b & 0x7F) << 8) + table[position++] - 8192; - } - else if((b & 0xE0) == 0xC0) - { - int val = ((b & 0x3F) << 16); - val += (table[position++] << 8); - val += table[position++]; - return val - 1048576; - } - else if(b == 0xFF) - { - int val = table[position++] << 24; - val += table[position++] << 16; - val += table[position++] << 8; - val += table[position++] << 0; - return val; - } - else - { - throw new InvalidProgramException(); - } - } - - public int GetLineNumber(int ilOffset) - { - int i = 0; - int prevILOffset = 0; - int prevLineNum = ReadPackedInteger(ref i) + (64 + 50); - int line; - if(prevLineNum > 0) - { - line = prevLineNum; - } - else - { - prevLineNum = 4 * -prevLineNum; - line = -1; - } - while(i < table.Length) - { - byte lead = table[i++]; - int deltaPC = lead & 31; - int deltaLineNo = (lead >> 5) - 2; - if(deltaPC == 31) - { - deltaPC = ReadPackedInteger(ref i) + (64 + 31); - } - if(deltaLineNo == 5) - { - deltaLineNo = ReadPackedInteger(ref i); - } - int currILOffset = prevILOffset + deltaPC; - if(currILOffset > ilOffset) - { - return line; - } - line = prevLineNum + deltaLineNo; - prevILOffset = currILOffset; - prevLineNum = line; - } - return line; - } - - } + private void WritePackedInteger(int val) + { + if (val >= -64 && val < 64) + { + val += 64; + stream.WriteByte((byte)val); + } + else if (val >= -8192 && val < 8192) + { + val += 8192; + stream.WriteByte((byte)(0x80 + (val >> 8))); + stream.WriteByte((byte)val); + } + else if (val >= -1048576 && val < 1048576) + { + val += 1048576; + stream.WriteByte((byte)(0xC0 + (val >> 16))); + stream.WriteByte((byte)(val >> 8)); + stream.WriteByte((byte)val); + } + else + { + stream.WriteByte(0xFF); + stream.WriteByte((byte)(val >> 24)); + stream.WriteByte((byte)(val >> 16)); + stream.WriteByte((byte)(val >> 8)); + stream.WriteByte((byte)(val >> 0)); + } + } + } + + private int ReadPackedInteger(ref int position) + { + byte b = table[position++]; + if (b < 128) + { + return b - 64; + } + else if ((b & 0xC0) == 0x80) + { + return ((b & 0x7F) << 8) + table[position++] - 8192; + } + else if ((b & 0xE0) == 0xC0) + { + int val = ((b & 0x3F) << 16); + val += (table[position++] << 8); + val += table[position++]; + return val - 1048576; + } + else if (b == 0xFF) + { + int val = table[position++] << 24; + val += table[position++] << 16; + val += table[position++] << 8; + val += table[position++] << 0; + return val; + } + else + { + throw new InvalidProgramException(); + } + } + + public int GetLineNumber(int ilOffset) + { + int i = 0; + int prevILOffset = 0; + int prevLineNum = ReadPackedInteger(ref i) + (64 + 50); + int line; + if (prevLineNum > 0) + { + line = prevLineNum; + } + else + { + prevLineNum = 4 * -prevLineNum; + line = -1; + } + while (i < table.Length) + { + byte lead = table[i++]; + int deltaPC = lead & 31; + int deltaLineNo = (lead >> 5) - 2; + if (deltaPC == 31) + { + deltaPC = ReadPackedInteger(ref i) + (64 + 31); + } + if (deltaLineNo == 5) + { + deltaLineNo = ReadPackedInteger(ref i); + } + int currILOffset = prevILOffset + deltaPC; + if (currILOffset > ilOffset) + { + return line; + } + line = prevLineNum + deltaLineNo; + prevILOffset = currILOffset; + prevLineNum = line; + } + return line; + } + + } } diff --git a/src/IKVM.Runtime/ByteCodeHelperMethods.cs b/src/IKVM.Runtime/ByteCodeHelperMethods.cs index 666a21a672..e0691d5f28 100644 --- a/src/IKVM.Runtime/ByteCodeHelperMethods.cs +++ b/src/IKVM.Runtime/ByteCodeHelperMethods.cs @@ -21,20 +21,13 @@ Jeroen Frijters jeroen@frijters.net */ -using System; +using System.Reflection; using IKVM.CoreLib.Diagnostics; -using IKVM.CoreLib.Symbols.IkvmReflection; -using IKVM.CoreLib.Symbols.Reflection; +using IKVM.CoreLib.Symbols; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; #endif namespace IKVM.Runtime @@ -45,64 +38,64 @@ namespace IKVM.Runtime class ByteCodeHelperMethods { - internal readonly MethodInfo multianewarray; - internal readonly MethodInfo multianewarray_ghost; - internal readonly MethodInfo anewarray_ghost; - internal readonly MethodInfo f2i; - internal readonly MethodInfo d2i; - internal readonly MethodInfo f2l; - internal readonly MethodInfo d2l; - internal readonly MethodInfo arraycopy_fast; - internal readonly MethodInfo arraycopy_primitive_8; - internal readonly MethodInfo arraycopy_primitive_4; - internal readonly MethodInfo arraycopy_primitive_2; - internal readonly MethodInfo arraycopy_primitive_1; - internal readonly MethodInfo arraycopy; - internal readonly MethodInfo DynamicCast; - internal readonly MethodInfo DynamicAaload; - internal readonly MethodInfo DynamicAastore; - internal readonly MethodInfo DynamicClassLiteral; - internal readonly MethodInfo DynamicMultianewarray; - internal readonly MethodInfo DynamicNewarray; - internal readonly MethodInfo DynamicNewCheckOnly; - internal readonly MethodInfo DynamicCreateDelegate; - internal readonly MethodInfo DynamicLoadMethodType; - internal readonly MethodInfo DynamicLoadMethodHandle; - internal readonly MethodInfo DynamicBinderMemberLookup; - internal readonly MethodInfo DynamicMapException; - internal readonly MethodInfo DynamicCallerID; - internal readonly MethodInfo DynamicLinkIndyCallSite; - internal readonly MethodInfo DynamicEraseInvokeExact; - internal readonly MethodInfo VerboseCastFailure; - internal readonly MethodInfo SkipFinalizer; - internal readonly MethodInfo SkipFinalizerOf; - internal readonly MethodInfo DynamicInstanceOf; - internal readonly MethodInfo VolatileReadBoolean; - internal readonly MethodInfo VolatileReadByte; - internal readonly MethodInfo VolatileReadChar; - internal readonly MethodInfo VolatileReadShort; - internal readonly MethodInfo VolatileReadInt; - internal readonly MethodInfo VolatileReadLong; - internal readonly MethodInfo VolatileReadFloat; - internal readonly MethodInfo VolatileReadDouble; - internal readonly MethodInfo VolatileWriteBoolean; - internal readonly MethodInfo VolatileWriteByte; - internal readonly MethodInfo VolatileWriteChar; - internal readonly MethodInfo VolatileWriteShort; - internal readonly MethodInfo VolatileWriteInt; - internal readonly MethodInfo VolatileWriteLong; - internal readonly MethodInfo VolatileWriteFloat; - internal readonly MethodInfo VolatileWriteDouble; - internal readonly MethodInfo CompareAndSwapObject; - internal readonly MethodInfo CompareAndSwapInt; - internal readonly MethodInfo CompareAndSwapLong; - internal readonly MethodInfo CompareAndSwapDouble; - internal readonly MethodInfo MapException; - internal readonly MethodInfo GetDelegateForInvokeExact; - internal readonly MethodInfo GetDelegateForInvoke; - internal readonly MethodInfo GetDelegateForInvokeBasic; - internal readonly MethodInfo LoadMethodType; - internal readonly MethodInfo LinkIndyCallSite; + internal readonly IMethodSymbol multianewarray; + internal readonly IMethodSymbol multianewarray_ghost; + internal readonly IMethodSymbol anewarray_ghost; + internal readonly IMethodSymbol f2i; + internal readonly IMethodSymbol d2i; + internal readonly IMethodSymbol f2l; + internal readonly IMethodSymbol d2l; + internal readonly IMethodSymbol arraycopy_fast; + internal readonly IMethodSymbol arraycopy_primitive_8; + internal readonly IMethodSymbol arraycopy_primitive_4; + internal readonly IMethodSymbol arraycopy_primitive_2; + internal readonly IMethodSymbol arraycopy_primitive_1; + internal readonly IMethodSymbol arraycopy; + internal readonly IMethodSymbol DynamicCast; + internal readonly IMethodSymbol DynamicAaload; + internal readonly IMethodSymbol DynamicAastore; + internal readonly IMethodSymbol DynamicClassLiteral; + internal readonly IMethodSymbol DynamicMultianewarray; + internal readonly IMethodSymbol DynamicNewarray; + internal readonly IMethodSymbol DynamicNewCheckOnly; + internal readonly IMethodSymbol DynamicCreateDelegate; + internal readonly IMethodSymbol DynamicLoadMethodType; + internal readonly IMethodSymbol DynamicLoadMethodHandle; + internal readonly IMethodSymbol DynamicBinderMemberLookup; + internal readonly IMethodSymbol DynamicMapException; + internal readonly IMethodSymbol DynamicCallerID; + internal readonly IMethodSymbol DynamicLinkIndyCallSite; + internal readonly IMethodSymbol DynamicEraseInvokeExact; + internal readonly IMethodSymbol VerboseCastFailure; + internal readonly IMethodSymbol SkipFinalizer; + internal readonly IMethodSymbol SkipFinalizerOf; + internal readonly IMethodSymbol DynamicInstanceOf; + internal readonly IMethodSymbol VolatileReadBoolean; + internal readonly IMethodSymbol VolatileReadByte; + internal readonly IMethodSymbol VolatileReadChar; + internal readonly IMethodSymbol VolatileReadShort; + internal readonly IMethodSymbol VolatileReadInt; + internal readonly IMethodSymbol VolatileReadLong; + internal readonly IMethodSymbol VolatileReadFloat; + internal readonly IMethodSymbol VolatileReadDouble; + internal readonly IMethodSymbol VolatileWriteBoolean; + internal readonly IMethodSymbol VolatileWriteByte; + internal readonly IMethodSymbol VolatileWriteChar; + internal readonly IMethodSymbol VolatileWriteShort; + internal readonly IMethodSymbol VolatileWriteInt; + internal readonly IMethodSymbol VolatileWriteLong; + internal readonly IMethodSymbol VolatileWriteFloat; + internal readonly IMethodSymbol VolatileWriteDouble; + internal readonly IMethodSymbol CompareAndSwapObject; + internal readonly IMethodSymbol CompareAndSwapInt; + internal readonly IMethodSymbol CompareAndSwapLong; + internal readonly IMethodSymbol CompareAndSwapDouble; + internal readonly IMethodSymbol MapException; + internal readonly IMethodSymbol GetDelegateForInvokeExact; + internal readonly IMethodSymbol GetDelegateForInvoke; + internal readonly IMethodSymbol GetDelegateForInvokeBasic; + internal readonly IMethodSymbol LoadMethodType; + internal readonly IMethodSymbol LinkIndyCallSite; /// /// Initializes a new instance. @@ -110,11 +103,7 @@ class ByteCodeHelperMethods /// public ByteCodeHelperMethods(RuntimeContext context) { -#if IMPORTER || EXPORTER - var typeofByteCodeHelper = ((IkvmReflectionTypeSymbol)context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper")).ReflectionObject; -#else - var typeofByteCodeHelper = ((ReflectionTypeSymbol)context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper")).ReflectionObject; -#endif + var typeofByteCodeHelper = context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper"); multianewarray = GetHelper(typeofByteCodeHelper, "multianewarray"); multianewarray_ghost = GetHelper(typeofByteCodeHelper, "multianewarray_ghost"); anewarray_ghost = GetHelper(typeofByteCodeHelper, "anewarray_ghost"); @@ -144,29 +133,29 @@ public ByteCodeHelperMethods(RuntimeContext context) DynamicLinkIndyCallSite = GetHelper(typeofByteCodeHelper, "DynamicLinkIndyCallSite"); DynamicEraseInvokeExact = GetHelper(typeofByteCodeHelper, "DynamicEraseInvokeExact"); VerboseCastFailure = GetHelper(typeofByteCodeHelper, "VerboseCastFailure"); - SkipFinalizer = GetHelper(typeofByteCodeHelper, "SkipFinalizer", new Type[] { }); - SkipFinalizerOf = GetHelper(typeofByteCodeHelper, "SkipFinalizer", new Type[] { context.Types.Object }); + SkipFinalizer = GetHelper(typeofByteCodeHelper, "SkipFinalizer", []); + SkipFinalizerOf = GetHelper(typeofByteCodeHelper, "SkipFinalizer", [context.Types.Object]); DynamicInstanceOf = GetHelper(typeofByteCodeHelper, "DynamicInstanceOf"); - VolatileReadBoolean = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Boolean.MakeByRefType() }); - VolatileReadByte = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Byte.MakeByRefType() }); - VolatileReadChar = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Char.MakeByRefType() }); - VolatileReadShort = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Int16.MakeByRefType() }); - VolatileReadInt = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Int32.MakeByRefType() }); - VolatileReadLong = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Int64.MakeByRefType() }); - VolatileReadFloat = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Single.MakeByRefType() }); - VolatileReadDouble = GetHelper(typeofByteCodeHelper, "VolatileRead", new Type[] { context.Types.Double.MakeByRefType() }); - VolatileWriteBoolean = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Boolean.MakeByRefType(), context.Types.Boolean }); - VolatileWriteByte = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Byte.MakeByRefType(), context.Types.Byte }); - VolatileWriteChar = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Char.MakeByRefType(), context.Types.Char }); - VolatileWriteShort = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Int16.MakeByRefType(), context.Types.Int16 }); - VolatileWriteInt = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Int32.MakeByRefType(), context.Types.Int32 }); - VolatileWriteLong = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Int64.MakeByRefType(), context.Types.Int64 }); - VolatileWriteFloat = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Single.MakeByRefType(), context.Types.Single }); - VolatileWriteDouble = GetHelper(typeofByteCodeHelper, "VolatileWrite", new Type[] { context.Types.Double.MakeByRefType(), context.Types.Double }); - CompareAndSwapObject = GetHelper(typeofByteCodeHelper, "CompareAndSwap", new[] { context.Types.Object.MakeByRefType(), context.Types.Object, context.Types.Object }); - CompareAndSwapInt = GetHelper(typeofByteCodeHelper, "CompareAndSwap", new[] { context.Types.Int32.MakeByRefType(), context.Types.Int32, context.Types.Int32 }); - CompareAndSwapLong = GetHelper(typeofByteCodeHelper, "CompareAndSwap", new[] { context.Types.Int64.MakeByRefType(), context.Types.Int64, context.Types.Int64 }); - CompareAndSwapDouble = GetHelper(typeofByteCodeHelper, "CompareAndSwap", new[] { context.Types.Double.MakeByRefType(), context.Types.Double, context.Types.Double }); + VolatileReadBoolean = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Boolean.MakeByRefType()]); + VolatileReadByte = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Byte.MakeByRefType()]); + VolatileReadChar = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Char.MakeByRefType()]); + VolatileReadShort = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Int16.MakeByRefType()]); + VolatileReadInt = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Int32.MakeByRefType()]); + VolatileReadLong = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Int64.MakeByRefType()]); + VolatileReadFloat = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Single.MakeByRefType()]); + VolatileReadDouble = GetHelper(typeofByteCodeHelper, "VolatileRead", [context.Types.Double.MakeByRefType()]); + VolatileWriteBoolean = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Boolean.MakeByRefType(), context.Types.Boolean]); + VolatileWriteByte = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Byte.MakeByRefType(), context.Types.Byte]); + VolatileWriteChar = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Char.MakeByRefType(), context.Types.Char]); + VolatileWriteShort = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Int16.MakeByRefType(), context.Types.Int16]); + VolatileWriteInt = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Int32.MakeByRefType(), context.Types.Int32]); + VolatileWriteLong = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Int64.MakeByRefType(), context.Types.Int64]); + VolatileWriteFloat = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Single.MakeByRefType(), context.Types.Single]); + VolatileWriteDouble = GetHelper(typeofByteCodeHelper, "VolatileWrite", [context.Types.Double.MakeByRefType(), context.Types.Double]); + CompareAndSwapObject = GetHelper(typeofByteCodeHelper, "CompareAndSwap", [context.Types.Object.MakeByRefType(), context.Types.Object, context.Types.Object]); + CompareAndSwapInt = GetHelper(typeofByteCodeHelper, "CompareAndSwap", [context.Types.Int32.MakeByRefType(), context.Types.Int32, context.Types.Int32]); + CompareAndSwapLong = GetHelper(typeofByteCodeHelper, "CompareAndSwap", [context.Types.Int64.MakeByRefType(), context.Types.Int64, context.Types.Int64]); + CompareAndSwapDouble = GetHelper(typeofByteCodeHelper, "CompareAndSwap", [context.Types.Double.MakeByRefType(), context.Types.Double, context.Types.Double]); MapException = GetHelper(typeofByteCodeHelper, "MapException"); GetDelegateForInvokeExact = GetHelper(typeofByteCodeHelper, "GetDelegateForInvokeExact"); GetDelegateForInvoke = GetHelper(typeofByteCodeHelper, "GetDelegateForInvoke"); @@ -175,12 +164,12 @@ public ByteCodeHelperMethods(RuntimeContext context) LinkIndyCallSite = GetHelper(typeofByteCodeHelper, "LinkIndyCallSite"); } - static MethodInfo GetHelper(Type type, string method) + static IMethodSymbol GetHelper(ITypeSymbol type, string method) { return GetHelper(type, method, null); } - static MethodInfo GetHelper(Type type, string method, Type[] parameters) + static IMethodSymbol GetHelper(ITypeSymbol type, string method, ITypeSymbol[] parameters) { var mi = parameters == null ? type.GetMethod(method) : type.GetMethod(method, parameters); if (mi == null) diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index 91a05f0c5b..0d17bb2132 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -27,11 +27,11 @@ Jeroen Frijters using System.Diagnostics.SymbolStore; using System.Diagnostics; +using IKVM.CoreLib.Symbols; + #if IMPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; #else using System.Reflection; using System.Reflection.Emit; @@ -45,11 +45,11 @@ class CodeEmitterFactory readonly RuntimeContext context; - MethodInfo objectToString; - MethodInfo verboseCastFailure; - MethodInfo monitorEnter; - MethodInfo monitorExit; - MethodInfo memoryBarrier; + IMethodSymbol objectToString; + IMethodSymbol verboseCastFailure; + IMethodSymbol monitorEnter; + IMethodSymbol monitorExit; + IMethodSymbol memoryBarrier; /// /// Initializes a new instance. @@ -60,15 +60,15 @@ public CodeEmitterFactory(RuntimeContext context) this.context = context ?? throw new ArgumentNullException(nameof(context)); } - public MethodInfo ObjectToStringMethod => objectToString ??= context.Types.Object.GetMethod("ToString", BindingFlags.Public | BindingFlags.Instance, null, [], null); + public IMethodSymbol ObjectToStringMethod => objectToString ??= context.Types.Object.GetMethod("ToString", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance, []); - public MethodInfo VerboseCastFailureMethod => verboseCastFailure ??= JVM.SafeGetEnvironmentVariable("IKVM_VERBOSE_CAST") == null ? null : context.ByteCodeHelperMethods.VerboseCastFailure; + public IMethodSymbol VerboseCastFailureMethod => verboseCastFailure ??= JVM.SafeGetEnvironmentVariable("IKVM_VERBOSE_CAST") == null ? null : context.ByteCodeHelperMethods.VerboseCastFailure; - public MethodInfo MonitorEnterMethod => monitorEnter ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).AsReflection().GetMethod("Enter", BindingFlags.Public | BindingFlags.Static, null, [context.Types.Object], null); + public IMethodSymbol MonitorEnterMethod => monitorEnter ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); - public MethodInfo MonitorExitMethod => monitorExit ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).AsReflection().GetMethod("Exit", BindingFlags.Public | BindingFlags.Static, null, [context.Types.Object], null); + public IMethodSymbol MonitorExitMethod => monitorExit ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); - public MethodInfo MemoryBarrierMethod => memoryBarrier ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Thread).FullName).GetMethod("MemoryBarrier", []).AsReflection(); + public IMethodSymbol MemoryBarrierMethod => memoryBarrier ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Thread).FullName).GetMethod("MemoryBarrier", []); public bool ExperimentalOptimizations = JVM.SafeGetEnvironmentVariable("IKVM_EXPERIMENTAL_OPTIMIZATIONS") != null; @@ -79,7 +79,7 @@ public CodeEmitterFactory(RuntimeContext context) /// public CodeEmitter Create(MethodBuilder mb) { - return new CodeEmitter(context, mb.GetILGenerator(), mb.DeclaringType); + return new CodeEmitter(context, mb.GetILGenerator(), context.Resolver.ResolveType(mb.DeclaringType)); } #if IMPORTER == false @@ -110,7 +110,7 @@ sealed class CodeEmitter CodeEmitterLocal[] tempLocals = new CodeEmitterLocal[32]; ISymbolDocumentWriter symbols; List code = new List(10); - readonly Type declaringType; + readonly ITypeSymbol declaringType; enum CodeType : short { @@ -216,11 +216,11 @@ internal OpCodeWrapper(OpCode opcode, object data) internal long ValueInt64 => (long)data; - internal Type Type => (Type)data; + internal ITypeSymbol Type => (ITypeSymbol)data; - internal FieldInfo FieldInfo => (FieldInfo)data; + internal IFieldSymbol FieldInfo => (IFieldSymbol)data; - internal MethodBase MethodBase => (MethodBase)data; + internal IMethodBaseSymbol MethodBase => (IMethodBaseSymbol)data; internal void RealEmit(int ilOffset, CodeEmitter codeEmitter, ref int lineNumber) { @@ -254,14 +254,14 @@ sealed class CalliWrapper { internal readonly CallingConvention unmanagedCallConv; - internal readonly Type returnType; - internal readonly Type[] parameterTypes; + internal readonly ITypeSymbol returnType; + internal readonly ITypeSymbol[] parameterTypes; - internal CalliWrapper(CallingConvention unmanagedCallConv, Type returnType, Type[] parameterTypes) + internal CalliWrapper(CallingConvention unmanagedCallConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) { this.unmanagedCallConv = unmanagedCallConv; this.returnType = returnType; - this.parameterTypes = parameterTypes == null ? null : (Type[])parameterTypes.Clone(); + this.parameterTypes = parameterTypes == null ? null : (ITypeSymbol[])parameterTypes.Clone(); } } @@ -270,16 +270,16 @@ sealed class ManagedCalliWrapper { internal readonly CallingConventions callConv; - internal readonly Type returnType; - internal readonly Type[] parameterTypes; - internal readonly Type[] optionalParameterTypes; + internal readonly ITypeSymbol returnType; + internal readonly ITypeSymbol[] parameterTypes; + internal readonly ITypeSymbol[] optionalParameterTypes; - internal ManagedCalliWrapper(CallingConventions callConv, Type returnType, Type[] parameterTypes, Type[] optionalParameterTypes) + internal ManagedCalliWrapper(CallingConventions callConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes, ITypeSymbol[] optionalParameterTypes) { this.callConv = callConv; this.returnType = returnType; - this.parameterTypes = parameterTypes == null ? null : (Type[])parameterTypes.Clone(); - this.optionalParameterTypes = optionalParameterTypes == null ? null : (Type[])optionalParameterTypes.Clone(); + this.parameterTypes = parameterTypes == null ? null : (ITypeSymbol[])parameterTypes.Clone(); + this.optionalParameterTypes = optionalParameterTypes == null ? null : (ITypeSymbol[])optionalParameterTypes.Clone(); } } @@ -290,7 +290,7 @@ internal ManagedCalliWrapper(CallingConventions callConv, Type returnType, Type[ /// /// /// - public CodeEmitter(RuntimeContext context, ILGenerator ilgen, Type declaringType) + public CodeEmitter(RuntimeContext context, ILGenerator ilgen, ITypeSymbol declaringType) { this.context = context; this.ilgen_real = ilgen; @@ -345,7 +345,7 @@ private void RealEmitPseudoOpCode(int ilOffset, CodeType type, object data) ilgen_real.BeginExceptionBlock(); break; case CodeType.BeginCatchBlock: - ilgen_real.BeginCatchBlock((Type)data); + ilgen_real.BeginCatchBlock(((ITypeSymbol)data).AsReflection()); break; case CodeType.BeginFaultBlock: ilgen_real.BeginFaultBlock(); @@ -358,13 +358,13 @@ private void RealEmitPseudoOpCode(int ilOffset, CodeType type, object data) ilgen_real.Emit(OpCodes.Br_S, (sbyte)-2); // bogus target of implicit leave break; case CodeType.MemoryBarrier: - ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MemoryBarrierMethod); + ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MemoryBarrierMethod.AsReflection()); break; case CodeType.MonitorEnter: - ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MonitorEnterMethod); + ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MonitorEnterMethod.AsReflection()); break; case CodeType.MonitorExit: - ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MonitorExitMethod); + ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MonitorExitMethod.AsReflection()); break; case CodeType.TailCallPrevention: ilgen_real.Emit(OpCodes.Ldnull); @@ -398,17 +398,17 @@ void RealEmitOpCode(OpCode opcode, object arg) { ilgen_real.Emit(opcode, l); } - else if (arg is MethodInfo mi) + else if (arg is IMethodSymbol mi) { - ilgen_real.Emit(opcode, mi); + ilgen_real.Emit(opcode, mi.AsReflection()); } - else if (arg is ConstructorInfo ci) + else if (arg is IConstructorSymbol ci) { - ilgen_real.Emit(opcode, ci); + ilgen_real.Emit(opcode, ci.AsReflection()); } - else if (arg is FieldInfo fi) + else if (arg is IFieldSymbol fi) { - ilgen_real.Emit(opcode, fi); + ilgen_real.Emit(opcode, fi.AsReflection()); } else if (arg is sbyte sby) { @@ -434,9 +434,9 @@ void RealEmitOpCode(OpCode opcode, object arg) { ilgen_real.Emit(opcode, s); } - else if (arg is Type type) + else if (arg is ITypeSymbol type) { - ilgen_real.Emit(opcode, type); + ilgen_real.Emit(opcode, type.AsReflection()); } else if (arg is CodeEmitterLocal local) { @@ -456,11 +456,11 @@ void RealEmitOpCode(OpCode opcode, object arg) } else if (arg is ManagedCalliWrapper margs) { - ilgen_real.EmitCalli(opcode, margs.callConv, margs.returnType, margs.parameterTypes, margs.optionalParameterTypes); + ilgen_real.EmitCalli(opcode, margs.callConv, margs.returnType.AsReflection(), margs.parameterTypes.AsReflection(), margs.optionalParameterTypes.AsReflection()); } else if (arg is CalliWrapper args) { - ilgen_real.EmitCalli(opcode, args.unmanagedCallConv, args.returnType, args.parameterTypes); + ilgen_real.EmitCalli(opcode, args.unmanagedCallConv, args.returnType.AsReflection(), args.parameterTypes.AsReflection()); } else { @@ -585,7 +585,7 @@ bool IsSideEffectFreePush(int index) // when the type is initialized (which is what we mean in the rest of the IKVM code as well) // but it is good to point it out here because strictly speaking we're violating the // BeforeFieldInit contract here by considering dummy loads not to be field accesses. - if ((field.DeclaringType.Attributes & TypeAttributes.BeforeFieldInit) != 0) + if ((field.DeclaringType.Attributes & System.Reflection.TypeAttributes.BeforeFieldInit) != 0) { return true; } @@ -833,7 +833,7 @@ void OptimizePatterns() } } - bool MatchCompare(int index, OpCode cmp1, OpCode cmp2, Type type) + bool MatchCompare(int index, OpCode cmp1, OpCode cmp2, ITypeSymbol type) { return code[index].opcode == OpCodes.Stloc && code[index].Local.LocalType == type && code[index + 1].opcode == OpCodes.Stloc && code[index + 1].Local.LocalType == type @@ -2115,33 +2115,31 @@ internal void DefineSymbolDocument(ModuleBuilder module, string url, Guid langua #endif } - internal CodeEmitterLocal UnsafeAllocTempLocal(Type type) + internal CodeEmitterLocal UnsafeAllocTempLocal(ITypeSymbol type) { int free = -1; for (int i = 0; i < tempLocals.Length; i++) { - CodeEmitterLocal lb = tempLocals[i]; + var lb = tempLocals[i]; if (lb == null) { if (free == -1) - { free = i; - } } else if (lb.LocalType == type) { return lb; } } - CodeEmitterLocal lb1 = DeclareLocal(type); + + var lb1 = DeclareLocal(type); if (free != -1) - { tempLocals[free] = lb1; - } + return lb1; } - internal CodeEmitterLocal AllocTempLocal(Type type) + internal CodeEmitterLocal AllocTempLocal(ITypeSymbol type) { for (int i = 0; i < tempLocals.Length; i++) { @@ -2170,7 +2168,7 @@ internal void ReleaseTempLocal(CodeEmitterLocal lb) } } - internal void BeginCatchBlock(Type exceptionType) + internal void BeginCatchBlock(ITypeSymbol exceptionType) { EmitPseudoOpCode(CodeType.BeginCatchBlock, exceptionType); } @@ -2199,7 +2197,7 @@ internal void BeginScope() EmitPseudoOpCode(CodeType.BeginScope, null); } - internal CodeEmitterLocal DeclareLocal(Type localType) + internal CodeEmitterLocal DeclareLocal(ITypeSymbol localType) { var local = new CodeEmitterLocal(localType); EmitPseudoOpCode(CodeType.DeclareLocal, local); @@ -2221,7 +2219,7 @@ internal void EmitUnaligned(byte alignment) EmitOpCode(OpCodes.Unaligned, alignment); } - internal void Emit(OpCode opcode, MethodBase mb) + internal void Emit(OpCode opcode, IMethodBaseSymbol mb) { EmitOpCode(opcode, mb); } @@ -2231,7 +2229,7 @@ internal void EmitLdc_R8(double arg) EmitOpCode(OpCodes.Ldc_R8, arg); } - internal void Emit(OpCode opcode, FieldInfo field) + internal void Emit(OpCode opcode, IFieldSymbol field) { EmitOpCode(opcode, field); } @@ -2374,17 +2372,17 @@ internal void Emit(OpCode opcode, string arg) EmitOpCode(opcode, arg); } - internal void Emit(OpCode opcode, Type cls) + internal void Emit(OpCode opcode, ITypeSymbol cls) { EmitOpCode(opcode, cls); } - internal void EmitCalli(OpCode opcode, CallingConvention unmanagedCallConv, Type returnType, Type[] parameterTypes) + internal void EmitCalli(OpCode opcode, CallingConvention unmanagedCallConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) { EmitOpCode(opcode, new CalliWrapper(unmanagedCallConv, returnType, parameterTypes)); } - internal void EmitCalli(OpCode opcode, CallingConventions unmanagedCallConv, Type returnType, Type[] parameterTypes, Type[] optionalParameterTypes) + internal void EmitCalli(OpCode opcode, CallingConventions unmanagedCallConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes, ITypeSymbol[] optionalParameterTypes) { EmitOpCode(opcode, new ManagedCalliWrapper(unmanagedCallConv, returnType, parameterTypes, optionalParameterTypes)); } @@ -2405,9 +2403,9 @@ internal void MarkLabel(CodeEmitterLabel loc) EmitPseudoOpCode(CodeType.Label, loc); } - internal void ThrowException(Type excType) + internal void ThrowException(ITypeSymbol excType) { - Emit(OpCodes.Newobj, excType.GetConstructor(Type.EmptyTypes)); + Emit(OpCodes.Newobj, excType.GetConstructor([])); Emit(OpCodes.Throw); } @@ -2462,7 +2460,7 @@ internal void EmitNullCheck() Emit(OpCodes.Pop); } - internal void EmitCastclass(Type type) + internal void EmitCastclass(ITypeSymbol type) { if (context.CodeEmitterFactory.VerboseCastFailureMethod != null) { @@ -2488,7 +2486,7 @@ internal void EmitCastclass(Type type) // This is basically the same as Castclass, except that it // throws an IncompatibleClassChangeError on failure. - internal void EmitAssertType(Type type) + internal void EmitAssertType(ITypeSymbol type) { var isnull = DefineLabel(); Emit(OpCodes.Dup); @@ -2504,7 +2502,7 @@ internal void EmitAssertType(Type type) MarkLabel(ok); } - internal void EmitUnboxSpecial(Type type) + internal void EmitUnboxSpecial(ITypeSymbol type) { // NOTE if the reference is null, we treat it as a default instance of the value type. var label1 = DefineLabel(); @@ -2569,7 +2567,7 @@ internal void Emit_ldiv() MarkLabel(label2); } - internal void Emit_instanceof(Type type) + internal void Emit_instanceof(ITypeSymbol type) { Emit(OpCodes.Isinst, type); Emit(OpCodes.Ldnull); @@ -2605,7 +2603,7 @@ internal void Emit_if_le_lt_ge_gt(Comparison comp, CodeEmitterLabel label) } } - private void EmitCmp(Type type, OpCode cmp1, OpCode cmp2) + private void EmitCmp(ITypeSymbol type, OpCode cmp1, OpCode cmp2) { var value1 = AllocTempLocal(type); var value2 = AllocTempLocal(type); diff --git a/src/IKVM.Runtime/CodeEmitterLocal.cs b/src/IKVM.Runtime/CodeEmitterLocal.cs index d9f8e2b265..6f9161b3a7 100644 --- a/src/IKVM.Runtime/CodeEmitterLocal.cs +++ b/src/IKVM.Runtime/CodeEmitterLocal.cs @@ -21,14 +21,13 @@ Jeroen Frijters jeroen@frijters.net */ -using System; +using IKVM.CoreLib.Symbols; #if IMPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; -using Type = IKVM.Reflection.Type; #else using System.Reflection.Emit; + #endif namespace IKVM.Runtime @@ -37,16 +36,16 @@ namespace IKVM.Runtime sealed class CodeEmitterLocal { - private Type type; + private ITypeSymbol type; private string name; private LocalBuilder local; - internal CodeEmitterLocal(Type type) + internal CodeEmitterLocal(ITypeSymbol type) { this.type = type; } - internal Type LocalType + internal ITypeSymbol LocalType { get { return type; } } @@ -64,13 +63,13 @@ internal int __LocalIndex internal void Emit(ILGenerator ilgen, OpCode opcode) { // it's a temporary local that is only allocated on-demand - local ??= ilgen.DeclareLocal(type); + local ??= ilgen.DeclareLocal(type.AsReflection()); ilgen.Emit(opcode, local); } internal void Declare(ILGenerator ilgen) { - local = ilgen.DeclareLocal(type); + local = ilgen.DeclareLocal(type.AsReflection()); #if NETFRAMEWORK || IMPORTER if (name != null) diff --git a/src/IKVM.Runtime/DefineMethodHelper.cs b/src/IKVM.Runtime/DefineMethodHelper.cs index f04b221f46..5468da3375 100644 --- a/src/IKVM.Runtime/DefineMethodHelper.cs +++ b/src/IKVM.Runtime/DefineMethodHelper.cs @@ -74,7 +74,7 @@ internal MethodBuilder DefineMethod(RuntimeJavaTypeFactory context, TypeBuilder if (firstParameter != null) { parameterTypes[0] = firstParameter; - modopt[0] = Type.EmptyTypes; + modopt[0] = []; } for (int i = 0; i < parameters.Length; i++) { diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index fd0caf88a2..b8f86ec232 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -529,7 +529,7 @@ public static ModuleBuilder CreateModuleBuilder(RuntimeContext context, Assembly #if NETFRAMEWORK if (!AppDomain.CurrentDomain.IsFullyTrusted) - attribs.Add(new CustomAttributeBuilder(typeof(System.Security.SecurityTransparentAttribute).GetConstructor(Type.EmptyTypes), new object[0])); + attribs.Add(new CustomAttributeBuilder(typeof(System.Security.SecurityTransparentAttribute).GetConstructor([]), [])); #endif var assemblyBuilder = DefineDynamicAssembly(name, access, attribs); @@ -548,7 +548,7 @@ public static ModuleBuilder CreateModuleBuilder(RuntimeContext context, Assembly var moduleBuilder = assemblyBuilder.DefineDynamicModule(name.Name); #endif - moduleBuilder.SetCustomAttribute(new CustomAttributeBuilder(typeof(IKVM.Attributes.JavaModuleAttribute).GetConstructor(Type.EmptyTypes), new object[0])); + moduleBuilder.SetCustomAttribute(new CustomAttributeBuilder(typeof(IKVM.Attributes.JavaModuleAttribute).GetConstructor([]), [])); return moduleBuilder; } diff --git a/src/IKVM.Runtime/EnumHelper.cs b/src/IKVM.Runtime/EnumHelper.cs index 1e6917c62d..90173db618 100644 --- a/src/IKVM.Runtime/EnumHelper.cs +++ b/src/IKVM.Runtime/EnumHelper.cs @@ -24,11 +24,7 @@ Jeroen Frijters using System; using System.Diagnostics; -#if IMPORTER || EXPORTER -using IKVM.Reflection; - -using Type = IKVM.Reflection.Type; -#endif +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { @@ -36,24 +32,13 @@ namespace IKVM.Runtime static class EnumHelper { - internal static Type GetUnderlyingType(Type enumType) - { - -#if IMPORTER || EXPORTER - return enumType.GetEnumUnderlyingType(); -#else - return Enum.GetUnderlyingType(enumType); -#endif - } - -#if IMPORTER - - internal static object Parse(RuntimeContext context, Type type, string value) + internal static object Parse(RuntimeContext context, ITypeSymbol type, string value) { object retval = null; + foreach (string str in value.Split(',')) { - FieldInfo field = type.GetField(str.Trim(), BindingFlags.Public | BindingFlags.Static); + var field = type.GetField(str.Trim(), System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static); if (field == null) { throw new InvalidOperationException("Enum value '" + str + "' not found in " + type.FullName); @@ -70,7 +55,6 @@ internal static object Parse(RuntimeContext context, Type type, string value) return retval; } -#endif // note that we only support the integer types that C# supports // (the CLI also supports bool, char, IntPtr & UIntPtr) @@ -86,7 +70,7 @@ internal static object OrBoxedIntegrals(RuntimeContext context, object v1, objec else { long v = ((IConvertible)v1).ToInt64(null) | ((IConvertible)v2).ToInt64(null); - switch (Type.GetTypeCode(context.Resolver.ResolveCoreType(v1.GetType().FullName).AsReflection())) + switch (context.Resolver.ResolveCoreType(v1.GetType().FullName).TypeCode) { case TypeCode.SByte: return (sbyte)v; @@ -109,7 +93,7 @@ internal static object OrBoxedIntegrals(RuntimeContext context, object v1, objec } // this method can be used to convert an enum value or its underlying value to a Java primitive - internal static object GetPrimitiveValue(RuntimeContext context, Type underlyingType, object obj) + internal static object GetPrimitiveValue(RuntimeContext context, ITypeSymbol underlyingType, object obj) { // Note that this method doesn't trust that obj is of the correct type, // because it turns out there exist assemblies (e.g. gtk-sharp.dll) that diff --git a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs new file mode 100644 index 0000000000..09b5a01401 --- /dev/null +++ b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs @@ -0,0 +1,28 @@ +using System; + +using IKVM.CoreLib.Symbols; + +#if IMPORTER || EXPORTER +using Type = IKVM.Reflection.Type; +#endif + +namespace IKVM.Runtime +{ + + /// + /// Provides an interface to resolve a managed type symbols extended for the Runtime classes. + /// + interface IRuntimeSymbolResolver : ISymbolResolver + { + + /// + /// Gets the associated with the specified type. + /// + /// + /// + ITypeSymbol ResolveType(Type type); + + } + + +} diff --git a/src/IKVM.Runtime/JNI/JNIEnv.cs b/src/IKVM.Runtime/JNI/JNIEnv.cs index be813a7e4a..51a0c46f15 100644 --- a/src/IKVM.Runtime/JNI/JNIEnv.cs +++ b/src/IKVM.Runtime/JNI/JNIEnv.cs @@ -353,7 +353,7 @@ internal static jint ThrowNew(JNIEnv* pEnv, nint clazz, byte* msg) { wrapper.Finish(); var cons = (java.lang.reflect.Constructor)mw.ToMethodOrConstructor(false); - JVM.SetPendingException((Exception)cons.newInstance(msg == null ? new object[0] : new object[] { DecodeMUTF8Argument(msg, nameof(msg)) }, env.callerID)); + JVM.SetPendingException((Exception)cons.newInstance(msg == null ? [] : new object[] { DecodeMUTF8Argument(msg, nameof(msg)) }, env.callerID)); return JNI_OK; } catch (RetargetableJavaException x) diff --git a/src/IKVM.Runtime/JVM.Resolver.cs b/src/IKVM.Runtime/JVM.Resolver.cs index b366e9e5a4..18fc01b756 100644 --- a/src/IKVM.Runtime/JVM.Resolver.cs +++ b/src/IKVM.Runtime/JVM.Resolver.cs @@ -9,6 +9,10 @@ using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Reflection; +#if IMPORTER || EXPORTER +using Type = IKVM.Reflection.Type; +#endif + namespace IKVM.Runtime { @@ -20,7 +24,7 @@ static partial class JVM /// /// Provides support for resolving managed types from the current JVM environment. /// - internal class Resolver : ISymbolResolver + internal class Resolver : IRuntimeSymbolResolver { /// @@ -87,6 +91,12 @@ public ITypeSymbol ResolveRuntimeType(string typeName) return typeof(Resolver).Assembly.GetType(typeName) is { } t ? _context.GetOrCreateTypeSymbol(t) : null; } + /// + public ITypeSymbol ResolveType(Type type) + { + return type is { } t ? _context.GetOrCreateTypeSymbol(t) : null; + } + } } diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs index e0ae4ff524..ea4d8fa576 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs @@ -72,7 +72,7 @@ static class Class var type = Type.GetType(name); if (type != null) - tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(type); + tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.ResolveType(type)); if (tw == null) { @@ -359,6 +359,7 @@ public static object[] getEnclosingMethod0(global::java.lang.Class thisClass) { var wrapper = RuntimeJavaType.FromClass(thisClass); wrapper.Finish(); + var decl = wrapper.DeclaringTypeWrapper; if (decl == null) return null; @@ -368,7 +369,7 @@ public static object[] getEnclosingMethod0(global::java.lang.Class thisClass) throw new IllegalAccessError(string.Format("tried to access class {0} from class {1}", decl.Name, wrapper.Name)); decl.Finish(); - RuntimeJavaType[] declInner = decl.InnerClasses; + var declInner = decl.InnerClasses; for (int i = 0; i < declInner.Length; i++) { if (declInner[i].Name == wrapper.Name && declInner[i].EnsureLoadable(decl.ClassLoader) == wrapper) @@ -398,8 +399,7 @@ public static object[] getEnclosingMethod0(global::java.lang.Class thisClass) { // The protection domain for statically compiled code is created lazily (not at global::java.lang.Class creation time), // to work around boot strap issues. - var acl = wrapper.ClassLoader as RuntimeAssemblyClassLoader; - if (acl != null) + if (wrapper.ClassLoader is RuntimeAssemblyClassLoader acl) pd = acl.GetProtectionDomain(); else if (wrapper is RuntimeAnonymousJavaType) { @@ -445,7 +445,7 @@ public static object[] getEnclosingMethod0(global::java.lang.Class thisClass) public static string getGenericSignature0(global::java.lang.Class thisClass) { - RuntimeJavaType tw = RuntimeJavaType.FromClass(thisClass); + var tw = RuntimeJavaType.FromClass(thisClass); tw.Finish(); return tw.GetGenericSignature(); } @@ -453,14 +453,14 @@ public static string getGenericSignature0(global::java.lang.Class thisClass) internal static object AnnotationsToMap(RuntimeClassLoader loader, object[] objAnn) { #if FIRST_PASS - return null; + throw new NotImplementedException(); #else - global::java.util.LinkedHashMap map = new global::java.util.LinkedHashMap(); + var map = new global::java.util.LinkedHashMap(); if (objAnn != null) { foreach (object obj in objAnn) { - global::java.lang.annotation.Annotation a = obj as global::java.lang.annotation.Annotation; + var a = obj as global::java.lang.annotation.Annotation; if (a != null) { map.put(a.annotationType(), FreezeOrWrapAttribute(a)); @@ -469,12 +469,11 @@ internal static object AnnotationsToMap(RuntimeClassLoader loader, object[] objA { a = (global::java.lang.annotation.Annotation)JVM.NewAnnotation(loader.GetJavaClassLoader(), ((IKVM.Attributes.DynamicAnnotationAttribute)obj).Definition); if (a != null) - { map.put(a.annotationType(), a); - } } } } + return map; #endif } @@ -500,9 +499,10 @@ internal static object AnnotationsToMap(RuntimeClassLoader loader, object[] objA public static object getDeclaredAnnotationsImpl(global::java.lang.Class thisClass) { #if FIRST_PASS - return null; + throw new NotImplementedException(); #else - RuntimeJavaType wrapper = RuntimeJavaType.FromClass(thisClass); + var wrapper = RuntimeJavaType.FromClass(thisClass); + try { wrapper.Finish(); @@ -511,6 +511,7 @@ public static object getDeclaredAnnotationsImpl(global::java.lang.Class thisClas { throw x.ToJava(); } + return AnnotationsToMap(wrapper.ClassLoader, wrapper.GetDeclaredAnnotations()); #endif } @@ -518,16 +519,17 @@ public static object getDeclaredAnnotationsImpl(global::java.lang.Class thisClas public static object getDeclaredFields0(global::java.lang.Class thisClass, bool publicOnly) { #if FIRST_PASS - return null; + throw new NotImplementedException(); #else Profiler.Enter("Class.getDeclaredFields0"); + try { - RuntimeJavaType wrapper = RuntimeJavaType.FromClass(thisClass); - // we need to finish the type otherwise all fields will not be in the field map yet + var wrapper = RuntimeJavaType.FromClass(thisClass); wrapper.Finish(); - RuntimeJavaField[] fields = wrapper.GetFields(); - List list = new List(); + + var fields = wrapper.GetFields(); + var list = new List(); for (int i = 0; i < fields.Length; i++) { if (fields[i].IsHideFromReflection) @@ -543,6 +545,7 @@ public static object getDeclaredFields0(global::java.lang.Class thisClass, bool list.Add((global::java.lang.reflect.Field)fields[i].ToField(false, i)); } } + return list.ToArray(); } catch (RetargetableJavaException x) @@ -606,7 +609,7 @@ public static object getDeclaredMethods0(global::java.lang.Class thisClass, bool public static object getDeclaredConstructors0(global::java.lang.Class thisClass, bool publicOnly) { #if FIRST_PASS - return null; + throw new NotImplementedException(); #else Profiler.Enter("Class.getDeclaredConstructors0"); try @@ -652,7 +655,7 @@ public static object getDeclaredConstructors0(global::java.lang.Class thisClass, public static global::java.lang.Class[] getDeclaredClasses0(global::java.lang.Class thisClass) { #if FIRST_PASS - return null; + throw new NotImplementedException(); #else try { diff --git a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs index 5c6488df91..3997dd1f83 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs @@ -310,14 +310,14 @@ sealed class BoxUtil static readonly MethodInfo valueOfFloat = typeof(global::java.lang.Float).GetMethod("valueOf", new Type[] { typeof(float) }); static readonly MethodInfo valueOfLong = typeof(global::java.lang.Long).GetMethod("valueOf", new Type[] { typeof(long) }); static readonly MethodInfo valueOfDouble = typeof(global::java.lang.Double).GetMethod("valueOf", new Type[] { typeof(double) }); - static readonly MethodInfo byteValue = typeof(global::java.lang.Byte).GetMethod("byteValue", Type.EmptyTypes); - static readonly MethodInfo booleanValue = typeof(global::java.lang.Boolean).GetMethod("booleanValue", Type.EmptyTypes); - static readonly MethodInfo charValue = typeof(global::java.lang.Character).GetMethod("charValue", Type.EmptyTypes); - static readonly MethodInfo shortValue = typeof(global::java.lang.Short).GetMethod("shortValue", Type.EmptyTypes); - static readonly MethodInfo intValue = typeof(global::java.lang.Integer).GetMethod("intValue", Type.EmptyTypes); - static readonly MethodInfo floatValue = typeof(global::java.lang.Float).GetMethod("floatValue", Type.EmptyTypes); - static readonly MethodInfo longValue = typeof(global::java.lang.Long).GetMethod("longValue", Type.EmptyTypes); - static readonly MethodInfo doubleValue = typeof(global::java.lang.Double).GetMethod("doubleValue", Type.EmptyTypes); + static readonly MethodInfo byteValue = typeof(global::java.lang.Byte).GetMethod("byteValue", []); + static readonly MethodInfo booleanValue = typeof(global::java.lang.Boolean).GetMethod("booleanValue", []); + static readonly MethodInfo charValue = typeof(global::java.lang.Character).GetMethod("charValue", []); + static readonly MethodInfo shortValue = typeof(global::java.lang.Short).GetMethod("shortValue", []); + static readonly MethodInfo intValue = typeof(global::java.lang.Integer).GetMethod("intValue", []); + static readonly MethodInfo floatValue = typeof(global::java.lang.Float).GetMethod("floatValue", []); + static readonly MethodInfo longValue = typeof(global::java.lang.Long).GetMethod("longValue", []); + static readonly MethodInfo doubleValue = typeof(global::java.lang.Double).GetMethod("doubleValue", []); internal static void EmitUnboxArg(CodeEmitter ilgen, RuntimeJavaType type) { @@ -522,9 +522,9 @@ sealed class FastMethodAccessorImpl : global::sun.reflect.MethodAccessor /// static FastMethodAccessorImpl() { - nullPointerExceptionCtor = typeof(global::java.lang.NullPointerException).GetConstructor(Type.EmptyTypes); + nullPointerExceptionCtor = typeof(global::java.lang.NullPointerException).GetConstructor([]); nullPointerExceptionWithMessageCtor = typeof(global::java.lang.NullPointerException).GetConstructor(new[] { typeof(string) }); - illegalArgumentExceptionCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor(Type.EmptyTypes); + illegalArgumentExceptionCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor([]); illegalArgumentExceptionWithMessageCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor(new[] { typeof(string) }); illegalArgumentExceptionWithMessageAndCauseCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor(new[] { typeof(string), typeof(Exception) }); illegalArgumentExceptionWithCauseCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor(new[] { typeof(Exception) }); diff --git a/src/IKVM.Runtime/LambdaMetafactory.cs b/src/IKVM.Runtime/LambdaMetafactory.cs index fd160d6cf1..ea553973bc 100644 --- a/src/IKVM.Runtime/LambdaMetafactory.cs +++ b/src/IKVM.Runtime/LambdaMetafactory.cs @@ -419,7 +419,7 @@ private static MethodBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaTyp MethodBuilder ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, capturedTypes); CodeEmitter ilgen = context.Context.CodeEmitterFactory.Create(ctor); ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Call, context.Context.Types.Object.GetConstructor(Type.EmptyTypes)); + ilgen.Emit(OpCodes.Call, context.Context.Types.Object.GetConstructor([])); for (int i = 0; i < capturedTypes.Length; i++) { ilgen.EmitLdarg(0); @@ -471,7 +471,7 @@ private static MethodBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaTyp // writeReplace method if (serializable) { - MethodBuilder writeReplace = tb.DefineMethod("writeReplace", MethodAttributes.Private, context.Context.Types.Object, Type.EmptyTypes); + MethodBuilder writeReplace = tb.DefineMethod("writeReplace", MethodAttributes.Private, context.Context.Types.Object, []); ilgen = context.Context.CodeEmitterFactory.Create(writeReplace); context.TypeWrapper.EmitClassLiteral(ilgen); ilgen.Emit(OpCodes.Ldstr, cpi.GetRetType().Name.Replace('.', '/')); diff --git a/src/IKVM.Runtime/MethodHandleUtil.root.cs b/src/IKVM.Runtime/MethodHandleUtil.root.cs index 40fa2d848d..414420e073 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.root.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.root.cs @@ -23,14 +23,7 @@ Jeroen Frijters */ using System; -#if IMPORTER -using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { @@ -42,9 +35,9 @@ partial class MethodHandleUtil readonly RuntimeContext context; - readonly Type typeofMHA; - readonly Type[] typeofMHV; - readonly Type[] typeofMH; + readonly ITypeSymbol typeofMHA; + readonly ITypeSymbol[] typeofMHV; + readonly ITypeSymbol[] typeofMH; /// /// Initializes a new instance. @@ -53,58 +46,56 @@ public MethodHandleUtil(RuntimeContext context) { this.context = context ?? throw new ArgumentNullException(nameof(context)); - typeofMHA = context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHA`8").AsReflection(); - typeofMHV = new Type[] { - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`1").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`2").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`3").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`4").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`5").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`6").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`7").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`8").AsReflection(), + typeofMHA = context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHA`8"); + typeofMHV = new[] { + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`1"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`2"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`3"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`4"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`5"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`6"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`7"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`8"), }; - typeofMH = new Type[] { + typeofMH = new[] { null, - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`1").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`2").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`3").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`4").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`5").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`6").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`7").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`8").AsReflection(), - context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`9").AsReflection(), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`1"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`2"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`3"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`4"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`5"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`6"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`7"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`8"), + context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`9"), }; } - internal bool IsPackedArgsContainer(Type type) + internal bool IsPackedArgsContainer(ITypeSymbol type) { return type.IsGenericType && type.GetGenericTypeDefinition() == typeofMHA; } - internal Type CreateMethodHandleDelegateType(RuntimeJavaType[] args, RuntimeJavaType ret) + internal ITypeSymbol CreateMethodHandleDelegateType(RuntimeJavaType[] args, RuntimeJavaType ret) { - Type[] typeArgs = new Type[args.Length]; + var typeArgs = new ITypeSymbol[args.Length]; for (int i = 0; i < args.Length; i++) - { typeArgs[i] = args[i].TypeAsSignatureType; - } + return CreateDelegateType(typeArgs, ret.TypeAsSignatureType); } - internal Type CreateMemberWrapperDelegateType(RuntimeJavaType[] args, RuntimeJavaType ret) + internal ITypeSymbol CreateMemberWrapperDelegateType(RuntimeJavaType[] args, RuntimeJavaType ret) { - Type[] typeArgs = new Type[args.Length]; + var typeArgs = new ITypeSymbol[args.Length]; for (int i = 0; i < args.Length; i++) - { typeArgs[i] = AsBasicType(args[i]); - } + return CreateDelegateType(typeArgs, AsBasicType(ret)); } - Type CreateDelegateType(Type[] types, Type retType) + ITypeSymbol CreateDelegateType(ITypeSymbol[] types, ITypeSymbol retType) { if (types.Length == 0 && retType == context.Types.Void) { @@ -144,14 +135,14 @@ Type CreateDelegateType(Type[] types, Type retType) } } - Type[] SubArray(Type[] inArray, int start, int length) + ITypeSymbol[] SubArray(ITypeSymbol[] inArray, int start, int length) { - var outArray = new Type[length]; + var outArray = new ITypeSymbol[length]; Array.Copy(inArray, start, outArray, 0, length); return outArray; } - internal Type AsBasicType(RuntimeJavaType tw) + internal ITypeSymbol AsBasicType(RuntimeJavaType tw) { if (tw == context.PrimitiveJavaTypeFactory.BOOLEAN || tw == context.PrimitiveJavaTypeFactory.BYTE || tw == context.PrimitiveJavaTypeFactory.CHAR || tw == context.PrimitiveJavaTypeFactory.SHORT || tw == context.PrimitiveJavaTypeFactory.INT) return context.Types.Int32; @@ -161,7 +152,7 @@ internal Type AsBasicType(RuntimeJavaType tw) return context.Types.Object; } - internal bool HasOnlyBasicTypes(RuntimeJavaType[] args, RuntimeJavaType ret) + internal bool HasOnlyBasicTypes(RuntimeJavaType[] args, RuntimeJavaType ret) { foreach (var tw in args) if (!IsBasicType(tw)) diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index e219ae4c2d..31889ad730 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -23,6 +23,9 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; + + #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -39,78 +42,66 @@ namespace IKVM.Runtime static class ReflectUtil { - internal static bool IsSameAssembly(Type type1, Type type2) + internal static bool IsSameAssembly(ITypeSymbol type1, ITypeSymbol type2) { return type1.Assembly.Equals(type2.Assembly); } - internal static bool IsFromAssembly(Type type, Assembly assembly) + internal static bool IsFromAssembly(ITypeSymbol type, IAssemblySymbol assembly) { return type.Assembly.Equals(assembly); } - internal static Assembly GetAssembly(Type type) + internal static IAssemblySymbol GetAssembly(ITypeSymbol type) { return type.Assembly; } - internal static bool IsDynamicAssembly(Assembly asm) + internal static bool IsDynamicAssembly(IAssemblySymbol asm) { #if IMPORTER || EXPORTER return false; #else - return asm.IsDynamic; + return asm.AsReflection().IsDynamic; #endif } - internal static bool IsReflectionOnly(Type type) + internal static bool IsReflectionOnly(ITypeSymbol type) { while (type.HasElementType) type = type.GetElementType(); var asm = type.Assembly; - if (asm != null && asm.ReflectionOnly) + if (asm != null && asm.AsReflection().ReflectionOnly) return true; if (!type.IsGenericType || type.IsGenericTypeDefinition) return false; // we have a generic type instantiation, it might have ReflectionOnly type arguments - foreach (Type arg in type.GetGenericArguments()) + foreach (var arg in type.GetGenericArguments()) if (IsReflectionOnly(arg)) return true; return false; } - internal static bool ContainsTypeBuilder(Type type) + internal static bool ContainsTypeBuilder(ITypeSymbol type) { while (type.HasElementType) type = type.GetElementType(); if (!type.IsGenericType || type.IsGenericTypeDefinition) - return type is TypeBuilder; + return type.AsReflection() is TypeBuilder; - foreach (Type arg in type.GetGenericArguments()) + foreach (var arg in type.GetGenericArguments()) if (ContainsTypeBuilder(arg)) return true; - return type.GetGenericTypeDefinition() is TypeBuilder; - } - - internal static bool IsVector(Type type) - { -#if IMPORTER || EXPORTER - return type.__IsVector; -#else - // there's no API to distinguish an array of rank 1 from a vector, - // so we check if the type name ends in [], which indicates it's a vector - // (non-vectors will have [*] or [,]). - return type.IsArray && type.Name.EndsWith("[]"); -#endif + return type.GetGenericTypeDefinition().AsReflection() is TypeBuilder; } - internal static bool IsDynamicMethod(MethodInfo method) + internal static bool IsDynamicMethod(IMethodSymbol method) { // there's no way to distinguish a baked DynamicMethod from a RuntimeMethodInfo and // on top of that Mono behaves completely different from .NET @@ -128,10 +119,10 @@ internal static bool IsDynamicMethod(MethodInfo method) internal static MethodBuilder DefineTypeInitializer(TypeBuilder typeBuilder, RuntimeClassLoader loader) { var attr = MethodAttributes.Static | MethodAttributes.RTSpecialName | MethodAttributes.SpecialName | MethodAttributes.Private; - return typeBuilder.DefineMethod(ConstructorInfo.TypeConstructorName, attr, null, Type.EmptyTypes); + return typeBuilder.DefineMethod(ConstructorInfo.TypeConstructorName, attr, null, []); } - internal static bool MatchNameAndPublicKeyToken(AssemblyName name1, AssemblyName name2) + internal static bool MatchNameAndPublicKeyToken(System.Reflection.AssemblyName name1, System.Reflection.AssemblyName name2) { return name1.Name.Equals(name2.Name, StringComparison.OrdinalIgnoreCase) && CompareKeys(name1.GetPublicKeyToken(), name2.GetPublicKeyToken()); } @@ -150,7 +141,7 @@ static bool CompareKeys(byte[] b1, byte[] b2) return true; } - internal static bool IsConstructor(MethodBase method) + internal static bool IsConstructor(IMethodBaseSymbol method) { return method.IsSpecialName && method.Name == ConstructorInfo.ConstructorName; } @@ -165,12 +156,12 @@ internal static MethodBuilder DefineConstructor(TypeBuilder tb, MethodAttributes /// /// /// - internal static bool CanOwnDynamicMethod(Type type) + internal static bool CanOwnDynamicMethod(ITypeSymbol type) { return type != null && !type.IsInterface && !type.HasElementType && !type.IsGenericTypeDefinition && !type.IsGenericParameter; } - internal static bool MatchParameterInfos(ParameterInfo p1, ParameterInfo p2) + internal static bool MatchParameterInfos(IParameterSymbol p1, IParameterSymbol p2) { if (p1.ParameterType != p2.ParameterType) { @@ -187,41 +178,39 @@ internal static bool MatchParameterInfos(ParameterInfo p1, ParameterInfo p2) return true; } - private static bool MatchTypes(Type[] t1, Type[] t2) + private static bool MatchTypes(ITypeSymbol[] t1, ITypeSymbol[] t2) { if (t1.Length == t2.Length) { for (int i = 0; i < t1.Length; i++) - { if (t1[i] != t2[i]) - { return false; - } - } + return true; } + return false; } #if IMPORTER - internal static Type GetMissingType(Type type) + internal static ITypeSymbol GetMissingType(ITypeSymbol type) { while (type.HasElementType) type = type.GetElementType(); - if (type.__IsMissing) + if (type.IsMissing) { return type; } - else if (type.__ContainsMissingType) + else if (type.ContainsMissing) { if (type.IsGenericType) { foreach (var arg in type.GetGenericArguments()) { var t1 = GetMissingType(arg); - if (t1.__IsMissing) + if (t1.IsMissing) return t1; } } diff --git a/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs b/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs index f3cfa81716..e5d2c4518c 100644 --- a/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs @@ -22,14 +22,11 @@ Jeroen Frijters */ using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; #else -using System.Reflection; using System.Reflection.Emit; #endif @@ -39,8 +36,8 @@ namespace IKVM.Runtime sealed class RuntimeAccessStubJavaMethod : RuntimeSmartJavaMethod { - readonly MethodInfo stubVirtual; - readonly MethodInfo stubNonVirtual; + readonly IMethodSymbol stubVirtual; + readonly IMethodSymbol stubNonVirtual; /// /// Initializes a new instance. @@ -55,7 +52,7 @@ sealed class RuntimeAccessStubJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal RuntimeAccessStubJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodInfo core, MethodInfo stubVirtual, MethodInfo stubNonVirtual, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimeAccessStubJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodSymbol core, IMethodSymbol stubVirtual, IMethodSymbol stubNonVirtual, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, name, sig, core, returnType, parameterTypes, modifiers, flags) { this.stubVirtual = stubVirtual; diff --git a/src/IKVM.Runtime/RuntimeAnonymousJavaType.cs b/src/IKVM.Runtime/RuntimeAnonymousJavaType.cs index 9f05717537..86001a66c4 100644 --- a/src/IKVM.Runtime/RuntimeAnonymousJavaType.cs +++ b/src/IKVM.Runtime/RuntimeAnonymousJavaType.cs @@ -26,6 +26,7 @@ Jeroen Frijters using System.Reflection; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { @@ -38,32 +39,32 @@ namespace IKVM.Runtime sealed class RuntimeAnonymousJavaType : RuntimeJavaType { - readonly Type type; + readonly ITypeSymbol type; /// /// Initializes a new instance. /// /// /// - internal RuntimeAnonymousJavaType(RuntimeContext context, Type type) : + internal RuntimeAnonymousJavaType(RuntimeContext context, ITypeSymbol type) : base(context, TypeFlags.Anonymous, Modifiers.Final | Modifiers.Synthetic, GetName(context, type)) { this.type = type; } - internal static bool IsAnonymous(RuntimeContext context, Type type) + internal static bool IsAnonymous(RuntimeContext context, ITypeSymbol type) { return type.IsSpecialName && type.Name.StartsWith(NestedTypeName.IntrinsifiedAnonymousClass, StringComparison.Ordinal) && context.AttributeHelper.IsJavaModule(type.Module); } - private static string GetName(RuntimeContext context, Type type) + private static string GetName(RuntimeContext context, ITypeSymbol type) { return context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).Name + type.Name.Replace(NestedTypeName.IntrinsifiedAnonymousClass, "$$Lambda$"); } internal override RuntimeClassLoader ClassLoader => Context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).ClassLoader; - internal override Type TypeAsTBD + internal override ITypeSymbol TypeAsTBD { get { return type; } } @@ -122,7 +123,7 @@ protected override void LazyPublishMembers() SetFields(fields.ToArray()); } - void GetSig(MethodInfo mi, out RuntimeJavaType returnType, out RuntimeJavaType[] parameterTypes, out string signature) + void GetSig(IMethodSymbol mi, out RuntimeJavaType returnType, out RuntimeJavaType[] parameterTypes, out string signature) { returnType = RuntimeManagedByteCodeJavaType.GetParameterTypeWrapper(Context, mi.ReturnParameter); var parameters = mi.GetParameters(); diff --git a/src/IKVM.Runtime/RuntimeArrayJavaType.cs b/src/IKVM.Runtime/RuntimeArrayJavaType.cs index ed204a85fc..1bcc4c1b8a 100644 --- a/src/IKVM.Runtime/RuntimeArrayJavaType.cs +++ b/src/IKVM.Runtime/RuntimeArrayJavaType.cs @@ -25,6 +25,8 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -68,7 +70,7 @@ internal override RuntimeJavaType BaseTypeWrapper internal static MethodInfo GetCloneMethod(RuntimeContext context) { - return context.Types.Array.GetMethod("Clone", BindingFlags.Public | BindingFlags.Instance, null, Type.EmptyTypes, null); + return context.Types.Array.GetMethod("Clone", BindingFlags.Public | BindingFlags.Instance, null, [], null); } protected override void LazyPublishMembers() @@ -179,18 +181,18 @@ internal override RuntimeJavaType GetUltimateElementTypeWrapper() return ultimateElementTypeWrapper; } - internal static Type MakeArrayType(Type type, int dims) + internal static ITypeSymbol MakeArrayType(ITypeSymbol type, int dims) { // NOTE this is not just an optimization, but it is also required to // make sure that ReflectionOnly types stay ReflectionOnly types // (in particular instantiations of generic types from mscorlib that // have ReflectionOnly type parameters). for (int i = 0; i < dims; i++) - { type = type.MakeArrayType(); - } + return type; } + } } diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index ef11c41dcd..8ce64aa785 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -32,6 +32,8 @@ Jeroen Frijters using IKVM.CoreLib.Diagnostics; using IKVM.Attributes; using IKVM.Runtime.Syntax; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER @@ -68,7 +70,7 @@ internal class RuntimeAssemblyClassLoader : RuntimeClassLoader Dictionary> exports; string[] exportedAssemblyNames; AssemblyLoader[] exportedAssemblies; - Dictionary exportedLoaders; + Dictionary exportedLoaders; /// /// Manages a loaded assembly. @@ -77,13 +79,13 @@ sealed class AssemblyLoader { readonly RuntimeAssemblyClassLoader loader; - readonly Assembly assembly; + readonly IAssemblySymbol assembly; bool[] isJavaModule; - Module[] modules; + IModuleSymbol[] modules; Dictionary nameMap; bool hasDotNetModule; - AssemblyName[] internalsVisibleTo; + System.Reflection.AssemblyName[] internalsVisibleTo; string[] jarList; #if !IMPORTER && !EXPORTER && !FIRST_PASS sun.misc.URLClassPath urlClassPath; @@ -94,7 +96,7 @@ sealed class AssemblyLoader /// /// /// - internal AssemblyLoader(RuntimeAssemblyClassLoader loader, Assembly assembly) + internal AssemblyLoader(RuntimeAssemblyClassLoader loader, IAssemblySymbol assembly) { this.loader = loader ?? throw new ArgumentNullException(nameof(loader)); this.assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); @@ -114,8 +116,7 @@ internal AssemblyLoader(RuntimeAssemblyClassLoader loader, Assembly assembly) var map = jma.GetClassMap(); if (map != null) { - if (nameMap == null) - nameMap = new Dictionary(); + nameMap ??= []; for (int j = 0; j < map.Length; j += 2) { @@ -152,7 +153,7 @@ internal AssemblyLoader(RuntimeAssemblyClassLoader loader, Assembly assembly) } } - internal Assembly Assembly + internal IAssemblySymbol Assembly { get { return assembly; } } @@ -174,7 +175,7 @@ internal bool HasJavaModule /// /// /// - Type GetType(string name) + ITypeSymbol GetType(string name) { try { @@ -197,12 +198,12 @@ Type GetType(string name) } /// - /// Attempts to load a type with the specified name from the given . + /// Attempts to load a type with the specified name from the given . /// /// /// /// - Type GetType(Module module, string name) + ITypeSymbol GetType(IModuleSymbol module, string name) { try { @@ -224,13 +225,12 @@ Type GetType(Module module, string name) return null; } - Type GetJavaType(Module module, string name) + ITypeSymbol GetJavaType(IModuleSymbol module, string name) { try { string n = null; - if (nameMap != null) - nameMap.TryGetValue(name, out n); + nameMap?.TryGetValue(name, out n); var t = GetType(module, n ?? name); if (t == null) @@ -300,6 +300,7 @@ internal RuntimeJavaType DoLoad(string name) // let that generated the manufactured nested classes // (note that for generic outer types, we need to duplicate this in ClassLoaderWrapper.LoadGenericClass) RuntimeJavaType outer = null; + if (name.EndsWith(RuntimeManagedJavaType.DelegateInterfaceSuffix)) { outer = DoLoad(name.Substring(0, name.Length - RuntimeManagedJavaType.DelegateInterfaceSuffix.Length)); @@ -336,7 +337,7 @@ internal RuntimeJavaType DoLoad(string name) /// /// /// - internal JavaTypeName? GetTypeNameAndType(Type type, out bool isJavaType) + internal JavaTypeName? GetTypeNameAndType(ITypeSymbol type, out bool isJavaType) { // find the module index of the type's module var module = type.Module; @@ -373,7 +374,7 @@ internal RuntimeJavaType DoLoad(string name) } } - internal RuntimeJavaType CreateJavaTypeForAssemblyType(Type type) + internal RuntimeJavaType CreateJavaTypeForAssemblyType(ITypeSymbol type) { var name = GetTypeNameAndType(type, out bool isJavaType); if (name == null) @@ -393,7 +394,7 @@ internal RuntimeJavaType CreateJavaTypeForAssemblyType(Type type) } } - internal bool InternalsVisibleTo(AssemblyName otherName) + internal bool InternalsVisibleTo(System.Reflection.AssemblyName otherName) { if (internalsVisibleTo == null) Interlocked.CompareExchange(ref internalsVisibleTo, loader.Context.AttributeHelper.GetInternalsVisibleToAttributes(assembly), null); @@ -438,7 +439,7 @@ internal java.util.Enumeration FindResources(string name) /// /// /// - internal RuntimeAssemblyClassLoader(RuntimeContext context, Assembly assembly) : + internal RuntimeAssemblyClassLoader(RuntimeContext context, IAssemblySymbol assembly) : this(context, assembly, null) { @@ -450,7 +451,7 @@ internal RuntimeAssemblyClassLoader(RuntimeContext context, Assembly assembly) : /// /// /// - internal RuntimeAssemblyClassLoader(RuntimeContext context, Assembly assembly, string[] fixedReferences) : + internal RuntimeAssemblyClassLoader(RuntimeContext context, IAssemblySymbol assembly, string[] fixedReferences) : base(context, CodeGenOptions.None, null) { this.assemblyLoader = new AssemblyLoader(this, assembly); @@ -498,18 +499,18 @@ void DoInitializeExports() { if (delegates == null) { - if (ReflectUtil.IsDynamicAssembly(assemblyLoader.Assembly) == false && assemblyLoader.Assembly.GetManifestResourceInfo("ikvm.exports") != null) + if (ReflectUtil.IsDynamicAssembly(assemblyLoader.Assembly) == false && assemblyLoader.Assembly.AsReflection().GetManifestResourceInfo("ikvm.exports") != null) { var wildcardExports = new List(); - using (var stream = assemblyLoader.Assembly.GetManifestResourceStream("ikvm.exports")) + using (var stream = assemblyLoader.Assembly.AsReflection().GetManifestResourceStream("ikvm.exports")) { var rdr = new BinaryReader(stream); var assemblyCount = rdr.ReadInt32(); exports = new Dictionary>(); exportedAssemblies = new AssemblyLoader[assemblyCount]; exportedAssemblyNames = new string[assemblyCount]; - exportedLoaders = new Dictionary(); + exportedLoaders = new Dictionary(); for (int i = 0; i < assemblyCount; i++) { @@ -554,9 +555,9 @@ void LazyInitExports() DoInitializeExports(); } - internal Assembly MainAssembly => assemblyLoader.Assembly; + internal IAssemblySymbol MainAssembly => assemblyLoader.Assembly; - internal Assembly GetAssembly(RuntimeJavaType wrapper) + internal IAssemblySymbol GetAssembly(RuntimeJavaType wrapper) { Debug.Assert(wrapper.ClassLoader == this); @@ -566,7 +567,7 @@ internal Assembly GetAssembly(RuntimeJavaType wrapper) return wrapper.TypeAsBaseType.Assembly; } - Assembly LoadAssemblyOrClearName(ref string name, bool exported) + IAssemblySymbol LoadAssemblyOrClearName(ref string name, bool exported) { // previous load attempt failed if (name == null) @@ -574,7 +575,7 @@ Assembly LoadAssemblyOrClearName(ref string name, bool exported) try { - return Context.Resolver.ResolveAssembly(name).AsReflection(); + return Context.Resolver.ResolveAssembly(name); } catch { @@ -610,7 +611,7 @@ internal RuntimeJavaType DoLoad(string name) return null; } - internal JavaTypeName? GetTypeNameAndType(Type type, out bool isJavaType) + internal JavaTypeName? GetTypeNameAndType(ITypeSymbol type, out bool isJavaType) { return GetLoader(type.Assembly).GetTypeNameAndType(type, out isJavaType); } @@ -628,9 +629,9 @@ AssemblyLoader TryGetLoaderByIndex(int index) return loader; } - internal List GetAllAvailableAssemblies() + internal List GetAllAvailableAssemblies() { - var list = new List(); + var list = new List(); list.Add(assemblyLoader.Assembly); LazyInitExports(); @@ -648,7 +649,7 @@ internal List GetAllAvailableAssemblies() return list; } - AssemblyLoader GetLoader(Assembly assembly) + AssemblyLoader GetLoader(IAssemblySymbol assembly) { if (assemblyLoader.Assembly == assembly) return assemblyLoader; @@ -656,7 +657,7 @@ AssemblyLoader GetLoader(Assembly assembly) return GetLoaderForExportedAssembly(assembly); } - AssemblyLoader GetLoaderForExportedAssembly(Assembly assembly) + AssemblyLoader GetLoaderForExportedAssembly(IAssemblySymbol assembly) { LazyInitExports(); @@ -691,7 +692,7 @@ AssemblyLoader GetLoaderForExportedAssembly(Assembly assembly) /// /// /// - internal virtual RuntimeJavaType GetJavaTypeFromAssemblyType(Type type) + internal virtual RuntimeJavaType GetJavaTypeFromAssemblyType(ITypeSymbol type) { if (type.Name.EndsWith("[]")) throw new InternalException(); @@ -853,12 +854,12 @@ RuntimeJavaType FindReferenced(string name) #if !IMPORTER && !EXPORTER - static java.net.URL MakeResourceURL(Assembly asm, string name) + static java.net.URL MakeResourceURL(IAssemblySymbol asm, string name) { #if FIRST_PASS throw new NotImplementedException(); #else - return new java.io.File(Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, asm, JVM.Properties.HomePath), name)).toURI().toURL(); + return new java.io.File(Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, asm.AsReflection(), JVM.Properties.HomePath), name)).toURI().toURL(); #endif } @@ -868,7 +869,7 @@ static java.net.URL MakeResourceURL(Assembly asm, string name) throw new NotImplementedException(); #else // cannot find resources in dynamic assembly - if (assemblyLoader.Assembly.IsDynamic) + if (assemblyLoader.Assembly.AsReflection().IsDynamic) yield break; var found = false; @@ -884,14 +885,14 @@ static java.net.URL MakeResourceURL(Assembly asm, string name) if (assemblyLoader.HasJavaModule == false) { // attempt to find an assembly resource with the exact name - if (unmangledName != "" && assemblyLoader.Assembly.GetManifestResourceInfo(unmangledName) != null) + if (unmangledName != "" && assemblyLoader.Assembly.AsReflection().GetManifestResourceInfo(unmangledName) != null) { found = true; yield return MakeResourceURL(assemblyLoader.Assembly, unmangledName); } // the JavaResourceAttribute can be used to manufacture a named Java resource - foreach (var res in assemblyLoader.Assembly.GetCustomAttributes()) + foreach (var res in assemblyLoader.Assembly.AsReflection().GetCustomAttributes()) { if (res.JavaName == unmangledName) { @@ -903,7 +904,7 @@ static java.net.URL MakeResourceURL(Assembly asm, string name) // find an assembly resource with the managed resource name var name = JVM.MangleResourceName(unmangledName); - if (assemblyLoader.Assembly.GetManifestResourceInfo(name) != null) + if (assemblyLoader.Assembly.AsReflection().GetManifestResourceInfo(name) != null) { found = true; yield return MakeResourceURL(assemblyLoader.Assembly, name); @@ -932,7 +933,7 @@ static java.net.URL MakeResourceURL(Assembly asm, string name) yield return (java.net.URL)urls.nextElement(); } - if (loader.Assembly.GetManifestResourceInfo(name) != null) + if (loader.Assembly.AsReflection().GetManifestResourceInfo(name) != null) { found = true; yield return MakeResourceURL(loader.Assembly, name); @@ -945,7 +946,7 @@ static java.net.URL MakeResourceURL(Assembly asm, string name) { var tw = FindLoadedClass(unmangledName.Substring(0, unmangledName.Length - 6).Replace('/', '.')); if (tw != null && tw.ClassLoader == this && !tw.IsArray && !tw.IsDynamic) - yield return new java.io.File(Path.Combine(VfsTable.GetAssemblyClassesPath(JVM.Vfs.Context, assemblyLoader.Assembly, JVM.Properties.HomePath), unmangledName)).toURI().toURL(); + yield return new java.io.File(Path.Combine(VfsTable.GetAssemblyClassesPath(JVM.Vfs.Context, assemblyLoader.Assembly.AsReflection(), JVM.Properties.HomePath), unmangledName)).toURI().toURL(); } #endif } @@ -1081,7 +1082,7 @@ internal override java.lang.ClassLoader GetJavaClassLoader() internal virtual java.security.ProtectionDomain GetProtectionDomain() { if (protectionDomain == null) - Interlocked.CompareExchange(ref protectionDomain, new java.security.ProtectionDomain(assemblyLoader.Assembly), null); + Interlocked.CompareExchange(ref protectionDomain, new java.security.ProtectionDomain(assemblyLoader.Assembly.AsReflection()), null); return protectionDomain; } @@ -1104,26 +1105,24 @@ internal override bool InternalsVisibleToImpl(RuntimeJavaType wrapper, RuntimeJa #else // we're OK if the type being accessed (wrapper) is a dynamic type // or if the dynamic assembly has internal access - return GetAssembly(wrapper).Equals(GetTypeWrapperFactory().ModuleBuilder.Assembly) - || GetTypeWrapperFactory().HasInternalAccess; + return GetAssembly(wrapper).Equals(GetTypeWrapperFactory().ModuleBuilder.Assembly) || GetTypeWrapperFactory().HasInternalAccess; #endif } - AssemblyName otherName; + #if IMPORTER - ImportClassLoader ccl = other as ImportClassLoader; + var ccl = other as ImportClassLoader; if (ccl == null) - { return false; - } - otherName = ccl.GetAssemblyName(); + + var otherName = ccl.GetAssemblyName(); #else - RuntimeAssemblyClassLoader acl = other as RuntimeAssemblyClassLoader; + var acl = other as RuntimeAssemblyClassLoader; if (acl == null) - { return false; - } - otherName = acl.GetAssembly(friend).GetName(); + + var otherName = acl.GetAssembly(friend).GetName(); #endif + return GetLoader(GetAssembly(wrapper)).InternalsVisibleTo(otherName); } @@ -1185,9 +1184,9 @@ Type GetCustomClassLoaderType() } } - var attribs = assembly.GetCustomAttributes(typeof(CustomAssemblyClassLoaderAttribute), false); - if (attribs.Length == 1) - return ((CustomAssemblyClassLoaderAttribute)attribs[0]).Type; + var attribs = assembly.GetCustomAttribute(Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName), false); + if (attribs is not null) + return new CustomAssemblyClassLoaderAttribute((System.Type)attribs.Value.ConstructorArguments[0].Value); return null; } diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs index 6b847c2861..5b50ef6619 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs @@ -24,11 +24,10 @@ Jeroen Frijters using System; using System.Collections.Generic; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; - -using Type = IKVM.Reflection.Type; #else using System.Reflection; #endif @@ -51,7 +50,7 @@ class RuntimeAssemblyClassLoaderFactory /// Maps existing instances to instances. Allows /// assemblies to be unloaded. /// - readonly ConditionalWeakTable assemblyClassLoaders = new(); + readonly ConditionalWeakTable assemblyClassLoaders = new(); #if !IMPORTER && !EXPORTER && !FIRST_PASS internal Dictionary customClassLoaderRedirects; @@ -73,7 +72,7 @@ public RuntimeAssemblyClassLoaderFactory(RuntimeContext context) /// /// /// - public RuntimeAssemblyClassLoader FromAssembly(Assembly assembly) + public RuntimeAssemblyClassLoader FromAssembly(IAssemblySymbol assembly) { if (assemblyClassLoaders.TryGetValue(assembly, out RuntimeAssemblyClassLoader loader)) return loader; @@ -96,7 +95,7 @@ public RuntimeAssemblyClassLoader FromAssembly(Assembly assembly) /// /// /// - RuntimeAssemblyClassLoader Create(Assembly assembly) + RuntimeAssemblyClassLoader Create(IAssemblySymbol assembly) { // If the assembly is a part of a multi-assembly shared class loader, // it will export the __ type from the main assembly in the group. @@ -108,9 +107,9 @@ RuntimeAssemblyClassLoader Create(Assembly assembly) return FromAssembly(mainAssembly); } - var baseAssembly = context.Resolver.ResolveBaseAssembly().AsReflection(); + var baseAssembly = context.Resolver.ResolveBaseAssembly(); #if IMPORTER - if (baseAssembly != null && assembly.IsDefined(context.Resolver.ResolveRuntimeType("IKVM.Attributes.RemappedClassAttribute").AsReflection(), false)) + if (baseAssembly != null && assembly.IsDefined(context.Resolver.ResolveRuntimeType("IKVM.Attributes.RemappedClassAttribute"), false)) context.ClassLoaderFactory.LoadRemappedTypes(); #endif diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index 7c7c5ebce3..9443a3efa8 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -133,7 +133,7 @@ internal void EmitDynamicClassLiteral(CodeEmitter ilgen, RuntimeJavaType tw, boo if (!dynamicClassLiteral.TryGetValue(cacheKey, out var method)) { var fb = typeBuilder.DefineField("__<>class", context.JavaBase.TypeOfJavaLangClass.TypeAsSignatureType, FieldAttributes.PrivateScope | FieldAttributes.Static); - var mb = DefineHelperMethod("__<>class", context.JavaBase.TypeOfJavaLangClass.TypeAsSignatureType, Type.EmptyTypes); + var mb = DefineHelperMethod("__<>class", context.JavaBase.TypeOfJavaLangClass.TypeAsSignatureType, []); var ilgen2 = context.CodeEmitterFactory.Create(mb); ilgen2.Emit(OpCodes.Ldsfld, fb); var label = ilgen2.DefineLabel(); @@ -185,7 +185,7 @@ private void CreateGetCallerID() { RuntimeJavaType tw = context.JavaBase.TypeOfIkvmInternalCallerID; FieldBuilder callerIDField = typeBuilder.DefineField("__", tw.TypeAsSignatureType, FieldAttributes.Private | FieldAttributes.Static | FieldAttributes.SpecialName); - MethodBuilder mb = DefineHelperMethod("__", tw.TypeAsSignatureType, Type.EmptyTypes); + MethodBuilder mb = DefineHelperMethod("__", tw.TypeAsSignatureType, []); callerIDMethod = mb; CodeEmitter ilgen = context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldsfld, callerIDField); @@ -604,7 +604,7 @@ internal Type FinishImpl() // - we don't want the synthesized constructor to show up in Java if (!hasConstructor) { - var ilgen = context.CodeEmitterFactory.Create(ReflectUtil.DefineConstructor(typeBuilder, MethodAttributes.PrivateScope, Type.EmptyTypes)); + var ilgen = context.CodeEmitterFactory.Create(ReflectUtil.DefineConstructor(typeBuilder, MethodAttributes.PrivateScope, [])); ilgen.Emit(OpCodes.Ldnull); ilgen.Emit(OpCodes.Throw); ilgen.DoEmit(); @@ -1295,7 +1295,7 @@ void GenerateAccessStub(RuntimeJavaField fw, bool type1) { var propType = fw.FieldTypeWrapper.TypeAsPublicSignatureType; var modopt = wrapper.GetModOpt(fw.FieldTypeWrapper, true); - var pb = typeBuilder.DefineProperty(fw.Name, PropertyAttributes.None, propType, null, modopt, Type.EmptyTypes, null, null); + var pb = typeBuilder.DefineProperty(fw.Name, PropertyAttributes.None, propType, null, modopt, [], null, null); if (type1) context.AttributeHelper.HideFromReflection(pb); else @@ -1308,7 +1308,7 @@ void GenerateAccessStub(RuntimeJavaField fw, bool type1) // we append the IKVM.Attributes.AccessStub type to the modopt array for use in the property accessor method signature // to make sure they never conflict with any user defined methhods var modopt2 = ArrayUtil.Concat(modopt, context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName).AsReflection()); - var getter = typeBuilder.DefineMethod("get_" + fw.Name, attribs, CallingConventions.Standard, propType, null, modopt2, Type.EmptyTypes, null, null); + var getter = typeBuilder.DefineMethod("get_" + fw.Name, attribs, CallingConventions.Standard, propType, null, modopt2, [], null, null); context.AttributeHelper.HideFromJava(getter); pb.SetGetMethod(getter); var ilgen = context.CodeEmitterFactory.Create(getter); @@ -1607,7 +1607,7 @@ internal static class JniProxyBuilder static JniProxyBuilder() { mod = DynamicClassLoader.CreateJniProxyModuleBuilder(); - var cab = new CustomAttributeBuilder(JVM.Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName).GetConstructor([]).AsReflection(), new object[0]); + var cab = new CustomAttributeBuilder(JVM.Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName).GetConstructor([]).AsReflection(), []); mod.SetCustomAttribute(cab); } @@ -1950,7 +1950,7 @@ void ImplementInterfaces(RuntimeJavaType[] interfaces, List int { typeBuilder.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName).AsReflection()); // FXBUG we're using the same method name as the C# compiler here because both the .NET and Mono implementations of Xml serialization depend on this method name - var mb = typeBuilder.DefineMethod("System.Collections.IEnumerable.GetEnumerator", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final | MethodAttributes.SpecialName, context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerator).FullName).AsReflection(), Type.EmptyTypes); + var mb = typeBuilder.DefineMethod("System.Collections.IEnumerable.GetEnumerator", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final | MethodAttributes.SpecialName, context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerator).FullName).AsReflection(), []); context.AttributeHelper.HideFromJava(mb); typeBuilder.DefineMethodOverride(mb, context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName).GetMethod("GetEnumerator").AsReflection()); var ilgen = context.CodeEmitterFactory.Create(mb); @@ -2196,9 +2196,9 @@ internal MethodBuilder DefineThreadLocalType() int id = nestedTypeBuilders == null ? 0 : nestedTypeBuilders.Count; var tb = typeBuilder.DefineNestedType(NestedTypeName.ThreadLocal + id, TypeAttributes.NestedPrivate | TypeAttributes.Sealed, threadLocal.TypeAsBaseType); var fb = tb.DefineField("field", context.Types.Object, FieldAttributes.Private | FieldAttributes.Static); - fb.SetCustomAttribute(new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ThreadStaticAttribute).FullName).GetConstructor([]).AsReflection(), new object[0])); + fb.SetCustomAttribute(new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ThreadStaticAttribute).FullName).GetConstructor([]).AsReflection(), [])); - var mbGet = tb.DefineMethod("get", MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.Final, context.Types.Object, Type.EmptyTypes); + var mbGet = tb.DefineMethod("get", MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.Final, context.Types.Object, []); var ilgen = mbGet.GetILGenerator(); ilgen.Emit(OpCodes.Ldsfld, fb); ilgen.Emit(OpCodes.Ret); @@ -2209,7 +2209,7 @@ internal MethodBuilder DefineThreadLocalType() ilgen.Emit(OpCodes.Stsfld, fb); ilgen.Emit(OpCodes.Ret); - var cb = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, Type.EmptyTypes); + var cb = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, []); var ctorilgen = context.CodeEmitterFactory.Create(cb); ctorilgen.Emit(OpCodes.Ldarg_0); var basector = threadLocal.GetMethodWrapper("", "()V", false); @@ -2231,7 +2231,7 @@ internal MethodBuilder GetAtomicReferenceFieldUpdater(RuntimeJavaField field) RuntimeJavaType arfuTypeWrapper = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicAtomicReferenceFieldUpdater"); TypeBuilder tb = typeBuilder.DefineNestedType(NestedTypeName.AtomicReferenceFieldUpdater + arfuMap.Count, TypeAttributes.NestedPrivate | TypeAttributes.Sealed, arfuTypeWrapper.TypeAsBaseType); AtomicReferenceFieldUpdaterEmitter.EmitImpl(context, tb, field.GetField()); - cb = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, Type.EmptyTypes); + cb = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, []); arfuMap.Add(field, cb); CodeEmitter ctorilgen = context.CodeEmitterFactory.Create(cb); ctorilgen.Emit(OpCodes.Ldarg_0); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs index 9ad510cc31..7e4a7f3ecd 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs @@ -24,6 +24,7 @@ Jeroen Frijters using System; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER using IKVM.Reflection; @@ -49,41 +50,47 @@ private sealed partial class JavaTypeImpl private sealed class DelegateInvokeStubMethodWrapper : RuntimeJavaMethod { - readonly Type delegateType; + readonly ITypeSymbol delegateType; - internal DelegateInvokeStubMethodWrapper(RuntimeJavaType declaringType, Type delegateType, string sig) - : base(declaringType, RuntimeManagedJavaType.GetDelegateInvokeStubName(delegateType), sig, null, null, null, Modifiers.Public | Modifiers.Final, MemberFlags.HideFromReflection) + /// + /// Initializes a new instance. + /// + /// + /// + /// + internal DelegateInvokeStubMethodWrapper(RuntimeJavaType declaringType, ITypeSymbol delegateType, string sig) : + base(declaringType, RuntimeManagedJavaType.GetDelegateInvokeStubName(delegateType), sig, null, null, null, Modifiers.Public | Modifiers.Final, MemberFlags.HideFromReflection) { this.delegateType = delegateType; } internal MethodInfo DoLink(TypeBuilder tb) { - RuntimeJavaMethod mw = this.DeclaringType.GetMethodWrapper("Invoke", this.Signature, true); + var mw = DeclaringType.GetMethodWrapper("Invoke", Signature, true); - MethodInfo invoke = delegateType.GetMethod("Invoke"); - ParameterInfo[] parameters = invoke.GetParameters(); - Type[] parameterTypes = new Type[parameters.Length]; + var invoke = delegateType.GetMethod("Invoke"); + var parameters = invoke.GetParameters(); + var parameterTypes = new ITypeSymbol[parameters.Length]; for (int i = 0; i < parameterTypes.Length; i++) - { parameterTypes[i] = parameters[i].ParameterType; - } - MethodBuilder mb = tb.DefineMethod(this.Name, MethodAttributes.Public, invoke.ReturnType, parameterTypes); + + var mb = tb.DefineMethod(Name, MethodAttributes.Public, invoke.ReturnType.AsReflection(), parameterTypes.AsReflection()); DeclaringType.Context.AttributeHelper.HideFromReflection(mb); - CodeEmitter ilgen = DeclaringType.Context.CodeEmitterFactory.Create(mb); + var ilgen = DeclaringType.Context.CodeEmitterFactory.Create(mb); if (mw == null || mw.IsStatic || !mw.IsPublic) { ilgen.EmitThrow(mw == null || mw.IsStatic ? "java.lang.AbstractMethodError" : "java.lang.IllegalAccessError", DeclaringType.Name + ".Invoke" + Signature); ilgen.DoEmit(); return mb; } - CodeEmitterLocal[] byrefs = new CodeEmitterLocal[parameters.Length]; + + var byrefs = new CodeEmitterLocal[parameters.Length]; for (int i = 0; i < parameters.Length; i++) { if (parameters[i].ParameterType.IsByRef) { - Type elemType = parameters[i].ParameterType.GetElementType(); - CodeEmitterLocal local = ilgen.DeclareLocal(RuntimeArrayJavaType.MakeArrayType(elemType, 1)); + var elemType = parameters[i].ParameterType.GetElementType(); + var local = ilgen.DeclareLocal(RuntimeArrayJavaType.MakeArrayType(elemType, 1)); byrefs[i] = local; ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.Emit(OpCodes.Newarr, elemType); @@ -101,30 +108,29 @@ internal MethodInfo DoLink(TypeBuilder tb) for (int i = 0; i < parameters.Length; i++) { if (byrefs[i] != null) - { ilgen.Emit(OpCodes.Ldloc, byrefs[i]); - } else - { ilgen.EmitLdarg(i + 1); - } } + mw.Link(); mw.EmitCallvirt(ilgen); + CodeEmitterLocal returnValue = null; if (mw.ReturnType != DeclaringType.Context.PrimitiveJavaTypeFactory.VOID) { returnValue = ilgen.DeclareLocal(mw.ReturnType.TypeAsSignatureType); ilgen.Emit(OpCodes.Stloc, returnValue); } - CodeEmitterLabel exit = ilgen.DefineLabel(); + + var exit = ilgen.DefineLabel(); ilgen.EmitLeave(exit); ilgen.BeginFinallyBlock(); for (int i = 0; i < parameters.Length; i++) { if (byrefs[i] != null) { - Type elemType = byrefs[i].LocalType.GetElementType(); + var elemType = byrefs[i].LocalType.GetElementType(); ilgen.EmitLdarg(i + 1); ilgen.Emit(OpCodes.Ldloc, byrefs[i]); ilgen.Emit(OpCodes.Ldc_I4_0); @@ -132,13 +138,13 @@ internal MethodInfo DoLink(TypeBuilder tb) ilgen.Emit(OpCodes.Stobj, elemType); } } + ilgen.Emit(OpCodes.Endfinally); ilgen.EndExceptionBlock(); ilgen.MarkLabel(exit); if (returnValue != null) - { ilgen.Emit(OpCodes.Ldloc, returnValue); - } + ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); return mb; diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index 7dfb116548..2964cf197d 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -64,11 +64,11 @@ private sealed partial class JavaTypeImpl : DynamicImpl MethodBuilder finalizeMethod; int recursionCount; #if IMPORTER - RuntimeByteCodeJavaType enclosingClassWrapper; - AnnotationBuilder annotationBuilder; - TypeBuilder enumBuilder; - TypeBuilder privateInterfaceMethods; - ConcurrentDictionary nestedTypeNames; // only keys are used, values are always null + RuntimeByteCodeJavaType enclosingClassWrapper; + AnnotationBuilder annotationBuilder; + TypeBuilder enumBuilder; + TypeBuilder privateInterfaceMethods; + ConcurrentDictionary nestedTypeNames; // only keys are used, values are always null #endif internal JavaTypeImpl(RuntimeJavaType host, ClassFile f, RuntimeByteCodeJavaType wrapper) @@ -92,15 +92,15 @@ internal void CreateStep1() if (m.IsClassInitializer) { #if IMPORTER - if (IsSideEffectFreeStaticInitializerOrNoop(m, out var noop)) - { - if (noop) - flags |= MemberFlags.NoOp; - } - else - { - hasclinit = true; - } + if (IsSideEffectFreeStaticInitializerOrNoop(m, out var noop)) + { + if (noop) + flags |= MemberFlags.NoOp; + } + else + { + hasclinit = true; + } #else hasclinit = true; #endif @@ -110,12 +110,12 @@ internal void CreateStep1() flags |= MemberFlags.InternalAccess; #if IMPORTER - if (m.IsCallerSensitive && SupportsCallerID(m)) - flags |= MemberFlags.CallerID; + if (m.IsCallerSensitive && SupportsCallerID(m)) + flags |= MemberFlags.CallerID; - // set as module initializer - if (m.IsModuleInitializer) - flags |= MemberFlags.ModuleInitializer; + // set as module initializer + if (m.IsModuleInitializer) + flags |= MemberFlags.ModuleInitializer; #endif if (wrapper.IsGhost && m.IsVirtual) @@ -190,78 +190,78 @@ internal void CreateStep1() } } #if IMPORTER - wrapper.AddMapXmlFields(ref fields); + wrapper.AddMapXmlFields(ref fields); #endif wrapper.SetFields(fields); } #if IMPORTER - bool SupportsCallerID(ClassFile.Method method) - { - if ((classFile.Name == "sun.reflect.Reflection" && method.Name == "getCallerClass") || (classFile.Name == "java.lang.SecurityManager" && method.Name == "checkMemberAccess")) - { - // ignore CallerSensitive on methods that don't need CallerID parameter - return false; - } - else if (method.IsStatic) - { - return true; - } - else if ((classFile.IsFinal || classFile.Name == "java.lang.Runtime" || classFile.Name == "java.io.ObjectStreamClass") && wrapper.BaseTypeWrapper.GetMethodWrapper(method.Name, method.Signature, true) == null && !HasInterfaceMethod(wrapper, method.Name, method.Signature)) - { - // We only support CallerID instance methods on final or effectively final types, - // because we don't support interface stubs with CallerID. - // We also don't support a CallerID method overriding a method or implementing an interface. - return true; - } - else if (RequiresDynamicReflectionCallerClass(classFile.Name, method.Name, method.Signature)) - { - // We don't support CallerID for virtual methods that can be overridden or implement an interface, - // so these methods will do a dynamic stack walk if when Reflection.getCallerClass() is used. - return false; - } - else - { - // If we end up here, we either have to add support or add them to the white-list in the above clause - // to allow them to fall back to dynamic stack walking. - wrapper.ClassLoader.Diagnostics.CallerSensitiveOnUnsupportedMethod(classFile.Name, method.Name, method.Signature); - return false; - } - } - - static bool HasInterfaceMethod(RuntimeJavaType tw, string name, string signature) - { - for (; tw != null; tw = tw.BaseTypeWrapper) - { - foreach (var iface in tw.Interfaces) - { - if (iface.GetMethodWrapper(name, signature, false) != null) - { - return true; - } - if (HasInterfaceMethod(iface, name, signature)) - { - return true; - } - } - } - - return false; - } + bool SupportsCallerID(ClassFile.Method method) + { + if ((classFile.Name == "sun.reflect.Reflection" && method.Name == "getCallerClass") || (classFile.Name == "java.lang.SecurityManager" && method.Name == "checkMemberAccess")) + { + // ignore CallerSensitive on methods that don't need CallerID parameter + return false; + } + else if (method.IsStatic) + { + return true; + } + else if ((classFile.IsFinal || classFile.Name == "java.lang.Runtime" || classFile.Name == "java.io.ObjectStreamClass") && wrapper.BaseTypeWrapper.GetMethodWrapper(method.Name, method.Signature, true) == null && !HasInterfaceMethod(wrapper, method.Name, method.Signature)) + { + // We only support CallerID instance methods on final or effectively final types, + // because we don't support interface stubs with CallerID. + // We also don't support a CallerID method overriding a method or implementing an interface. + return true; + } + else if (RequiresDynamicReflectionCallerClass(classFile.Name, method.Name, method.Signature)) + { + // We don't support CallerID for virtual methods that can be overridden or implement an interface, + // so these methods will do a dynamic stack walk if when Reflection.getCallerClass() is used. + return false; + } + else + { + // If we end up here, we either have to add support or add them to the white-list in the above clause + // to allow them to fall back to dynamic stack walking. + wrapper.ClassLoader.Diagnostics.CallerSensitiveOnUnsupportedMethod(classFile.Name, method.Name, method.Signature); + return false; + } + } + + static bool HasInterfaceMethod(RuntimeJavaType tw, string name, string signature) + { + for (; tw != null; tw = tw.BaseTypeWrapper) + { + foreach (var iface in tw.Interfaces) + { + if (iface.GetMethodWrapper(name, signature, false) != null) + { + return true; + } + if (HasInterfaceMethod(iface, name, signature)) + { + return true; + } + } + } + + return false; + } #endif internal void CreateStep2() { #if IMPORTER - if (typeBuilder != null) - { - // in the static compiler we need to create the TypeBuilder from outer to inner - // and to avoid having to sort the classes this way, we instead call CreateStep2 - // on demand for outer wrappers and this necessitates us to keep track of - // whether we've already been called - return; - } + if (typeBuilder != null) + { + // in the static compiler we need to create the TypeBuilder from outer to inner + // and to avoid having to sort the classes this way, we instead call CreateStep2 + // on demand for outer wrappers and this necessitates us to keep track of + // whether we've already been called + return; + } #endif // this method is not allowed to throw exceptions (if it does, the runtime will abort) @@ -280,121 +280,121 @@ internal void CreateStep2() typeAttribs |= TypeAttributes.BeforeFieldInit; #if IMPORTER - bool cantNest = false; - bool setModifiers = false; - TypeBuilder enclosing = null; - string enclosingClassName = null; - // we only compile inner classes as nested types in the static compiler, because it has a higher cost - // and doesn't buy us anything in dynamic mode (and if fact, due to an FXBUG it would make handling - // the TypeResolve event very hard) - var outerClass = getOuterClass(); - if (outerClass.outerClass.IsNotNil) - { - enclosingClassName = classFile.GetConstantPoolClass(outerClass.outerClass); - } - else if (f.EnclosingMethod != null) - { - enclosingClassName = f.EnclosingMethod[0]; - } - - if (enclosingClassName != null) - { - if (!CheckInnerOuterNames(f.Name, enclosingClassName)) - { - wrapper.ClassLoader.Diagnostics.GenericCompilerWarning($"Incorrect {(outerClass.outerClass.IsNotNil ? "InnerClasses" : "EnclosingMethod")} attribute on {f.Name}"); - } - else - { - try - { - enclosingClassWrapper = wrapper.classLoader.TryLoadClassByName(enclosingClassName) as RuntimeByteCodeJavaType; - } - catch (RetargetableJavaException x) - { - wrapper.ClassLoader.Diagnostics.GenericCompilerWarning($"Unable to load outer class {enclosingClassName} for inner class {f.Name} ({x.GetType().Name}: {x.Message})"); - } - - if (enclosingClassWrapper != null) - { - // make sure the relationship is reciprocal (otherwise we run the risk of - // baking the outer type before the inner type) and that the inner and outer - // class live in the same class loader (when doing a multi target compilation, - // it is possible to split the two classes across assemblies) - var oimpl = enclosingClassWrapper.impl as JavaTypeImpl; - if (oimpl != null && enclosingClassWrapper.ClassLoader == wrapper.ClassLoader) - { - var outerClassFile = oimpl.classFile; - var outerInnerClasses = outerClassFile.InnerClasses; - if (outerInnerClasses == null) - { - enclosingClassWrapper = null; - } - else - { - var ok = false; - for (int i = 0; i < outerInnerClasses.Length; i++) - { - if (((outerInnerClasses[i].outerClass.IsNotNil && outerClassFile.GetConstantPoolClass(outerInnerClasses[i].outerClass) == outerClassFile.Name) || (outerInnerClasses[i].outerClass.IsNil && outerClass.outerClass.IsNil)) && outerInnerClasses[i].innerClass.IsNotNil && outerClassFile.GetConstantPoolClass(outerInnerClasses[i].innerClass) == f.Name) - { - ok = true; - break; - } - } - - if (!ok) - { - enclosingClassWrapper = null; - } - } - } - else - { - enclosingClassWrapper = null; - } - - if (enclosingClassWrapper != null) - { - enclosingClassWrapper.CreateStep2(); - enclosing = oimpl.typeBuilder; - if (outerClass.outerClass.IsNil) - { - // we need to record that we're not an inner classes, but an enclosed class - typeAttribs |= TypeAttributes.SpecialName; - } - } - else - { - wrapper.ClassLoader.Diagnostics.GenericCompilerWarning($"Non-reciprocal inner class {f.Name}"); - } - } - } - } - - if (f.IsPublic) - { - if (enclosing != null) - { - if (enclosingClassWrapper.IsPublic) - { - typeAttribs |= TypeAttributes.NestedPublic; - } - else - { - // We're a public type nested inside a non-public type, this means that we can't compile this type as a nested type, - // because that would mean it wouldn't be visible outside the assembly. - cantNest = true; - typeAttribs |= TypeAttributes.Public; - } - } - else - { - typeAttribs |= TypeAttributes.Public; - } - } - else if (enclosing != null) - { - typeAttribs |= TypeAttributes.NestedAssembly; - } + bool cantNest = false; + bool setModifiers = false; + TypeBuilder enclosing = null; + string enclosingClassName = null; + // we only compile inner classes as nested types in the static compiler, because it has a higher cost + // and doesn't buy us anything in dynamic mode (and if fact, due to an FXBUG it would make handling + // the TypeResolve event very hard) + var outerClass = getOuterClass(); + if (outerClass.outerClass.IsNotNil) + { + enclosingClassName = classFile.GetConstantPoolClass(outerClass.outerClass); + } + else if (f.EnclosingMethod != null) + { + enclosingClassName = f.EnclosingMethod[0]; + } + + if (enclosingClassName != null) + { + if (!CheckInnerOuterNames(f.Name, enclosingClassName)) + { + wrapper.ClassLoader.Diagnostics.GenericCompilerWarning($"Incorrect {(outerClass.outerClass.IsNotNil ? "InnerClasses" : "EnclosingMethod")} attribute on {f.Name}"); + } + else + { + try + { + enclosingClassWrapper = wrapper.classLoader.TryLoadClassByName(enclosingClassName) as RuntimeByteCodeJavaType; + } + catch (RetargetableJavaException x) + { + wrapper.ClassLoader.Diagnostics.GenericCompilerWarning($"Unable to load outer class {enclosingClassName} for inner class {f.Name} ({x.GetType().Name}: {x.Message})"); + } + + if (enclosingClassWrapper != null) + { + // make sure the relationship is reciprocal (otherwise we run the risk of + // baking the outer type before the inner type) and that the inner and outer + // class live in the same class loader (when doing a multi target compilation, + // it is possible to split the two classes across assemblies) + var oimpl = enclosingClassWrapper.impl as JavaTypeImpl; + if (oimpl != null && enclosingClassWrapper.ClassLoader == wrapper.ClassLoader) + { + var outerClassFile = oimpl.classFile; + var outerInnerClasses = outerClassFile.InnerClasses; + if (outerInnerClasses == null) + { + enclosingClassWrapper = null; + } + else + { + var ok = false; + for (int i = 0; i < outerInnerClasses.Length; i++) + { + if (((outerInnerClasses[i].outerClass.IsNotNil && outerClassFile.GetConstantPoolClass(outerInnerClasses[i].outerClass) == outerClassFile.Name) || (outerInnerClasses[i].outerClass.IsNil && outerClass.outerClass.IsNil)) && outerInnerClasses[i].innerClass.IsNotNil && outerClassFile.GetConstantPoolClass(outerInnerClasses[i].innerClass) == f.Name) + { + ok = true; + break; + } + } + + if (!ok) + { + enclosingClassWrapper = null; + } + } + } + else + { + enclosingClassWrapper = null; + } + + if (enclosingClassWrapper != null) + { + enclosingClassWrapper.CreateStep2(); + enclosing = oimpl.typeBuilder; + if (outerClass.outerClass.IsNil) + { + // we need to record that we're not an inner classes, but an enclosed class + typeAttribs |= TypeAttributes.SpecialName; + } + } + else + { + wrapper.ClassLoader.Diagnostics.GenericCompilerWarning($"Non-reciprocal inner class {f.Name}"); + } + } + } + } + + if (f.IsPublic) + { + if (enclosing != null) + { + if (enclosingClassWrapper.IsPublic) + { + typeAttribs |= TypeAttributes.NestedPublic; + } + else + { + // We're a public type nested inside a non-public type, this means that we can't compile this type as a nested type, + // because that would mean it wouldn't be visible outside the assembly. + cantNest = true; + typeAttribs |= TypeAttributes.Public; + } + } + else + { + typeAttribs |= TypeAttributes.Public; + } + } + else if (enclosing != null) + { + typeAttribs |= TypeAttributes.NestedAssembly; + } #else // IMPORTER if (f.IsPublic) { @@ -405,34 +405,34 @@ internal void CreateStep2() { typeAttribs |= TypeAttributes.Interface | TypeAttributes.Abstract; #if IMPORTER - // if any "meaningless" bits are set, preserve them - setModifiers |= (f.Modifiers & (Modifiers)0x99CE) != 0; - // by default we assume interfaces are abstract, so in the exceptional case we need a ModifiersAttribute - setModifiers |= (f.Modifiers & Modifiers.Abstract) == 0; - if (enclosing != null && !cantNest) - { - if (wrapper.IsGhost) - { - // TODO this is low priority, since the current Java class library doesn't define any ghost interfaces - // as inner classes - throw new NotImplementedException(); - } - - // LAMESPEC the CLI spec says interfaces cannot contain nested types (Part.II, 9.6), but that rule isn't enforced - // (and broken by J# as well), so we'll just ignore it too. - typeBuilder = enclosing.DefineNestedType(AllocNestedTypeName(enclosingClassWrapper.Name, f.Name), typeAttribs); - } - else - { - if (wrapper.IsGhost) - { - typeBuilder = wrapper.DefineGhostType(mangledTypeName, typeAttribs); - } - else - { - typeBuilder = wrapper.classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(mangledTypeName, typeAttribs); - } - } + // if any "meaningless" bits are set, preserve them + setModifiers |= (f.Modifiers & (Modifiers)0x99CE) != 0; + // by default we assume interfaces are abstract, so in the exceptional case we need a ModifiersAttribute + setModifiers |= (f.Modifiers & Modifiers.Abstract) == 0; + if (enclosing != null && !cantNest) + { + if (wrapper.IsGhost) + { + // TODO this is low priority, since the current Java class library doesn't define any ghost interfaces + // as inner classes + throw new NotImplementedException(); + } + + // LAMESPEC the CLI spec says interfaces cannot contain nested types (Part.II, 9.6), but that rule isn't enforced + // (and broken by J# as well), so we'll just ignore it too. + typeBuilder = enclosing.DefineNestedType(AllocNestedTypeName(enclosingClassWrapper.Name, f.Name), typeAttribs); + } + else + { + if (wrapper.IsGhost) + { + typeBuilder = wrapper.DefineGhostType(mangledTypeName, typeAttribs); + } + else + { + typeBuilder = wrapper.classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(mangledTypeName, typeAttribs); + } + } #else // IMPORTER typeBuilder = wrapper.classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(mangledTypeName, typeAttribs); #endif // IMPORTER @@ -441,17 +441,17 @@ internal void CreateStep2() { typeAttribs |= TypeAttributes.Class; #if IMPORTER - // if any "meaningless" bits are set, preserve them - setModifiers |= (f.Modifiers & (Modifiers)0x99CE) != 0; - // by default we assume ACC_SUPER for classes, so in the exceptional case we need a ModifiersAttribute - setModifiers |= !f.IsSuper; - if (enclosing != null && !cantNest) - { - // LAMESPEC the CLI spec says interfaces cannot contain nested types (Part.II, 9.6), but that rule isn't enforced - // (and broken by J# as well), so we'll just ignore it too. - typeBuilder = enclosing.DefineNestedType(AllocNestedTypeName(enclosingClassWrapper.Name, f.Name), typeAttribs); - } - else + // if any "meaningless" bits are set, preserve them + setModifiers |= (f.Modifiers & (Modifiers)0x99CE) != 0; + // by default we assume ACC_SUPER for classes, so in the exceptional case we need a ModifiersAttribute + setModifiers |= !f.IsSuper; + if (enclosing != null && !cantNest) + { + // LAMESPEC the CLI spec says interfaces cannot contain nested types (Part.II, 9.6), but that rule isn't enforced + // (and broken by J# as well), so we'll just ignore it too. + typeBuilder = enclosing.DefineNestedType(AllocNestedTypeName(enclosingClassWrapper.Name, f.Name), typeAttribs); + } + else #endif // IMPORTER { typeBuilder = wrapper.classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(mangledTypeName, typeAttribs); @@ -459,113 +459,113 @@ internal void CreateStep2() } #if IMPORTER - // When we're statically compiling, we associate the typeBuilder with the wrapper. This enables types in referenced assemblies to refer back to - // types that we're currently compiling (i.e. a cyclic dependency between the currently assembly we're compiling and a referenced assembly). - wrapper.Context.ClassLoaderFactory.SetWrapperForType(typeBuilder, wrapper); - - if (outerClass.outerClass.IsNotNil) - { - if (enclosing != null && cantNest) - { - wrapper.Context.AttributeHelper.SetNonNestedInnerClass(enclosing, f.Name); - } - if (enclosing == null || cantNest) - { - wrapper.Context.AttributeHelper.SetNonNestedOuterClass(typeBuilder, enclosingClassName); - } - } - - if (classFile.InnerClasses != null) - { - foreach (var inner in classFile.InnerClasses) - { - var name = classFile.GetConstantPoolClass(inner.innerClass); - var exists = false; - - try - { - exists = wrapper.ClassLoader.TryLoadClassByName(name) != null; - } - catch (RetargetableJavaException) - { - - } - - if (!exists) - { - wrapper.Context.AttributeHelper.SetNonNestedInnerClass(typeBuilder, name); - } - } - } - - if (typeBuilder.FullName != wrapper.Name && wrapper.Name.Replace('$', '+') != typeBuilder.FullName) - { - wrapper.classLoader.AddNameMapping(wrapper.Name, typeBuilder.FullName); - } - - if (f.IsAnnotation && Annotation.HasRetentionPolicyRuntime(f.Annotations)) - { - annotationBuilder = new AnnotationBuilder(wrapper.Context, this, enclosing); - wrapper.SetAnnotation(annotationBuilder); - } - - // For Java 5 Enum types, we generate a nested .NET enum. - // This is primarily to support annotations that take enum parameters. - if (f.IsEnum && f.IsPublic) - { - AddCliEnum(); - } - - AddInnerClassAttribute(enclosing != null, outerClass.innerClass.IsNotNil, mangledTypeName, outerClass.accessFlags); - if (classFile.DeprecatedAttribute && !Annotation.HasObsoleteAttribute(classFile.Annotations)) - { - wrapper.Context.AttributeHelper.SetDeprecatedAttribute(typeBuilder); - } - - if (classFile.GenericSignature != null) - { - wrapper.Context.AttributeHelper.SetSignatureAttribute(typeBuilder, classFile.GenericSignature); - } - if (classFile.EnclosingMethod != null) - { - if (outerClass.outerClass.IsNil && enclosing != null && !cantNest) - { - // we don't need to record the enclosing type, if we're compiling the current type as a nested type because of the EnclosingMethod attribute - wrapper.Context.AttributeHelper.SetEnclosingMethodAttribute(typeBuilder, null, classFile.EnclosingMethod[1], classFile.EnclosingMethod[2]); - } - else - { - wrapper.Context.AttributeHelper.SetEnclosingMethodAttribute(typeBuilder, classFile.EnclosingMethod[0], classFile.EnclosingMethod[1], classFile.EnclosingMethod[2]); - } - } - - if (classFile.RuntimeVisibleTypeAnnotations.Count > 0) - wrapper.Context.AttributeHelper.SetRuntimeVisibleTypeAnnotationsAttribute(typeBuilder, in classFile.RuntimeVisibleTypeAnnotations); - - if (wrapper.classLoader.EmitStackTraceInfo) - { - if (f.SourceFileAttribute != null) - { - if ((enclosingClassWrapper == null && f.SourceFileAttribute == typeBuilder.Name + ".java") - || (enclosingClassWrapper != null && f.SourceFileAttribute == enclosingClassWrapper.sourceFileName)) - { - // we don't need to record the name because it matches our heuristic - } - else - { - wrapper.Context.AttributeHelper.SetSourceFile(typeBuilder, f.SourceFileAttribute); - } - } - else - { - wrapper.Context.AttributeHelper.SetSourceFile(typeBuilder, null); - } - } - // NOTE in Whidbey we can (and should) use CompilerGeneratedAttribute to mark Synthetic types - if (setModifiers || classFile.IsInternal || (classFile.Modifiers & (Modifiers.Synthetic | Modifiers.Annotation | Modifiers.Enum)) != 0) - { - wrapper.Context.AttributeHelper.SetModifiers(typeBuilder, classFile.Modifiers, classFile.IsInternal); - } + // When we're statically compiling, we associate the typeBuilder with the wrapper. This enables types in referenced assemblies to refer back to + // types that we're currently compiling (i.e. a cyclic dependency between the currently assembly we're compiling and a referenced assembly). + wrapper.Context.ClassLoaderFactory.SetWrapperForType(typeBuilder, wrapper); + + if (outerClass.outerClass.IsNotNil) + { + if (enclosing != null && cantNest) + { + wrapper.Context.AttributeHelper.SetNonNestedInnerClass(enclosing, f.Name); + } + if (enclosing == null || cantNest) + { + wrapper.Context.AttributeHelper.SetNonNestedOuterClass(typeBuilder, enclosingClassName); + } + } + + if (classFile.InnerClasses != null) + { + foreach (var inner in classFile.InnerClasses) + { + var name = classFile.GetConstantPoolClass(inner.innerClass); + var exists = false; + + try + { + exists = wrapper.ClassLoader.TryLoadClassByName(name) != null; + } + catch (RetargetableJavaException) + { + + } + + if (!exists) + { + wrapper.Context.AttributeHelper.SetNonNestedInnerClass(typeBuilder, name); + } + } + } + + if (typeBuilder.FullName != wrapper.Name && wrapper.Name.Replace('$', '+') != typeBuilder.FullName) + { + wrapper.classLoader.AddNameMapping(wrapper.Name, typeBuilder.FullName); + } + + if (f.IsAnnotation && Annotation.HasRetentionPolicyRuntime(f.Annotations)) + { + annotationBuilder = new AnnotationBuilder(wrapper.Context, this, enclosing); + wrapper.SetAnnotation(annotationBuilder); + } + + // For Java 5 Enum types, we generate a nested .NET enum. + // This is primarily to support annotations that take enum parameters. + if (f.IsEnum && f.IsPublic) + { + AddCliEnum(); + } + + AddInnerClassAttribute(enclosing != null, outerClass.innerClass.IsNotNil, mangledTypeName, outerClass.accessFlags); + if (classFile.DeprecatedAttribute && !Annotation.HasObsoleteAttribute(classFile.Annotations)) + { + wrapper.Context.AttributeHelper.SetDeprecatedAttribute(typeBuilder); + } + + if (classFile.GenericSignature != null) + { + wrapper.Context.AttributeHelper.SetSignatureAttribute(typeBuilder, classFile.GenericSignature); + } + if (classFile.EnclosingMethod != null) + { + if (outerClass.outerClass.IsNil && enclosing != null && !cantNest) + { + // we don't need to record the enclosing type, if we're compiling the current type as a nested type because of the EnclosingMethod attribute + wrapper.Context.AttributeHelper.SetEnclosingMethodAttribute(typeBuilder, null, classFile.EnclosingMethod[1], classFile.EnclosingMethod[2]); + } + else + { + wrapper.Context.AttributeHelper.SetEnclosingMethodAttribute(typeBuilder, classFile.EnclosingMethod[0], classFile.EnclosingMethod[1], classFile.EnclosingMethod[2]); + } + } + + if (classFile.RuntimeVisibleTypeAnnotations.Count > 0) + wrapper.Context.AttributeHelper.SetRuntimeVisibleTypeAnnotationsAttribute(typeBuilder, in classFile.RuntimeVisibleTypeAnnotations); + + if (wrapper.classLoader.EmitStackTraceInfo) + { + if (f.SourceFileAttribute != null) + { + if ((enclosingClassWrapper == null && f.SourceFileAttribute == typeBuilder.Name + ".java") + || (enclosingClassWrapper != null && f.SourceFileAttribute == enclosingClassWrapper.sourceFileName)) + { + // we don't need to record the name because it matches our heuristic + } + else + { + wrapper.Context.AttributeHelper.SetSourceFile(typeBuilder, f.SourceFileAttribute); + } + } + else + { + wrapper.Context.AttributeHelper.SetSourceFile(typeBuilder, null); + } + } + // NOTE in Whidbey we can (and should) use CompilerGeneratedAttribute to mark Synthetic types + if (setModifiers || classFile.IsInternal || (classFile.Modifiers & (Modifiers.Synthetic | Modifiers.Annotation | Modifiers.Enum)) != 0) + { + wrapper.Context.AttributeHelper.SetModifiers(typeBuilder, classFile.Modifiers, classFile.IsInternal); + } #endif // IMPORTER if (hasclinit) { @@ -582,7 +582,7 @@ internal void CreateStep2() } } #if IMPORTER - finally { } + finally { } #else catch (Exception x) { @@ -593,50 +593,49 @@ internal void CreateStep2() #if IMPORTER - private void AddInnerClassAttribute(bool isNestedType, bool isInnerClass, string mangledTypeName, Modifiers innerClassFlags) - { - string name = classFile.Name; - - if (isNestedType) - { - if (name == enclosingClassWrapper.Name + "$" + typeBuilder.Name) - { - name = null; - } - } - else if (name == mangledTypeName) - { - name = null; - } - - if ((isInnerClass && RuntimeManagedByteCodeJavaType.PredictReflectiveModifiers(wrapper) != innerClassFlags) || name != null) - { - // HACK we abuse the InnerClassAttribute to record to real name for non-inner classes as well - wrapper.Context.AttributeHelper.SetInnerClass(typeBuilder, name, isInnerClass ? innerClassFlags : wrapper.Modifiers); - } - } - - private void AddCliEnum() - { - ImportClassLoader ccl = wrapper.classLoader; - string name = "__Enum"; - while (!ccl.ReserveName(classFile.Name + "$" + name)) - { - name += "_"; - } - enumBuilder = typeBuilder.DefineNestedType(name, TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.NestedPublic | TypeAttributes.Serializable, wrapper.Context.Types.Enum); - wrapper.Context.AttributeHelper.HideFromJava(enumBuilder); - enumBuilder.DefineField("value__", wrapper.Context.Types.Int32, FieldAttributes.Public | FieldAttributes.SpecialName | FieldAttributes.RTSpecialName); - for (int i = 0; i < classFile.Fields.Length; i++) - { - if (classFile.Fields[i].IsEnum) - { - FieldBuilder fieldBuilder = enumBuilder.DefineField(classFile.Fields[i].Name, enumBuilder, FieldAttributes.Public | FieldAttributes.Static | FieldAttributes.Literal); - fieldBuilder.SetConstant(i); - } - } - wrapper.SetEnumType(enumBuilder); - } + private void AddInnerClassAttribute(bool isNestedType, bool isInnerClass, string mangledTypeName, Modifiers innerClassFlags) + { + string name = classFile.Name; + + if (isNestedType) + { + if (name == enclosingClassWrapper.Name + "$" + typeBuilder.Name) + { + name = null; + } + } + else if (name == mangledTypeName) + { + name = null; + } + + if ((isInnerClass && RuntimeManagedByteCodeJavaType.PredictReflectiveModifiers(wrapper) != innerClassFlags) || name != null) + { + // HACK we abuse the InnerClassAttribute to record to real name for non-inner classes as well + wrapper.Context.AttributeHelper.SetInnerClass(typeBuilder, name, isInnerClass ? innerClassFlags : wrapper.Modifiers); + } + } + + void AddCliEnum() + { + var ccl = wrapper.classLoader; + string name = "__Enum"; + while (!ccl.ReserveName(classFile.Name + "$" + name)) + name += "_"; + + enumBuilder = typeBuilder.DefineNestedType(name, TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.NestedPublic | TypeAttributes.Serializable, wrapper.Context.Types.Enum.AsReflection()); + wrapper.Context.AttributeHelper.HideFromJava(enumBuilder); + enumBuilder.DefineField("value__", wrapper.Context.Types.Int32.AsReflection(), FieldAttributes.Public | FieldAttributes.SpecialName | FieldAttributes.RTSpecialName); + for (int i = 0; i < classFile.Fields.Length; i++) + { + if (classFile.Fields[i].IsEnum) + { + FieldBuilder fieldBuilder = enumBuilder.DefineField(classFile.Fields[i].Name, enumBuilder, FieldAttributes.Public | FieldAttributes.Static | FieldAttributes.Literal); + fieldBuilder.SetConstant(i); + } + } + wrapper.SetEnumType(enumBuilder); + } #endif void AddClinitTrigger() @@ -686,110 +685,110 @@ private static bool HasStructLayoutAttributeAnnotation(ClassFile c) } #if IMPORTER - private ClassFile.InnerClass getOuterClass() - { - ClassFile.InnerClass[] innerClasses = classFile.InnerClasses; - if (innerClasses != null) - { - for (int j = 0; j < innerClasses.Length; j++) - { - if (innerClasses[j].innerClass.IsNotNil && classFile.GetConstantPoolClass(innerClasses[j].innerClass) == classFile.Name) - { - return innerClasses[j]; - } - } - } - return new ClassFile.InnerClass(); - } - - private bool IsSideEffectFreeStaticInitializerOrNoop(ClassFile.Method m, out bool noop) - { - if (m.ExceptionTable.Length != 0) - { - noop = false; - return false; - } - noop = true; - for (int i = 0; i < m.Instructions.Length; i++) - { - NormalizedByteCode bc; - while ((bc = m.Instructions[i].NormalizedOpCode) == NormalizedByteCode.__goto) - { - int target = m.Instructions[i].TargetIndex; - if (target <= i) - { - // backward branch means we can't do anything - noop = false; - return false; - } - // we must skip the unused instructions because the "remove assertions" optimization - // uses a goto to remove the (now unused) code - i = target; - } - if (bc == NormalizedByteCode.__getstatic || bc == NormalizedByteCode.__putstatic) - { - ClassFile.ConstantPoolItemFieldref fld = classFile.SafeGetFieldref(m.Instructions[i].Arg1); - if (fld == null || fld.Class != classFile.Name) - { - noop = false; - return false; - } - // don't allow getstatic to load non-primitive fields, because that would - // cause the verifier to try to load the type - if (bc == NormalizedByteCode.__getstatic && "L[".IndexOf(fld.Signature[0]) != -1) - { - noop = false; - return false; - } - ClassFile.Field field = classFile.GetField(fld.Name, fld.Signature); - if (field == null) - { - noop = false; - return false; - } - if (bc == NormalizedByteCode.__putstatic) - { - if (field.IsProperty && field.PropertySetter != null) - { - noop = false; - return false; - } - } - else if (field.IsProperty && field.PropertyGetter != null) - { - noop = false; - return false; - } - } - else if (ByteCodeMetaData.CanThrowException(bc)) - { - noop = false; - return false; - } - else if (bc == NormalizedByteCode.__aconst_null - || (bc == NormalizedByteCode.__iconst && m.Instructions[i].Arg1 == 0) - || bc == NormalizedByteCode.__return - || bc == NormalizedByteCode.__nop) - { - // valid instructions in a potential noop - } - else - { - noop = false; - } - } - // the method needs to be verifiable to be side effect free, since we already analysed it, - // we know that the verifier won't try to load any types (which isn't allowed at this time) - try - { - wrapper.Context.MethodAnalyzerFactory.Create(null, wrapper, null, classFile, m, wrapper.classLoader); - return true; - } - catch (VerifyError) - { - return false; - } - } + private ClassFile.InnerClass getOuterClass() + { + ClassFile.InnerClass[] innerClasses = classFile.InnerClasses; + if (innerClasses != null) + { + for (int j = 0; j < innerClasses.Length; j++) + { + if (innerClasses[j].innerClass.IsNotNil && classFile.GetConstantPoolClass(innerClasses[j].innerClass) == classFile.Name) + { + return innerClasses[j]; + } + } + } + return new ClassFile.InnerClass(); + } + + private bool IsSideEffectFreeStaticInitializerOrNoop(ClassFile.Method m, out bool noop) + { + if (m.ExceptionTable.Length != 0) + { + noop = false; + return false; + } + noop = true; + for (int i = 0; i < m.Instructions.Length; i++) + { + NormalizedByteCode bc; + while ((bc = m.Instructions[i].NormalizedOpCode) == NormalizedByteCode.__goto) + { + int target = m.Instructions[i].TargetIndex; + if (target <= i) + { + // backward branch means we can't do anything + noop = false; + return false; + } + // we must skip the unused instructions because the "remove assertions" optimization + // uses a goto to remove the (now unused) code + i = target; + } + if (bc == NormalizedByteCode.__getstatic || bc == NormalizedByteCode.__putstatic) + { + ClassFile.ConstantPoolItemFieldref fld = classFile.SafeGetFieldref(m.Instructions[i].Arg1); + if (fld == null || fld.Class != classFile.Name) + { + noop = false; + return false; + } + // don't allow getstatic to load non-primitive fields, because that would + // cause the verifier to try to load the type + if (bc == NormalizedByteCode.__getstatic && "L[".IndexOf(fld.Signature[0]) != -1) + { + noop = false; + return false; + } + ClassFile.Field field = classFile.GetField(fld.Name, fld.Signature); + if (field == null) + { + noop = false; + return false; + } + if (bc == NormalizedByteCode.__putstatic) + { + if (field.IsProperty && field.PropertySetter != null) + { + noop = false; + return false; + } + } + else if (field.IsProperty && field.PropertyGetter != null) + { + noop = false; + return false; + } + } + else if (ByteCodeMetaData.CanThrowException(bc)) + { + noop = false; + return false; + } + else if (bc == NormalizedByteCode.__aconst_null + || (bc == NormalizedByteCode.__iconst && m.Instructions[i].Arg1 == 0) + || bc == NormalizedByteCode.__return + || bc == NormalizedByteCode.__nop) + { + // valid instructions in a potential noop + } + else + { + noop = false; + } + } + // the method needs to be verifiable to be side effect free, since we already analysed it, + // we know that the verifier won't try to load any types (which isn't allowed at this time) + try + { + wrapper.Context.MethodAnalyzerFactory.Create(null, wrapper, null, classFile, m, wrapper.classLoader); + return true; + } + catch (VerifyError) + { + return false; + } + } #endif // IMPORTER private RuntimeJavaMethod GetMethodWrapperDuringCtor(RuntimeJavaType lookup, IList methods, string name, string sig) @@ -862,35 +861,34 @@ private void AddMirandaMethods(List methods, List outer.Length + 1 && inner[outer.Length] == '$' && inner.StartsWith(outer, StringComparison.Ordinal); - } - - private string AllocNestedTypeName(string outer, string inner) - { - Debug.Assert(CheckInnerOuterNames(inner, outer)); - nestedTypeNames ??= new ConcurrentDictionary(); - return DynamicClassLoaderFactory.TypeNameMangleImpl(nestedTypeNames, inner.Substring(outer.Length + 1), null); - } + private static bool CheckInnerOuterNames(string inner, string outer) + { + // do some sanity checks on the inner/outer class names + return inner.Length > outer.Length + 1 && inner[outer.Length] == '$' && inner.StartsWith(outer, StringComparison.Ordinal); + } + + private string AllocNestedTypeName(string outer, string inner) + { + Debug.Assert(CheckInnerOuterNames(inner, outer)); + nestedTypeNames ??= new ConcurrentDictionary(); + return DynamicClassLoaderFactory.TypeNameMangleImpl(nestedTypeNames, inner.Substring(outer.Length + 1), null); + } #endif @@ -922,7 +920,7 @@ private static void CheckLoaderConstraints(RuntimeJavaMethod mw, RuntimeJavaMeth else { #if IMPORTER - StaticCompiler.LinkageError("Method \"{2}.{3}{4}\" has a return type \"{0}\" and tries to override method \"{5}.{3}{4}\" that has a return type \"{1}\"", mw.ReturnType, baseMethod.ReturnType, mw.DeclaringType.Name, mw.Name, mw.Signature, baseMethod.DeclaringType.Name); + StaticCompiler.LinkageError("Method \"{2}.{3}{4}\" has a return type \"{0}\" and tries to override method \"{5}.{3}{4}\" that has a return type \"{1}\"", mw.ReturnType, baseMethod.ReturnType, mw.DeclaringType.Name, mw.Name, mw.Signature, baseMethod.DeclaringType.Name); #else throw new LinkageError("Loader constraints violated"); #endif @@ -945,7 +943,7 @@ private static void CheckLoaderConstraints(RuntimeJavaMethod mw, RuntimeJavaMeth else { #if IMPORTER - StaticCompiler.LinkageError("Method \"{2}.{3}{4}\" has an argument type \"{0}\" and tries to override method \"{5}.{3}{4}\" that has an argument type \"{1}\"", here[i], there[i], mw.DeclaringType.Name, mw.Name, mw.Signature, baseMethod.DeclaringType.Name); + StaticCompiler.LinkageError("Method \"{2}.{3}{4}\" has an argument type \"{0}\" and tries to override method \"{5}.{3}{4}\" that has an argument type \"{1}\"", here[i], there[i], mw.DeclaringType.Name, mw.Name, mw.Signature, baseMethod.DeclaringType.Name); #else throw new LinkageError("Loader constraints violated"); #endif @@ -975,75 +973,75 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) } int fieldIndex = GetFieldIndex(fw); #if IMPORTER - if (wrapper.ClassLoader.RemoveUnusedFields - && fw.IsPrivate - && fw.IsStatic - && fw.IsFinal - && !fw.IsSerialVersionUID - && classFile.Fields[fieldIndex].Annotations == null - && !classFile.IsReferenced(classFile.Fields[fieldIndex])) - { - // unused, so we skip it - wrapper.ClassLoader.Diagnostics.GenericCompilerInfo($"Unused field {wrapper.Name}::{fw.Name}"); - return null; - } - - // for compatibility with broken Java code that assumes that reflection returns the fields in class declaration - // order, we emit the fields in class declaration order in the .NET metadata (and then when we retrieve them - // using .NET reflection, we sort on metadata token.) - if (fieldIndex > 0) - { - if (!fields[fieldIndex - 1].IsLinked) - { - for (int i = 0; i < fieldIndex; i++) - { - fields[i].Link(); - } - } - } - - if (fieldIndex >= classFile.Fields.Length) - { - // this must be a field defined in map.xml - FieldAttributes fieldAttribs = 0; - if (fw.IsPublic) - { - fieldAttribs |= FieldAttributes.Public; - } - else if (fw.IsProtected) - { - fieldAttribs |= FieldAttributes.FamORAssem; - } - else if (fw.IsPrivate) - { - fieldAttribs |= FieldAttributes.Private; - } - else - { - fieldAttribs |= FieldAttributes.Assembly; - } - if (fw.IsStatic) - { - fieldAttribs |= FieldAttributes.Static; - } - if (fw.IsFinal) - { - fieldAttribs |= FieldAttributes.InitOnly; - } - return DefineField(fw.Name, fw.FieldTypeWrapper, fieldAttribs, fw.IsVolatile); - } -#endif // IMPORTER - FieldBuilder field; - ClassFile.Field fld = classFile.Fields[fieldIndex]; - FieldAttributes attribs = 0; - string realFieldName = UnicodeUtil.EscapeInvalidSurrogates(fld.Name); - if (!ReferenceEquals(realFieldName, fld.Name)) - { - attribs |= FieldAttributes.SpecialName; + if (wrapper.ClassLoader.RemoveUnusedFields + && fw.IsPrivate + && fw.IsStatic + && fw.IsFinal + && !fw.IsSerialVersionUID + && classFile.Fields[fieldIndex].Annotations == null + && !classFile.IsReferenced(classFile.Fields[fieldIndex])) + { + // unused, so we skip it + wrapper.ClassLoader.Diagnostics.GenericCompilerInfo($"Unused field {wrapper.Name}::{fw.Name}"); + return null; } - MethodAttributes methodAttribs = MethodAttributes.HideBySig; -#if IMPORTER - bool setModifiers = fld.IsInternal || (fld.Modifiers & (Modifiers.Synthetic | Modifiers.Enum)) != 0; + + // for compatibility with broken Java code that assumes that reflection returns the fields in class declaration + // order, we emit the fields in class declaration order in the .NET metadata (and then when we retrieve them + // using .NET reflection, we sort on metadata token.) + if (fieldIndex > 0) + { + if (!fields[fieldIndex - 1].IsLinked) + { + for (int i = 0; i < fieldIndex; i++) + { + fields[i].Link(); + } + } + } + + if (fieldIndex >= classFile.Fields.Length) + { + // this must be a field defined in map.xml + FieldAttributes fieldAttribs = 0; + if (fw.IsPublic) + { + fieldAttribs |= FieldAttributes.Public; + } + else if (fw.IsProtected) + { + fieldAttribs |= FieldAttributes.FamORAssem; + } + else if (fw.IsPrivate) + { + fieldAttribs |= FieldAttributes.Private; + } + else + { + fieldAttribs |= FieldAttributes.Assembly; + } + if (fw.IsStatic) + { + fieldAttribs |= FieldAttributes.Static; + } + if (fw.IsFinal) + { + fieldAttribs |= FieldAttributes.InitOnly; + } + return DefineField(fw.Name, fw.FieldTypeWrapper, fieldAttribs, fw.IsVolatile); + } +#endif // IMPORTER + FieldBuilder field; + ClassFile.Field fld = classFile.Fields[fieldIndex]; + FieldAttributes attribs = 0; + string realFieldName = UnicodeUtil.EscapeInvalidSurrogates(fld.Name); + if (!ReferenceEquals(realFieldName, fld.Name)) + { + attribs |= FieldAttributes.SpecialName; + } + MethodAttributes methodAttribs = MethodAttributes.HideBySig; +#if IMPORTER + bool setModifiers = fld.IsInternal || (fld.Modifiers & (Modifiers.Synthetic | Modifiers.Enum)) != 0; #endif if (fld.IsPrivate) { @@ -1083,28 +1081,28 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) else { #if IMPORTER - if (wrapper.IsPublic && wrapper.NeedsType2AccessStub(fw)) - { - // this field is going to get a type 2 access stub, so we hide the actual field - attribs &= ~FieldAttributes.FieldAccessMask; - attribs |= FieldAttributes.Assembly; - // instead of adding HideFromJava we rename the field to avoid confusing broken compilers - // see https://sourceforge.net/tracker/?func=detail&atid=525264&aid=3056721&group_id=69637 - // additional note: now that we maintain the ordering of the fields, we need to recognize - // these fields so that we know where to insert the corresponding accessor property FieldWrapper. - realFieldName = NamePrefix.Type2AccessStubBackingField + realFieldName; - } - else if (fld.IsFinal) - { - if (wrapper.IsInterface || wrapper.classLoader.StrictFinalFieldSemantics) - { - attribs |= FieldAttributes.InitOnly; - } - else - { - setModifiers = true; - } - } + if (wrapper.IsPublic && wrapper.NeedsType2AccessStub(fw)) + { + // this field is going to get a type 2 access stub, so we hide the actual field + attribs &= ~FieldAttributes.FieldAccessMask; + attribs |= FieldAttributes.Assembly; + // instead of adding HideFromJava we rename the field to avoid confusing broken compilers + // see https://sourceforge.net/tracker/?func=detail&atid=525264&aid=3056721&group_id=69637 + // additional note: now that we maintain the ordering of the fields, we need to recognize + // these fields so that we know where to insert the corresponding accessor property FieldWrapper. + realFieldName = NamePrefix.Type2AccessStubBackingField + realFieldName; + } + else if (fld.IsFinal) + { + if (wrapper.IsInterface || wrapper.classLoader.StrictFinalFieldSemantics) + { + attribs |= FieldAttributes.InitOnly; + } + else + { + setModifiers = true; + } + } #else if (fld.IsFinal && wrapper.IsInterface) { @@ -1120,21 +1118,21 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) field.SetCustomAttribute(transientAttrib); } #if IMPORTER - { - // if the Java modifiers cannot be expressed in .NET, we emit the Modifiers attribute to store - // the Java modifiers - if (setModifiers) - wrapper.Context.AttributeHelper.SetModifiers(field, fld.Modifiers, fld.IsInternal); + { + // if the Java modifiers cannot be expressed in .NET, we emit the Modifiers attribute to store + // the Java modifiers + if (setModifiers) + wrapper.Context.AttributeHelper.SetModifiers(field, fld.Modifiers, fld.IsInternal); - if (fld.DeprecatedAttribute && !Annotation.HasObsoleteAttribute(fld.Annotations)) - wrapper.Context.AttributeHelper.SetDeprecatedAttribute(field); + if (fld.DeprecatedAttribute && !Annotation.HasObsoleteAttribute(fld.Annotations)) + wrapper.Context.AttributeHelper.SetDeprecatedAttribute(field); - if (fld.GenericSignature != null) - wrapper.Context.AttributeHelper.SetSignatureAttribute(field, fld.GenericSignature); + if (fld.GenericSignature != null) + wrapper.Context.AttributeHelper.SetSignatureAttribute(field, fld.GenericSignature); - if (fld.RuntimeVisibleTypeAnnotations.Count > 0) - wrapper.Context.AttributeHelper.SetRuntimeVisibleTypeAnnotationsAttribute(field, in fld.RuntimeVisibleTypeAnnotations); - } + if (fld.RuntimeVisibleTypeAnnotations.Count > 0) + wrapper.Context.AttributeHelper.SetRuntimeVisibleTypeAnnotationsAttribute(field, in fld.RuntimeVisibleTypeAnnotations); + } #endif return field; @@ -1142,7 +1140,7 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) FieldBuilder DefineField(string name, RuntimeJavaType tw, FieldAttributes attribs, bool isVolatile) { - var modreq = isVolatile ? [wrapper.Context.Types.IsVolatile] : Type.EmptyTypes; + var modreq = isVolatile ? [wrapper.Context.Types.IsVolatile] : []; return typeBuilder.DefineField(name, tw.TypeAsSignatureType, modreq, wrapper.GetModOpt(tw, false), attribs); } @@ -1152,746 +1150,749 @@ internal override void EmitRunClassConstructor(CodeEmitter ilgen) ilgen.Emit(OpCodes.Call, clinitMethod); } - internal override DynamicImpl Finish() - { - var baseTypeWrapper = wrapper.BaseTypeWrapper; - if (baseTypeWrapper != null) - { - baseTypeWrapper.Finish(); - baseTypeWrapper.LinkAll(); + internal override DynamicImpl Finish() + { + var baseTypeWrapper = wrapper.BaseTypeWrapper; + if (baseTypeWrapper != null) + { + baseTypeWrapper.Finish(); + baseTypeWrapper.LinkAll(); + } + + // NOTE there is a bug in the CLR (.NET 1.0 & 1.1 [1.2 is not yet available]) that + // causes the AppDomain.TypeResolve event to receive the incorrect type name for nested types. + // The Name in the ResolveEventArgs contains only the nested type name, not the full type name, + // for example, if the type being resolved is "MyOuterType+MyInnerType", then the event only + // receives "MyInnerType" as the name. Since we only compile inner classes as nested types + // when we're statically compiling, we can only run into this bug when we're statically compiling. + // NOTE To work around this bug, we have to make sure that all types that are going to be + // required in finished form, are finished explicitly here. It isn't clear what other types are + // required to be finished. I instrumented a static compilation of classpath.dll and this + // turned up no other cases of the TypeResolve event firing. + foreach (RuntimeJavaType iface in wrapper.interfaces) + { + iface.Finish(); + iface.LinkAll(); + } + + // make sure all classes are loaded, before we start finishing the type. During finishing, we + // may not run any Java code, because that might result in a request to finish the type that we + // are in the process of finishing, and this would be a problem. + // Prevent infinity recursion for broken class loaders by keeping a recursion count and falling + // back to late binding if we recurse more than twice. + var mode = System.Threading.Interlocked.Increment(ref recursionCount) > 2 || (JVM.DisableEagerClassLoading && wrapper.Name != "sun.reflect.misc.Trampoline") + ? LoadMode.ReturnUnloadable + : LoadMode.Link; + try + { + classFile.Link(wrapper, mode); + + for (int i = 0; i < fields.Length; i++) + fields[i].Link(mode); + + for (int i = 0; i < methods.Length; i++) + methods[i].Link(mode); + } + finally + { + System.Threading.Interlocked.Decrement(ref recursionCount); + } + + // this is the correct lock, FinishCore doesn't call any user code and mutates global state, + // so it needs to be protected by a lock. + lock (this) + { + FinishedTypeImpl impl; + try + { + // call FinishCore in the finally to avoid Thread.Abort interrupting the thread + } + finally + { + impl = FinishCore(); + } + return impl; + } + } + + FinishedTypeImpl FinishCore() + { + // it is possible that the loading of the referenced classes triggered a finish of us, + // if that happens, we just return + if (finishedType != null) + return finishedType; + + if (finishInProgress) + throw new InvalidOperationException("Recursive finish attempt for " + wrapper.Name); + + finishInProgress = true; + wrapper.ClassLoader.Diagnostics.GenericCompilerTrace($"Finishing: {wrapper.Name}"); + Profiler.Enter("JavaTypeImpl.Finish.Core"); + + try + { + RuntimeJavaType declaringTypeWrapper = null; + var innerClassesTypeWrappers = Array.Empty(); + + // if we're an inner class, we need to attach an InnerClass attribute + ClassFile.InnerClass[] innerclasses = classFile.InnerClasses; + if (innerclasses != null) + { + // TODO consider not pre-computing innerClassesTypeWrappers and declaringTypeWrapper here + var wrappers = new List(); + for (int i = 0; i < innerclasses.Length; i++) + { + if (innerclasses[i].innerClass.IsNotNil && innerclasses[i].outerClass.IsNotNil) + { + if (classFile.GetConstantPoolClassType(innerclasses[i].outerClass) == wrapper) + { + wrappers.Add(classFile.GetConstantPoolClassType(innerclasses[i].innerClass)); + } + if (classFile.GetConstantPoolClassType(innerclasses[i].innerClass) == wrapper) + { + declaringTypeWrapper = classFile.GetConstantPoolClassType(innerclasses[i].outerClass); + } + } + } + innerClassesTypeWrappers = wrappers.ToArray(); +#if IMPORTER + // before we bake our type, we need to link any inner annotations to allow them to create their attribute type (as a nested type) + foreach (var tw in innerClassesTypeWrappers) + { + var dtw = tw as RuntimeByteCodeJavaType; + if (dtw != null) + { + var impl = dtw.impl as JavaTypeImpl; + if (impl != null) + if (impl.annotationBuilder != null) + impl.annotationBuilder.Link(); + } + } +#endif + } +#if IMPORTER + + if (annotationBuilder != null) + { + var cab = new CustomAttributeBuilder(wrapper.Context.Resolver.ResolveRuntimeType(typeof(AnnotationAttributeAttribute).FullName).AsReflection().GetConstructor(new Type[] { wrapper.Context.Types.String }), new object[] { UnicodeUtil.EscapeInvalidSurrogates(annotationBuilder.AttributeTypeName) }); + typeBuilder.SetCustomAttribute(cab); + } + + if (!wrapper.IsInterface && wrapper.IsMapUnsafeException) + { + // mark all exceptions that are unsafe for mapping with a custom attribute, + // so that at runtime we can quickly assertain if an exception type can be + // caught without filtering + wrapper.Context.AttributeHelper.SetExceptionIsUnsafeForMapping(typeBuilder); + } +#endif + + var context = new FinishContext(wrapper.Context, host, classFile, wrapper, typeBuilder); + var type = context.FinishImpl(); + +#if IMPORTER + if (annotationBuilder != null) + { + annotationBuilder.Finish(this); + } + if (enumBuilder != null) + { + enumBuilder.CreateType(); + } + if (privateInterfaceMethods != null) + { + privateInterfaceMethods.CreateType(); + } +#endif + var finishedClinitMethod = (MethodInfo)clinitMethod; +#if !IMPORTER + if (finishedClinitMethod != null) + { + // In dynamic mode, we may need to emit a call to this method from a DynamicMethod which doesn't support calling unfinished methods, + // so we must resolve to the real method here. + finishedClinitMethod = type.GetMethod("__", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic); + } +#endif + + finishedType = new FinishedTypeImpl(type, innerClassesTypeWrappers, declaringTypeWrapper, wrapper.ReflectiveModifiers, Metadata.Create(classFile), finishedClinitMethod, finalizeMethod, host); + return finishedType; + } +#if !IMPORTER + catch (Exception x) + { + throw new InternalException($"Exception during finishing of: {wrapper.Name}", x); + } +#endif + finally + { + Profiler.Leave("JavaTypeImpl.Finish.Core"); + } + } + +#if IMPORTER + + private bool IsValidAnnotationElementType(string type) + { + if (type[0] == '[') + type = type.Substring(1); + + switch (type) + { + case "Z": + case "B": + case "S": + case "C": + case "I": + case "J": + case "F": + case "D": + case "Ljava.lang.String;": + case "Ljava.lang.Class;": + return true; + } + + if (type.StartsWith("L") && type.EndsWith(";")) + { + try + { + var tw = wrapper.ClassLoader.TryLoadClassByName(type.Substring(1, type.Length - 2)); + if (tw != null) + { + if ((tw.Modifiers & Modifiers.Annotation) != 0) + return true; + + if ((tw.Modifiers & Modifiers.Enum) != 0) + { + var enumType = wrapper.Context.ClassLoaderFactory.GetBootstrapClassLoader().TryLoadClassByName("java.lang.Enum"); + if (enumType != null && tw.IsSubTypeOf(enumType)) + return true; + } + } + } + catch + { + + } + } + + return false; + } + + sealed class AnnotationBuilder : Annotation + { + + readonly RuntimeContext context; + + JavaTypeImpl impl; + TypeBuilder outer; + TypeBuilder annotationTypeBuilder; + TypeBuilder attributeTypeBuilder; + MethodBuilder defineConstructor; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + internal AnnotationBuilder(RuntimeContext context, JavaTypeImpl o, TypeBuilder outer) + { + this.context = context; + this.impl = o; + this.outer = outer; + } + + internal void Link() + { + if (impl == null) + { + return; + } + JavaTypeImpl o = impl; + impl = null; + + // Make sure the annotation type only has valid methods + for (int i = 0; i < o.methods.Length; i++) + { + if (!o.methods[i].IsStatic) + { + if (!o.methods[i].Signature.StartsWith("()")) + { + return; + } + if (!o.IsValidAnnotationElementType(o.methods[i].Signature.Substring(2))) + { + return; + } + } + } + + // we only set annotationTypeBuilder if we're valid + annotationTypeBuilder = o.typeBuilder; + + var annotationAttributeBaseType = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.AnnotationAttributeBase"); + + // make sure we don't clash with another class name + var ccl = o.wrapper.classLoader; + string name = UnicodeUtil.EscapeInvalidSurrogates(o.classFile.Name); + while (!ccl.ReserveName(name + "Attribute")) + { + name += "_"; + } + + var typeAttributes = TypeAttributes.Class | TypeAttributes.Sealed; + if (o.enclosingClassWrapper != null) + { + if (o.wrapper.IsPublic) + { + typeAttributes |= TypeAttributes.NestedPublic; + } + else + { + typeAttributes |= TypeAttributes.NestedAssembly; + } + attributeTypeBuilder = outer.DefineNestedType(o.AllocNestedTypeName(o.enclosingClassWrapper.Name, name + "Attribute"), typeAttributes, annotationAttributeBaseType.TypeAsBaseType); + } + else + { + if (o.wrapper.IsPublic) + { + typeAttributes |= TypeAttributes.Public; + } + else + { + typeAttributes |= TypeAttributes.NotPublic; + } + attributeTypeBuilder = o.wrapper.classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(name + "Attribute", typeAttributes, annotationAttributeBaseType.TypeAsBaseType); + } + if (o.wrapper.IsPublic) + { + // In the Java world, the class appears as a non-public proxy class + context.AttributeHelper.SetModifiers(attributeTypeBuilder, Modifiers.Final, false); + } + + // NOTE we "abuse" the InnerClassAttribute to add a custom attribute to name the class "$Proxy[Annotation]" in the Java world + int dotindex = o.classFile.Name.LastIndexOf('.') + 1; + context.AttributeHelper.SetInnerClass(attributeTypeBuilder, o.classFile.Name.Substring(0, dotindex) + "$Proxy" + o.classFile.Name.Substring(dotindex), Modifiers.Final); + attributeTypeBuilder.AddInterfaceImplementation(o.typeBuilder); + context.AttributeHelper.SetImplementsAttribute(attributeTypeBuilder, new RuntimeJavaType[] { o.wrapper }); + + if (o.classFile.Annotations != null) + { + CustomAttributeBuilder attributeUsageAttribute = null; + bool hasAttributeUsageAttribute = false; + foreach (object[] def in o.classFile.Annotations) + { + if (def[1].Equals("Ljava/lang/annotation/Target;") && !hasAttributeUsageAttribute) + { + for (int i = 2; i < def.Length; i += 2) + { + if (def[i].Equals("value")) + { + object[] val = def[i + 1] as object[]; + if (val != null + && val.Length > 0 + && val[0].Equals(AnnotationDefaultAttribute.TAG_ARRAY)) + { + AttributeTargets targets = 0; + for (int j = 1; j < val.Length; j++) + { + object[] eval = val[j] as object[]; + if (eval != null + && eval.Length == 3 + && eval[0].Equals(AnnotationDefaultAttribute.TAG_ENUM) + && eval[1].Equals("Ljava/lang/annotation/ElementType;")) + { + switch ((string)eval[2]) + { + case "ANNOTATION_TYPE": + targets |= AttributeTargets.Interface; + break; + case "CONSTRUCTOR": + targets |= AttributeTargets.Constructor; + break; + case "FIELD": + targets |= AttributeTargets.Field; + break; + case "LOCAL_VARIABLE": + break; + case "METHOD": + targets |= AttributeTargets.Method; + break; + case "PACKAGE": + targets |= AttributeTargets.Interface; + break; + case "PARAMETER": + targets |= AttributeTargets.Parameter; + break; + case "TYPE": + targets |= AttributeTargets.Class | AttributeTargets.Interface | AttributeTargets.Struct | AttributeTargets.Delegate | AttributeTargets.Enum; + break; + } + } + } + + attributeUsageAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName).GetConstructor([context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName)]).AsReflection(), [targets]); + } + } + } + } + else + { + // apply any .NET custom attributes that are on the annotation to the custom attribute we synthesize + // (for example, to allow AttributeUsageAttribute to be overridden) + Annotation annotation = Annotation.Load(o.wrapper, def); + if (annotation != null && annotation.IsCustomAttribute) + { + annotation.Apply(o.wrapper.ClassLoader, attributeTypeBuilder, def); + } + if (def[1].Equals("Lcli/System/AttributeUsageAttribute$Annotation;")) + { + hasAttributeUsageAttribute = true; + } + } + } + if (attributeUsageAttribute != null && !hasAttributeUsageAttribute) + { + attributeTypeBuilder.SetCustomAttribute(attributeUsageAttribute); + } + } + + defineConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, new Type[] { context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType().AsReflection() }); + context.AttributeHelper.SetEditorBrowsableNever(defineConstructor); } - // NOTE there is a bug in the CLR (.NET 1.0 & 1.1 [1.2 is not yet available]) that - // causes the AppDomain.TypeResolve event to receive the incorrect type name for nested types. - // The Name in the ResolveEventArgs contains only the nested type name, not the full type name, - // for example, if the type being resolved is "MyOuterType+MyInnerType", then the event only - // receives "MyInnerType" as the name. Since we only compile inner classes as nested types - // when we're statically compiling, we can only run into this bug when we're statically compiling. - // NOTE To work around this bug, we have to make sure that all types that are going to be - // required in finished form, are finished explicitly here. It isn't clear what other types are - // required to be finished. I instrumented a static compilation of classpath.dll and this - // turned up no other cases of the TypeResolve event firing. - foreach (RuntimeJavaType iface in wrapper.interfaces) + private static Type TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) { - iface.Finish(); - iface.LinkAll(); + bool isArray = false; + if (tw.IsArray) + { + isArray = true; + tw = tw.ElementTypeWrapper; + } + if (tw.Annotation != null) + { + // we don't support Annotation args + return null; + } + else + { + Type argType; + if (tw == tw.Context.JavaBase.TypeOfJavaLangClass) + { + argType = tw.Context.Types.Type; + } + else if (tw.EnumType != null) // is it a Java enum? + { + argType = tw.EnumType; + } + else if (IsDotNetEnum(tw)) + { + argType = tw.DeclaringTypeWrapper.TypeAsSignatureType; + } + else + { + argType = tw.TypeAsSignatureType; + } + if (isArray) + { + argType = RuntimeArrayJavaType.MakeArrayType(argType, 1); + } + return argType; + } } - // make sure all classes are loaded, before we start finishing the type. During finishing, we - // may not run any Java code, because that might result in a request to finish the type that we - // are in the process of finishing, and this would be a problem. - // Prevent infinity recursion for broken class loaders by keeping a recursion count and falling - // back to late binding if we recurse more than twice. - var mode = System.Threading.Interlocked.Increment(ref recursionCount) > 2 || (JVM.DisableEagerClassLoading && wrapper.Name != "sun.reflect.misc.Trampoline") - ? LoadMode.ReturnUnloadable - : LoadMode.Link; - try + private static bool IsDotNetEnum(RuntimeJavaType tw) { - classFile.Link(wrapper, mode); - - for (int i = 0; i < fields.Length; i++) - fields[i].Link(mode); - - for (int i = 0; i < methods.Length; i++) - methods[i].Link(mode); + return tw.IsFakeNestedType && (tw.Modifiers & Modifiers.Enum) != 0; } - finally + + internal string AttributeTypeName { - System.Threading.Interlocked.Decrement(ref recursionCount); + get + { + Link(); + if (attributeTypeBuilder != null) + { + return attributeTypeBuilder.FullName; + } + return null; + } } - // this is the correct lock, FinishCore doesn't call any user code and mutates global state, - // so it needs to be protected by a lock. - lock (this) + private static void EmitSetValueCall(RuntimeJavaType annotationAttributeBaseType, CodeEmitter ilgen, string name, RuntimeJavaType tw, int argIndex) { - FinishedTypeImpl impl; - try + ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(OpCodes.Ldstr, name); + ilgen.EmitLdarg(argIndex); + if (tw.TypeAsSignatureType.IsValueType) { - // call FinishCore in the finally to avoid Thread.Abort interrupting the thread + ilgen.Emit(OpCodes.Box, tw.TypeAsSignatureType); } - finally + else if (tw.EnumType != null) // is it a Java enum? { - impl = FinishCore(); + ilgen.Emit(OpCodes.Box, tw.EnumType); } - return impl; + else if (IsDotNetEnum(tw)) + { + ilgen.Emit(OpCodes.Box, tw.DeclaringTypeWrapper.TypeAsSignatureType); + } + var setValueMethod = annotationAttributeBaseType.GetMethodWrapper("setValue", "(Ljava.lang.String;Ljava.lang.Object;)V", false); + setValueMethod.Link(); + setValueMethod.EmitCall(ilgen); } - } - FinishedTypeImpl FinishCore() - { - // it is possible that the loading of the referenced classes triggered a finish of us, - // if that happens, we just return - if (finishedType != null) - return finishedType; + internal void Finish(JavaTypeImpl o) + { + Link(); - if (finishInProgress) - throw new InvalidOperationException("Recursive finish attempt for " + wrapper.Name); + // not a valid annotation type + if (annotationTypeBuilder == null) + return; - finishInProgress = true; - wrapper.ClassLoader.Diagnostics.GenericCompilerTrace($"Finishing: {wrapper.Name}"); - Profiler.Enter("JavaTypeImpl.Finish.Core"); + var annotationAttributeBaseType = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.AnnotationAttributeBase"); + annotationAttributeBaseType.Finish(); - try - { - RuntimeJavaType declaringTypeWrapper = null; - var innerClassesTypeWrappers = Array.Empty(); + var requiredArgCount = 0; + var valueArg = -1; + var unsupported = false; + for (int i = 0; i < o.methods.Length; i++) + { + if (!o.methods[i].IsStatic) + { + if (valueArg == -1 && o.methods[i].Name == "value") + valueArg = i; - // if we're an inner class, we need to attach an InnerClass attribute - ClassFile.InnerClass[] innerclasses = classFile.InnerClasses; - if (innerclasses != null) + if (o.classFile.Methods[i].AnnotationDefault == null) + { + if (TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType) == null) + { + unsupported = true; + break; + } + + requiredArgCount++; + } + } + } + + var defaultConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, unsupported || requiredArgCount > 0 ? MethodAttributes.Private : MethodAttributes.Public, []); + CodeEmitter ilgen; + + if (!unsupported) { - // TODO consider not pre-computing innerClassesTypeWrappers and declaringTypeWrapper here - var wrappers = new List(); - for (int i = 0; i < innerclasses.Length; i++) + if (requiredArgCount > 0) { - if (innerclasses[i].innerClass.IsNotNil && innerclasses[i].outerClass.IsNotNil) + var args = new Type[requiredArgCount]; + for (int i = 0, j = 0; i < o.methods.Length; i++) { - if (classFile.GetConstantPoolClassType(innerclasses[i].outerClass) == wrapper) + if (!o.methods[i].IsStatic) { - wrappers.Add(classFile.GetConstantPoolClassType(innerclasses[i].innerClass)); + if (o.classFile.Methods[i].AnnotationDefault == null) + { + args[j++] = TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType); + } } - if (classFile.GetConstantPoolClassType(innerclasses[i].innerClass) == wrapper) + } + + var reqArgConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, args); + context.AttributeHelper.HideFromJava(reqArgConstructor); + ilgen = context.CodeEmitterFactory.Create(reqArgConstructor); + ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(OpCodes.Call, defaultConstructor); + + for (int i = 0, j = 0; i < o.methods.Length; i++) + { + if (!o.methods[i].IsStatic) { - declaringTypeWrapper = classFile.GetConstantPoolClassType(innerclasses[i].outerClass); + if (o.classFile.Methods[i].AnnotationDefault == null) + { + reqArgConstructor.DefineParameter(++j, ParameterAttributes.None, o.methods[i].Name); + EmitSetValueCall(annotationAttributeBaseType, ilgen, o.methods[i].Name, o.methods[i].ReturnType, j); + } } } + + ilgen.Emit(OpCodes.Ret); + ilgen.DoEmit(); + } + else if (valueArg != -1) + { + // We don't have any required parameters, but we do have an optional "value" parameter, + // so we create an additional constructor (the default constructor will be public in this case) + // that accepts the value parameter. + Type argType = TypeWrapperToAnnotationParameterType(o.methods[valueArg].ReturnType); + if (argType != null) + { + MethodBuilder cb = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, new Type[] { argType }); + context.AttributeHelper.HideFromJava(cb); + cb.DefineParameter(1, ParameterAttributes.None, "value"); + ilgen = context.CodeEmitterFactory.Create(cb); + ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(OpCodes.Call, defaultConstructor); + EmitSetValueCall(annotationAttributeBaseType, ilgen, "value", o.methods[valueArg].ReturnType, 1); + ilgen.Emit(OpCodes.Ret); + ilgen.DoEmit(); + } } - innerClassesTypeWrappers = wrappers.ToArray(); -#if IMPORTER - // before we bake our type, we need to link any inner annotations to allow them to create their attribute type (as a nested type) - foreach (var tw in innerClassesTypeWrappers) - { - var dtw = tw as RuntimeByteCodeJavaType; - if (dtw != null) - { - var impl = dtw.impl as JavaTypeImpl; - if (impl != null) - if (impl.annotationBuilder != null) - impl.annotationBuilder.Link(); - } - } -#endif } -#if IMPORTER - - if (annotationBuilder != null) - { - var cab = new CustomAttributeBuilder(wrapper.Context.Resolver.ResolveRuntimeType(typeof(AnnotationAttributeAttribute).FullName).AsReflection().GetConstructor(new Type[] { wrapper.Context.Types.String }), new object[] { UnicodeUtil.EscapeInvalidSurrogates(annotationBuilder.AttributeTypeName) }); - typeBuilder.SetCustomAttribute(cab); - } - - if (!wrapper.IsInterface && wrapper.IsMapUnsafeException) - { - // mark all exceptions that are unsafe for mapping with a custom attribute, - // so that at runtime we can quickly assertain if an exception type can be - // caught without filtering - wrapper.Context.AttributeHelper.SetExceptionIsUnsafeForMapping(typeBuilder); - } -#endif - - var context = new FinishContext(wrapper.Context, host, classFile, wrapper, typeBuilder); - var type = context.FinishImpl(); -#if IMPORTER - if (annotationBuilder != null) - { - annotationBuilder.Finish(this); - } - if (enumBuilder != null) - { - enumBuilder.CreateType(); - } - if (privateInterfaceMethods != null) - { - privateInterfaceMethods.CreateType(); - } -#endif - var finishedClinitMethod = (MethodInfo)clinitMethod; -#if !IMPORTER - if (finishedClinitMethod != null) + ilgen = context.CodeEmitterFactory.Create(defaultConstructor); + ilgen.Emit(OpCodes.Ldarg_0); + o.wrapper.EmitClassLiteral(ilgen); + annotationAttributeBaseType.GetMethodWrapper("", "(Ljava.lang.Class;)V", false).EmitCall(ilgen); + ilgen.Emit(OpCodes.Ret); + ilgen.DoEmit(); + + ilgen = context.CodeEmitterFactory.Create(defineConstructor); + ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(OpCodes.Call, defaultConstructor); + ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(OpCodes.Ldarg_1); + annotationAttributeBaseType.GetMethodWrapper("setDefinition", "([Ljava.lang.Object;)V", false).EmitCall(ilgen); + ilgen.Emit(OpCodes.Ret); + ilgen.DoEmit(); + + var getValueMethod = annotationAttributeBaseType.GetMethodWrapper("getValue", "(Ljava.lang.String;)Ljava.lang.Object;", false); + var getByteValueMethod = annotationAttributeBaseType.GetMethodWrapper("getByteValue", "(Ljava.lang.String;)B", false); + var getBooleanValueMethod = annotationAttributeBaseType.GetMethodWrapper("getBooleanValue", "(Ljava.lang.String;)Z", false); + var getCharValueMethod = annotationAttributeBaseType.GetMethodWrapper("getCharValue", "(Ljava.lang.String;)C", false); + var getShortValueMethod = annotationAttributeBaseType.GetMethodWrapper("getShortValue", "(Ljava.lang.String;)S", false); + var getIntValueMethod = annotationAttributeBaseType.GetMethodWrapper("getIntValue", "(Ljava.lang.String;)I", false); + var getFloatValueMethod = annotationAttributeBaseType.GetMethodWrapper("getFloatValue", "(Ljava.lang.String;)F", false); + var getLongValueMethod = annotationAttributeBaseType.GetMethodWrapper("getLongValue", "(Ljava.lang.String;)J", false); + var getDoubleValueMethod = annotationAttributeBaseType.GetMethodWrapper("getDoubleValue", "(Ljava.lang.String;)D", false); + for (int i = 0; i < o.methods.Length; i++) { - // In dynamic mode, we may need to emit a call to this method from a DynamicMethod which doesn't support calling unfinished methods, - // so we must resolve to the real method here. - finishedClinitMethod = type.GetMethod("__", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic); + // skip and non-virtual interface methods introduced in Java 8 + if (o.methods[i].IsVirtual) + { + MethodBuilder mb = o.methods[i].GetDefineMethodHelper().DefineMethod(o.wrapper, attributeTypeBuilder, o.methods[i].Name, MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.Final | MethodAttributes.NewSlot); + attributeTypeBuilder.DefineMethodOverride(mb, (MethodInfo)o.methods[i].GetMethod()); + ilgen = context.CodeEmitterFactory.Create(mb); + ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(OpCodes.Ldstr, o.methods[i].Name); + if (o.methods[i].ReturnType.IsPrimitive) + { + if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.BYTE) + { + getByteValueMethod.EmitCall(ilgen); + } + else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.BOOLEAN) + { + getBooleanValueMethod.EmitCall(ilgen); + } + else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.CHAR) + { + getCharValueMethod.EmitCall(ilgen); + } + else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.SHORT) + { + getShortValueMethod.EmitCall(ilgen); + } + else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.INT) + { + getIntValueMethod.EmitCall(ilgen); + } + else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.FLOAT) + { + getFloatValueMethod.EmitCall(ilgen); + } + else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.LONG) + { + getLongValueMethod.EmitCall(ilgen); + } + else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.DOUBLE) + { + getDoubleValueMethod.EmitCall(ilgen); + } + else + { + throw new InvalidOperationException(); + } + } + else + { + getValueMethod.EmitCall(ilgen); + o.methods[i].ReturnType.EmitCheckcast(ilgen); + } + ilgen.Emit(OpCodes.Ret); + ilgen.DoEmit(); + + if (o.classFile.Methods[i].AnnotationDefault != null + && !(o.methods[i].Name == "value" && requiredArgCount == 0)) + { + // now add a .NET property for this annotation optional parameter + Type argType = TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType); + if (argType != null) + { + PropertyBuilder pb = attributeTypeBuilder.DefineProperty(o.methods[i].Name, PropertyAttributes.None, argType, []); + context.AttributeHelper.HideFromJava(pb); + MethodBuilder setter = attributeTypeBuilder.DefineMethod("set_" + o.methods[i].Name, MethodAttributes.Public, context.Types.Void, new Type[] { argType }); + context.AttributeHelper.HideFromJava(setter); + pb.SetSetMethod(setter); + ilgen = context.CodeEmitterFactory.Create(setter); + EmitSetValueCall(annotationAttributeBaseType, ilgen, o.methods[i].Name, o.methods[i].ReturnType, 1); + ilgen.Emit(OpCodes.Ret); + ilgen.DoEmit(); + MethodBuilder getter = attributeTypeBuilder.DefineMethod("get_" + o.methods[i].Name, MethodAttributes.Public, argType, []); + context.AttributeHelper.HideFromJava(getter); + pb.SetGetMethod(getter); + // TODO implement the getter method + ilgen = context.CodeEmitterFactory.Create(getter); + ilgen.ThrowException(context.Resolver.ResolveCoreType(typeof(NotImplementedException).FullName).AsReflection()); + ilgen.DoEmit(); + } + } + } } -#endif + attributeTypeBuilder.CreateType(); + } - finishedType = new FinishedTypeImpl(type, innerClassesTypeWrappers, declaringTypeWrapper, wrapper.ReflectiveModifiers, Metadata.Create(classFile), finishedClinitMethod, finalizeMethod, host); - return finishedType; + private CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) + { + Link(); + ConstructorInfo ctor = defineConstructor != null + ? defineConstructor.__AsConstructorInfo() + : context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").AsReflection().GetConstructor(new Type[] { context.Types.Object.MakeArrayType() }); + return new CustomAttributeBuilder(ctor, new object[] { AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation)) }); } -#if !IMPORTER - catch (Exception x) + + internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) { - throw new InternalException($"Exception during finishing of: {wrapper.Name}", x); + tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } -#endif - finally + + internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) { - Profiler.Leave("JavaTypeImpl.Finish.Core"); + mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - } -#if IMPORTER + internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation) + { + fb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); + } + + internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation) + { + pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); + } - private bool IsValidAnnotationElementType(string type) - { - if (type[0] == '[') - type = type.Substring(1); - - switch (type) - { - case "Z": - case "B": - case "S": - case "C": - case "I": - case "J": - case "F": - case "D": - case "Ljava.lang.String;": - case "Ljava.lang.Class;": - return true; - } - - if (type.StartsWith("L") && type.EndsWith(";")) - { - try - { - var tw = wrapper.ClassLoader.TryLoadClassByName(type.Substring(1, type.Length - 2)); - if (tw != null) - { - if ((tw.Modifiers & Modifiers.Annotation) != 0) - return true; - - if ((tw.Modifiers & Modifiers.Enum) != 0) - { - var enumType = wrapper.Context.ClassLoaderFactory.GetBootstrapClassLoader().TryLoadClassByName("java.lang.Enum"); - if (enumType != null && tw.IsSubTypeOf(enumType)) - return true; - } - } - } - catch - { - - } - } - - return false; - } - - sealed class AnnotationBuilder : Annotation - { - - readonly RuntimeContext context; - - JavaTypeImpl impl; - TypeBuilder outer; - TypeBuilder annotationTypeBuilder; - TypeBuilder attributeTypeBuilder; - MethodBuilder defineConstructor; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - internal AnnotationBuilder(RuntimeContext context, JavaTypeImpl o, TypeBuilder outer) - { - this.context = context; - this.impl = o; - this.outer = outer; - } - - internal void Link() - { - if (impl == null) - { - return; - } - JavaTypeImpl o = impl; - impl = null; - - // Make sure the annotation type only has valid methods - for (int i = 0; i < o.methods.Length; i++) - { - if (!o.methods[i].IsStatic) - { - if (!o.methods[i].Signature.StartsWith("()")) - { - return; - } - if (!o.IsValidAnnotationElementType(o.methods[i].Signature.Substring(2))) - { - return; - } - } - } - - // we only set annotationTypeBuilder if we're valid - annotationTypeBuilder = o.typeBuilder; - - var annotationAttributeBaseType = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.AnnotationAttributeBase"); - - // make sure we don't clash with another class name - var ccl = o.wrapper.classLoader; - string name = UnicodeUtil.EscapeInvalidSurrogates(o.classFile.Name); - while (!ccl.ReserveName(name + "Attribute")) - { - name += "_"; - } - - var typeAttributes = TypeAttributes.Class | TypeAttributes.Sealed; - if (o.enclosingClassWrapper != null) - { - if (o.wrapper.IsPublic) - { - typeAttributes |= TypeAttributes.NestedPublic; - } - else - { - typeAttributes |= TypeAttributes.NestedAssembly; - } - attributeTypeBuilder = outer.DefineNestedType(o.AllocNestedTypeName(o.enclosingClassWrapper.Name, name + "Attribute"), typeAttributes, annotationAttributeBaseType.TypeAsBaseType); - } - else - { - if (o.wrapper.IsPublic) - { - typeAttributes |= TypeAttributes.Public; - } - else - { - typeAttributes |= TypeAttributes.NotPublic; - } - attributeTypeBuilder = o.wrapper.classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(name + "Attribute", typeAttributes, annotationAttributeBaseType.TypeAsBaseType); - } - if (o.wrapper.IsPublic) - { - // In the Java world, the class appears as a non-public proxy class - context.AttributeHelper.SetModifiers(attributeTypeBuilder, Modifiers.Final, false); - } - - // NOTE we "abuse" the InnerClassAttribute to add a custom attribute to name the class "$Proxy[Annotation]" in the Java world - int dotindex = o.classFile.Name.LastIndexOf('.') + 1; - context.AttributeHelper.SetInnerClass(attributeTypeBuilder, o.classFile.Name.Substring(0, dotindex) + "$Proxy" + o.classFile.Name.Substring(dotindex), Modifiers.Final); - attributeTypeBuilder.AddInterfaceImplementation(o.typeBuilder); - context.AttributeHelper.SetImplementsAttribute(attributeTypeBuilder, new RuntimeJavaType[] { o.wrapper }); - - if (o.classFile.Annotations != null) - { - CustomAttributeBuilder attributeUsageAttribute = null; - bool hasAttributeUsageAttribute = false; - foreach (object[] def in o.classFile.Annotations) - { - if (def[1].Equals("Ljava/lang/annotation/Target;") && !hasAttributeUsageAttribute) - { - for (int i = 2; i < def.Length; i += 2) - { - if (def[i].Equals("value")) - { - object[] val = def[i + 1] as object[]; - if (val != null - && val.Length > 0 - && val[0].Equals(AnnotationDefaultAttribute.TAG_ARRAY)) - { - AttributeTargets targets = 0; - for (int j = 1; j < val.Length; j++) - { - object[] eval = val[j] as object[]; - if (eval != null - && eval.Length == 3 - && eval[0].Equals(AnnotationDefaultAttribute.TAG_ENUM) - && eval[1].Equals("Ljava/lang/annotation/ElementType;")) - { - switch ((string)eval[2]) - { - case "ANNOTATION_TYPE": - targets |= AttributeTargets.Interface; - break; - case "CONSTRUCTOR": - targets |= AttributeTargets.Constructor; - break; - case "FIELD": - targets |= AttributeTargets.Field; - break; - case "LOCAL_VARIABLE": - break; - case "METHOD": - targets |= AttributeTargets.Method; - break; - case "PACKAGE": - targets |= AttributeTargets.Interface; - break; - case "PARAMETER": - targets |= AttributeTargets.Parameter; - break; - case "TYPE": - targets |= AttributeTargets.Class | AttributeTargets.Interface | AttributeTargets.Struct | AttributeTargets.Delegate | AttributeTargets.Enum; - break; - } - } - } - - attributeUsageAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName).GetConstructor([context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName)]).AsReflection(), [targets]); - } - } - } - } - else - { - // apply any .NET custom attributes that are on the annotation to the custom attribute we synthesize - // (for example, to allow AttributeUsageAttribute to be overridden) - Annotation annotation = Annotation.Load(o.wrapper, def); - if (annotation != null && annotation.IsCustomAttribute) - { - annotation.Apply(o.wrapper.ClassLoader, attributeTypeBuilder, def); - } - if (def[1].Equals("Lcli/System/AttributeUsageAttribute$Annotation;")) - { - hasAttributeUsageAttribute = true; - } - } - } - if (attributeUsageAttribute != null && !hasAttributeUsageAttribute) - { - attributeTypeBuilder.SetCustomAttribute(attributeUsageAttribute); - } - } - - defineConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, new Type[] { context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType().AsReflection() }); - context.AttributeHelper.SetEditorBrowsableNever(defineConstructor); - } - - private static Type TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) - { - bool isArray = false; - if (tw.IsArray) - { - isArray = true; - tw = tw.ElementTypeWrapper; - } - if (tw.Annotation != null) - { - // we don't support Annotation args - return null; - } - else - { - Type argType; - if (tw == tw.Context.JavaBase.TypeOfJavaLangClass) - { - argType = tw.Context.Types.Type; - } - else if (tw.EnumType != null) // is it a Java enum? - { - argType = tw.EnumType; - } - else if (IsDotNetEnum(tw)) - { - argType = tw.DeclaringTypeWrapper.TypeAsSignatureType; - } - else - { - argType = tw.TypeAsSignatureType; - } - if (isArray) - { - argType = RuntimeArrayJavaType.MakeArrayType(argType, 1); - } - return argType; - } - } - - private static bool IsDotNetEnum(RuntimeJavaType tw) - { - return tw.IsFakeNestedType && (tw.Modifiers & Modifiers.Enum) != 0; - } - - internal string AttributeTypeName - { - get - { - Link(); - if (attributeTypeBuilder != null) - { - return attributeTypeBuilder.FullName; - } - return null; - } - } - - private static void EmitSetValueCall(RuntimeJavaType annotationAttributeBaseType, CodeEmitter ilgen, string name, RuntimeJavaType tw, int argIndex) - { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldstr, name); - ilgen.EmitLdarg(argIndex); - if (tw.TypeAsSignatureType.IsValueType) - { - ilgen.Emit(OpCodes.Box, tw.TypeAsSignatureType); - } - else if (tw.EnumType != null) // is it a Java enum? - { - ilgen.Emit(OpCodes.Box, tw.EnumType); - } - else if (IsDotNetEnum(tw)) - { - ilgen.Emit(OpCodes.Box, tw.DeclaringTypeWrapper.TypeAsSignatureType); - } - var setValueMethod = annotationAttributeBaseType.GetMethodWrapper("setValue", "(Ljava.lang.String;Ljava.lang.Object;)V", false); - setValueMethod.Link(); - setValueMethod.EmitCall(ilgen); - } - - internal void Finish(JavaTypeImpl o) - { - Link(); - if (annotationTypeBuilder == null) - { - // not a valid annotation type - return; - } - RuntimeJavaType annotationAttributeBaseType = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.AnnotationAttributeBase"); - annotationAttributeBaseType.Finish(); - - int requiredArgCount = 0; - int valueArg = -1; - bool unsupported = false; - for (int i = 0; i < o.methods.Length; i++) - { - if (!o.methods[i].IsStatic) - { - if (valueArg == -1 && o.methods[i].Name == "value") - { - valueArg = i; - } - if (o.classFile.Methods[i].AnnotationDefault == null) - { - if (TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType) == null) - { - unsupported = true; - break; - } - requiredArgCount++; - } - } - } - - MethodBuilder defaultConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, unsupported || requiredArgCount > 0 ? MethodAttributes.Private : MethodAttributes.Public, Type.EmptyTypes); - CodeEmitter ilgen; - - if (!unsupported) - { - if (requiredArgCount > 0) - { - Type[] args = new Type[requiredArgCount]; - for (int i = 0, j = 0; i < o.methods.Length; i++) - { - if (!o.methods[i].IsStatic) - { - if (o.classFile.Methods[i].AnnotationDefault == null) - { - args[j++] = TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType); - } - } - } - MethodBuilder reqArgConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, args); - context.AttributeHelper.HideFromJava(reqArgConstructor); - ilgen = context.CodeEmitterFactory.Create(reqArgConstructor); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Call, defaultConstructor); - for (int i = 0, j = 0; i < o.methods.Length; i++) - { - if (!o.methods[i].IsStatic) - { - if (o.classFile.Methods[i].AnnotationDefault == null) - { - reqArgConstructor.DefineParameter(++j, ParameterAttributes.None, o.methods[i].Name); - EmitSetValueCall(annotationAttributeBaseType, ilgen, o.methods[i].Name, o.methods[i].ReturnType, j); - } - } - } - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); - } - else if (valueArg != -1) - { - // We don't have any required parameters, but we do have an optional "value" parameter, - // so we create an additional constructor (the default constructor will be public in this case) - // that accepts the value parameter. - Type argType = TypeWrapperToAnnotationParameterType(o.methods[valueArg].ReturnType); - if (argType != null) - { - MethodBuilder cb = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, new Type[] { argType }); - context.AttributeHelper.HideFromJava(cb); - cb.DefineParameter(1, ParameterAttributes.None, "value"); - ilgen = context.CodeEmitterFactory.Create(cb); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Call, defaultConstructor); - EmitSetValueCall(annotationAttributeBaseType, ilgen, "value", o.methods[valueArg].ReturnType, 1); - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); - } - } - } - - ilgen = context.CodeEmitterFactory.Create(defaultConstructor); - ilgen.Emit(OpCodes.Ldarg_0); - o.wrapper.EmitClassLiteral(ilgen); - annotationAttributeBaseType.GetMethodWrapper("", "(Ljava.lang.Class;)V", false).EmitCall(ilgen); - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); - - ilgen = context.CodeEmitterFactory.Create(defineConstructor); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Call, defaultConstructor); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldarg_1); - annotationAttributeBaseType.GetMethodWrapper("setDefinition", "([Ljava.lang.Object;)V", false).EmitCall(ilgen); - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); - - var getValueMethod = annotationAttributeBaseType.GetMethodWrapper("getValue", "(Ljava.lang.String;)Ljava.lang.Object;", false); - var getByteValueMethod = annotationAttributeBaseType.GetMethodWrapper("getByteValue", "(Ljava.lang.String;)B", false); - var getBooleanValueMethod = annotationAttributeBaseType.GetMethodWrapper("getBooleanValue", "(Ljava.lang.String;)Z", false); - var getCharValueMethod = annotationAttributeBaseType.GetMethodWrapper("getCharValue", "(Ljava.lang.String;)C", false); - var getShortValueMethod = annotationAttributeBaseType.GetMethodWrapper("getShortValue", "(Ljava.lang.String;)S", false); - var getIntValueMethod = annotationAttributeBaseType.GetMethodWrapper("getIntValue", "(Ljava.lang.String;)I", false); - var getFloatValueMethod = annotationAttributeBaseType.GetMethodWrapper("getFloatValue", "(Ljava.lang.String;)F", false); - var getLongValueMethod = annotationAttributeBaseType.GetMethodWrapper("getLongValue", "(Ljava.lang.String;)J", false); - var getDoubleValueMethod = annotationAttributeBaseType.GetMethodWrapper("getDoubleValue", "(Ljava.lang.String;)D", false); - for (int i = 0; i < o.methods.Length; i++) - { - // skip and non-virtual interface methods introduced in Java 8 - if (o.methods[i].IsVirtual) - { - MethodBuilder mb = o.methods[i].GetDefineMethodHelper().DefineMethod(o.wrapper, attributeTypeBuilder, o.methods[i].Name, MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.Final | MethodAttributes.NewSlot); - attributeTypeBuilder.DefineMethodOverride(mb, (MethodInfo)o.methods[i].GetMethod()); - ilgen = context.CodeEmitterFactory.Create(mb); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldstr, o.methods[i].Name); - if (o.methods[i].ReturnType.IsPrimitive) - { - if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.BYTE) - { - getByteValueMethod.EmitCall(ilgen); - } - else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.BOOLEAN) - { - getBooleanValueMethod.EmitCall(ilgen); - } - else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.CHAR) - { - getCharValueMethod.EmitCall(ilgen); - } - else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.SHORT) - { - getShortValueMethod.EmitCall(ilgen); - } - else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.INT) - { - getIntValueMethod.EmitCall(ilgen); - } - else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.FLOAT) - { - getFloatValueMethod.EmitCall(ilgen); - } - else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.LONG) - { - getLongValueMethod.EmitCall(ilgen); - } - else if (o.methods[i].ReturnType == context.PrimitiveJavaTypeFactory.DOUBLE) - { - getDoubleValueMethod.EmitCall(ilgen); - } - else - { - throw new InvalidOperationException(); - } - } - else - { - getValueMethod.EmitCall(ilgen); - o.methods[i].ReturnType.EmitCheckcast(ilgen); - } - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); - - if (o.classFile.Methods[i].AnnotationDefault != null - && !(o.methods[i].Name == "value" && requiredArgCount == 0)) - { - // now add a .NET property for this annotation optional parameter - Type argType = TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType); - if (argType != null) - { - PropertyBuilder pb = attributeTypeBuilder.DefineProperty(o.methods[i].Name, PropertyAttributes.None, argType, Type.EmptyTypes); - context.AttributeHelper.HideFromJava(pb); - MethodBuilder setter = attributeTypeBuilder.DefineMethod("set_" + o.methods[i].Name, MethodAttributes.Public, context.Types.Void, new Type[] { argType }); - context.AttributeHelper.HideFromJava(setter); - pb.SetSetMethod(setter); - ilgen = context.CodeEmitterFactory.Create(setter); - EmitSetValueCall(annotationAttributeBaseType, ilgen, o.methods[i].Name, o.methods[i].ReturnType, 1); - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); - MethodBuilder getter = attributeTypeBuilder.DefineMethod("get_" + o.methods[i].Name, MethodAttributes.Public, argType, Type.EmptyTypes); - context.AttributeHelper.HideFromJava(getter); - pb.SetGetMethod(getter); - // TODO implement the getter method - ilgen = context.CodeEmitterFactory.Create(getter); - ilgen.ThrowException(context.Resolver.ResolveCoreType(typeof(NotImplementedException).FullName).AsReflection()); - ilgen.DoEmit(); - } - } - } - } - attributeTypeBuilder.CreateType(); - } - - private CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) - { - Link(); - ConstructorInfo ctor = defineConstructor != null - ? defineConstructor.__AsConstructorInfo() - : context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").AsReflection().GetConstructor(new Type[] { context.Types.Object.MakeArrayType() }); - return new CustomAttributeBuilder(ctor, new object[] { AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation)) }); - } - - internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) - { - tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); - } - - internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) - { - mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); - } - - internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation) - { - fb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); - } - - internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation) - { - pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); - } - - internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) - { - ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); - } - - internal override void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation) - { - pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); - } - - internal override bool IsCustomAttribute - { - get { return false; } - } - } + internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) + { + ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); + } + + internal override void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation) + { + pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); + } + + internal override bool IsCustomAttribute + { + get { return false; } + } + } #endif // IMPORTER internal override RuntimeJavaType[] InnerClasses @@ -2291,7 +2292,7 @@ static MethodInfo GetBaseFinalizeMethod(RuntimeJavaType wrapper) } var type = wrapper.TypeAsBaseType; - var baseFinalize = type.GetMethod("__", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, Type.EmptyTypes, null); + var baseFinalize = type.GetMethod("__", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, [], null); if (baseFinalize != null) return baseFinalize; @@ -2455,11 +2456,11 @@ internal override MethodBase LinkMethod(RuntimeJavaMethod mw) wrapper.EmitLevel4Warning(mmw.IsConflictError ? HardError.IncompatibleClassChangeError : HardError.AbstractMethodError, message); } #if IMPORTER - if (wrapper.IsInterface && !mmw.IsAbstract) - { - // even though we're not visible to reflection we need to record the fact that we have a default implementation - wrapper.Context.AttributeHelper.SetModifiers(mb, mmw.Modifiers, false); - } + if (wrapper.IsInterface && !mmw.IsAbstract) + { + // even though we're not visible to reflection we need to record the fact that we have a default implementation + wrapper.Context.AttributeHelper.SetModifiers(mb, mmw.Modifiers, false); + } #endif return mb; } @@ -2502,50 +2503,50 @@ internal override MethodBase LinkMethod(RuntimeJavaMethod mw) methods[index].SetDeclaredExceptions(exceptions); #if IMPORTER - wrapper.Context.AttributeHelper.SetThrowsAttribute(method, exceptions); - - if (setModifiers || m.IsInternal || (m.Modifiers & (Modifiers.Synthetic | Modifiers.Bridge)) != 0) - wrapper.Context.AttributeHelper.SetModifiers(method, m.Modifiers, m.IsInternal); - - // synthetic and bridge methods should not be visible to the user and set as compiler generated - if ((m.Modifiers & (Modifiers.Synthetic | Modifiers.Bridge)) != 0 && (m.IsPublic || m.IsProtected) && wrapper.IsPublic && !IsAccessBridge(classFile, m)) - { - wrapper.Context.AttributeHelper.SetCompilerGenerated(method); - wrapper.Context.AttributeHelper.SetEditorBrowsableNever(method); - } - - // ensure deprecated attribute appears on method if obsolete not specified - if (m.DeprecatedAttribute && !Annotation.HasObsoleteAttribute(m.Annotations)) - { - wrapper.Context.AttributeHelper.SetDeprecatedAttribute(method); - } - - // apply .NET attribute to record Java generic signature - if (m.GenericSignature != null) - { - wrapper.Context.AttributeHelper.SetSignatureAttribute(method, m.GenericSignature); - } - - if (wrapper.ClassLoader.NoParameterReflection) - { - // ignore MethodParameters (except to extract parameter names) - } - else if (m.MalformedMethodParameters) - { - wrapper.Context.AttributeHelper.SetMethodParametersAttribute(method, null); - } - else if (m.MethodParameters != null) - { - var modifiers = new Modifiers[m.MethodParameters.Length]; - for (int i = 0; i < modifiers.Length; i++) - modifiers[i] = (Modifiers)m.MethodParameters[i].accessFlags; - - wrapper.Context.AttributeHelper.SetMethodParametersAttribute(method, modifiers); - } - - // copy runtime visible annotations as attributes - if (m.RuntimeVisibleTypeAnnotations.Count > 0) - wrapper.Context.AttributeHelper.SetRuntimeVisibleTypeAnnotationsAttribute(method, in m.RuntimeVisibleTypeAnnotations); + wrapper.Context.AttributeHelper.SetThrowsAttribute(method, exceptions); + + if (setModifiers || m.IsInternal || (m.Modifiers & (Modifiers.Synthetic | Modifiers.Bridge)) != 0) + wrapper.Context.AttributeHelper.SetModifiers(method, m.Modifiers, m.IsInternal); + + // synthetic and bridge methods should not be visible to the user and set as compiler generated + if ((m.Modifiers & (Modifiers.Synthetic | Modifiers.Bridge)) != 0 && (m.IsPublic || m.IsProtected) && wrapper.IsPublic && !IsAccessBridge(classFile, m)) + { + wrapper.Context.AttributeHelper.SetCompilerGenerated(method); + wrapper.Context.AttributeHelper.SetEditorBrowsableNever(method); + } + + // ensure deprecated attribute appears on method if obsolete not specified + if (m.DeprecatedAttribute && !Annotation.HasObsoleteAttribute(m.Annotations)) + { + wrapper.Context.AttributeHelper.SetDeprecatedAttribute(method); + } + + // apply .NET attribute to record Java generic signature + if (m.GenericSignature != null) + { + wrapper.Context.AttributeHelper.SetSignatureAttribute(method, m.GenericSignature); + } + + if (wrapper.ClassLoader.NoParameterReflection) + { + // ignore MethodParameters (except to extract parameter names) + } + else if (m.MalformedMethodParameters) + { + wrapper.Context.AttributeHelper.SetMethodParametersAttribute(method, null); + } + else if (m.MethodParameters != null) + { + var modifiers = new Modifiers[m.MethodParameters.Length]; + for (int i = 0; i < modifiers.Length; i++) + modifiers[i] = (Modifiers)m.MethodParameters[i].accessFlags; + + wrapper.Context.AttributeHelper.SetMethodParametersAttribute(method, modifiers); + } + + // copy runtime visible annotations as attributes + if (m.RuntimeVisibleTypeAnnotations.Count > 0) + wrapper.Context.AttributeHelper.SetRuntimeVisibleTypeAnnotationsAttribute(method, in m.RuntimeVisibleTypeAnnotations); #else // IMPORTER @@ -2663,20 +2664,20 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier attribs |= MethodAttributes.SpecialName; } #if IMPORTER - if ((m.Modifiers & Modifiers.Bridge) != 0 && (m.IsPublic || m.IsProtected) && wrapper.IsPublic) - { - string sigbase = m.Signature.Substring(0, m.Signature.LastIndexOf(')') + 1); - foreach (var mw in methods) - { - if (mw.Name == m.Name && mw.Signature.StartsWith(sigbase) && mw.Signature != m.Signature) - { - // To prevent bridge methods with covariant return types from confusing - // other .NET compilers (like C#), we rename the bridge method. - name = NamePrefix.Bridge + name; - break; - } - } - } + if ((m.Modifiers & Modifiers.Bridge) != 0 && (m.IsPublic || m.IsProtected) && wrapper.IsPublic) + { + string sigbase = m.Signature.Substring(0, m.Signature.LastIndexOf(')') + 1); + foreach (var mw in methods) + { + if (mw.Name == m.Name && mw.Signature.StartsWith(sigbase) && mw.Signature != m.Signature) + { + // To prevent bridge methods with covariant return types from confusing + // other .NET compilers (like C#), we rename the bridge method. + name = NamePrefix.Bridge + name; + break; + } + } + } #endif if ((attribs & MethodAttributes.Virtual) != 0 && !classFile.IsInterface) { @@ -2709,7 +2710,7 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier } MethodBuilder mb = null; #if IMPORTER - mb = wrapper.DefineGhostMethod(typeBuilder, name, attribs, methods[index]); + mb = wrapper.DefineGhostMethod(typeBuilder, name, attribs, methods[index]); #endif if (mb == null) { @@ -2784,7 +2785,7 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier tb, NamePrefix.PrivateInterfaceInstanceMethod + name, attribs | MethodAttributes.Static | MethodAttributes.SpecialName, typeBuilder, false); #if IMPORTER - wrapper.Context.AttributeHelper.SetNameSig(mb, m.Name, m.Signature); + wrapper.Context.AttributeHelper.SetNameSig(mb, m.Name, m.Signature); #endif } setModifiers = true; @@ -2825,7 +2826,7 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier if (m.IsFinal) attr |= MethodAttributes.Final; - finalizeMethod = typeBuilder.DefineMethod(finalizeName, attr, CallingConventions.Standard, wrapper.Context.Types.Void, Type.EmptyTypes); + finalizeMethod = typeBuilder.DefineMethod(finalizeName, attr, CallingConventions.Standard, wrapper.Context.Types.Void, []); if (finalizeName != baseFinalize.Name) typeBuilder.DefineMethodOverride(finalizeMethod, baseFinalize); @@ -2858,11 +2859,11 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier ilgen.DoEmit(); } #if IMPORTER - if (classFile.Methods[index].AnnotationDefault != null) - { - var cab = new CustomAttributeBuilder(wrapper.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.AnnotationDefaultAttribute").AsReflection().GetConstructor([wrapper.Context.Types.Object]), [AnnotationDefaultAttribute.Escape(classFile.Methods[index].AnnotationDefault)]); - mb.SetCustomAttribute(cab); - } + if (classFile.Methods[index].AnnotationDefault != null) + { + var cab = new CustomAttributeBuilder(wrapper.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.AnnotationDefaultAttribute").GetConstructor([wrapper.Context.Types.Object]), [AnnotationDefaultAttribute.Escape(classFile.Methods[index].AnnotationDefault)]); + mb.SetCustomAttribute(cab); + } #endif } @@ -2920,28 +2921,28 @@ private static MethodAttributes GetMethodAccess(RuntimeJavaMethod mw) } #if IMPORTER - // The classic example of an access bridge is StringBuilder.length(), the JDK 6 compiler - // generates this to work around a reflection problem (which otherwise wouldn't surface the - // length() method, because it is defined in the non-public base class AbstractStringBuilder.) - private static bool IsAccessBridge(ClassFile classFile, ClassFile.Method m) - { - // HACK this is a pretty gross hack - // We look at the method body to figure out if the bridge method calls another method with the exact - // same name/signature and if that is the case, we assume that it is an access bridge. - // This code is based on the javac algorithm in addBridgeIfNeeded(...) in com/sun/tools/javac/comp/TransTypes.java. - if ((m.Modifiers & (Modifiers.Abstract | Modifiers.Native | Modifiers.Public | Modifiers.Bridge)) == (Modifiers.Public | Modifiers.Bridge)) - { - foreach (ClassFile.Method.Instruction instr in m.Instructions) - { - if (instr.NormalizedOpCode == NormalizedByteCode.__invokespecial) - { - ClassFile.ConstantPoolItemMI cpi = classFile.SafeGetMethodref(instr.Arg1); - return cpi != null && cpi.Name == m.Name && cpi.Signature == m.Signature; - } - } - } - return false; - } + // The classic example of an access bridge is StringBuilder.length(), the JDK 6 compiler + // generates this to work around a reflection problem (which otherwise wouldn't surface the + // length() method, because it is defined in the non-public base class AbstractStringBuilder.) + private static bool IsAccessBridge(ClassFile classFile, ClassFile.Method m) + { + // HACK this is a pretty gross hack + // We look at the method body to figure out if the bridge method calls another method with the exact + // same name/signature and if that is the case, we assume that it is an access bridge. + // This code is based on the javac algorithm in addBridgeIfNeeded(...) in com/sun/tools/javac/comp/TransTypes.java. + if ((m.Modifiers & (Modifiers.Abstract | Modifiers.Native | Modifiers.Public | Modifiers.Bridge)) == (Modifiers.Public | Modifiers.Bridge)) + { + foreach (ClassFile.Method.Instruction instr in m.Instructions) + { + if (instr.NormalizedOpCode == NormalizedByteCode.__invokespecial) + { + ClassFile.ConstantPoolItemMI cpi = classFile.SafeGetMethodref(instr.Arg1); + return cpi != null && cpi.Name == m.Name && cpi.Signature == m.Signature; + } + } + } + return false; + } #endif // IMPORTER internal override Type Type diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index 35bf3c4ed3..ad900b87fb 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -960,7 +960,7 @@ private Type[] GetModOpt(RuntimeJavaType tw, bool mustBePublic) internal static Type[] GetModOpt(RuntimeJavaTypeFactory context, RuntimeJavaType tw, bool mustBePublic) { - Type[] modopt = Type.EmptyTypes; + Type[] modopt = []; if (tw.IsUnloadable) { if (((RuntimeUnloadableJavaType)tw).MissingType == null) diff --git a/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs b/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs index ec600f9026..00a6b1c0a3 100644 --- a/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs +++ b/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs @@ -110,7 +110,7 @@ internal void DoLink(TypeBuilder tb) { setter.Link(); } - pb = tb.DefineProperty(this.Name, PropertyAttributes.None, this.FieldTypeWrapper.TypeAsSignatureType, Type.EmptyTypes); + pb = tb.DefineProperty(this.Name, PropertyAttributes.None, this.FieldTypeWrapper.TypeAsSignatureType, []); if (getter != null) { pb.SetGetMethod((MethodBuilder)getter.GetMethod()); @@ -212,7 +212,7 @@ internal override object GetValue(object obj) { throw new java.lang.NoSuchMethodError(); } - return getter.Invoke(obj, new object[0]); + return getter.Invoke(obj, []); } internal override void SetValue(object obj, object value) diff --git a/src/IKVM.Runtime/RuntimeClassLoader.cs b/src/IKVM.Runtime/RuntimeClassLoader.cs index 8f7f29d52c..03a426852d 100644 --- a/src/IKVM.Runtime/RuntimeClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeClassLoader.cs @@ -744,7 +744,7 @@ internal virtual java.lang.ClassLoader GetJavaClassLoader() internal Type[] ArgTypeListFromSig(string signature) { if (signature[1] == ')') - return Type.EmptyTypes; + return []; var javaTypes = ArgJavaTypeListFromSig(signature, LoadMode.LoadOrThrow); var types = new Type[javaTypes.Length]; diff --git a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs index 1a0eb7c92d..c84a9c54cd 100644 --- a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs @@ -25,9 +25,10 @@ Jeroen Frijters using System.Collections.Generic; using System.Diagnostics; +using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Diagnostics; -#if NETCOREAPP +#if NET using System.Runtime.Loader; #endif @@ -54,8 +55,8 @@ class RuntimeClassLoaderFactory readonly RuntimeContext context; readonly object wrapperLock = new object(); - internal readonly Dictionary globalTypeToTypeWrapper = new Dictionary(); - internal readonly Dictionary remappedTypes = new Dictionary(); + internal readonly Dictionary globalTypeToTypeWrapper = new Dictionary(); + internal readonly Dictionary remappedTypes = new Dictionary(); readonly List genericClassLoaders = new List(); #if IMPORTER || EXPORTER @@ -99,14 +100,14 @@ internal void SetBootstrapClassLoader(RuntimeClassLoader bootstrapClassLoader) internal void LoadRemappedTypes() { // if we're compiling the base assembly, we won't be able to resolve one - var baseAssembly = context.Resolver.ResolveBaseAssembly().AsReflection(); + var baseAssembly = context.Resolver.ResolveBaseAssembly(); if (baseAssembly != null && remappedTypes.Count == 0) { var remapped = context.AttributeHelper.GetRemappedClasses(baseAssembly); if (remapped.Length > 0) { foreach (var r in remapped) - remappedTypes.Add(r.RemappedType, r.Name); + remappedTypes.Add(context.Resolver.ResolveType(r.RemappedType), r.Name); } else { @@ -119,7 +120,7 @@ internal void LoadRemappedTypes() } } - internal bool IsRemappedType(Type type) + internal bool IsRemappedType(ITypeSymbol type) { return remappedTypes.ContainsKey(type); } @@ -171,15 +172,13 @@ internal RuntimeClassLoader GetClassLoaderWrapper(java.lang.ClassLoader javaClas /// /// /// - internal RuntimeJavaType GetJavaTypeFromType(Type type) + internal RuntimeJavaType GetJavaTypeFromType(ITypeSymbol type) { #if IMPORTER - if (type.__ContainsMissingType) - { + if (type.ContainsMissing) return new RuntimeUnloadableJavaType(context, type); - } #endif - //Tracer.Info(Tracer.Runtime, "GetWrapperFromType: {0}", type.AssemblyQualifiedName); + #if !IMPORTER RuntimeJavaType.AssertFinished(type); #endif @@ -194,7 +193,7 @@ internal RuntimeJavaType GetJavaTypeFromType(Type type) return wrapper; #if EXPORTER - if (type.__IsMissing || type.__ContainsMissingType) + if (type.IsMissing || type.ContainsMissing) { wrapper = new RuntimeUnloadableJavaType(context, type); globalTypeToTypeWrapper.Add(type, wrapper); @@ -206,12 +205,12 @@ internal RuntimeJavaType GetJavaTypeFromType(Type type) { wrapper = LoadClassCritical(remapped); } - else if (ReflectUtil.IsVector(type)) + else if (type.IsSZArray) { // it might be an array of a dynamically compiled Java type int rank = 1; - Type elem = type.GetElementType(); - while (ReflectUtil.IsVector(elem)) + var elem = type.GetElementType(); + while (elem.IsSZArray) { rank++; elem = elem.GetElementType(); diff --git a/src/IKVM.Runtime/RuntimeConstantJavaField.cs b/src/IKVM.Runtime/RuntimeConstantJavaField.cs index 269364aec4..178e1a693a 100644 --- a/src/IKVM.Runtime/RuntimeConstantJavaField.cs +++ b/src/IKVM.Runtime/RuntimeConstantJavaField.cs @@ -25,6 +25,8 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -64,7 +66,7 @@ sealed class RuntimeConstantJavaField : RuntimeJavaField /// /// /// - internal RuntimeConstantJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, string name, string sig, Modifiers modifiers, FieldInfo field, object constant, MemberFlags flags) : + internal RuntimeConstantJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, string name, string sig, Modifiers modifiers, IFieldSymbol field, object constant, MemberFlags flags) : base(declaringType, fieldType, name, sig, modifiers, field, flags) { if (IsStatic == false) diff --git a/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs b/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs index 3f54ca98c2..3eb7ca57da 100644 --- a/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs @@ -22,14 +22,11 @@ Jeroen Frijters */ using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; #else -using System.Reflection; using System.Reflection.Emit; #endif @@ -39,7 +36,7 @@ namespace IKVM.Runtime sealed class RuntimeConstructorAccessStubJavaMethod : RuntimeSmartJavaMethod { - readonly ConstructorInfo stub; + readonly IConstructorSymbol stub; /// /// Initializes a new instance. @@ -51,7 +48,7 @@ sealed class RuntimeConstructorAccessStubJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal RuntimeConstructorAccessStubJavaMethod(RuntimeJavaType declaringType, string sig, ConstructorInfo core, ConstructorInfo stub, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimeConstructorAccessStubJavaMethod(RuntimeJavaType declaringType, string sig, IConstructorSymbol core, IConstructorSymbol stub, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, StringConstants.INIT, sig, core, declaringType.Context.PrimitiveJavaTypeFactory.VOID, parameterTypes, modifiers, flags) { this.stub = stub; diff --git a/src/IKVM.Runtime/RuntimeContext.cs b/src/IKVM.Runtime/RuntimeContext.cs index e2d770865c..ef2ec783b4 100644 --- a/src/IKVM.Runtime/RuntimeContext.cs +++ b/src/IKVM.Runtime/RuntimeContext.cs @@ -29,7 +29,7 @@ class RuntimeContext readonly RuntimeContextOptions options; readonly IDiagnosticHandler diagnostics; - readonly ISymbolResolver resolver; + readonly IRuntimeSymbolResolver resolver; readonly bool bootstrap; readonly ConcurrentDictionary singletons = new(); @@ -81,7 +81,7 @@ class RuntimeContext /// /// /// - public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, ISymbolResolver resolver, bool bootstrap, StaticCompiler staticCompiler) + public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, IRuntimeSymbolResolver resolver, bool bootstrap, StaticCompiler staticCompiler) { this.options = options ?? throw new ArgumentNullException(nameof(options)); this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); @@ -92,14 +92,14 @@ public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnost #else - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, ISymbolResolver resolver, bool bootstrap) + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, IRuntimeSymbolResolver resolver, bool bootstrap) { this.options = options ?? throw new ArgumentNullException(nameof(options)); this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); @@ -143,10 +143,10 @@ T GetOrCreateSingleton(ref T value, Func create) /// public RuntimeContextOptions Options => options; - /// - /// Gets the associated with this instance of the runtime. - /// - public ISymbolResolver Resolver => resolver; + /// + /// Gets the associated with this instance of the runtime. + /// + public IRuntimeSymbolResolver Resolver => resolver; /// /// Gets whether or not the runtime is running in bootstrap mode; that is, we are compiling the Java base assembly itself. diff --git a/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs b/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs index 6287028aac..3350b11ea0 100644 --- a/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs @@ -22,14 +22,11 @@ Jeroen Frijters */ using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; #else -using System.Reflection; using System.Reflection.Emit; #endif @@ -39,7 +36,7 @@ namespace IKVM.Runtime sealed class RuntimeDefaultInterfaceJavaMethod : RuntimeSmartJavaMethod { - MethodInfo impl; + IMethodSymbol impl; /// /// Initializes a new instance. @@ -53,13 +50,13 @@ sealed class RuntimeDefaultInterfaceJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal RuntimeDefaultInterfaceJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodInfo ifmethod, MethodInfo impl, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimeDefaultInterfaceJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodSymbol ifmethod, IMethodSymbol impl, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, name, sig, ifmethod, returnType, parameterTypes, modifiers, flags) { this.impl = impl; } - internal static MethodInfo GetImpl(RuntimeJavaMethod mw) + internal static IMethodSymbol GetImpl(RuntimeJavaMethod mw) { var dimw = mw as RuntimeDefaultInterfaceJavaMethod; if (dimw != null) @@ -68,7 +65,7 @@ internal static MethodInfo GetImpl(RuntimeJavaMethod mw) return ((RuntimeGhostJavaMethod)mw).GetDefaultImpl(); } - internal static void SetImpl(RuntimeJavaMethod mw, MethodInfo impl) + internal static void SetImpl(RuntimeJavaMethod mw, IMethodSymbol impl) { var dimw = mw as RuntimeDefaultInterfaceJavaMethod; if (dimw != null) diff --git a/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs b/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs index f2a5e1702c..894722bc20 100644 --- a/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs @@ -24,6 +24,7 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -39,8 +40,8 @@ namespace IKVM.Runtime sealed class RuntimeGhostJavaMethod : RuntimeSmartJavaMethod { - MethodInfo ghostMethod; - MethodInfo defaultImpl; + IMethodSymbol ghostMethod; + IMethodSymbol defaultImpl; /// /// Initializes a new instance. @@ -54,7 +55,7 @@ sealed class RuntimeGhostJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal RuntimeGhostJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodBase method, MethodInfo ghostMethod, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimeGhostJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodBaseSymbol method, IMethodSymbol ghostMethod, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, name, sig, method, returnType, parameterTypes, modifiers, flags) { // make sure we weren't handed the ghostMethod in the wrapper value type @@ -81,17 +82,17 @@ protected override void CallvirtImpl(CodeEmitter ilgen) [HideFromJava] internal override object Invoke(object obj, object[] args) { - return InvokeAndUnwrapException(ghostMethod, DeclaringType.GhostWrap(obj), args); + return InvokeAndUnwrapException(ghostMethod.AsReflection(), DeclaringType.GhostWrap(obj), args); } #endif - internal void SetDefaultImpl(MethodInfo impl) + internal void SetDefaultImpl(IMethodSymbol impl) { this.defaultImpl = impl; } - internal MethodInfo GetDefaultImpl() + internal IMethodSymbol GetDefaultImpl() { return defaultImpl; } @@ -105,7 +106,7 @@ internal void SetGhostMethod(MethodBuilder mb) internal MethodBuilder GetGhostMethod() { - return (MethodBuilder)ghostMethod; + return (MethodBuilder)ghostMethod.AsReflection(); } #endif diff --git a/src/IKVM.Runtime/RuntimeJavaField.cs b/src/IKVM.Runtime/RuntimeJavaField.cs index 5b6a1ae853..c4cd21c80e 100644 --- a/src/IKVM.Runtime/RuntimeJavaField.cs +++ b/src/IKVM.Runtime/RuntimeJavaField.cs @@ -23,16 +23,13 @@ Jeroen Frijters */ using System; using System.Diagnostics; +using System.Threading; using IKVM.Attributes; - -using System.Threading; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; #else using System.Reflection; using System.Reflection.Emit; @@ -47,7 +44,7 @@ abstract class RuntimeJavaField : RuntimeJavaMember #if !IMPORTER && !FIRST_PASS && !EXPORTER volatile java.lang.reflect.Field reflectionField; #endif - FieldInfo field; + IFieldSymbol field; RuntimeJavaType fieldType; /// @@ -60,7 +57,7 @@ abstract class RuntimeJavaField : RuntimeJavaMember /// /// /// - internal RuntimeJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, string name, string sig, Modifiers modifiers, FieldInfo field, MemberFlags flags) : + internal RuntimeJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, string name, string sig, Modifiers modifiers, IFieldSymbol field, MemberFlags flags) : base(declaringType, name, sig, modifiers, flags) { if (name == null) @@ -97,7 +94,7 @@ this is not RuntimeConstantJavaField && /// /// /// - internal RuntimeJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, string name, string sig, ExModifiers modifiers, FieldInfo field) : + internal RuntimeJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, string name, string sig, ExModifiers modifiers, IFieldSymbol field) : this(declaringType, fieldType, name, sig, modifiers.Modifiers, field, (modifiers.IsInternal ? MemberFlags.InternalAccess : MemberFlags.None)) { @@ -118,7 +115,7 @@ void UpdateNonPublicTypeInSignatureFlag() /// Gets the CLR that forms the implementation of the field. /// /// - internal FieldInfo GetField() + internal IFieldSymbol GetField() { AssertLinked(); return field; @@ -431,7 +428,7 @@ internal bool IsSerialVersionUID } } - internal static RuntimeJavaField Create(RuntimeJavaType declaringType, RuntimeJavaType fieldType, FieldInfo fi, string name, string sig, ExModifiers modifiers) + internal static RuntimeJavaField Create(RuntimeJavaType declaringType, RuntimeJavaType fieldType, IFieldSymbol fi, string name, string sig, ExModifiers modifiers) { // volatile long & double field accesses must be made atomic if ((modifiers.Modifiers & Modifiers.Volatile) != 0 && (sig == "J" || sig == "D")) @@ -443,7 +440,7 @@ internal static RuntimeJavaField Create(RuntimeJavaType declaringType, RuntimeJa #if !IMPORTER && !EXPORTER internal virtual void ResolveField() { - var fb = field as FieldBuilder; + var fb = field.AsReflection() as FieldBuilder; if (fb != null) { #if NETFRAMEWORK @@ -511,8 +508,8 @@ Delegate CreateUnsafeGetDelegate() FieldTypeWrapper.Finish(); ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD, true, ft, new[] { typeof(object) }); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, ft, [typeof(object)]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -558,8 +555,8 @@ Delegate CreateUnsafeSetDelegate() FieldTypeWrapper.Finish(); ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD, true, typeof(void), new[] { typeof(object), ft }); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, typeof(void), [typeof(object), ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -603,8 +600,8 @@ Delegate GetUnsafeVolatileGetDelegate() Delegate CreateUnsafeVolatileGetDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType : typeof(object); - var dm = new DynamicMethod($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", ft, new[] { typeof(object) }, DeclaringType.TypeAsTBD.Module, true); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); + var dm = new DynamicMethod($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", ft, [typeof(object)], DeclaringType.TypeAsTBD.Module.AsReflection(), true); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -648,8 +645,8 @@ Delegate GetUnsafeVolatileSetDelegate() Delegate CreateUnsafeVolatileSetDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD, true, typeof(void), new[] { typeof(object), ft }); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, typeof(void), [typeof(object), ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -696,8 +693,8 @@ Delegate GetUnsafeCompareAndSwapDelegate() Delegate CreateUnsafeCompareAndSwapDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD, true, typeof(bool), new[] { typeof(object), ft, ft }); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, typeof(bool), [typeof(object), ft, ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) diff --git a/src/IKVM.Runtime/RuntimeJavaMethod.cs b/src/IKVM.Runtime/RuntimeJavaMethod.cs index 6e752c734b..2456f18eea 100644 --- a/src/IKVM.Runtime/RuntimeJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeJavaMethod.cs @@ -27,7 +27,9 @@ Jeroen Frijters using IKVM.Attributes; using System.Linq; -using IKVM.CoreLib.Diagnostics; + +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER @@ -46,7 +48,7 @@ namespace IKVM.Runtime abstract class RuntimeJavaMethod : RuntimeJavaMember { - MethodBase method; + IMethodBaseSymbol method; string[] declaredExceptions; RuntimeJavaType returnTypeWrapper; RuntimeJavaType[] parameterTypeWrappers; @@ -97,7 +99,7 @@ internal virtual bool EmitIntrinsic(EmitIntrinsicContext context) /// /// /// - internal RuntimeJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodBase method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimeJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodBaseSymbol method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, name, sig, modifiers, flags) { Profiler.Count("MethodWrapper"); @@ -142,7 +144,7 @@ internal void SetDeclaredExceptions(string[] exceptions) { declaredExceptions = exceptions != null && exceptions.Length > 0 ? (string[])exceptions.Clone() : Array.Empty(); } - + /// /// Gest the declared exceptions for the method. /// @@ -225,18 +227,20 @@ internal java.lang.reflect.Executable ToMethodOrConstructor(bool copy) } #if !FIRST_PASS - private java.lang.Class[] GetExceptions() + + java.lang.Class[] GetExceptions() { - string[] classes = declaredExceptions; - Type[] types = Type.EmptyTypes; + Type[] types = []; + + var classes = declaredExceptions; if (classes == null) { // NOTE if method is a MethodBuilder, GetCustomAttributes doesn't work (and if // the method had any declared exceptions, the declaredExceptions field would have // been set) - if (method != null && method is not MethodBuilder) + if (method != null && method.AsReflection() is not MethodBuilder) { - ThrowsAttribute attr = DeclaringType.Context.AttributeHelper.GetThrows(method); + var attr = DeclaringType.Context.AttributeHelper.GetThrows(method); if (attr != null) { classes = attr.classes; @@ -244,25 +248,25 @@ private java.lang.Class[] GetExceptions() } } } + if (classes != null) { - java.lang.Class[] array = new java.lang.Class[classes.Length]; + var array = new java.lang.Class[classes.Length]; for (int i = 0; i < classes.Length; i++) - { array[i] = this.DeclaringType.ClassLoader.LoadClassByName(classes[i]).ClassObject; - } + return array; } else { - java.lang.Class[] array = new java.lang.Class[types.Length]; + var array = new java.lang.Class[types.Length]; for (int i = 0; i < types.Length; i++) - { array[i] = types[i]; - } + return array; } } + #endif // !FIRST_PASS internal static RuntimeJavaMethod FromExecutable(java.lang.reflect.Executable executable) @@ -381,7 +385,7 @@ internal DefineMethodHelper GetDefineMethodHelper() } #endif - internal Type ReturnTypeForDefineMethod + internal ITypeSymbol ReturnTypeForDefineMethod { get { @@ -389,23 +393,20 @@ internal Type ReturnTypeForDefineMethod } } - internal Type[] GetParametersForDefineMethod() + internal ITypeSymbol[] GetParametersForDefineMethod() { - RuntimeJavaType[] wrappers = GetParameters(); - int len = wrappers.Length; + var wrappers = GetParameters(); + var len = wrappers.Length; if (HasCallerID) - { len++; - } - Type[] temp = new Type[len]; + + var temp = new ITypeSymbol[len]; for (int i = 0; i < wrappers.Length; i++) - { temp[i] = wrappers[i].TypeAsSignatureType; - } + if (HasCallerID) - { temp[len - 1] = DeclaringType.Context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType; - } + return temp; } @@ -413,7 +414,7 @@ internal Type[] GetParametersForDefineMethod() // for Java types, this is the method that contains the compiled Java bytecode // for remapped types, this is the mbCore method (not the helper) // Note that for some artificial methods (notably wrap() in enums), method is null - internal MethodBase GetMethod() + internal IMethodBaseSymbol GetMethod() { AssertLinked(); return method; @@ -451,7 +452,7 @@ internal bool RequiresNonVirtualDispatcher #if !IMPORTER && !EXPORTER - internal Type GetDelegateType() + internal ITypeSymbol GetDelegateType() { var paramTypes = GetParameters(); if (paramTypes.Length > MethodHandleUtil.MaxArity) @@ -460,7 +461,7 @@ internal Type GetDelegateType() if (type == null) type = DeclaringType.ClassLoader.GetTypeWrapperFactory().DefineDelegate(paramTypes.Length, ReturnType == DeclaringType.Context.PrimitiveJavaTypeFactory.VOID); - var types = new Type[paramTypes.Length + (ReturnType == DeclaringType.Context.PrimitiveJavaTypeFactory.VOID ? 0 : 1)]; + var types = new ITypeSymbol[paramTypes.Length + (ReturnType == DeclaringType.Context.PrimitiveJavaTypeFactory.VOID ? 0 : 1)]; for (int i = 0; i < paramTypes.Length; i++) types[i] = paramTypes[i].TypeAsSignatureType; @@ -482,7 +483,7 @@ internal void ResolveMethod() throw new NotImplementedException(); #else // if we've still got the builder object, we need to replace it with the real thing before we can call it - var mb = method as MethodBuilder; + var mb = method.AsReflection() as MethodBuilder; if (mb != null) { #if NETFRAMEWORK @@ -537,14 +538,14 @@ internal virtual object InvokeNonvirtualRemapped(object obj, object[] args) /// /// [HideFromJava] - protected static object InvokeAndUnwrapException(MethodBase mb, object obj, object[] args) + protected static object InvokeAndUnwrapException(IMethodBaseSymbol mb, object obj, object[] args) { #if FIRST_PASS throw new NotImplementedException(); #else try { - return mb.Invoke(obj, args); + return mb.AsReflection().Invoke(obj, args); } catch (TargetInvocationException e) { diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index e16b878896..ff32a16733 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -22,17 +22,19 @@ Jeroen Frijters */ using System; -using System.Collections.Generic; using System.Diagnostics; +using System.Linq; using IKVM.Attributes; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; + #else using System.Reflection; using System.Reflection.Emit; @@ -106,11 +108,12 @@ internal void EmitClassLiteral(CodeEmitter ilgen) if (!this.IsFastClassLiteralSafe || IsForbiddenTypeParameterType(type)) { int rank = 0; - while (ReflectUtil.IsVector(type)) + while (type.IsSZArray) { rank++; type = type.GetElementType(); } + if (rank == 0) { ilgen.Emit(OpCodes.Ldtoken, type); @@ -125,18 +128,18 @@ internal void EmitClassLiteral(CodeEmitter ilgen) } else { - var classLiteralType = Context.Resolver.ResolveRuntimeType("IKVM.Runtime.ClassLiteral`1").AsReflection().MakeGenericType(type); + var classLiteralType = Context.Resolver.ResolveRuntimeType("IKVM.Runtime.ClassLiteral`1").MakeGenericType(type); ilgen.Emit(OpCodes.Call, classLiteralType.GetProperty("Value").GetMethod); } } #endif - private Type GetClassLiteralType() + ITypeSymbol GetClassLiteralType() { - Debug.Assert(!this.IsPrimitive); + Debug.Assert(IsPrimitive == false); - RuntimeJavaType tw = this; + var tw = this; if (tw.IsGhostArray) { var rank = tw.ArrayRank; @@ -151,16 +154,14 @@ private Type GetClassLiteralType() } } - bool IsForbiddenTypeParameterType(Type type) + bool IsForbiddenTypeParameterType(ITypeSymbol type) { // these are the types that may not be used as a type argument when instantiating a generic type return type == context.Types.Void -#if NETFRAMEWORK - || type == context.Resolver.ResolveCoreType(typeof(ArgIterator).FullName).AsReflection() -#endif - || type == context.Resolver.ResolveCoreType(typeof(RuntimeArgumentHandle).FullName).AsReflection() - || type == context.Resolver.ResolveCoreType(typeof(TypedReference).FullName).AsReflection() - || type.ContainsGenericParameters + || type == context.Resolver.ResolveCoreType(typeof(ArgIterator).FullName) + || type == context.Resolver.ResolveCoreType(typeof(RuntimeArgumentHandle).FullName) + || type == context.Resolver.ResolveCoreType(typeof(TypedReference).FullName) + || type.ContainsGenericParameters || type.IsByRef; } @@ -247,9 +248,9 @@ private void LazyInitClass() #if !FIRST_PASS java.lang.Class clazz; // note that this has to be the same check as in EmitClassLiteral - if (!this.IsFastClassLiteralSafe) + if (!IsFastClassLiteralSafe) { - if (this.IsPrimitive) + if (IsPrimitive) { clazz = GetPrimitiveClass(); } @@ -260,53 +261,37 @@ private void LazyInitClass() } else { - Type type = GetClassLiteralType(); + var type = GetClassLiteralType(); if (IsForbiddenTypeParameterType(type)) - { - clazz = new java.lang.Class(type); - } + clazz = new java.lang.Class(type.AsReflection()); else - { - clazz = (java.lang.Class)typeof(ClassLiteral<>).MakeGenericType(type).GetProperty("Value").GetGetMethod().Invoke(null, Array.Empty()); - } + clazz = (java.lang.Class)typeof(ClassLiteral<>).MakeGenericType(type.AsReflection()).GetProperty("Value").GetGetMethod().Invoke(null, []); } + clazz.typeWrapper = this; - // MONOBUG Interlocked.Exchange is broken on Mono, so we use CompareExchange System.Threading.Interlocked.CompareExchange(ref classObject, clazz, null); #endif } } } -#if __MonoCS__ - // MONOBUG this method is to work around an mcs bug - internal static void SetTypeWrapperHack(object clazz, TypeWrapper type) - { -#if !FIRST_PASS - typeof(java.lang.Class).GetField("typeWrapper", BindingFlags.NonPublic | BindingFlags.Instance).SetValue(clazz, type); -#endif - } -#endif - #if !FIRST_PASS - private static void ResolvePrimitiveTypeWrapperClasses(RuntimeContext context) + static void ResolvePrimitiveTypeWrapperClasses(RuntimeContext context) { // note that we're evaluating all ClassObject properties for the side effect // (to initialize and associate the ClassObject with the TypeWrapper) - if (context.PrimitiveJavaTypeFactory.BYTE.ClassObject == null - || context.PrimitiveJavaTypeFactory.CHAR.ClassObject == null - || context.PrimitiveJavaTypeFactory.DOUBLE.ClassObject == null - || context.PrimitiveJavaTypeFactory.FLOAT.ClassObject == null - || context.PrimitiveJavaTypeFactory.INT.ClassObject == null - || context.PrimitiveJavaTypeFactory.LONG.ClassObject == null - || context.PrimitiveJavaTypeFactory.SHORT.ClassObject == null - || context.PrimitiveJavaTypeFactory.BOOLEAN.ClassObject == null - || context.PrimitiveJavaTypeFactory.VOID.ClassObject == null) - { + if (context.PrimitiveJavaTypeFactory.BYTE.ClassObject == null || + context.PrimitiveJavaTypeFactory.CHAR.ClassObject == null || + context.PrimitiveJavaTypeFactory.DOUBLE.ClassObject == null || + context.PrimitiveJavaTypeFactory.FLOAT.ClassObject == null || + context.PrimitiveJavaTypeFactory.INT.ClassObject == null || + context.PrimitiveJavaTypeFactory.LONG.ClassObject == null || + context.PrimitiveJavaTypeFactory.SHORT.ClassObject == null || + context.PrimitiveJavaTypeFactory.BOOLEAN.ClassObject == null || + context.PrimitiveJavaTypeFactory.VOID.ClassObject == null) throw new InvalidOperationException(); - } } #endif @@ -326,10 +311,11 @@ internal static RuntimeJavaType FromClass(java.lang.Class clazz) return FromClass(clazz); } - if (type == typeof(void) || type.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(type)) - tw = JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(type); + var symbol = JVM.Context.Resolver.ResolveType(type); + if (type == typeof(void) || type.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(symbol)) + tw = JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(symbol); else - tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(type); + tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(symbol); clazz.typeWrapper = tw; } @@ -467,29 +453,11 @@ internal virtual bool IsGhost } // is this an array type of which the ultimate element type is a ghost? - internal bool IsGhostArray - { - get - { - return !IsUnloadable && IsArray && (ElementTypeWrapper.IsGhost || ElementTypeWrapper.IsGhostArray); - } - } + internal bool IsGhostArray => !IsUnloadable && IsArray && (ElementTypeWrapper.IsGhost || ElementTypeWrapper.IsGhostArray); - internal virtual FieldInfo GhostRefField - { - get - { - throw new InvalidOperationException(); - } - } + internal virtual IFieldSymbol GhostRefField => throw new InvalidOperationException(); - internal virtual bool IsRemapped - { - get - { - return false; - } - } + internal virtual bool IsRemapped => false; internal bool IsArray { @@ -558,7 +526,7 @@ internal bool IsIntOnStackPrimitive } } - private static bool IsJavaPrimitive(RuntimeContext context, Type type) + private static bool IsJavaPrimitive(RuntimeContext context, ITypeSymbol type) { return type == context.PrimitiveJavaTypeFactory.BOOLEAN.TypeAsTBD || type == context.PrimitiveJavaTypeFactory.BYTE.TypeAsTBD @@ -789,26 +757,26 @@ internal RuntimeJavaField[] GetFields() #if IMPORTER - private static bool CheckMissingBaseTypes(RuntimeContext context, Type type) + static bool CheckMissingBaseTypes(RuntimeContext context, ITypeSymbol type) { while (type != null) { - if (type.__ContainsMissingType) + if (type.ContainsMissing) { context.StaticCompiler.IssueMissingTypeMessage(type); return false; } - bool ok = true; - foreach (Type iface in type.__GetDeclaredInterfaces()) - { + + var ok = true; + foreach (var iface in type.GetInterfaces(false)) ok &= CheckMissingBaseTypes(context, iface); - } + if (!ok) - { return false; - } + type = type.BaseType; } + return true; } @@ -821,6 +789,7 @@ internal RuntimeJavaMethod GetMethodWrapper(string name, string sig, bool inheri var _name = string.IsInterned(name); var _sig = string.IsInterned(sig); + foreach (var mw in methods) { // NOTE we can use ref equality, because names and signatures are always interned by MemberWrapper @@ -947,12 +916,12 @@ static bool MatchingPackageNames(string name1, string name2) return string.CompareOrdinal(name1, skip1, name2, skip2, index1 - skip1) == 0; } - internal abstract Type TypeAsTBD + internal abstract ITypeSymbol TypeAsTBD { get; } - internal Type TypeAsSignatureType + internal ITypeSymbol TypeAsSignatureType { get { @@ -966,11 +935,11 @@ internal Type TypeAsSignatureType } } - internal Type TypeAsPublicSignatureType => (IsPublic ? this : GetPublicBaseTypeWrapper()).TypeAsSignatureType; + internal ITypeSymbol TypeAsPublicSignatureType => (IsPublic ? this : GetPublicBaseTypeWrapper()).TypeAsSignatureType; - internal virtual Type TypeAsBaseType => TypeAsTBD; + internal virtual ITypeSymbol TypeAsBaseType => TypeAsTBD; - internal Type TypeAsLocalOrStackType + internal ITypeSymbol TypeAsLocalOrStackType { get { @@ -991,7 +960,7 @@ internal Type TypeAsLocalOrStackType } /** Use this if the type is used as an array or array element */ - internal Type TypeAsArrayType + internal ITypeSymbol TypeAsArrayType { get { @@ -1005,7 +974,7 @@ internal Type TypeAsArrayType } } - internal Type TypeAsExceptionType + internal ITypeSymbol TypeAsExceptionType { get { @@ -1223,29 +1192,28 @@ internal void LinkAll() } #if !IMPORTER + [Conditional("DEBUG")] - internal static void AssertFinished(Type type) + internal static void AssertFinished(ITypeSymbol type) { if (type != null) { while (type.HasElementType) - { type = type.GetElementType(); - } - Debug.Assert(!(type is TypeBuilder)); + + Debug.Assert(!(type.AsReflection() is TypeBuilder)); } } + #endif #if !IMPORTER && !EXPORTER internal void RunClassInit() { - Type t = IsRemapped ? TypeAsBaseType : TypeAsTBD; + var t = IsRemapped ? TypeAsBaseType : TypeAsTBD; if (t != null) - { - System.Runtime.CompilerServices.RuntimeHelpers.RunClassConstructor(t.TypeHandle); - } + System.Runtime.CompilerServices.RuntimeHelpers.RunClassConstructor(t.AsReflection().TypeHandle); } #endif @@ -1270,6 +1238,7 @@ internal void EmitConvSignatureTypeToStackType(CodeEmitter ilgen) { if (IsUnloadable) { + } else if (this == context.PrimitiveJavaTypeFactory.BYTE) { @@ -1281,7 +1250,7 @@ internal void EmitConvSignatureTypeToStackType(CodeEmitter ilgen) } else if (IsGhost) { - CodeEmitterLocal local = ilgen.DeclareLocal(TypeAsSignatureType); + var local = ilgen.DeclareLocal(TypeAsSignatureType); ilgen.Emit(OpCodes.Stloc, local); ilgen.Emit(OpCodes.Ldloca, local); ilgen.Emit(OpCodes.Ldfld, GhostRefField); @@ -1442,13 +1411,13 @@ internal virtual void EmitStind(CodeEmitter il) #endif // NOTE don't call this method, call MethodWrapper.Link instead - internal virtual MethodBase LinkMethod(RuntimeJavaMethod mw) + internal virtual IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) { return mw.GetMethod(); } // NOTE don't call this method, call FieldWrapper.Link instead - internal virtual FieldInfo LinkField(RuntimeJavaField fw) + internal virtual IFieldSymbol LinkField(RuntimeJavaField fw) { return fw.GetField(); } @@ -1517,57 +1486,33 @@ internal virtual int GetSourceLineNumber(MethodBase mb, int ilOffset) internal virtual object GetAnnotationDefault(RuntimeJavaMethod mw) { - MethodBase mb = mw.GetMethod(); + var mb = mw.GetMethod(); if (mb != null) { - object[] attr = mb.GetCustomAttributes(typeof(AnnotationDefaultAttribute), false); - if (attr.Length == 1) - { - return JVM.NewAnnotationElementValue(mw.DeclaringType.ClassLoader.GetJavaClassLoader(), mw.ReturnType.ClassObject, ((AnnotationDefaultAttribute)attr[0]).Value); - } + var attr = mb.AsReflection().GetCustomAttribute(); + if (attr != null) + return JVM.NewAnnotationElementValue(mw.DeclaringType.ClassLoader.GetJavaClassLoader(), mw.ReturnType.ClassObject, attr.Value); } + return null; } + #endif // !IMPORTER && !EXPORTER internal virtual Annotation Annotation => null; - internal virtual Type EnumType => null; + internal virtual ITypeSymbol EnumType => null; - private static Type[] GetInterfaces(Type type) + static ITypeSymbol[] GetInterfaces(ITypeSymbol type) { -#if IMPORTER || EXPORTER - List list = new List(); - for (; type != null && !type.__IsMissing; type = type.BaseType) - { - AddInterfaces(list, type); - } - return list.ToArray(); -#else - return type.GetInterfaces(); -#endif - } + var ifaces = type.GetInterfaces(); + if (ifaces.Any(i => i.IsMissing)) + ifaces = ifaces.Where(i => i.IsMissing == false).ToArray(); -#if IMPORTER || EXPORTER - - private static void AddInterfaces(List list, Type type) - { - foreach (var iface in type.__GetDeclaredInterfaces()) - { - if (!list.Contains(iface)) - { - list.Add(iface); - if (!iface.__IsMissing) - { - AddInterfaces(list, iface); - } - } - } + return ifaces; } -#endif - - protected static RuntimeJavaType[] GetImplementedInterfacesAsTypeWrappers(RuntimeContext context, Type type) + protected static RuntimeJavaType[] GetImplementedInterfacesAsTypeWrappers(RuntimeContext context, ITypeSymbol type) { var interfaceTypes = GetInterfaces(type); var interfaces = new RuntimeJavaType[interfaceTypes.Length]; @@ -1617,12 +1562,14 @@ internal RuntimeJavaType GetPublicBaseTypeWrapper() #if !EXPORTER // return the constructor used for automagic .NET serialization - internal virtual MethodBase GetSerializationConstructor() + internal virtual IMethodBaseSymbol GetSerializationConstructor() { - return TypeAsBaseType.GetConstructor(BindingFlags.NonPublic | BindingFlags.Instance, null, [context.Resolver.ResolveCoreType(typeof(System.Runtime.Serialization.SerializationInfo).FullName).AsReflection(), context.Resolver.ResolveCoreType(typeof(System.Runtime.Serialization.StreamingContext).FullName).AsReflection()], null); + return TypeAsBaseType.GetConstructor( + System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance, + [context.Resolver.ResolveCoreType(typeof(System.Runtime.Serialization.SerializationInfo).FullName), context.Resolver.ResolveCoreType(typeof(System.Runtime.Serialization.StreamingContext).FullName)]); } - internal virtual MethodBase GetBaseSerializationConstructor() + internal virtual IMethodBaseSymbol GetBaseSerializationConstructor() { return BaseTypeWrapper.GetSerializationConstructor(); } @@ -1630,6 +1577,7 @@ internal virtual MethodBase GetBaseSerializationConstructor() #endif #if !IMPORTER && !EXPORTER + internal virtual object GhostWrap(object obj) { return obj; @@ -1639,6 +1587,7 @@ internal virtual object GhostUnwrap(object obj) { return obj; } + #endif internal bool IsDynamic @@ -1671,11 +1620,14 @@ internal virtual byte[] GetFieldRawTypeAnnotations(RuntimeJavaField fw) } #if !IMPORTER && !EXPORTER + internal virtual RuntimeJavaType Host { get { return null; } } + #endif + } } diff --git a/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs b/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs index e9d01832e1..1da4591ce1 100644 --- a/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs +++ b/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs @@ -21,18 +21,15 @@ Jeroen Frijters jeroen@frijters.net */ - -using System; using System.Collections.Generic; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; -using Type = IKVM.Reflection.Type; using ProtectionDomain = System.Object; #else -using System.Reflection; using System.Reflection.Emit; using ProtectionDomain = java.security.ProtectionDomain; @@ -54,9 +51,9 @@ abstract class RuntimeJavaTypeFactory internal abstract string AllocMangledName(RuntimeByteCodeJavaType tw); - internal abstract Type DefineUnloadable(string name); + internal abstract ITypeSymbol DefineUnloadable(string name); - internal abstract Type DefineDelegate(int parameterCount, bool returnVoid); + internal abstract ITypeSymbol DefineDelegate(int parameterCount, bool returnVoid); internal abstract bool HasInternalAccess { get; } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs index 5f7b3a646f..624b90831a 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs @@ -22,6 +22,8 @@ Jeroen Frijters */ using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -39,10 +41,10 @@ namespace IKVM.Runtime sealed class RuntimeManagedByteCodeAccessStubJavaField : RuntimeJavaField { - readonly MethodInfo getter; - readonly MethodInfo setter; + readonly IMethodSymbol getter; + readonly IMethodSymbol setter; - static Modifiers GetModifiers(PropertyInfo property) + static Modifiers GetModifiers(IPropertySymbol property) { // NOTE we only support the subset of modifiers that is expected for "access stub" properties var getter = property.GetGetMethod(true); @@ -61,7 +63,7 @@ static Modifiers GetModifiers(PropertyInfo property) /// /// /// - internal RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, PropertyInfo property, RuntimeJavaType propertyType) : + internal RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, IPropertySymbol property, RuntimeJavaType propertyType) : this(wrapper, property, null, propertyType, GetModifiers(property), MemberFlags.HideFromReflection | MemberFlags.AccessStub) { @@ -74,7 +76,7 @@ internal RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, Prop /// /// /// - internal RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, PropertyInfo property, FieldInfo field, RuntimeJavaType propertyType) : + internal RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, IPropertySymbol property, IFieldSymbol field, RuntimeJavaType propertyType) : this(wrapper, property, field, propertyType, wrapper.Context.AttributeHelper.GetModifiersAttribute(property).Modifiers, MemberFlags.AccessStub) { @@ -89,7 +91,7 @@ internal RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, Prop /// /// /// - private RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, PropertyInfo property, FieldInfo field, RuntimeJavaType propertyType, Modifiers modifiers, MemberFlags flags) : + private RuntimeManagedByteCodeAccessStubJavaField(RuntimeJavaType wrapper, IPropertySymbol property, IFieldSymbol field, RuntimeJavaType propertyType, Modifiers modifiers, MemberFlags flags) : base(wrapper, propertyType, property.Name, propertyType.SigName, modifiers, field, flags) { this.getter = property.GetGetMethod(true); diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs index d9ca623897..da72483acf 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs @@ -21,6 +21,7 @@ Jeroen Frijters jeroen@frijters.net */ +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -41,8 +42,8 @@ partial class RuntimeManagedByteCodeJavaType sealed class DelegateConstructorJavaMethod : RuntimeJavaMethod { - readonly ConstructorInfo constructor; - MethodInfo invoke; + readonly IConstructorSymbol constructor; + IMethodSymbol invoke; /// /// Initializes a new instance. @@ -51,7 +52,7 @@ sealed class DelegateConstructorJavaMethod : RuntimeJavaMethod /// /// DelegateConstructorJavaMethod(RuntimeJavaType tw, RuntimeJavaType iface, ExModifiers mods) : - base(tw, StringConstants.INIT, "(" + iface.SigName + ")V", null, tw.Context.PrimitiveJavaTypeFactory.VOID, new RuntimeJavaType[] { iface }, mods.Modifiers, mods.IsInternal ? MemberFlags.InternalAccess : MemberFlags.None) + base(tw, StringConstants.INIT, "(" + iface.SigName + ")V", null, tw.Context.PrimitiveJavaTypeFactory.VOID, [iface], mods.Modifiers, mods.IsInternal ? MemberFlags.InternalAccess : MemberFlags.None) { } @@ -61,17 +62,17 @@ sealed class DelegateConstructorJavaMethod : RuntimeJavaMethod /// /// /// - internal DelegateConstructorJavaMethod(RuntimeJavaType tw, MethodBase method) : + internal DelegateConstructorJavaMethod(RuntimeJavaType tw, IMethodBaseSymbol method) : this(tw, tw.ClassLoader.LoadClassByName(tw.Name + RuntimeManagedJavaType.DelegateInterfaceSuffix), tw.Context.AttributeHelper.GetModifiers(method, false)) { - constructor = (ConstructorInfo)method; + constructor = (IConstructorSymbol)method; } protected override void DoLinkMethod() { var mw = GetParameters()[0].GetMethods()[0]; mw.Link(); - invoke = (MethodInfo)mw.GetMethod(); + invoke = (IMethodSymbol)mw.GetMethod(); } #if EMITTERS diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs index ebbefa4c08..db1e751010 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs @@ -21,15 +21,7 @@ Jeroen Frijters jeroen@frijters.net */ -using System; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -#endif +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { @@ -40,8 +32,8 @@ partial class RuntimeManagedByteCodeJavaType public sealed class GhostJavaType : RuntimeManagedByteCodeJavaType { - volatile FieldInfo ghostRefField; - volatile Type typeAsBaseType; + volatile IFieldSymbol ghostRefField; + volatile ITypeSymbol typeAsBaseType; /// /// Initializes a new instance. @@ -49,33 +41,15 @@ public sealed class GhostJavaType : RuntimeManagedByteCodeJavaType /// /// /// - internal GhostJavaType(RuntimeContext context, string name, Type type) : + internal GhostJavaType(RuntimeContext context, string name, ITypeSymbol type) : base(context, name, type) { } - internal override Type TypeAsBaseType - { - get - { - if (typeAsBaseType == null) - typeAsBaseType = type.GetNestedType("__Interface"); + internal override ITypeSymbol TypeAsBaseType => typeAsBaseType ??= type.GetNestedType("__Interface"); - return typeAsBaseType; - } - } - - internal override FieldInfo GhostRefField - { - get - { - if (ghostRefField == null) - ghostRefField = type.GetField("__"); - - return ghostRefField; - } - } + internal override IFieldSymbol GhostRefField => ghostRefField ??= type.GetField("__"); internal override bool IsGhost => true; @@ -83,12 +57,12 @@ internal override FieldInfo GhostRefField internal override object GhostWrap(object obj) { - return type.GetMethod("Cast").Invoke(null, new object[] { obj }); + return type.GetMethod("Cast").AsReflection().Invoke(null, [obj]); } internal override object GhostUnwrap(object obj) { - return type.GetMethod("ToObject").Invoke(obj, new object[0]); + return type.GetMethod("ToObject").AsReflection().Invoke(obj, []); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs index 985828ac46..6202c75115 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs @@ -24,14 +24,11 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; #else -using System.Reflection; using System.Reflection.Emit; #endif @@ -44,9 +41,9 @@ partial class RuntimeManagedByteCodeJavaType sealed class RemappedJavaMethod : RuntimeSmartJavaMethod { - readonly MethodInfo mbHelper; + readonly IMethodSymbol mbHelper; #if !IMPORTER - readonly MethodInfo mbNonvirtualHelper; + readonly IMethodSymbol mbNonvirtualHelper; #endif /// @@ -62,7 +59,7 @@ sealed class RemappedJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal RemappedJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodBase method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, ExModifiers modifiers, bool hideFromReflection, MethodInfo mbHelper, MethodInfo mbNonvirtualHelper) : + internal RemappedJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodBaseSymbol method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, ExModifiers modifiers, bool hideFromReflection, IMethodSymbol mbHelper, IMethodSymbol mbNonvirtualHelper) : base(declaringType, name, sig, method, returnType, parameterTypes, modifiers.Modifiers, (modifiers.IsInternal ? MemberFlags.InternalAccess : MemberFlags.None) | (hideFromReflection ? MemberFlags.HideFromReflection : MemberFlags.None)) { this.mbHelper = mbHelper; @@ -76,7 +73,7 @@ internal RemappedJavaMethod(RuntimeJavaType declaringType, string name, string s protected override void CallImpl(CodeEmitter ilgen) { var mb = GetMethod(); - var mi = mb as MethodInfo; + var mi = mb as IMethodSymbol; if (mi != null) { if (!IsStatic && IsFinal) @@ -114,7 +111,7 @@ protected override void CallvirtImpl(CodeEmitter ilgen) protected override void NewobjImpl(CodeEmitter ilgen) { var mb = GetMethod(); - var mi = mb as MethodInfo; + var mi = mb as IMethodSymbol; if (mi != null) { Debug.Assert(mi.Name == "newhelper"); @@ -157,25 +154,27 @@ internal override object CreateInstance(object[] args) internal override object InvokeNonvirtualRemapped(object obj, object[] args) { var mi = mbNonvirtualHelper ?? mbHelper; - return mi.Invoke(null, ArrayUtil.Concat(obj, args)); + return mi.AsReflection().Invoke(null, ArrayUtil.Concat(obj, args)); } + #endif // !IMPORTER && !FIRST_PASS && !EXPORTER #if EMITTERS + internal override void EmitCallvirtReflect(CodeEmitter ilgen) { var mb = mbHelper ?? GetMethod(); ilgen.Emit(mb.IsStatic ? OpCodes.Call : OpCodes.Callvirt, mb); } + #endif // EMITTERS internal string GetGenericSignature() { - SignatureAttribute attr = DeclaringType.Context.AttributeHelper.GetSignature(mbHelper != null ? mbHelper : GetMethod()); + var attr = DeclaringType.Context.AttributeHelper.GetSignature(mbHelper != null ? mbHelper : GetMethod()); if (attr != null) - { return attr.Signature; - } + return null; } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs index 2f004376c0..8e03fb3358 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs @@ -25,6 +25,8 @@ Jeroen Frijters using System.Collections.Generic; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -44,7 +46,7 @@ partial class RuntimeManagedByteCodeJavaType internal sealed class RemappedJavaType : RuntimeManagedByteCodeJavaType { - readonly Type remappedType; + readonly ITypeSymbol remappedType; /// /// initializes a new instance. @@ -53,20 +55,25 @@ internal sealed class RemappedJavaType : RuntimeManagedByteCodeJavaType /// /// /// - internal RemappedJavaType(RuntimeContext context, string name, Type type) : + internal RemappedJavaType(RuntimeContext context, string name, ITypeSymbol type) : base(context, name, type) { var attr = Context.AttributeHelper.GetRemappedType(type) ?? throw new InvalidOperationException(); - remappedType = attr.Type; + remappedType = Context.Resolver.ResolveType(attr.Type); } - internal override Type TypeAsTBD => remappedType; + internal override ITypeSymbol TypeAsTBD => remappedType; internal override bool IsRemapped => true; protected override void LazyPublishMethods() { - const BindingFlags bindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; + const System.Reflection.BindingFlags bindingFlags = + System.Reflection.BindingFlags.DeclaredOnly | + System.Reflection.BindingFlags.Public | + System.Reflection.BindingFlags.NonPublic | + System.Reflection.BindingFlags.Static | + System.Reflection.BindingFlags.Instance; var list = new List(); @@ -79,7 +86,7 @@ protected override void LazyPublishMethods() // if we're a remapped interface, we need to get the methods from the real interface if (remappedType.IsInterface) { - var nestedHelper = type.GetNestedType("__Helper", BindingFlags.Public | BindingFlags.Static); + var nestedHelper = type.GetNestedType("__Helper", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static); foreach (var m in Context.AttributeHelper.GetRemappedInterfaceMethods(type)) { var method = remappedType.GetMethod(m.MappedTo); @@ -104,7 +111,7 @@ protected override void LazyPublishMethods() SetMethods(list.ToArray()); } - private void AddMethod(List list, MethodBase method) + private void AddMethod(List list, IMethodBaseSymbol method) { var flags = Context.AttributeHelper.GetHideFromJavaFlags(method); if ((flags & HideFromJavaFlags.Code) == 0 && (remappedType.IsSealed || !method.Name.StartsWith("instancehelper_")) && (!remappedType.IsSealed || method.IsStatic)) @@ -114,39 +121,38 @@ private void AddMethod(List list, MethodBase method) protected override void LazyPublishFields() { var list = new List(); - var fields = type.GetFields(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance); + var fields = type.GetFields(System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance); foreach (var field in fields) { - HideFromJavaFlags hideFromJavaFlags = Context.AttributeHelper.GetHideFromJavaFlags(field); + var hideFromJavaFlags = Context.AttributeHelper.GetHideFromJavaFlags(field); if ((hideFromJavaFlags & HideFromJavaFlags.Code) == 0) list.Add(CreateFieldWrapper(field, hideFromJavaFlags)); } + SetFields(list.ToArray()); } - RuntimeJavaMethod CreateRemappedMethodWrapper(MethodBase mb, HideFromJavaFlags hideFromJavaflags) + RuntimeJavaMethod CreateRemappedMethodWrapper(IMethodBaseSymbol mb, HideFromJavaFlags hideFromJavaflags) { var modifiers = Context.AttributeHelper.GetModifiers(mb, false); var flags = MemberFlags.None; GetNameSigFromMethodBase(mb, out var name, out var sig, out var retType, out var paramTypes, ref flags); - var mbHelper = mb as MethodInfo; + var mbHelper = mb as IMethodSymbol; var hideFromReflection = mbHelper != null && (hideFromJavaflags & HideFromJavaFlags.Reflection) != 0; - MethodInfo mbNonvirtualHelper = null; + IMethodSymbol mbNonvirtualHelper = null; if (!mb.IsStatic && !mb.IsConstructor) { - ParameterInfo[] parameters = mb.GetParameters(); - Type[] argTypes = new Type[parameters.Length + 1]; + var parameters = mb.GetParameters(); + var argTypes = new ITypeSymbol[parameters.Length + 1]; argTypes[0] = remappedType; for (int i = 0; i < parameters.Length; i++) - { argTypes[i + 1] = parameters[i].ParameterType; - } - MethodInfo helper = type.GetMethod("instancehelper_" + mb.Name, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static, null, argTypes, null); + + var helper = type.GetMethod("instancehelper_" + mb.Name, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static, null, argTypes, null); if (helper != null) - { mbHelper = helper; - } + mbNonvirtualHelper = type.GetMethod("nonvirtualhelper/" + mb.Name, BindingFlags.NonPublic | BindingFlags.Static, null, argTypes, null); } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index 82ee77df55..a0a349676e 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -29,12 +29,20 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.Runtime.Syntax; using IKVM.ByteCode; +using IKVM.CoreLib.Symbols; +using com.sun.org.apache.bcel.@internal.generic; +using System.Linq; + + + #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; +using System.Runtime.Serialization.Formatters; + #else using System.Reflection; using System.Reflection.Emit; @@ -67,22 +75,16 @@ public RuntimeManagedByteCodeJavaTypeFactory(RuntimeContext context) /// /// /// - public RuntimeManagedByteCodeJavaType newInstance(string name, Type type) + public RuntimeManagedByteCodeJavaType newInstance(string name, ITypeSymbol type) { // TODO since ghost and remapped types can only exist in the core library assembly, we probably // should be able to remove the Type.IsDefined() tests in most cases if (type.IsValueType && context.AttributeHelper.IsGhostInterface(type)) - { return new RuntimeManagedByteCodeJavaType.GhostJavaType(context, name, type); - } else if (context.AttributeHelper.IsRemappedType(type)) - { return new RuntimeManagedByteCodeJavaType.RemappedJavaType(context, name, type); - } else - { return new RuntimeManagedByteCodeJavaType(context, name, type); - } } } @@ -93,11 +95,11 @@ public RuntimeManagedByteCodeJavaType newInstance(string name, Type type) internal partial class RuntimeManagedByteCodeJavaType : RuntimeJavaType { - readonly Type type; + readonly ITypeSymbol type; RuntimeJavaType baseTypeWrapper; volatile RuntimeJavaType[] interfaces; - MethodInfo clinitMethod; + IMethodSymbol clinitMethod; volatile bool clinitMethodSet; Modifiers reflectiveModifiers; @@ -107,7 +109,7 @@ internal partial class RuntimeManagedByteCodeJavaType : RuntimeJavaType /// /// /// - internal static JavaTypeName? GetName(RuntimeContext context, Type type) + internal static JavaTypeName? GetName(RuntimeContext context, ITypeSymbol type) { if (type.HasElementType) return null; @@ -132,7 +134,7 @@ internal partial class RuntimeManagedByteCodeJavaType : RuntimeJavaType return TypeNameUtil.Unescape(type.FullName); } - static RuntimeJavaType GetBaseTypeWrapper(RuntimeContext context, Type type) + static RuntimeJavaType GetBaseTypeWrapper(RuntimeContext context, ITypeSymbol type) { if (type.IsInterface || context.AttributeHelper.IsGhostInterface(type)) { @@ -148,7 +150,7 @@ static RuntimeJavaType GetBaseTypeWrapper(RuntimeContext context, Type type) var attr = context.AttributeHelper.GetRemappedType(type); if (attr != null) { - if (attr.Type == context.Types.Object) + if (context.Resolver.ResolveType(attr.Type) == context.Types.Object) return null; else return context.JavaBase.TypeOfJavaLangObject; @@ -188,10 +190,10 @@ public RuntimeManagedByteCodeJavaType(RuntimeContext context, ExModifiers exmod, /// /// /// - public RuntimeManagedByteCodeJavaType(RuntimeContext context, string name, Type type) : + public RuntimeManagedByteCodeJavaType(RuntimeContext context, string name, ITypeSymbol type) : this(context, GetModifiers(context, type), name) { - Debug.Assert(!(type is TypeBuilder)); + Debug.Assert(!(type.AsReflection() is TypeBuilder)); Debug.Assert(!type.Name.EndsWith("[]")); this.type = type; @@ -210,7 +212,7 @@ internal override RuntimeJavaType BaseTypeWrapper internal override RuntimeClassLoader ClassLoader => Context.AssemblyClassLoaderFactory.FromAssembly(type.Assembly); - static ExModifiers GetModifiers(RuntimeContext context, Type type) + static ExModifiers GetModifiers(RuntimeContext context, ITypeSymbol type) { ModifiersAttribute attr = context.AttributeHelper.GetModifiersAttribute(type); if (attr != null) @@ -252,14 +254,22 @@ internal override bool HasStaticInitializer { try { - clinitMethod = type.GetMethod("__", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic); + clinitMethod = type.GetMethod("__", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic); } #if IMPORTER - catch (IKVM.Reflection.MissingMemberException) { } + catch (IKVM.Reflection.MissingMemberException) + { + + } #endif - finally { } + finally + { + + } + clinitMethodSet = true; } + return clinitMethod != null; } } @@ -326,19 +336,19 @@ private RuntimeJavaType[] GetInterfaces() return interfaceWrappers; } - private bool IsNestedTypeAnonymousOrLocalClass(Type type) + private bool IsNestedTypeAnonymousOrLocalClass(ITypeSymbol type) { - switch (type.Attributes & (TypeAttributes.SpecialName | TypeAttributes.VisibilityMask)) + switch (type.Attributes & (System.Reflection.TypeAttributes.SpecialName | System.Reflection.TypeAttributes.VisibilityMask)) { - case TypeAttributes.SpecialName | TypeAttributes.NestedPublic: - case TypeAttributes.SpecialName | TypeAttributes.NestedAssembly: + case System.Reflection.TypeAttributes.SpecialName | System.Reflection.TypeAttributes.NestedPublic: + case System.Reflection.TypeAttributes.SpecialName | System.Reflection.TypeAttributes.NestedAssembly: return Context.AttributeHelper.HasEnclosingMethodAttribute(type); default: return false; } } - private bool IsAnnotationAttribute(Type type) + private bool IsAnnotationAttribute(ITypeSymbol type) { return type.Name.EndsWith("Attribute", StringComparison.Ordinal) && type.IsClass && type.BaseType.FullName == "ikvm.internal.AnnotationAttributeBase"; } @@ -348,7 +358,8 @@ internal override RuntimeJavaType[] InnerClasses get { var wrappers = new List(); - foreach (var nested in type.GetNestedTypes(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.DeclaredOnly)) + + foreach (var nested in type.GetNestedTypes(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.DeclaredOnly)) { if (IsAnnotationAttribute(nested)) { @@ -368,10 +379,9 @@ internal override RuntimeJavaType[] InnerClasses wrappers.Add(Context.ClassLoaderFactory.GetJavaTypeFromType(nested)); } } + foreach (string s in Context.AttributeHelper.GetNonNestedInnerClasses(type)) - { wrappers.Add(ClassLoader.LoadClassByName(s)); - } return wrappers.ToArray(); } @@ -382,19 +392,15 @@ internal override RuntimeJavaType DeclaringTypeWrapper get { if (IsNestedTypeAnonymousOrLocalClass(type)) - { return null; - } - Type declaringType = type.DeclaringType; + + var declaringType = type.DeclaringType; if (declaringType != null) - { return Context.ClassLoaderFactory.GetJavaTypeFromType(declaringType); - } - string decl = Context.AttributeHelper.GetNonNestedOuterClasses(type); + + var decl = Context.AttributeHelper.GetNonNestedOuterClasses(type); if (decl != null) - { return ClassLoader.LoadClassByName(decl); - } return null; } @@ -407,14 +413,12 @@ private static bool IsAnonymousClassName(string name) if (index > 1 && index < name.Length) { while (index < name.Length) - { if ("0123456789".IndexOf(name[index++]) == -1) - { return false; - } - } + return true; } + return false; } @@ -423,14 +427,14 @@ private static bool IsAnonymousClassName(string name) // The heuristics are based on javac from Java 7. internal static Modifiers PredictReflectiveModifiers(RuntimeJavaType tw) { - Modifiers modifiers = Modifiers.Static | (tw.Modifiers & (Modifiers.Public | Modifiers.Abstract | Modifiers.Interface)); + var modifiers = Modifiers.Static | (tw.Modifiers & (Modifiers.Public | Modifiers.Abstract | Modifiers.Interface)); + // javac marks anonymous classes as final, but the InnerClasses attribute access_flags does not have the ACC_FINAL flag set if (tw.IsFinal && !IsAnonymousClassName(tw.Name)) - { modifiers |= Modifiers.Final; - } + // javac uses the this$0 field to store the outer instance reference for non-static inner classes - foreach (RuntimeJavaField fw in tw.GetFields()) + foreach (var fw in tw.GetFields()) { if (fw.Name == "this$0") { @@ -438,6 +442,7 @@ internal static Modifiers PredictReflectiveModifiers(RuntimeJavaType tw) break; } } + return modifiers; } @@ -448,7 +453,8 @@ internal override Modifiers ReflectiveModifiers if (reflectiveModifiers == 0) { Modifiers mods; - InnerClassAttribute attr = Context.AttributeHelper.GetInnerClass(type); + var attr = Context.AttributeHelper.GetInnerClass(type); + if (attr != null) { // the mask comes from RECOGNIZED_INNER_CLASS_MODIFIERS in src/hotspot/share/vm/classfile/classFileParser.cpp @@ -465,17 +471,18 @@ internal override Modifiers ReflectiveModifiers // (minus ACC_SUPER) mods = Modifiers & (Modifiers)0x7611; } + if (IsInterface) - { mods |= Modifiers.Abstract; - } + reflectiveModifiers = mods; } + return reflectiveModifiers; } } - internal override Type TypeAsBaseType + internal override ITypeSymbol TypeAsBaseType { get { @@ -483,7 +490,7 @@ internal override Type TypeAsBaseType } } - private void SigTypePatchUp(string sigtype, ref RuntimeJavaType type) + void SigTypePatchUp(string sigtype, ref RuntimeJavaType type) { if (sigtype != type.SigName) { @@ -497,9 +504,7 @@ private void SigTypePatchUp(string sigtype, ref RuntimeJavaType type) { type = Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(type.TypeAsTBD); if (sigtype != type.SigName) - { throw new InvalidOperationException(); - } } else if (type.IsNonPrimitiveValueType) { @@ -511,12 +516,11 @@ private void SigTypePatchUp(string sigtype, ref RuntimeJavaType type) else { if (sigtype[0] == 'L') - { sigtype = sigtype.Substring(1, sigtype.Length - 2); - } + try { - RuntimeJavaType tw = ClassLoader.TryLoadClassByName(sigtype); + var tw = ClassLoader.TryLoadClassByName(sigtype); if (tw != null && tw.IsRemapped) { type = tw; @@ -525,15 +529,17 @@ private void SigTypePatchUp(string sigtype, ref RuntimeJavaType type) } catch (RetargetableJavaException) { + } + type = new RuntimeUnloadableJavaType(Context, sigtype); } } } - private static void ParseSig(string sig, out string[] sigparam, out string sigret) + static void ParseSig(string sig, out string[] sigparam, out string sigret) { - List list = new List(); + var list = new List(); int pos = 1; for (; ; ) { @@ -576,7 +582,7 @@ private static void ParseSig(string sig, out string[] sigparam, out string sigre } } - private static bool IsCallerID(RuntimeContext context, Type type) + static bool IsCallerID(RuntimeContext context, ITypeSymbol type) { #if EXPORTER return type.FullName == "ikvm.internal.CallerID"; @@ -585,27 +591,19 @@ private static bool IsCallerID(RuntimeContext context, Type type) #endif } - private static bool IsCallerSensitive(MethodBase mb) + static bool IsCallerSensitive(IMethodBaseSymbol mb) { -#if FIRST_PASS - return false; -#elif IMPORTER || EXPORTER - foreach (CustomAttributeData cad in mb.GetCustomAttributesData()) - { + foreach (var cad in mb.GetCustomAttributes()) if (cad.AttributeType.FullName == "sun.reflect.CallerSensitiveAttribute") - { return true; - } - } + return false; -#else - return mb.IsDefined(typeof(global::sun.reflect.CallerSensitiveAttribute), false); -#endif } - private void GetNameSigFromMethodBase(MethodBase method, out string name, out string sig, out RuntimeJavaType retType, out RuntimeJavaType[] paramTypes, ref MemberFlags flags) + void GetNameSigFromMethodBase(IMethodBaseSymbol method, out string name, out string sig, out RuntimeJavaType retType, out RuntimeJavaType[] paramTypes, ref MemberFlags flags) { - retType = method is ConstructorInfo ? Context.PrimitiveJavaTypeFactory.VOID : GetParameterTypeWrapper(Context, ((MethodInfo)method).ReturnParameter); + retType = method is IConstructorSymbol ? Context.PrimitiveJavaTypeFactory.VOID : GetParameterTypeWrapper(Context, ((IMethodSymbol)method).ReturnParameter); + var parameters = method.GetParameters(); int len = parameters.Length; if (len > 0 && IsCallerID(Context, parameters[len - 1].ParameterType) && ClassLoader == Context.ClassLoaderFactory.GetBootstrapClassLoader() && IsCallerSensitive(method)) @@ -613,6 +611,7 @@ private void GetNameSigFromMethodBase(MethodBase method, out string name, out st len--; flags |= MemberFlags.CallerID; } + paramTypes = new RuntimeJavaType[len]; for (int i = 0; i < len; i++) paramTypes[i] = GetParameterTypeWrapper(Context, parameters[i]); @@ -626,6 +625,7 @@ private void GetNameSigFromMethodBase(MethodBase method, out string name, out st // HACK newhelper methods have a return type, but it should be void if (name == "") retType = Context.PrimitiveJavaTypeFactory.VOID; + SigTypePatchUp(sigret, ref retType); // if we have a remapped method, the paramTypes array contains an additional entry for "this" so we have // to remove that @@ -638,7 +638,7 @@ private void GetNameSigFromMethodBase(MethodBase method, out string name, out st } else { - if (method is ConstructorInfo) + if (method.IsConstructor) { name = method.IsStatic ? "" : ""; } @@ -652,9 +652,7 @@ private void GetNameSigFromMethodBase(MethodBase method, out string name, out st } if (method.IsSpecialName && method.Name.StartsWith(NamePrefix.DefaultMethod, StringComparison.Ordinal)) - { paramTypes = ArrayUtil.DropFirst(paramTypes); - } var sb = new System.Text.StringBuilder("("); foreach (RuntimeJavaType tw in paramTypes) @@ -667,7 +665,7 @@ private void GetNameSigFromMethodBase(MethodBase method, out string name, out st protected override void LazyPublishMethods() { - const BindingFlags flags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; + const System.Reflection.BindingFlags flags = System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance; var isDelegate = type.BaseType == Context.Types.MulticastDelegate; var methods = new List(); @@ -685,7 +683,7 @@ protected override void LazyPublishMethods() if (type.IsInterface && (type.IsPublic || type.IsNestedPublic)) { - var privateInterfaceMethods = type.GetNestedType(NestedTypeName.PrivateInterfaceMethods, BindingFlags.NonPublic); + var privateInterfaceMethods = type.GetNestedType(NestedTypeName.PrivateInterfaceMethods, System.Reflection.BindingFlags.NonPublic); if (privateInterfaceMethods != null) AddMethods(privateInterfaceMethods.GetMethods(flags), methods); } @@ -693,20 +691,18 @@ protected override void LazyPublishMethods() SetMethods(methods.ToArray()); } - private void AddMethods(MethodInfo[] add, List methods) + private void AddMethods(IMethodSymbol[] add, List methods) { foreach (var method in add) AddMethodOrConstructor(method, Context.AttributeHelper.GetHideFromJavaFlags(method), methods); } - private void AddMethodOrConstructor(MethodBase method, HideFromJavaFlags hideFromJavaFlags, List methods) + private void AddMethodOrConstructor(IMethodBaseSymbol method, HideFromJavaFlags hideFromJavaFlags, List methods) { if ((hideFromJavaFlags & HideFromJavaFlags.Code) != 0) { if (method.Name.StartsWith(NamePrefix.Incomplete, StringComparison.Ordinal)) - { SetHasIncompleteInterfaceImplementation(); - } } else { @@ -716,35 +712,36 @@ private void AddMethodOrConstructor(MethodBase method, HideFromJavaFlags hideFro } else { - var mi = method as MethodInfo; + var mi = method as IMethodSymbol; var hideFromReflection = mi != null && (hideFromJavaFlags & HideFromJavaFlags.Reflection) != 0; var flags = hideFromReflection ? MemberFlags.HideFromReflection : MemberFlags.None; GetNameSigFromMethodBase(method, out var name, out var sig, out var retType, out var paramTypes, ref flags); + var mods = Context.AttributeHelper.GetModifiers(method, false); if (mods.IsInternal) - { flags |= MemberFlags.InternalAccess; - } + if (hideFromReflection && name.StartsWith(NamePrefix.AccessStub, StringComparison.Ordinal)) { - int id = Int32.Parse(name.Substring(NamePrefix.AccessStub.Length, name.IndexOf('|', NamePrefix.AccessStub.Length) - NamePrefix.AccessStub.Length)); + var id = int.Parse(name.Substring(NamePrefix.AccessStub.Length, name.IndexOf('|', NamePrefix.AccessStub.Length) - NamePrefix.AccessStub.Length)); name = name.Substring(name.IndexOf('|', NamePrefix.AccessStub.Length) + 1); flags |= MemberFlags.AccessStub; - MethodInfo nonvirt = type.GetMethod(NamePrefix.NonVirtual + id, BindingFlags.NonPublic | BindingFlags.DeclaredOnly | BindingFlags.Instance); + + var nonvirt = type.GetMethod(NamePrefix.NonVirtual + id, System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Instance); methods.Add(new RuntimeAccessStubJavaMethod(this, name, sig, mi, mi, nonvirt ?? mi, retType, paramTypes, mods.Modifiers & ~Modifiers.Final, flags)); return; } - MethodInfo impl; + IMethodSymbol impl; RuntimeJavaMethod mw; if (IsGhost && (mods.Modifiers & (Modifiers.Static | Modifiers.Private)) == 0) { - var types = new Type[paramTypes.Length]; + var types = new ITypeSymbol[paramTypes.Length]; for (int i = 0; i < types.Length; i++) types[i] = paramTypes[i].TypeAsSignatureType; var ifmethod = TypeAsBaseType.GetMethod(method.Name, types); - mw = new RuntimeGhostJavaMethod(this, name, sig, ifmethod, (MethodInfo)method, retType, paramTypes, mods.Modifiers, flags); + mw = new RuntimeGhostJavaMethod(this, name, sig, ifmethod, (IMethodSymbol)method, retType, paramTypes, mods.Modifiers, flags); if (!mw.IsAbstract) ((RuntimeGhostJavaMethod)mw).SetDefaultImpl(TypeAsSignatureType.GetMethod(NamePrefix.DefaultMethod + method.Name, types)); } @@ -760,58 +757,57 @@ private void AddMethodOrConstructor(MethodBase method, HideFromJavaFlags hideFro { mw = new RuntimeTypicalJavaMethod(this, name, sig, method, retType, paramTypes, mods.Modifiers, flags); } + if (mw.HasNonPublicTypeInSignature) { if (mi != null) { - MethodInfo stubVirt; - MethodInfo stubNonVirt; - if (GetType2AccessStubs(name, sig, out stubVirt, out stubNonVirt)) + if (GetType2AccessStubs(name, sig, out var stubVirt, out var stubNonVirt)) { mw = new RuntimeAccessStubJavaMethod(this, name, sig, mi, stubVirt, stubNonVirt ?? stubVirt, retType, paramTypes, mw.Modifiers, flags); } } else { - ConstructorInfo stub; - if (GetType2AccessStub(sig, out stub)) + if (GetType2AccessStub(sig, out var stub)) { - mw = new RuntimeConstructorAccessStubJavaMethod(this, sig, (ConstructorInfo)method, stub, paramTypes, mw.Modifiers, flags); + mw = new RuntimeConstructorAccessStubJavaMethod(this, sig, (IConstructorSymbol)method, stub, paramTypes, mw.Modifiers, flags); } } } + methods.Add(mw); } } } - MethodInfo GetDefaultInterfaceMethodImpl(MethodInfo method, string expectedSig) + IMethodSymbol GetDefaultInterfaceMethodImpl(IMethodSymbol method, string expectedSig) { - foreach (MethodInfo candidate in method.DeclaringType.GetMethods(BindingFlags.Public | BindingFlags.Static | BindingFlags.DeclaredOnly)) + foreach (var candidate in method.DeclaringType.GetMethods(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.DeclaredOnly)) { - if (candidate.IsSpecialName - && candidate.Name.StartsWith(NamePrefix.DefaultMethod, StringComparison.Ordinal) - && candidate.Name.Length == method.Name.Length + NamePrefix.DefaultMethod.Length - && candidate.Name.EndsWith(method.Name, StringComparison.Ordinal)) + if (candidate.IsSpecialName && + candidate.Name.StartsWith(NamePrefix.DefaultMethod, StringComparison.Ordinal) && + candidate.Name.Length == method.Name.Length + NamePrefix.DefaultMethod.Length && + candidate.Name.EndsWith(method.Name, StringComparison.Ordinal)) { - string name; - string sig; - RuntimeJavaType retType; - RuntimeJavaType[] paramTypes; - MemberFlags flags = MemberFlags.None; - GetNameSigFromMethodBase(candidate, out name, out sig, out retType, out paramTypes, ref flags); + var flags = MemberFlags.None; + GetNameSigFromMethodBase(candidate, out _, out var sig, out _, out _, ref flags); if (sig == expectedSig) - { return candidate; - } } } + return null; } - bool GetType2AccessStubs(string name, string sig, out MethodInfo stubVirt, out MethodInfo stubNonVirt) + bool GetType2AccessStubs(string name, string sig, out IMethodSymbol stubVirt, out IMethodSymbol stubNonVirt) { - const BindingFlags flags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; + const System.Reflection.BindingFlags flags = + System.Reflection.BindingFlags.DeclaredOnly | + System.Reflection.BindingFlags.Public | + System.Reflection.BindingFlags.NonPublic | + System.Reflection.BindingFlags.Static | + System.Reflection.BindingFlags.Instance; stubVirt = null; stubNonVirt = null; @@ -823,13 +819,9 @@ bool GetType2AccessStubs(string name, string sig, out MethodInfo stubVirt, out M if (attr != null && attr.Name == name && attr.Sig == sig) { if (method.Name.StartsWith(NamePrefix.NonVirtual, StringComparison.Ordinal)) - { stubNonVirt = method; - } else - { stubVirt = method; - } } } } @@ -837,9 +829,13 @@ bool GetType2AccessStubs(string name, string sig, out MethodInfo stubVirt, out M return stubVirt != null; } - bool GetType2AccessStub(string sig, out ConstructorInfo stub) + bool GetType2AccessStub(string sig, out IConstructorSymbol stub) { - const BindingFlags flags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance; + const System.Reflection.BindingFlags flags = + System.Reflection.BindingFlags.DeclaredOnly | + System.Reflection.BindingFlags.Public | + System.Reflection.BindingFlags.NonPublic | + System.Reflection.BindingFlags.Instance; stub = null; foreach (var ctor in type.GetConstructors(flags)) @@ -848,23 +844,26 @@ bool GetType2AccessStub(string sig, out ConstructorInfo stub) { var attr = Context.AttributeHelper.GetNameSig(ctor); if (attr != null && attr.Sig == sig) - { stub = ctor; - } } } return stub != null; } - static int SortFieldByToken(FieldInfo field1, FieldInfo field2) + static int SortFieldByToken(IFieldSymbol field1, IFieldSymbol field2) { return field1.MetadataToken.CompareTo(field2.MetadataToken); } protected override void LazyPublishFields() { - const BindingFlags flags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; + const System.Reflection.BindingFlags flags = + System.Reflection.BindingFlags.DeclaredOnly | + System.Reflection.BindingFlags.Public | + System.Reflection.BindingFlags.NonPublic | + System.Reflection.BindingFlags.Static | + System.Reflection.BindingFlags.Instance; var fields = new List(); var rawfields = type.GetFields(flags); @@ -918,7 +917,7 @@ static bool MatchTypes(RuntimeJavaType tw1, RuntimeJavaType tw2) return tw1 == tw2 || (tw1.IsUnloadable && tw2.IsUnloadable && tw1.Name == tw2.Name); } - void AddPropertyFieldWrapper(List fields, PropertyInfo property, FieldInfo field) + void AddPropertyFieldWrapper(List fields, IPropertySymbol property, IFieldSymbol field) { // NOTE explictly defined properties (in map.xml) are decorated with HideFromJava, // so we don't need to worry about them here @@ -940,13 +939,13 @@ void AddPropertyFieldWrapper(List fields, PropertyInfo propert } } - static RuntimeJavaType TypeWrapperFromModOpt(RuntimeContext context, Type[] modopt) + static RuntimeJavaType TypeWrapperFromModOpt(RuntimeContext context, ITypeSymbol[] modopt) { int rank = 0; RuntimeJavaType tw = null; foreach (var type in modopt) { - if (type == context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName).AsReflection()) + if (type == context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName)) { // ignore } @@ -974,17 +973,17 @@ static RuntimeJavaType TypeWrapperFromModOpt(RuntimeContext context, Type[] modo return tw; } - RuntimeJavaType GetPropertyTypeWrapper(PropertyInfo property) + RuntimeJavaType GetPropertyTypeWrapper(IPropertySymbol property) { return TypeWrapperFromModOpt(Context, property.GetOptionalCustomModifiers()) ?? Context.ClassLoaderFactory.GetJavaTypeFromType(property.PropertyType); } - internal static RuntimeJavaType GetFieldTypeWrapper(RuntimeContext context, FieldInfo field) + internal static RuntimeJavaType GetFieldTypeWrapper(RuntimeContext context, IFieldSymbol field) { return TypeWrapperFromModOpt(context, field.GetOptionalCustomModifiers()) ?? context.ClassLoaderFactory.GetJavaTypeFromType(field.FieldType); } - internal static RuntimeJavaType GetParameterTypeWrapper(RuntimeContext context, ParameterInfo param) + internal static RuntimeJavaType GetParameterTypeWrapper(RuntimeContext context, IParameterSymbol param) { var tw = TypeWrapperFromModOpt(context, param.GetOptionalCustomModifiers()); if (tw != null) @@ -1000,7 +999,7 @@ internal static RuntimeJavaType GetParameterTypeWrapper(RuntimeContext context, return context.ClassLoaderFactory.GetJavaTypeFromType(parameterType); } - RuntimeJavaField CreateFieldWrapper(FieldInfo field, HideFromJavaFlags hideFromJavaFlags) + RuntimeJavaField CreateFieldWrapper(IFieldSymbol field, HideFromJavaFlags hideFromJavaFlags) { var modifiers = Context.AttributeHelper.GetModifiers(field, false); var type = GetFieldTypeWrapper(Context, field); @@ -1012,14 +1011,13 @@ RuntimeJavaField CreateFieldWrapper(FieldInfo field, HideFromJavaFlags hideFromJ if (field.IsLiteral) { var flags = MemberFlags.None; + if ((hideFromJavaFlags & HideFromJavaFlags.Reflection) != 0) - { flags |= MemberFlags.HideFromReflection; - } + if (modifiers.IsInternal) - { flags |= MemberFlags.InternalAccess; - } + return new RuntimeConstantJavaField(this, type, name, type.SigName, modifiers.Modifiers, field, null, flags); } else @@ -1028,7 +1026,7 @@ RuntimeJavaField CreateFieldWrapper(FieldInfo field, HideFromJavaFlags hideFromJ } } - internal override Type TypeAsTBD => type; + internal override ITypeSymbol TypeAsTBD => type; internal override bool IsMapUnsafeException => Context.AttributeHelper.IsExceptionIsUnsafeForMapping(type); @@ -1121,9 +1119,18 @@ internal override string[] GetEnclosingMethod() return null; } + object[] CastArray(CustomAttribute[] l) + { + var a = new object[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = l[i]; + + return a; + } + internal override object[] GetDeclaredAnnotations() { - return type.GetCustomAttributes(false); + return CastArray(type.GetCustomAttribute(false)); } internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) @@ -1135,7 +1142,7 @@ internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) return null; } - return mb.GetCustomAttributes(false); + return CastArray(mb.GetCustomAttributes(false)); } internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) @@ -1158,7 +1165,7 @@ internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) var attribs = new object[parameters.Length - skip - skipEnd][]; for (int i = skip; i < parameters.Length - skipEnd; i++) - attribs[i - skip] = parameters[i].GetCustomAttributes(false); + attribs[i - skip] = CastArray(parameters[i].GetCustomAttributes(false)); return attribs; } @@ -1167,10 +1174,10 @@ internal override object[] GetFieldAnnotations(RuntimeJavaField fw) { var field = fw.GetField(); if (field != null) - return field.GetCustomAttributes(false); + return CastArray(field.GetCustomAttributes(false)); if (fw is RuntimeManagedByteCodePropertyJavaField prop) - return prop.GetProperty().GetCustomAttributes(false); + return CastArray(prop.GetProperty().GetCustomAttributes(false)); return Array.Empty(); } @@ -1181,17 +1188,17 @@ internal sealed class CompiledAnnotation : Annotation { readonly RuntimeContext context; - readonly ConstructorInfo constructor; + readonly IConstructorSymbol constructor; /// /// Initializes a new instance. /// /// /// - internal CompiledAnnotation(RuntimeContext context, Type type) + internal CompiledAnnotation(RuntimeContext context, ITypeSymbol type) { this.context = context ?? throw new ArgumentNullException(nameof(context)); - constructor = type.GetConstructor(new Type[] { context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType().AsReflection() }); + constructor = type.GetConstructor(new ITypeSymbol[] { context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType() }); } private CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) @@ -1247,11 +1254,11 @@ internal override Annotation Annotation } } - internal override Type EnumType + internal override ITypeSymbol EnumType { get { - if ((this.Modifiers & Modifiers.Enum) != 0) + if ((Modifiers & Modifiers.Enum) != 0) return type.GetNestedType("__Enum"); return null; @@ -1262,9 +1269,9 @@ internal override Type EnumType internal override string GetSourceFileName() { - var attr = type.GetCustomAttributes(typeof(SourceFileAttribute), false); - if (attr.Length == 1) - return ((SourceFileAttribute)attr[0]).SourceFile; + var attr = type.GetCustomAttribute(Context.Resolver.ResolveType(typeof(SourceFileAttribute))); + if (attr != null && attr.Value.ConstructorArguments.Length > 0) + return (string)attr.Value.ConstructorArguments[0].Value; if (DeclaringTypeWrapper != null) return DeclaringTypeWrapper.GetSourceFileName(); @@ -1272,7 +1279,7 @@ internal override string GetSourceFileName() if (IsNestedTypeAnonymousOrLocalClass(type)) return Context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).GetSourceFileName(); - if (type.Module.IsDefined(typeof(SourceFileAttribute), false)) + if (type.Module.IsDefined(Context.Resolver.ResolveType(typeof(SourceFileAttribute)), false)) return type.Name + ".java"; return null; @@ -1280,9 +1287,9 @@ internal override string GetSourceFileName() internal override int GetSourceLineNumber(MethodBase mb, int ilOffset) { - var attr = mb.GetCustomAttributes(typeof(LineNumberTableAttribute), false); - if (attr.Length == 1) - return ((LineNumberTableAttribute)attr[0]).GetLineNumber(ilOffset); + var attr = type.GetCustomAttribute(Context.Resolver.ResolveType(typeof(LineNumberTableAttribute))); + if (attr != null && attr.Value.Constructor != null) + return ((LineNumberTableAttribute)attr.Value.Constructor.AsReflection().Invoke(attr.Value.ConstructorArguments.Cast().ToArray())).GetLineNumber(ilOffset); return -1; } @@ -1305,13 +1312,13 @@ internal override byte[] GetRawTypeAnnotations() internal override byte[] GetMethodRawTypeAnnotations(RuntimeJavaMethod mw) { - MethodBase mb = mw.GetMethod(); + var mb = mw.GetMethod(); return mb == null ? null : Context.AttributeHelper.GetRuntimeVisibleTypeAnnotations(mb); } internal override byte[] GetFieldRawTypeAnnotations(RuntimeJavaField fw) { - FieldInfo fi = fw.GetField(); + var fi = fw.GetField(); return fi == null ? null : Context.AttributeHelper.GetRuntimeVisibleTypeAnnotations(fi); } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs b/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs index 80611d28c9..87f276f303 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs @@ -21,6 +21,7 @@ Jeroen Frijters jeroen@frijters.net */ +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -41,7 +42,7 @@ namespace IKVM.Runtime sealed class RuntimeManagedByteCodePropertyJavaField : RuntimeJavaField { - readonly PropertyInfo property; + readonly IPropertySymbol property; /// /// Initializes a new instance. @@ -49,13 +50,13 @@ sealed class RuntimeManagedByteCodePropertyJavaField : RuntimeJavaField /// /// /// - internal RuntimeManagedByteCodePropertyJavaField(RuntimeJavaType declaringType, PropertyInfo property, ExModifiers modifiers) : + internal RuntimeManagedByteCodePropertyJavaField(RuntimeJavaType declaringType, IPropertySymbol property, ExModifiers modifiers) : base(declaringType, declaringType.Context.ClassLoaderFactory.GetJavaTypeFromType(property.PropertyType), property.Name, declaringType.Context.ClassLoaderFactory.GetJavaTypeFromType(property.PropertyType).SigName, modifiers, null) { this.property = property; } - internal PropertyInfo GetProperty() + internal IPropertySymbol GetProperty() { return property; } @@ -111,7 +112,7 @@ internal override object GetValue(object obj) if (getter == null) throw new java.lang.NoSuchMethodError(); - return getter.Invoke(obj, new object[0]); + return getter.AsReflection().Invoke(obj, []); } internal override void SetValue(object obj, object value) @@ -120,7 +121,7 @@ internal override void SetValue(object obj, object value) if (setter == null) throw new java.lang.NoSuchMethodError(); - setter.Invoke(obj, new object[] { value }); + setter.AsReflection().Invoke(obj, new object[] { value }); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs index 347bde315d..b96ed3f2d5 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs @@ -104,7 +104,7 @@ static object[] UnwrapArray(object annotation) } } - return new object[0]; + return []; } internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs index 9bd4613d3c..a4867ea4da 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs @@ -25,6 +25,8 @@ Jeroen Frijters using System.Collections.Generic; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -54,8 +56,8 @@ sealed partial class RuntimeManagedJavaType sealed partial class AttributeAnnotationJavaType : AttributeAnnotationJavaTypeBase { - readonly Type fakeType; - readonly Type attributeType; + readonly ITypeSymbol fakeType; + readonly ITypeSymbol attributeType; volatile RuntimeJavaType[] innerClasses; /// @@ -63,21 +65,21 @@ sealed partial class AttributeAnnotationJavaType : AttributeAnnotationJavaTypeBa /// /// /// - internal AttributeAnnotationJavaType(RuntimeContext context, string name, Type attributeType) : + internal AttributeAnnotationJavaType(RuntimeContext context, string name, ITypeSymbol attributeType) : base(context, name) { #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetAttributeType(attributeType); #elif !FIRST_PASS - this.fakeType = typeof(ikvm.@internal.AttributeAnnotation<>).MakeGenericType(attributeType); + this.fakeType = context.Resolver.ResolveType(typeof(ikvm.@internal.AttributeAnnotation<>)).MakeGenericType(attributeType); #endif this.attributeType = attributeType; } - static bool IsSupportedType(RuntimeContext context, Type type) + static bool IsSupportedType(RuntimeContext context, ITypeSymbol type) { // Java annotations only support one-dimensional arrays - if (ReflectUtil.IsVector(type)) + if (type.IsSZArray) type = type.GetElementType(); return type == context.Types.String @@ -93,27 +95,27 @@ static bool IsSupportedType(RuntimeContext context, Type type) || type.IsEnum; } - internal static void GetConstructors(RuntimeContext context, Type type, out ConstructorInfo defCtor, out ConstructorInfo singleOneArgCtor) + internal static void GetConstructors(RuntimeContext context, ITypeSymbol type, out IConstructorSymbol defCtor, out IConstructorSymbol singleOneArgCtor) { defCtor = null; int oneArgCtorCount = 0; - ConstructorInfo oneArgCtor = null; - ConstructorInfo[] constructors = type.GetConstructors(BindingFlags.Public | BindingFlags.Instance); + IConstructorSymbol oneArgCtor = null; + var constructors = type.GetConstructors(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance); // HACK we have a special rule to make some additional custom attributes from mscorlib usable: // Attributes that have two constructors, one an enum and another one taking a byte, short or int, // we only expose the enum constructor. if (constructors.Length == 2 && type.Assembly == context.Types.Object.Assembly) { - ParameterInfo[] p0 = constructors[0].GetParameters(); - ParameterInfo[] p1 = constructors[1].GetParameters(); + var p0 = constructors[0].GetParameters(); + var p1 = constructors[1].GetParameters(); if (p0.Length == 1 && p1.Length == 1) { - Type t0 = p0[0].ParameterType; - Type t1 = p1[0].ParameterType; + var t0 = p0[0].ParameterType; + var t1 = p1[0].ParameterType; bool swapped = false; if (t1.IsEnum) { - Type tmp = t0; + var tmp = t0; t0 = t1; t1 = tmp; swapped = true; @@ -137,9 +139,9 @@ internal static void GetConstructors(RuntimeContext context, Type type, out Cons { if (type.FullName == "System.Runtime.CompilerServices.MethodImplAttribute") { - foreach (ConstructorInfo ci in constructors) + foreach (var ci in constructors) { - ParameterInfo[] p = ci.GetParameters(); + var p = ci.GetParameters(); if (p.Length == 1 && p[0].ParameterType.IsEnum) { singleOneArgCtor = ci; @@ -149,9 +151,9 @@ internal static void GetConstructors(RuntimeContext context, Type type, out Cons } } - foreach (ConstructorInfo ci in constructors) + foreach (var ci in constructors) { - ParameterInfo[] args = ci.GetParameters(); + var args = ci.GetParameters(); if (args.Length == 0) { defCtor = ci; @@ -185,13 +187,13 @@ sealed class AttributeAnnotationJavaMethod : DynamicOnlyJavaMethod /// /// /// - internal AttributeAnnotationJavaMethod(AttributeAnnotationJavaType tw, string name, Type type, bool optional) : + internal AttributeAnnotationJavaMethod(AttributeAnnotationJavaType tw, string name, ITypeSymbol type, bool optional) : this(tw, name, MapType(tw.Context, type, false), optional) { } - static RuntimeJavaType MapType(RuntimeContext context, Type type, bool isArray) + static RuntimeJavaType MapType(RuntimeContext context, ITypeSymbol type, bool isArray) { if (type == context.Types.String) { @@ -235,20 +237,20 @@ static RuntimeJavaType MapType(RuntimeContext context, Type type, bool isArray) } else if (type.IsEnum) { - foreach (RuntimeJavaType tw in context.ClassLoaderFactory.GetJavaTypeFromType(type).InnerClasses) + foreach (var tw in context.ClassLoaderFactory.GetJavaTypeFromType(type).InnerClasses) { if (tw is EnumEnumJavaType) { - if (!isArray && type.IsDefined(context.Resolver.ResolveCoreType(typeof(FlagsAttribute).FullName).AsReflection(), false)) - { + if (!isArray && type.IsDefined(context.Resolver.ResolveCoreType(typeof(FlagsAttribute).FullName), false)) return tw.MakeArrayType(1); - } + return tw; } } + throw new InvalidOperationException(); } - else if (!isArray && ReflectUtil.IsVector(type)) + else if (isArray == false && type.IsSZArray) { return MapType(context, type.GetElementType(), true).MakeArrayType(1); } @@ -285,7 +287,7 @@ protected override void LazyPublishMembers() if (singleOneArgCtor != null) methods.Add(new AttributeAnnotationJavaMethod(this, "value", singleOneArgCtor.GetParameters()[0].ParameterType, defCtor != null)); - foreach (var pi in attributeType.GetProperties(BindingFlags.Instance | BindingFlags.Public)) + foreach (var pi in attributeType.GetProperties(System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public)) { // the getter and setter methods both need to be public // the getter signature must be: Getter() @@ -293,12 +295,12 @@ protected override void LazyPublishMembers() // the property type needs to be a supported type var getter = pi.GetGetMethod(); var setter = pi.GetSetMethod(); - ParameterInfo[] parameters; + IParameterSymbol[] parameters; if (getter != null && getter.GetParameters().Length == 0 && getter.ReturnType == pi.PropertyType && setter != null && (parameters = setter.GetParameters()).Length == 1 && parameters[0].ParameterType == pi.PropertyType && setter.ReturnType == Context.Types.Void && IsSupportedType(Context, pi.PropertyType)) AddMethodIfUnique(methods, new AttributeAnnotationJavaMethod(this, pi.Name, pi.PropertyType, true)); } - foreach (var fi in attributeType.GetFields(BindingFlags.Public | BindingFlags.Instance)) + foreach (var fi in attributeType.GetFields(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance)) if (!fi.IsInitOnly && IsSupportedType(Context, fi.FieldType)) AddMethodIfUnique(methods, new AttributeAnnotationJavaMethod(this, fi.Name, fi.FieldType, true)); @@ -374,7 +376,7 @@ internal override object GetAnnotationDefault(RuntimeJavaMethod mw) } else if (mw.ReturnType.IsArray) { - return Array.CreateInstance(mw.ReturnType.TypeAsArrayType, 0); + return Array.CreateInstance(mw.ReturnType.TypeAsArrayType.AsReflection(), 0); } } @@ -385,7 +387,7 @@ internal override object GetAnnotationDefault(RuntimeJavaMethod mw) internal override RuntimeJavaType DeclaringTypeWrapper => Context.ClassLoaderFactory.GetJavaTypeFromType(attributeType); - internal override Type TypeAsTBD => fakeType; + internal override ITypeSymbol TypeAsTBD => fakeType; internal override RuntimeJavaType[] InnerClasses => innerClasses ??= GetInnerClasses(); @@ -411,39 +413,39 @@ AttributeUsageAttribute GetAttributeUsage() AttributeTargets validOn = AttributeTargets.All; bool allowMultiple = false; bool inherited = true; - foreach (CustomAttributeData cad in CustomAttributeData.GetCustomAttributes(attributeType)) + foreach (var cad in attributeType.GetCustomAttributes()) { - if (cad.Constructor.DeclaringType == Context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName).AsReflection()) + if (cad.Constructor.DeclaringType == Context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName)) { - if (cad.ConstructorArguments.Count == 1 && cad.ConstructorArguments[0].ArgumentType == Context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName).AsReflection()) + if (cad.ConstructorArguments.Length == 1 && cad.ConstructorArguments[0].ArgumentType == Context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName)) { validOn = (AttributeTargets)cad.ConstructorArguments[0].Value; } - foreach (CustomAttributeNamedArgument cana in cad.NamedArguments) + + foreach (var cana in cad.NamedArguments) { if (cana.MemberInfo.Name == "AllowMultiple") - { allowMultiple = (bool)cana.TypedValue.Value; - } else if (cana.MemberInfo.Name == "Inherited") - { inherited = (bool)cana.TypedValue.Value; - } } } } - AttributeUsageAttribute attr = new AttributeUsageAttribute(validOn); + + var attr = new AttributeUsageAttribute(validOn); attr.AllowMultiple = allowMultiple; attr.Inherited = inherited; return attr; } #if !IMPORTER && !FIRST_PASS && !EXPORTER + internal override object[] GetDeclaredAnnotations() { // note that AttributeUsageAttribute.Inherited does not map to java.lang.annotation.Inherited - AttributeTargets validOn = GetAttributeUsage().ValidOn; - List targets = new List(); + var validOn = GetAttributeUsage().ValidOn; + var targets = new List(); + if ((validOn & (AttributeTargets.Class | AttributeTargets.Interface | AttributeTargets.Struct | AttributeTargets.Enum | AttributeTargets.Delegate | AttributeTargets.Assembly)) != 0) { targets.Add(java.lang.annotation.ElementType.TYPE); @@ -468,23 +470,23 @@ internal override object[] GetDeclaredAnnotations() targetMap.put("value", targets.ToArray()); java.util.HashMap retentionMap = new java.util.HashMap(); retentionMap.put("value", java.lang.annotation.RetentionPolicy.RUNTIME); - return new object[] { - java.lang.reflect.Proxy.newProxyInstance(null, new java.lang.Class[] { typeof(java.lang.annotation.Target) }, new sun.reflect.annotation.AnnotationInvocationHandler(typeof(java.lang.annotation.Target), targetMap)), - java.lang.reflect.Proxy.newProxyInstance(null, new java.lang.Class[] { typeof(java.lang.annotation.Retention) }, new sun.reflect.annotation.AnnotationInvocationHandler(typeof(java.lang.annotation.Retention), retentionMap)) - }; + return [ + java.lang.reflect.Proxy.newProxyInstance(null, [typeof(java.lang.annotation.Target)], new sun.reflect.annotation.AnnotationInvocationHandler(typeof(java.lang.annotation.Target), targetMap)), + java.lang.reflect.Proxy.newProxyInstance(null, [typeof(java.lang.annotation.Retention)], new sun.reflect.annotation.AnnotationInvocationHandler(typeof(java.lang.annotation.Retention), retentionMap)) + ]; } #endif sealed class AttributeAnnotation : Annotation { - readonly Type type; + readonly ITypeSymbol type; /// /// Initializes a new instance. /// /// - internal AttributeAnnotation(Type type) + internal AttributeAnnotation(ITypeSymbol type) { this.type = type; } @@ -492,14 +494,14 @@ internal AttributeAnnotation(Type type) CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { object[] arr = (object[])annotation; - ConstructorInfo defCtor; - ConstructorInfo singleOneArgCtor; object ctorArg = null; - GetConstructors(loader.Context, type, out defCtor, out singleOneArgCtor); - List properties = new List(); - List propertyValues = new List(); - List fields = new List(); - List fieldValues = new List(); + + GetConstructors(loader.Context, type, out var defCtor, out var singleOneArgCtor); + var properties = new List(); + var propertyValues = new List(); + var fields = new List(); + var fieldValues = new List(); + for (int i = 2; i < arr.Length; i += 2) { string name = (string)arr[i]; @@ -509,7 +511,7 @@ CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, obj } else { - PropertyInfo pi = type.GetProperty(name, BindingFlags.Public | BindingFlags.Instance); + var pi = type.GetProperty(name, System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance); if (pi != null) { properties.Add(pi); @@ -517,7 +519,7 @@ CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, obj } else { - FieldInfo fi = type.GetField(name, BindingFlags.Public | BindingFlags.Instance); + var fi = type.GetField(name, System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance); if (fi != null) { fields.Add(fi); @@ -526,21 +528,24 @@ CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, obj } } } + if (ctorArg == null && defCtor == null) { // TODO required argument is missing } - return new CustomAttributeBuilder(ctorArg == null ? defCtor : singleOneArgCtor, - ctorArg == null ? new object[0] : new object[] { ctorArg }, - properties.ToArray(), + + return new CustomAttributeBuilder( + ctorArg == null ? defCtor.AsReflection() : singleOneArgCtor.AsReflection(), + ctorArg == null ? [] : new object[] { ctorArg }, + properties.ToArray().AsReflection(), propertyValues.ToArray(), - fields.ToArray(), + fields.ToArray().AsReflection(), fieldValues.ToArray()); } internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) { - if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.StructLayoutAttribute).FullName).AsReflection() && tb.BaseType != loader.Context.Types.Object) + if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.StructLayoutAttribute).FullName) && loader.Context.Resolver.ResolveType(tb.BaseType) != loader.Context.Types.Object) { // we have to handle this explicitly, because if we apply an illegal StructLayoutAttribute, // TypeBuilder.CreateType() will later on throw an exception. @@ -569,7 +574,7 @@ internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, obj { // TODO with the current custom attribute annotation restrictions it is impossible to use this CA, // but if we make it possible, we should also implement it here - if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.DefaultParameterValueAttribute).FullName).AsReflection()) + if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.DefaultParameterValueAttribute).FullName)) throw new NotImplementedException(); else pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); @@ -578,11 +583,11 @@ internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, obj internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) { #if IMPORTER - if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.CompilerServices.TypeForwardedToAttribute).FullName).AsReflection()) + if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.CompilerServices.TypeForwardedToAttribute).FullName)) { ab.__AddTypeForwarder((Type)ConvertValue(loader, loader.Context.Types.Type, ((object[])annotation)[3])); } - else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyVersionAttribute).FullName).AsReflection()) + else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyVersionAttribute).FullName)) { string str = (string)ConvertValue(loader, loader.Context.Types.String, ((object[])annotation)[3]); Version version; @@ -595,7 +600,7 @@ internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, obje loader.Diagnostics.InvalidCustomAttribute(type.FullName, "The version '" + str + "' is invalid."); } } - else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyCultureAttribute).FullName).AsReflection()) + else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyCultureAttribute).FullName)) { string str = (string)ConvertValue(loader, loader.Context.Types.String, ((object[])annotation)[3]); if (str != "") @@ -603,18 +608,19 @@ internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, obje ab.__SetAssemblyCulture(str); } } - else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyDelaySignAttribute).FullName).AsReflection() - || type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyKeyFileAttribute).FullName).AsReflection() - || type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyKeyNameAttribute).FullName).AsReflection()) + else if ( + type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyDelaySignAttribute).FullName) || + type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyKeyFileAttribute).FullName) || + type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyKeyNameAttribute).FullName)) { loader.Diagnostics.IgnoredCustomAttribute(type.FullName, "Please use the corresponding compiler switch."); } - else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyAlgorithmIdAttribute).FullName).AsReflection()) + else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyAlgorithmIdAttribute).FullName)) { // this attribute is currently not exposed as an annotation and isn't very interesting throw new NotImplementedException(); } - else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyFlagsAttribute).FullName).AsReflection()) + else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyFlagsAttribute).FullName)) { // this attribute is currently not exposed as an annotation and isn't very interesting throw new NotImplementedException(); @@ -624,7 +630,7 @@ internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, obje ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } #else - ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); + ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); #endif } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs index bc808390ff..ee8ee78f2c 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs @@ -21,9 +21,8 @@ Jeroen Frijters jeroen@frijters.net */ -using System; - using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -31,7 +30,6 @@ Jeroen Frijters using Type = IKVM.Reflection.Type; #else -using System.Reflection; using System.Reflection.Emit; #endif @@ -47,7 +45,7 @@ sealed class ByRefJavaMethod : RuntimeSmartJavaMethod #if !IMPORTER readonly bool[] byrefs; #endif - readonly Type[] args; + readonly ITypeSymbol[] args; /// /// Initializes a new instance. @@ -62,7 +60,7 @@ sealed class ByRefJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal ByRefJavaMethod(Type[] args, bool[] byrefs, RuntimeJavaType declaringType, string name, string sig, MethodBase method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, bool hideFromReflection) : + internal ByRefJavaMethod(ITypeSymbol[] args, bool[] byrefs, RuntimeJavaType declaringType, string name, string sig, IMethodBaseSymbol method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, bool hideFromReflection) : base(declaringType, name, sig, method, returnType, parameterTypes, modifiers, hideFromReflection ? MemberFlags.HideFromReflection : MemberFlags.None) { this.args = args; @@ -72,6 +70,7 @@ internal ByRefJavaMethod(Type[] args, bool[] byrefs, RuntimeJavaType declaringTy } #if EMITTERS + protected override void CallImpl(CodeEmitter ilgen) { ConvertByRefArgs(ilgen); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs index b9a0b9f6eb..669a191746 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs @@ -71,7 +71,7 @@ internal override void EmitCall(CodeEmitter ilgen) ilgen.MarkLabel(label2); ilgen.EmitThrow("java.lang.NullPointerException"); ilgen.MarkLabel(label1); - ilgen.Emit(OpCodes.Call, DeclaringType.Context.Types.Object.GetMethod("MemberwiseClone", BindingFlags.Instance | BindingFlags.NonPublic, null, Type.EmptyTypes, null)); + ilgen.Emit(OpCodes.Call, DeclaringType.Context.Types.Object.GetMethod("MemberwiseClone", BindingFlags.Instance | BindingFlags.NonPublic, null, [], null)); } internal override void EmitCallvirt(CodeEmitter ilgen) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs index 87e804711a..6d00693b27 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs @@ -24,19 +24,12 @@ Jeroen Frijters using System; using IKVM.Attributes; - -#if IMPORTER || EXPORTER -using Type = IKVM.Reflection.Type; -#endif +using IKVM.CoreLib.Symbols; #if IMPORTER using IKVM.Tools.Importer; #endif -#if EXPORTER -using IKVM.Tools.Exporter; -#endif - namespace IKVM.Runtime { @@ -46,7 +39,7 @@ sealed partial class RuntimeManagedJavaType sealed class DelegateInnerClassJavaType : FakeJavaType { - readonly Type fakeType; + readonly ITypeSymbol fakeType; /// /// Initializes a new instance. @@ -54,13 +47,13 @@ sealed class DelegateInnerClassJavaType : FakeJavaType /// /// /// - internal DelegateInnerClassJavaType(RuntimeContext context, string name, Type delegateType) : + internal DelegateInnerClassJavaType(RuntimeContext context, string name, ITypeSymbol delegateType) : base(context, Modifiers.Public | Modifiers.Interface | Modifiers.Abstract, name, null) { #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetDelegateType(delegateType); #elif !FIRST_PASS - this.fakeType = typeof(ikvm.@internal.DelegateInterface<>).MakeGenericType(delegateType); + this.fakeType = context.Resolver.ResolveType(typeof(ikvm.@internal.DelegateInterface<>)).MakeGenericType(delegateType); #endif var invoke = delegateType.GetMethod("Invoke"); var parameters = invoke.GetParameters(); @@ -76,22 +69,24 @@ internal DelegateInnerClassJavaType(RuntimeContext context, string name, Type de flags |= MemberFlags.DelegateInvokeWithByRefParameter; parameterType = RuntimeArrayJavaType.MakeArrayType(parameterType.GetElementType(), 1); } + argTypeWrappers[i] = Context.ClassLoaderFactory.GetJavaTypeFromType(parameterType); sb.Append(argTypeWrappers[i].SigName); } var returnType = Context.ClassLoaderFactory.GetJavaTypeFromType(invoke.ReturnType); sb.Append(")").Append(returnType.SigName); + var invokeMethod = new DynamicOnlyJavaMethod(this, "Invoke", sb.ToString(), returnType, argTypeWrappers, flags); - SetMethods(new RuntimeJavaMethod[] { invokeMethod }); - SetFields(Array.Empty()); + SetMethods([invokeMethod]); + SetFields([]); } internal override RuntimeJavaType DeclaringTypeWrapper => Context.ClassLoaderFactory.GetJavaTypeFromType(fakeType.GetGenericArguments()[0]); internal override RuntimeClassLoader ClassLoader => DeclaringTypeWrapper.ClassLoader; - internal override Type TypeAsTBD => fakeType; + internal override ITypeSymbol TypeAsTBD => fakeType; internal override bool IsFastClassLiteralSafe => true; diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs index f709eb7aac..9d5dc4e1ab 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs @@ -25,6 +25,8 @@ Jeroen Frijters using System.Collections.Generic; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -49,7 +51,7 @@ sealed partial class RuntimeManagedJavaType sealed partial class EnumEnumJavaType : FakeJavaType { - readonly Type fakeType; + readonly ITypeSymbol fakeType; /// /// Initializes a new instance. @@ -57,13 +59,13 @@ sealed partial class EnumEnumJavaType : FakeJavaType /// /// /// - internal EnumEnumJavaType(RuntimeContext context, string name, Type enumType) : + internal EnumEnumJavaType(RuntimeContext context, string name, ITypeSymbol enumType) : base(context, Modifiers.Public | Modifiers.Enum | Modifiers.Final, name, context.ClassLoaderFactory.LoadClassCritical("java.lang.Enum")) { #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetEnumType(enumType); #elif !FIRST_PASS - this.fakeType = typeof(ikvm.@internal.EnumEnum<>).MakeGenericType(enumType); + this.fakeType = context.Resolver.ResolveType(typeof(ikvm.@internal.EnumEnum<>)).MakeGenericType(enumType); #endif } @@ -105,7 +107,7 @@ internal EnumJavaField(RuntimeJavaType tw, string name, int ordinal) : internal override object GetValue(object obj) { if (val == null) - System.Threading.Interlocked.CompareExchange(ref val, Activator.CreateInstance(this.DeclaringType.TypeAsTBD, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new object[] { this.Name, ordinal }, null), null); + System.Threading.Interlocked.CompareExchange(ref val, Activator.CreateInstance(this.DeclaringType.TypeAsTBD.AsReflection(), BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new object[] { this.Name, ordinal }, null), null); return val; } @@ -120,7 +122,7 @@ internal override void SetValue(object obj, object value) #if EMITTERS protected override void EmitGetImpl(CodeEmitter ilgen) { - var typeofByteCodeHelper = DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper").AsReflection(); + var typeofByteCodeHelper = DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper"); ilgen.Emit(OpCodes.Ldstr, Name); ilgen.Emit(OpCodes.Call, typeofByteCodeHelper.GetMethod("GetDotNetEnumField").MakeGenericMethod(DeclaringType.TypeAsBaseType)); } @@ -142,7 +144,7 @@ sealed class EnumValuesJavaMethod : RuntimeJavaMethod /// /// internal EnumValuesJavaMethod(RuntimeJavaType declaringType) : - base(declaringType, "values", "()[" + declaringType.SigName, null, declaringType.MakeArrayType(1), Array.Empty(), Modifiers.Public | Modifiers.Static, MemberFlags.None) + base(declaringType, "values", "()[" + declaringType.SigName, null, declaringType.MakeArrayType(1), [], Modifiers.Public | Modifiers.Static, MemberFlags.None) { } @@ -153,12 +155,11 @@ internal EnumValuesJavaMethod(RuntimeJavaType declaringType) : internal override object Invoke(object obj, object[] args) { - RuntimeJavaField[] values = this.DeclaringType.GetFields(); - object[] array = (object[])Array.CreateInstance(this.DeclaringType.TypeAsArrayType, values.Length); + var values = DeclaringType.GetFields(); + var array = (object[])Array.CreateInstance(DeclaringType.TypeAsArrayType.AsReflection(), values.Length); for (int i = 0; i < values.Length; i++) - { array[i] = values[i].GetValue(null); - } + return array; } @@ -170,14 +171,14 @@ protected override void LazyPublishMembers() { var fields = new List(); int ordinal = 0; - foreach (var field in DeclaringTypeWrapper.TypeAsTBD.GetFields(BindingFlags.Static | BindingFlags.Public)) + foreach (var field in DeclaringTypeWrapper.TypeAsTBD.GetFields(System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public)) if (field.IsLiteral) fields.Add(new EnumJavaField(this, field.Name, ordinal++)); // TODO if the enum already has an __unspecified value, rename this one fields.Add(new EnumJavaField(this, "__unspecified", ordinal++)); SetFields(fields.ToArray()); - SetMethods(new RuntimeJavaMethod[] { new EnumValuesJavaMethod(this), new EnumValueOfJavaMethod(this) }); + SetMethods([new EnumValuesJavaMethod(this), new EnumValueOfJavaMethod(this)]); base.LazyPublishMembers(); } @@ -185,7 +186,7 @@ protected override void LazyPublishMembers() internal override RuntimeClassLoader ClassLoader => DeclaringTypeWrapper.ClassLoader; - internal override Type TypeAsTBD => fakeType; + internal override ITypeSymbol TypeAsTBD => fakeType; internal override bool IsFastClassLiteralSafe => true; diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.OpenGenericJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.OpenGenericJavaType.cs index bde1900458..1a21b48019 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.OpenGenericJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.OpenGenericJavaType.cs @@ -24,6 +24,7 @@ Jeroen Frijters using System; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using Type = IKVM.Reflection.Type; @@ -48,9 +49,9 @@ sealed partial class RuntimeManagedJavaType sealed class OpenGenericJavaType : RuntimeJavaType { - readonly Type type; + readonly ITypeSymbol type; - static Modifiers GetModifiers(Type type) + static Modifiers GetModifiers(ITypeSymbol type) { var modifiers = Modifiers.Abstract | Modifiers.Final; if (type.IsInterface) @@ -65,7 +66,7 @@ static Modifiers GetModifiers(Type type) /// /// /// - internal OpenGenericJavaType(RuntimeContext context, Type type, string name) : + internal OpenGenericJavaType(RuntimeContext context, ITypeSymbol type, string name) : base(context, TypeFlags.None, GetModifiers(type), name) { this.type = type; @@ -73,7 +74,7 @@ internal OpenGenericJavaType(RuntimeContext context, Type type, string name) : internal override RuntimeJavaType BaseTypeWrapper => type.IsInterface ? null : Context.JavaBase.TypeOfJavaLangObject; - internal override Type TypeAsTBD => type; + internal override ITypeSymbol TypeAsTBD => type; internal override RuntimeClassLoader ClassLoader => Context.AssemblyClassLoaderFactory.FromAssembly(type.Assembly); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index c864042dad..523b20f724 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -26,6 +26,7 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -59,13 +60,13 @@ sealed partial class RuntimeManagedJavaType : RuntimeJavaType internal const string GenericAttributeAnnotationReturnValueTypeName = "ikvm.internal.AttributeAnnotationReturnValue`1"; internal const string GenericAttributeAnnotationMultipleTypeName = "ikvm.internal.AttributeAnnotationMultiple`1"; - readonly Type type; + readonly ITypeSymbol type; RuntimeJavaType baseTypeWrapper; RuntimeJavaType[] innerClasses; RuntimeJavaType outerClass; RuntimeJavaType[] interfaces; - static Modifiers GetModifiers(Type type) + static Modifiers GetModifiers(ITypeSymbol type) { Modifiers modifiers = 0; if (type.IsPublic) @@ -111,7 +112,7 @@ static Modifiers GetModifiers(Type type) // NOTE when this is called on a remapped type, the "warped" underlying type name is returned. // E.g. GetName(typeof(object)) returns "cli.System.Object". - internal static string GetName(RuntimeContext context, Type type) + internal static string GetName(RuntimeContext context, ITypeSymbol type) { Debug.Assert(!type.Name.EndsWith("[]") && !context.AttributeHelper.IsJavaModule(type.Module)); @@ -127,8 +128,9 @@ internal static string GetName(RuntimeContext context, Type type) var sb = new System.Text.StringBuilder(); sb.Append(MangleTypeName(type.GetGenericTypeDefinition().FullName)); sb.Append("_$$$_"); - string sep = ""; - foreach (Type t1 in type.GetGenericArguments()) + + var sep = ""; + foreach (var t1 in type.GetGenericArguments()) { var t = t1; sb.Append(sep); @@ -141,7 +143,7 @@ internal static string GetName(RuntimeContext context, Type type) // class Base { } // class Derived : Base { } // - while (ReflectUtil.IsVector(t)) + while (t.IsSZArray) { t = t.GetElementType(); sb.Append('A'); @@ -269,20 +271,20 @@ internal static string DemangleTypeName(string name) // TODO from a perf pov it may be better to allow creation of TypeWrappers, // but to simply make sure they don't have ClassObject - internal static bool IsAllowedOutside(Type type) + internal static bool IsAllowedOutside(ITypeSymbol type) { // SECURITY we never expose types from IKVM.Runtime, because doing so would lead to a security hole, // since the reflection implementation lives inside this assembly, all internal members would // be accessible through Java reflection. #if !FIRST_PASS && !IMPORTER && !EXPORTER - if (type.Assembly == typeof(RuntimeManagedJavaType).Assembly) + if (type.Assembly.AsReflection() == typeof(RuntimeManagedJavaType).Assembly) return false; #endif return true; } - internal static RuntimeJavaType Create(RuntimeContext context, Type type, string name) + internal static RuntimeJavaType Create(RuntimeContext context, ITypeSymbol type, string name) { if (type.ContainsGenericParameters) { @@ -300,13 +302,13 @@ internal static RuntimeJavaType Create(RuntimeContext context, Type type, string /// /// /// - RuntimeManagedJavaType(RuntimeContext context, Type type, string name) : + RuntimeManagedJavaType(RuntimeContext context, ITypeSymbol type, string name) : base(context, TypeFlags.None, GetModifiers(type), name) { Debug.Assert(!type.IsByRef, type.FullName); Debug.Assert(!type.IsPointer, type.FullName); Debug.Assert(!type.Name.EndsWith("[]"), type.FullName); - Debug.Assert(type is not TypeBuilder, type.FullName); + Debug.Assert(type.AsReflection() is not TypeBuilder, type.FullName); Debug.Assert(!Context.AttributeHelper.IsJavaModule(type.Module)); this.type = type; @@ -316,7 +318,7 @@ internal static RuntimeJavaType Create(RuntimeContext context, Type type, string internal override RuntimeClassLoader ClassLoader => type.IsGenericType ? Context.ClassLoaderFactory.GetGenericClassLoader(this) : Context.AssemblyClassLoaderFactory.FromAssembly(type.Assembly); - internal static string GetDelegateInvokeStubName(Type delegateType) + internal static string GetDelegateInvokeStubName(ITypeSymbol delegateType) { var delegateInvoke = delegateType.GetMethod("Invoke"); var parameters = delegateInvoke.GetParameters(); @@ -334,8 +336,9 @@ protected override void LazyPublishMembers() // special support for enums if (type.IsEnum) { - Type underlyingType = EnumHelper.GetUnderlyingType(type); - Type javaUnderlyingType; + var underlyingType = type.GetEnumUnderlyingType(); + + ITypeSymbol javaUnderlyingType; if (underlyingType == Context.Types.SByte) { javaUnderlyingType = Context.Types.Byte; @@ -358,7 +361,7 @@ protected override void LazyPublishMembers() } var fieldType = Context.ClassLoaderFactory.GetJavaTypeFromType(javaUnderlyingType); - var fields = type.GetFields(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.Static); + var fields = type.GetFields(System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static); var fieldsList = new List(); for (int i = 0; i < fields.Length; i++) { @@ -381,7 +384,7 @@ protected override void LazyPublishMembers() else { var fieldsList = new List(); - var fields = type.GetFields(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance); + var fields = type.GetFields(System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance); for (int i = 0; i < fields.Length; i++) { // TODO for remapped types, instance fields need to be converted to static getter/setter methods @@ -411,7 +414,7 @@ protected override void LazyPublishMembers() if (type == Context.Types.MulticastDelegate) methodsList.Add("()V", new MulticastDelegateCtorJavaMethod(this)); - var constructors = type.GetConstructors(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance); + var constructors = type.GetConstructors(System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance); for (int i = 0; i < constructors.Length; i++) { if (MakeMethodDescriptor(constructors[i], out var name, out var sig, out var args, out var ret)) @@ -429,7 +432,7 @@ protected override void LazyPublishMembers() methodsList.Add("()V", new ValueTypeDefaultCtorJavaMethod(this)); } - var methods = type.GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance); + var methods = type.GetMethods(System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance); for (int i = 0; i < methods.Length; i++) { if (methods[i].IsStatic && type.IsInterface) @@ -545,10 +548,8 @@ protected override void LazyPublishMembers() #if !IMPORTER && !EXPORTER && !FIRST_PASS // support serializing .NET exceptions (by replacing them with a placeholder exception) - if (typeof(Exception).IsAssignableFrom(type) && !typeof(java.io.Serializable.__Interface).IsAssignableFrom(type) && !methodsList.ContainsKey("writeReplace()Ljava.lang.Object;")) - { + if (Context.Types.Exception.IsAssignableFrom(type) && Context.Resolver.ResolveType(typeof(java.io.Serializable.__Interface)).IsAssignableFrom(type) == false && methodsList.ContainsKey("writeReplace()Ljava.lang.Object;") == false) methodsList.Add("writeReplace()Ljava.lang.Object;", new ExceptionWriteReplaceJavaMethod(this)); - } #endif @@ -558,7 +559,7 @@ protected override void LazyPublishMembers() } } - void InterfaceMethodStubHelper(Dictionary methodsList, MethodBase method, string name, string sig, RuntimeJavaType[] args, RuntimeJavaType ret) + void InterfaceMethodStubHelper(Dictionary methodsList, IMethodBaseSymbol method, string name, string sig, RuntimeJavaType[] args, RuntimeJavaType ret) { var key = name + sig; methodsList.TryGetValue(key, out var existing); @@ -578,11 +579,11 @@ void InterfaceMethodStubHelper(Dictionary methodsList } } - internal static bool IsUnsupportedAbstractMethod(MethodBase mb) + internal static bool IsUnsupportedAbstractMethod(IMethodBaseSymbol mb) { if (mb.IsAbstract) { - var mi = (MethodInfo)mb; + var mi = (IMethodSymbol)mb; if (mi.ReturnType.IsByRef || IsPointerType(mi.ReturnType) || mb.IsGenericMethodDefinition) return true; @@ -594,7 +595,7 @@ internal static bool IsUnsupportedAbstractMethod(MethodBase mb) return false; } - static bool IsPointerType(Type type) + static bool IsPointerType(ITypeSymbol type) { while (type.HasElementType) { @@ -604,14 +605,10 @@ static bool IsPointerType(Type type) type = type.GetElementType(); } -#if IMPORTER || EXPORTER - return type.__IsFunctionPointer; -#else - return false; -#endif + return type.IsUnmanagedFunctionPointer; } - bool MakeMethodDescriptor(MethodBase mb, out string name, out string sig, out RuntimeJavaType[] args, out RuntimeJavaType ret) + bool MakeMethodDescriptor(IMethodBaseSymbol mb, out string name, out string sig, out RuntimeJavaType[] args, out RuntimeJavaType ret) { if (mb.IsGenericMethodDefinition) { @@ -668,7 +665,7 @@ bool MakeMethodDescriptor(MethodBase mb, out string name, out string sig, out Ru } else { - var type = ((MethodInfo)mb).ReturnType; + var type = ((IMethodSymbol)mb).ReturnType; if (IsPointerType(type) || type.IsByRef) { name = null; @@ -686,7 +683,7 @@ bool MakeMethodDescriptor(MethodBase mb, out string name, out string sig, out Ru internal override RuntimeJavaType[] Interfaces => interfaces ??= GetImplementedInterfacesAsTypeWrappers(Context, type); - static bool IsAttribute(RuntimeContext context, Type type) + static bool IsAttribute(RuntimeContext context, ITypeSymbol type) { if (!type.IsAbstract && type.IsSubclassOf(context.Types.Attribute) && type.IsVisible) { @@ -710,7 +707,7 @@ static bool IsAttribute(RuntimeContext context, Type type) return false; } - static bool IsDelegate(RuntimeContext context, Type type) + static bool IsDelegate(RuntimeContext context, ITypeSymbol type) { // HACK non-public delegates do not get the special treatment (because they are likely to refer to // non-public types in the arg list and they're not really useful anyway) @@ -739,7 +736,7 @@ static bool IsDelegate(RuntimeContext context, Type type) RuntimeJavaType[] GetInnerClasses() { - var nestedTypes = type.GetNestedTypes(BindingFlags.Public | BindingFlags.NonPublic); + var nestedTypes = type.GetNestedTypes(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic); var list = new List(nestedTypes.Length); for (int i = 0; i < nestedTypes.Length; i++) if (!nestedTypes[i].IsGenericTypeDefinition) @@ -776,7 +773,7 @@ internal override RuntimeJavaType DeclaringTypeWrapper internal override Modifiers ReflectiveModifiers => DeclaringTypeWrapper != null ? Modifiers | Modifiers.Static : Modifiers; - RuntimeJavaField CreateFieldWrapperDotNet(Modifiers modifiers, string name, Type fieldType, FieldInfo field) + RuntimeJavaField CreateFieldWrapperDotNet(Modifiers modifiers, string name, ITypeSymbol fieldType, IFieldSymbol field) { var type = Context.ClassLoaderFactory.GetJavaTypeFromType(fieldType); if (field.IsLiteral) @@ -790,7 +787,7 @@ RuntimeJavaField CreateFieldWrapperDotNet(Modifiers modifiers, string name, Type /// /// /// - static bool IsRemappedImplDerived(RuntimeContext context, Type type) + static bool IsRemappedImplDerived(RuntimeContext context, ITypeSymbol type) { for (; type != null; type = type.BaseType) if (!context.ClassLoaderFactory.IsRemappedType(type) && context.ClassLoaderFactory.GetJavaTypeFromType(type).IsRemapped) @@ -799,7 +796,7 @@ static bool IsRemappedImplDerived(RuntimeContext context, Type type) return false; } - RuntimeJavaMethod CreateMethodWrapper(string name, string sig, RuntimeJavaType[] argTypeWrappers, RuntimeJavaType retTypeWrapper, MethodBase mb, bool privateInterfaceImplHack) + RuntimeJavaMethod CreateMethodWrapper(string name, string sig, RuntimeJavaType[] argTypeWrappers, RuntimeJavaType retTypeWrapper, IMethodBaseSymbol mb, bool privateInterfaceImplHack) { var exmods = Context.AttributeHelper.GetModifiers(mb, true); var mods = exmods.Modifiers; @@ -813,7 +810,7 @@ RuntimeJavaMethod CreateMethodWrapper(string name, string sig, RuntimeJavaType[] } var parameters = mb.GetParameters(); - var args = new Type[parameters.Length]; + var args = new ITypeSymbol[parameters.Length]; var hasByRefArgs = false; bool[] byrefs = null; @@ -836,7 +833,7 @@ RuntimeJavaMethod CreateMethodWrapper(string name, string sig, RuntimeJavaType[] if (hasByRefArgs) { - if (mb is not ConstructorInfo && !mb.IsStatic) + if (mb.IsConstructor == false && !mb.IsStatic) mods |= Modifiers.Final; return new ByRefJavaMethod(args, byrefs, this, name, sig, mb, retTypeWrapper, argTypeWrappers, mods, false); @@ -847,7 +844,7 @@ RuntimeJavaMethod CreateMethodWrapper(string name, string sig, RuntimeJavaType[] } } - internal override Type TypeAsTBD => type; + internal override ITypeSymbol TypeAsTBD => type; internal override bool IsRemapped => Context.ClassLoaderFactory.IsRemappedType(type); @@ -918,7 +915,12 @@ internal override MethodParametersEntry[] GetMethodParameters(RuntimeJavaMethod internal override object[] GetDeclaredAnnotations() { - return type.GetCustomAttributes(false); + var l = type.GetCustomAttributes(); + var a = new object[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = l[i]; + + return a; } internal override object[] GetFieldAnnotations(RuntimeJavaField fw) @@ -927,7 +929,12 @@ internal override object[] GetFieldAnnotations(RuntimeJavaField fw) if (fi == null) return null; - return fi.GetCustomAttributes(false); + var l = fi.GetCustomAttributes(); + var a = new object[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = l[i]; + + return a; } internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) @@ -936,7 +943,12 @@ internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) if (mb == null) return null; - return mb.GetCustomAttributes(false); + var l = mb.GetCustomAttributes(); + var a = new object[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = l[i]; + + return a; } internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) @@ -948,10 +960,18 @@ internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) var parameters = mb.GetParameters(); var attribs = new object[parameters.Length][]; for (int i = 0; i < parameters.Length; i++) - attribs[i] = parameters[i].GetCustomAttributes(false); + { + var l = parameters[i].GetCustomAttributes(); + var a = new object[l.Length]; + for (int j = 0; j < l.Length; j++) + a[j] = l[j]; + + attribs[i] = a; + } return attribs; } + #endif internal override bool IsFastClassLiteralSafe => type != Context.Types.Void && !type.IsPrimitive && !IsRemapped; @@ -970,13 +990,11 @@ internal override bool IsPackageAccessibleFrom(RuntimeJavaType wrapper) return false; // check accessibility for nested types - for (Type type = TypeAsTBD; type.IsNested; type = type.DeclaringType) + for (var type = TypeAsTBD; type.IsNested; type = type.DeclaringType) { // we don't support family (protected) access if (!type.IsNestedAssembly && !type.IsNestedFamORAssem && !type.IsNestedPublic) - { return false; - } } return true; diff --git a/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs b/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs index 1893aa1034..d6c1aace87 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -42,7 +44,7 @@ class RuntimeManagedJavaTypeFactory { readonly RuntimeContext context; - readonly ConditionalWeakTable cache = new ConditionalWeakTable(); + readonly ConditionalWeakTable cache = new ConditionalWeakTable(); /// /// Initializes a new instance. @@ -59,9 +61,9 @@ public RuntimeManagedJavaTypeFactory(RuntimeContext context) /// /// /// - public RuntimeJavaType GetJavaTypeFromManagedType(Type type) + public RuntimeJavaType GetJavaTypeFromManagedType(ITypeSymbol type) { - return cache.GetValue(type, _ => context.AssemblyClassLoaderFactory.FromAssembly(_.Assembly).GetJavaTypeFromAssemblyType(_)); + return cache.GetValue(type, _ => context.AssemblyClassLoaderFactory.FromAssembly(_.Assembly.AsReflection()).GetJavaTypeFromAssemblyType(_.AsReflection())); } /// @@ -69,7 +71,7 @@ public RuntimeJavaType GetJavaTypeFromManagedType(Type type) /// /// /// - public RuntimeJavaType GetBaseJavaType(Type type) + public RuntimeJavaType GetBaseJavaType(ITypeSymbol type) { // interfaces have no base type if (type.IsInterface) diff --git a/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs b/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs index 1603b19752..d0e2256a54 100644 --- a/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs +++ b/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -76,7 +78,7 @@ public RuntimePrimitiveJavaTypeFactory(RuntimeContext context) sealed class RuntimePrimitiveJavaType : RuntimeJavaType { - readonly Type type; + readonly ITypeSymbol type; readonly string sigName; /// @@ -84,7 +86,7 @@ sealed class RuntimePrimitiveJavaType : RuntimeJavaType /// /// /// - public RuntimePrimitiveJavaType(RuntimeContext context, Type type, string sigName) : + public RuntimePrimitiveJavaType(RuntimeContext context, ITypeSymbol type, string sigName) : base(context, TypeFlags.None, Modifiers.Public | Modifiers.Abstract | Modifiers.Final, null) { this.type = type; @@ -93,7 +95,7 @@ public RuntimePrimitiveJavaType(RuntimeContext context, Type type, string sigNam internal override RuntimeJavaType BaseTypeWrapper => null; - internal static bool IsPrimitiveType(RuntimeContext context, Type type) + internal static bool IsPrimitiveType(RuntimeContext context, ITypeSymbol type) { return type == context.PrimitiveJavaTypeFactory.BYTE.type || type == context.PrimitiveJavaTypeFactory.CHAR.type @@ -110,7 +112,7 @@ internal static bool IsPrimitiveType(RuntimeContext context, Type type) internal override RuntimeClassLoader ClassLoader => Context.ClassLoaderFactory.GetBootstrapClassLoader(); - internal override Type TypeAsTBD => type; + internal override ITypeSymbol TypeAsTBD => type; public override string ToString() => "RuntimePrimitiveJavaType[" + sigName + "]"; diff --git a/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs b/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs index 730c8447bd..e7535f9f79 100644 --- a/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs @@ -22,14 +22,11 @@ Jeroen Frijters */ using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER -using IKVM.Reflection; using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; #else -using System.Reflection; using System.Reflection.Emit; #endif @@ -50,7 +47,7 @@ sealed class RuntimePrivateInterfaceJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal RuntimePrivateInterfaceJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodBase method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimePrivateInterfaceJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodBaseSymbol method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, name, sig, method, returnType, parameterTypes, modifiers, flags) { diff --git a/src/IKVM.Runtime/RuntimeSimpleJavaField.cs b/src/IKVM.Runtime/RuntimeSimpleJavaField.cs index b2f055afc0..bba30138f1 100644 --- a/src/IKVM.Runtime/RuntimeSimpleJavaField.cs +++ b/src/IKVM.Runtime/RuntimeSimpleJavaField.cs @@ -23,6 +23,8 @@ Jeroen Frijters */ using System.Diagnostics; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -55,7 +57,7 @@ sealed class RuntimeSimpleJavaField : RuntimeJavaField /// /// /// - internal RuntimeSimpleJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, FieldInfo fi, string name, string sig, ExModifiers modifiers) : + internal RuntimeSimpleJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, IFieldSymbol fi, string name, string sig, ExModifiers modifiers) : base(declaringType, fieldType, name, sig, modifiers, fi) { Debug.Assert(!(fieldType == declaringType.Context.PrimitiveJavaTypeFactory.DOUBLE || fieldType == declaringType.Context.PrimitiveJavaTypeFactory.LONG) || !IsVolatile); @@ -65,12 +67,12 @@ internal RuntimeSimpleJavaField(RuntimeJavaType declaringType, RuntimeJavaType f internal override object GetValue(object obj) { - return GetField().GetValue(obj); + return GetField().AsReflection().GetValue(obj); } internal override void SetValue(object obj, object value) { - GetField().SetValue(obj, value); + GetField().AsReflection().SetValue(obj, value); } #endif @@ -134,7 +136,7 @@ protected override void EmitUnsafeGetImpl(CodeEmitter il) if (IsFinal) { il.Emit(OpCodes.Ldsflda, fi); - il.Emit(OpCodes.Call, DeclaringType.Context.Resolver.ResolveRuntimeType(typeof(RuntimeSimpleJavaField).FullName).AsReflection().GetMethod(nameof(UnsafeGetImplByRefNoInline), BindingFlags.Static | BindingFlags.NonPublic).MakeGenericMethod(fi.FieldType)); + il.Emit(OpCodes.Call, DeclaringType.Context.Resolver.ResolveRuntimeType(typeof(RuntimeSimpleJavaField).FullName).GetMethod(nameof(UnsafeGetImplByRefNoInline), System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.NonPublic).MakeGenericMethod(fi.FieldType)); } else { diff --git a/src/IKVM.Runtime/RuntimeSmartJavaMethod.cs b/src/IKVM.Runtime/RuntimeSmartJavaMethod.cs index 38de8ed72c..0ea23f718e 100644 --- a/src/IKVM.Runtime/RuntimeSmartJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeSmartJavaMethod.cs @@ -24,6 +24,7 @@ Jeroen Frijters using System; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -48,7 +49,7 @@ abstract class RuntimeSmartJavaMethod : RuntimeJavaMethod /// /// /// - internal RuntimeSmartJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodBase method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimeSmartJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodBaseSymbol method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, name, sig, method, returnType, parameterTypes, modifiers, flags) { diff --git a/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs b/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs index c58ff76265..e2a384afa6 100644 --- a/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs @@ -22,6 +22,8 @@ Jeroen Frijters */ using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -50,7 +52,7 @@ sealed class RuntimeTypicalJavaMethod : RuntimeSmartJavaMethod /// /// /// - internal RuntimeTypicalJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodBase method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : + internal RuntimeTypicalJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodBaseSymbol method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags) : base(declaringType, name, sig, method, returnType, parameterTypes, modifiers, flags) { diff --git a/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs b/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs index 05961e1edc..a0265537b4 100644 --- a/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs +++ b/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs @@ -23,6 +23,8 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -43,8 +45,8 @@ sealed class RuntimeUnloadableJavaType : RuntimeJavaType internal const string ContainerTypeName = "__"; - readonly Type missingType; - Type customModifier; + readonly ITypeSymbol missingType; + ITypeSymbol customModifier; /// /// Initializes a new instance. @@ -62,7 +64,7 @@ internal RuntimeUnloadableJavaType(RuntimeContext context, string name) : /// /// /// - internal RuntimeUnloadableJavaType(RuntimeContext context, Type missingType) : + internal RuntimeUnloadableJavaType(RuntimeContext context, ITypeSymbol missingType) : this(context, missingType.FullName) // TODO demangle and re-mangle appropriately { this.missingType = missingType; @@ -74,7 +76,7 @@ internal RuntimeUnloadableJavaType(RuntimeContext context, Type missingType) : /// /// /// - internal RuntimeUnloadableJavaType(RuntimeContext context, string name, Type customModifier) : + internal RuntimeUnloadableJavaType(RuntimeContext context, string name, ITypeSymbol customModifier) : this(context, name) { this.customModifier = customModifier; @@ -86,9 +88,9 @@ internal RuntimeUnloadableJavaType(RuntimeContext context, string name, Type cus internal override RuntimeJavaType EnsureLoadable(RuntimeClassLoader loader) { - var tw = loader.TryLoadClassByName(this.Name); + var tw = loader.TryLoadClassByName(Name); if (tw == null) - throw new NoClassDefFoundError(this.Name); + throw new NoClassDefFoundError(Name); return tw; } @@ -110,7 +112,7 @@ protected override void LazyPublishMembers() throw new InvalidOperationException("LazyPublishMembers called on UnloadableTypeWrapper: " + Name); } - internal override Type TypeAsTBD => throw new InvalidOperationException("get_Type called on UnloadableTypeWrapper: " + Name); + internal override ITypeSymbol TypeAsTBD => throw new InvalidOperationException("get_Type called on UnloadableTypeWrapper: " + Name); internal override RuntimeJavaType[] Interfaces { @@ -137,9 +139,9 @@ internal override void Finish() throw new InvalidOperationException("Finish called on UnloadableTypeWrapper: " + Name); } - internal Type MissingType => missingType; + internal ITypeSymbol MissingType => missingType; - internal Type CustomModifier => customModifier; + internal ITypeSymbol CustomModifier => customModifier; internal void SetCustomModifier(Type type) { diff --git a/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs b/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs index 9c5f66c0af..e2c161e133 100644 --- a/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs +++ b/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs @@ -23,6 +23,8 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -49,7 +51,7 @@ sealed class RuntimeVolatileLongDoubleJavaField : RuntimeJavaField /// /// /// - internal RuntimeVolatileLongDoubleJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, FieldInfo fi, string name, string sig, ExModifiers modifiers) : + internal RuntimeVolatileLongDoubleJavaField(RuntimeJavaType declaringType, RuntimeJavaType fieldType, IFieldSymbol fi, string name, string sig, ExModifiers modifiers) : base(declaringType, fieldType, name, sig, modifiers, fi) { if (sig != "J" && sig != "D") diff --git a/src/IKVM.Runtime/SymbolExtensions.cs b/src/IKVM.Runtime/SymbolExtensions.cs index d49d1486e9..65a6c08dff 100644 --- a/src/IKVM.Runtime/SymbolExtensions.cs +++ b/src/IKVM.Runtime/SymbolExtensions.cs @@ -30,6 +30,18 @@ public static Assembly AsReflection(this IAssemblySymbol symbol) #endif } + public static Module AsReflection(this IModuleSymbol symbol) + { + if (symbol == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionModuleSymbol)symbol).ReflectionObject; +#else + return ((ReflectionModuleSymbol)symbol).ReflectionObject; +#endif + } + public static Type AsReflection(this ITypeSymbol symbol) { if (symbol == null) @@ -42,6 +54,30 @@ public static Type AsReflection(this ITypeSymbol symbol) #endif } + public static Type[] AsReflection(this ITypeSymbol[] symbols) + { + if (symbols == null) + return null; + + var a = new Type[symbols.Length]; + for (int i = 0; i < symbols.Length; i++) + a[i] = AsReflection(symbols[i]); + + return a; + } + + public static MethodBase AsReflection(this IMethodBaseSymbol symbol) + { + if (symbol == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionMethodBaseSymbol)symbol).ReflectionObject; +#else + return ((ReflectionMethodBaseSymbol)symbol).ReflectionObject; +#endif + } + public static ConstructorInfo AsReflection(this IConstructorSymbol symbol) { if (symbol == null) @@ -78,6 +114,18 @@ public static FieldInfo AsReflection(this IFieldSymbol symbol) #endif } + public static FieldInfo[] AsReflection(this IFieldSymbol[] symbols) + { + if (symbols == null) + return null; + + var a = new FieldInfo[symbols.Length]; + for (int i = 0; i < symbols.Length; i++) + a[i] = AsReflection(symbols[i]); + + return a; + } + public static PropertyInfo AsReflection(this IPropertySymbol symbol) { if (symbol == null) @@ -90,6 +138,18 @@ public static PropertyInfo AsReflection(this IPropertySymbol symbol) #endif } + public static PropertyInfo[] AsReflection(this IPropertySymbol[] symbols) + { + if (symbols == null) + return null; + + var a = new PropertyInfo[symbols.Length]; + for (int i = 0; i < symbols.Length; i++) + a[i] = AsReflection(symbols[i]); + + return a; + } + } } diff --git a/src/IKVM.Runtime/Types.cs b/src/IKVM.Runtime/Types.cs index e085932131..f790f81720 100644 --- a/src/IKVM.Runtime/Types.cs +++ b/src/IKVM.Runtime/Types.cs @@ -22,7 +22,8 @@ Jeroen Frijters */ using System; -using System.Threading; + +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using Type = IKVM.Reflection.Type; @@ -39,34 +40,34 @@ class Types readonly RuntimeContext context; - Type typeOfObject; - Type typeOfValueType; - Type typeOfEnum; - Type typeOfType; - Type typeOfString; - Type typeOfException; - Type typeOfArray; - Type typeOfAttribute; - Type typeOfDelegate; - Type typeOfMulticastDelegate; - Type typeOfRuntimeTypeHandle; - - Type typeOfIntPtr; - Type typeOfVoid; - Type typeOfBoolean; - Type typeOfByte; - Type typeOfSByte; - Type typeOfChar; - Type typeOfInt16; - Type typeOfUInt16; - Type typeOfInt32; - Type typeOfUInt32; - Type typeOfInt64; - Type typeOfUInt64; - Type typeOfSingle; - Type typeOfDouble; - - Type typeOfIsVolatile; + ITypeSymbol typeOfObject; + ITypeSymbol typeOfValueType; + ITypeSymbol typeOfEnum; + ITypeSymbol typeOfType; + ITypeSymbol typeOfString; + ITypeSymbol typeOfException; + ITypeSymbol typeOfArray; + ITypeSymbol typeOfAttribute; + ITypeSymbol typeOfDelegate; + ITypeSymbol typeOfMulticastDelegate; + ITypeSymbol typeOfRuntimeTypeHandle; + + ITypeSymbol typeOfIntPtr; + ITypeSymbol typeOfVoid; + ITypeSymbol typeOfBoolean; + ITypeSymbol typeOfByte; + ITypeSymbol typeOfSByte; + ITypeSymbol typeOfChar; + ITypeSymbol typeOfInt16; + ITypeSymbol typeOfUInt16; + ITypeSymbol typeOfInt32; + ITypeSymbol typeOfUInt32; + ITypeSymbol typeOfInt64; + ITypeSymbol typeOfUInt64; + ITypeSymbol typeOfSingle; + ITypeSymbol typeOfDouble; + + ITypeSymbol typeOfIsVolatile; /// /// Initializes a new instance. @@ -83,62 +84,62 @@ public Types(RuntimeContext context) /// /// /// - Type Import(System.Type type) + ITypeSymbol Import(System.Type type) { - return context.Resolver.ResolveCoreType(type.FullName).AsReflection(); + return context.Resolver.ResolveCoreType(type.FullName); } - public Type Object => typeOfObject ??= Import(typeof(System.Object)); + public ITypeSymbol Object => typeOfObject ??= Import(typeof(System.Object)); - public Type ValueType => typeOfValueType ??= Import(typeof(System.ValueType)); + public ITypeSymbol ValueType => typeOfValueType ??= Import(typeof(System.ValueType)); - public Type Enum => typeOfEnum ??= Import(typeof(System.Enum)); + public ITypeSymbol Enum => typeOfEnum ??= Import(typeof(System.Enum)); - public Type Type => typeOfType ??= Import(typeof(System.Type)); + public ITypeSymbol Type => typeOfType ??= Import(typeof(System.Type)); - public Type String => typeOfString ??= Import(typeof(System.String)); + public ITypeSymbol String => typeOfString ??= Import(typeof(System.String)); - public Type Exception => typeOfException ??= Import(typeof(System.Exception)); + public ITypeSymbol Exception => typeOfException ??= Import(typeof(System.Exception)); - public Type Array => typeOfArray ??= Import(typeof(System.Array)); + public ITypeSymbol Array => typeOfArray ??= Import(typeof(System.Array)); - public Type Attribute => typeOfAttribute ??= Import(typeof(System.Attribute)); + public ITypeSymbol Attribute => typeOfAttribute ??= Import(typeof(System.Attribute)); - public Type Delegate => typeOfDelegate ??= Import(typeof(System.Delegate)); + public ITypeSymbol Delegate => typeOfDelegate ??= Import(typeof(System.Delegate)); - public Type MulticastDelegate => typeOfMulticastDelegate ??= Import(typeof(System.MulticastDelegate)); + public ITypeSymbol MulticastDelegate => typeOfMulticastDelegate ??= Import(typeof(System.MulticastDelegate)); - public Type RuntimeTypeHandle => typeOfRuntimeTypeHandle ??= Import(typeof(System.RuntimeTypeHandle)); + public ITypeSymbol RuntimeTypeHandle => typeOfRuntimeTypeHandle ??= Import(typeof(System.RuntimeTypeHandle)); - public Type IntPtr => typeOfIntPtr ??= Import(typeof(IntPtr)); + public ITypeSymbol IntPtr => typeOfIntPtr ??= Import(typeof(IntPtr)); - public Type Void => typeOfVoid ??= Import(typeof(void)); + public ITypeSymbol Void => typeOfVoid ??= Import(typeof(void)); - public Type Boolean => typeOfBoolean ??= Import(typeof(bool)); + public ITypeSymbol Boolean => typeOfBoolean ??= Import(typeof(bool)); - public Type Byte => typeOfByte ??= Import(typeof(byte)); + public ITypeSymbol Byte => typeOfByte ??= Import(typeof(byte)); - public Type SByte => typeOfSByte ??= Import(typeof(sbyte)); + public ITypeSymbol SByte => typeOfSByte ??= Import(typeof(sbyte)); - public Type Char => typeOfChar ??= Import(typeof(char)); + public ITypeSymbol Char => typeOfChar ??= Import(typeof(char)); - public Type Int16 => typeOfInt16 ??= Import(typeof(short)); + public ITypeSymbol Int16 => typeOfInt16 ??= Import(typeof(short)); - public Type UInt16 => typeOfUInt16 ??= Import(typeof(ushort)); + public ITypeSymbol UInt16 => typeOfUInt16 ??= Import(typeof(ushort)); - public Type Int32 => typeOfInt32 ??= Import(typeof(int)); + public ITypeSymbol Int32 => typeOfInt32 ??= Import(typeof(int)); - public Type UInt32 => typeOfUInt32 ??= Import(typeof(uint)); + public ITypeSymbol UInt32 => typeOfUInt32 ??= Import(typeof(uint)); - public Type Int64 => typeOfInt64 ??= Import(typeof(long)); + public ITypeSymbol Int64 => typeOfInt64 ??= Import(typeof(long)); - public Type UInt64 => typeOfUInt64 ??= Import(typeof(ulong)); + public ITypeSymbol UInt64 => typeOfUInt64 ??= Import(typeof(ulong)); - public Type Single => typeOfSingle ??= Import(typeof(float)); + public ITypeSymbol Single => typeOfSingle ??= Import(typeof(float)); - public Type Double => typeOfDouble ??= Import(typeof(double)); + public ITypeSymbol Double => typeOfDouble ??= Import(typeof(double)); - public Type IsVolatile => typeOfIsVolatile ??= Import(typeof(System.Runtime.CompilerServices.IsVolatile)); + public ITypeSymbol IsVolatile => typeOfIsVolatile ??= Import(typeof(System.Runtime.CompilerServices.IsVolatile)); } diff --git a/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs b/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs index 6ac29415a5..5e8cb20fc6 100644 --- a/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs +++ b/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs @@ -109,7 +109,7 @@ IEnumerable GetAssemblyTypes() } catch { - return Type.EmptyTypes; + return []; } } diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index 9efe8b7346..72f7e81b48 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -118,11 +118,11 @@ public CompilerFactory(RuntimeContext context, bool bootstrap) public MethodInfo FixateExceptionMethod => fixateExceptionMethod ??= bootstrap ? (MethodInfo)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", new Type[] { context.Types.Exception }); - public MethodInfo SuppressFillInStackTraceMethod => suppressFillInStackTraceMethod ??= bootstrap ? (MethodInfo)Throwable.GetMethodWrapper("__", "()V", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", Type.EmptyTypes); + public MethodInfo SuppressFillInStackTraceMethod => suppressFillInStackTraceMethod ??= bootstrap ? (MethodInfo)Throwable.GetMethodWrapper("__", "()V", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", []); public MethodInfo GetTypeFromHandleMethod => getTypeFromHandleMethod ??= context.Types.Type.GetMethod("GetTypeFromHandle", BindingFlags.Static | BindingFlags.Public, null, [context.Types.RuntimeTypeHandle], null); - public MethodInfo GetTypeMethod => getTypeMethod ??= context.Types.Object.GetMethod("GetType", BindingFlags.Public | BindingFlags.Instance, null, Type.EmptyTypes, null); + public MethodInfo GetTypeMethod => getTypeMethod ??= context.Types.Object.GetMethod("GetType", BindingFlags.Public | BindingFlags.Instance, null, [], null); public MethodInfo KeepAliveMethod => keepAliveMethod ??= context.Resolver.ResolveCoreType(typeof(GC).FullName).AsReflection().GetMethod("KeepAlive", BindingFlags.Static | BindingFlags.Public, null, [context.Types.Object], null); @@ -2761,7 +2761,7 @@ internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDyn static MethodBuilder CreateBootstrapStub(Compiler compiler, ClassFile.ConstantPoolItemInvokeDynamic cpi, Type delegateType, TypeBuilder tb, FieldBuilder fb, MethodInfo methodGetTarget) { var typeofCallSite = compiler.finish.Context.ClassLoaderFactory.LoadClassCritical("java.lang.invoke.CallSite").TypeAsSignatureType; - var args = Type.EmptyTypes; + var args = []; if (delegateType.IsGenericType) { diff --git a/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj b/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj index 00fd909a0f..d3db518a92 100644 --- a/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj +++ b/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj @@ -93,6 +93,7 @@ + diff --git a/src/IKVM.Tools.Importer/FakeTypes.cs b/src/IKVM.Tools.Importer/FakeTypes.cs index dce91bf0f0..61bf501de3 100644 --- a/src/IKVM.Tools.Importer/FakeTypes.cs +++ b/src/IKVM.Tools.Importer/FakeTypes.cs @@ -23,12 +23,11 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; using IKVM.Reflection; using IKVM.Reflection.Emit; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer { @@ -37,11 +36,11 @@ class FakeTypes readonly RuntimeContext context; - Type genericEnumEnumType; - Type genericDelegateInterfaceType; - Type genericAttributeAnnotationType; - Type genericAttributeAnnotationMultipleType; - Type genericAttributeAnnotationReturnValueType; + ITypeSymbol genericEnumEnumType; + ITypeSymbol genericDelegateInterfaceType; + ITypeSymbol genericAttributeAnnotationType; + ITypeSymbol genericAttributeAnnotationMultipleType; + ITypeSymbol genericAttributeAnnotationReturnValueType; /// /// Initializes a new instance. @@ -52,27 +51,27 @@ public FakeTypes(RuntimeContext context) this.context = context ?? throw new ArgumentNullException(nameof(context)); } - internal Type GetEnumType(Type enumType) + internal ITypeSymbol GetEnumType(ITypeSymbol enumType) { return genericEnumEnumType.MakeGenericType(enumType); } - internal Type GetDelegateType(Type delegateType) + internal ITypeSymbol GetDelegateType(ITypeSymbol delegateType) { return genericDelegateInterfaceType.MakeGenericType(delegateType); } - internal Type GetAttributeType(Type attributeType) + internal ITypeSymbol GetAttributeType(ITypeSymbol attributeType) { return genericAttributeAnnotationType.MakeGenericType(attributeType); } - internal Type GetAttributeMultipleType(Type attributeType) + internal ITypeSymbol GetAttributeMultipleType(ITypeSymbol attributeType) { return genericAttributeAnnotationMultipleType.MakeGenericType(attributeType); } - internal Type GetAttributeReturnValueType(Type attributeType) + internal ITypeSymbol GetAttributeReturnValueType(ITypeSymbol attributeType) { return genericAttributeAnnotationReturnValueType.MakeGenericType(attributeType); } @@ -80,8 +79,8 @@ internal Type GetAttributeReturnValueType(Type attributeType) internal void Create(ModuleBuilder modb, RuntimeClassLoader loader) { var tb = modb.DefineType(RuntimeManagedJavaType.GenericDelegateInterfaceTypeName, TypeAttributes.Interface | TypeAttributes.Abstract | TypeAttributes.Public); - tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.MulticastDelegate); - genericDelegateInterfaceType = tb.CreateType(); + tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.MulticastDelegate.AsReflection()); + genericDelegateInterfaceType = context.Resolver.ResolveType(tb.CreateType()); genericAttributeAnnotationType = CreateAnnotationType(modb, RuntimeManagedJavaType.GenericAttributeAnnotationTypeName); genericAttributeAnnotationMultipleType = CreateAnnotationType(modb, RuntimeManagedJavaType.GenericAttributeAnnotationMultipleTypeName); @@ -91,36 +90,36 @@ internal void Create(ModuleBuilder modb, RuntimeClassLoader loader) internal void Finish(RuntimeClassLoader loader) { - var tb = (TypeBuilder)genericEnumEnumType; + var tb = (TypeBuilder)genericEnumEnumType.AsReflection(); var enumTypeWrapper = loader.LoadClassByName("java.lang.Enum"); enumTypeWrapper.Finish(); - tb.SetParent(enumTypeWrapper.TypeAsBaseType); - var ilgen = context.CodeEmitterFactory.Create(ReflectUtil.DefineConstructor(tb, MethodAttributes.Private, new Type[] { context.Types.String, context.Types.Int32 })); + tb.SetParent(enumTypeWrapper.TypeAsBaseType.AsReflection()); + var ilgen = context.CodeEmitterFactory.Create(ReflectUtil.DefineConstructor(tb, MethodAttributes.Private, [context.Types.String.AsReflection(), context.Types.Int32.AsReflection()])); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ldarg_1); ilgen.Emit(OpCodes.Ldarg_2); enumTypeWrapper.GetMethodWrapper("", "(Ljava.lang.String;I)V", false).EmitCall(ilgen); ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); - genericEnumEnumType = tb.CreateType(); + genericEnumEnumType = context.Resolver.ResolveType(tb.CreateType()); } - private void CreateEnumEnum(ModuleBuilder modb, RuntimeClassLoader loader) + void CreateEnumEnum(ModuleBuilder modb, RuntimeClassLoader loader) { var tb = modb.DefineType(RuntimeManagedJavaType.GenericEnumEnumTypeName, TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.Public); var gtpb = tb.DefineGenericParameters("T")[0]; - gtpb.SetBaseTypeConstraint(context.Types.Enum); - genericEnumEnumType = tb; + gtpb.SetBaseTypeConstraint(context.Types.Enum.AsReflection()); + genericEnumEnumType = context.Resolver.ResolveType(tb); } - private Type CreateAnnotationType(ModuleBuilder modb, string name) + ITypeSymbol CreateAnnotationType(ModuleBuilder modb, string name) { var tb = modb.DefineType(name, TypeAttributes.Interface | TypeAttributes.Abstract | TypeAttributes.Public); - tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.Attribute); - return tb.CreateType(); + tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.Attribute.AsReflection()); + return context.Resolver.ResolveType(tb.CreateType()); } - internal void Load(Assembly assembly) + internal void Load(IAssemblySymbol assembly) { genericEnumEnumType = assembly.GetType(RuntimeManagedJavaType.GenericEnumEnumTypeName); genericDelegateInterfaceType = assembly.GetType(RuntimeManagedJavaType.GenericDelegateInterfaceTypeName); diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index d3251bd5fc..8bbc52ed53 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -134,9 +134,18 @@ internal void AddReference(ImportClassLoader ccl) peerReferences.Add(ccl); } - internal AssemblyName GetAssemblyName() + internal System.Reflection.AssemblyName GetAssemblyName() { - return assemblyBuilder.GetName(); + var src = assemblyBuilder.GetName(); + return new System.Reflection.AssemblyName + { + Name = src.Name, + Version = src.Version, + CultureName = src.CultureName, + HashAlgorithm = (System.Configuration.Assemblies.AssemblyHashAlgorithm)src.HashAlgorithm, + Flags = (System.Reflection.AssemblyNameFlags)src.Flags, + ContentType = (System.Reflection.AssemblyContentType)src.ContentType, + }; } private static PermissionSet Combine(PermissionSet p1, PermissionSet p2) diff --git a/src/IKVM.Tools.Importer/StaticCompiler.cs b/src/IKVM.Tools.Importer/StaticCompiler.cs index 0f45623fc7..f5e3f7cb74 100644 --- a/src/IKVM.Tools.Importer/StaticCompiler.cs +++ b/src/IKVM.Tools.Importer/StaticCompiler.cs @@ -30,6 +30,7 @@ Jeroen Frijters using System.Reflection.PortableExecutable; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; using IKVM.Reflection; using IKVM.Reflection.Diagnostics; using IKVM.Runtime; @@ -204,15 +205,14 @@ internal Type GetType(RuntimeClassLoader loader, string name) internal static void LinkageError(string msg, RuntimeJavaType actualType, RuntimeJavaType expectedType, params object[] values) { - object[] args = new object[values.Length + 2]; + var args = new object[values.Length + 2]; values.CopyTo(args, 2); args[0] = AssemblyQualifiedName(actualType); args[1] = AssemblyQualifiedName(expectedType); - string str = string.Format(msg, args); + + var str = string.Format(msg, args); if (actualType is RuntimeUnloadableJavaType && (expectedType is RuntimeManagedByteCodeJavaType || expectedType is RuntimeManagedJavaType)) - { - str += string.Format("\n\t(Please add a reference to {0})", expectedType.TypeAsBaseType.Assembly.Location); - } + str += string.Format("\n\t(Please add a reference to {0})", expectedType.TypeAsBaseType.Assembly.AsReflection().Location); throw new FatalCompilerErrorException(DiagnosticEvent.LinkageError(str)); } @@ -231,10 +231,10 @@ static string AssemblyQualifiedName(RuntimeJavaType javaType) return javaType.Name + " (unknown assembly)"; } - internal void IssueMissingTypeMessage(Type type) + internal void IssueMissingTypeMessage(ITypeSymbol type) { type = ReflectUtil.GetMissingType(type); - if (type.Assembly.__IsMissing) + if (type.Assembly.IsMissing) diagnostics.MissingReference(type.FullName, type.Assembly.FullName); else diagnostics.MissingType(type.FullName, type.Assembly.FullName); From 947bb0e2d1e18f026be98fb14b8bff72d7b04a52 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 15 Sep 2024 17:44:55 -0500 Subject: [PATCH 03/59] Replace underlying stuff when completing a type. --- .../Reflection/ReflectionSymbolTests.cs | 22 +++ .../AssemblyNameEqualityComparer.cs | 130 ++++++++++++++++++ .../Symbols/Emit/IAssemblySymbolBuilder.cs | 5 + .../Symbols/Emit/IModuleSymbolBuilder.cs | 5 + .../Symbols/Emit/ITypeSymbolBuilder.cs | 2 +- .../Emit/ReflectionAssemblySymbolBuilder.cs | 18 +++ .../Emit/ReflectionModuleSymbolBuilder.cs | 12 ++ .../Emit/ReflectionParameterBuilderInfo.cs | 43 ++++++ .../Emit/ReflectionTypeSymbolBuilder.cs | 16 ++- .../Reflection/ReflectionAssemblySymbol.cs | 48 ++++--- .../Reflection/ReflectionConstructorSymbol.cs | 21 ++- .../Reflection/ReflectionEventSymbol.cs | 12 +- .../Reflection/ReflectionFieldSymbol.cs | 12 +- .../Reflection/ReflectionMemberSymbol.cs | 13 +- .../Reflection/ReflectionMethodBaseSymbol.cs | 16 ++- .../Reflection/ReflectionModuleSymbol.cs | 24 +++- .../Reflection/ReflectionParameterSymbol.cs | 80 +++-------- .../Reflection/ReflectionPropertySymbol.cs | 15 +- .../Reflection/ReflectionSymbolContext.cs | 31 ++++- .../Reflection/ReflectionTypeSymbol.cs | 23 +++- src/IKVM.CoreLib/System/TypeExtensions.cs | 33 +++-- 21 files changed, 475 insertions(+), 106 deletions(-) create mode 100644 src/IKVM.CoreLib/Reflection/AssemblyNameEqualityComparer.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index efbd5e2846..f01a0bf35c 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -382,6 +382,28 @@ public void CanResolveMultipleEventBuilders() event2Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event2)); } + [TestMethod] + public void CanCompleteTypeBuilder() + { + var c = new ReflectionSymbolContext(); + var a = new ReflectionAssemblySymbolBuilder(c, AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect)); + + var moduleBuilder = a.DefineModule("DynamicModule"); + var moduleSymbol = moduleBuilder.Symbol; + + var type1Builder = moduleBuilder.DefineType("DynamicType1"); + var type1Symbol = type1Builder.Symbol; + type1Symbol.Should().BeOfType(); + + type1Builder.Complete(); + var type1SymbolAgain = type1Builder.Symbol; + type1SymbolAgain.Should().BeSameAs(type1Symbol); + type1SymbolAgain.Name.Should().Be("DynamicType1"); + + // check that we can relookup type + moduleSymbol.GetType("DynamicType1").Should().BeSameAs(type1SymbolAgain); + } + [TestMethod] public void CanCreateAndResolveDynamicMethodOnModule() { diff --git a/src/IKVM.CoreLib/Reflection/AssemblyNameEqualityComparer.cs b/src/IKVM.CoreLib/Reflection/AssemblyNameEqualityComparer.cs new file mode 100644 index 0000000000..fe1a16f44e --- /dev/null +++ b/src/IKVM.CoreLib/Reflection/AssemblyNameEqualityComparer.cs @@ -0,0 +1,130 @@ +using System; +using System.Collections.Generic; +using System.Reflection; + +namespace IKVM.CoreLib.Reflection +{ + + class AssemblyNameEqualityComparer : IEqualityComparer + { + + /// + /// Gets the default instance of this comparer. + /// + public static readonly AssemblyNameEqualityComparer Instance = new(); + + /// + /// Initializes a new instance. + /// + public AssemblyNameEqualityComparer() + { + + } + + + /// + public bool Equals(AssemblyName? x, AssemblyName? y) + { + // this expects non-null AssemblyName + if (x == null || y == null) + return false; + + if (ReferenceEquals(x, y)) + return true; + + if (x.Name != null && y.Name != null) + { + if (string.Compare(x.Name, y.Name, StringComparison.OrdinalIgnoreCase) != 0) + return false; + } + else if (!(x.Name == null && y.Name == null)) + { + return false; + } + + if (x.Version != null && y.Version != null) + { + if (x.Version != y.Version) + return false; + } + else if (!(x.Version == null && y.Version == null)) + { + return false; + } + + if (x.CultureInfo != null && y.CultureInfo != null) + { + if (!x.CultureInfo.Equals(y.CultureInfo)) + return false; + } + else if (!(x.CultureInfo == null && y.CultureInfo == null)) + { + return false; + } + + var xArray = x.GetPublicKeyToken(); + var yArray = y.GetPublicKeyToken(); + if (!IsSameKeyToken(xArray, yArray)) + return false; + + return true; + } + + /// + public int GetHashCode(AssemblyName obj) + { + int hashcode = 0; + + if (obj.Name != null) + hashcode ^= obj.Name.GetHashCode(); + + if (obj.Version != null) + hashcode ^= obj.Version.GetHashCode(); + + if (obj.CultureInfo != null) + hashcode ^= obj.CultureInfo.GetHashCode(); + + var objArray = obj.GetPublicKeyToken(); + if (objArray != null) + { + // distinguishing no PKToken from "PKToken = null" which is an array of length=0 + hashcode ^= objArray.Length.GetHashCode() + 1; + if (objArray.Length > 0) + hashcode ^= BitConverter.ToUInt64(objArray, 0).GetHashCode(); + } + + return hashcode; + } + + static bool IsSameKeyToken(byte[]? reqKeyToken, byte[]? curKeyToken) + { + bool isSame = false; + + if (reqKeyToken == null && curKeyToken == null) + { + // Both Key Tokens are not set, treat them as same. + isSame = true; + } + else if (reqKeyToken != null && curKeyToken != null) + { + // Both KeyTokens are set. + if (reqKeyToken.Length == curKeyToken.Length) + { + isSame = true; + for (int i = 0; i < reqKeyToken.Length; i++) + { + if (reqKeyToken[i] != curKeyToken[i]) + { + isSame = false; + break; + } + } + } + } + + return isSame; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs index c89940b3a4..e4d72dc17d 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs @@ -24,6 +24,11 @@ interface IAssemblySymbolBuilder : ISymbolBuilder /// void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + /// + /// Finishes all modules of the assembly, updating the associated symbols. + /// + void Complete(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index 5d059cc092..4ffa0fdb15 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -85,6 +85,11 @@ interface IModuleSymbolBuilder : ISymbolBuilder /// void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + /// + /// Finishes all types of the module, updating the associated symbols. + /// + void Complete(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs index ebe0c59156..7bed9beb7b 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs @@ -319,7 +319,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder /// /// Finishes the type, updating the associated symbol. /// - void Finish(); + void Complete(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index ee8c1f6873..25f8018f33 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -44,6 +44,24 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); } + /// + public void Complete() + { + foreach (var module in _builder.GetModules()) + { + if (module is ModuleBuilder moduleBuilder) + { + moduleBuilder.CreateGlobalFunctions(); + + foreach (var type in moduleBuilder.GetTypes()) + if (type is TypeBuilder typeBuilder) + if (typeBuilder.IsCreated() == false) + if (typeBuilder.CreateType() is { } t) + ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); + } + } + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index 83f3a6ea19..0861c2c9e7 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -81,6 +81,18 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); } + /// + public void Complete() + { + _builder.CreateGlobalFunctions(); + + foreach (var type in _builder.GetTypes()) + if (type is TypeBuilder typeBuilder) + if (typeBuilder.IsCreated() == false) + if (typeBuilder.CreateType() is { } t) + ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs new file mode 100644 index 0000000000..bb28d0082e --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs @@ -0,0 +1,43 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + /// + /// Fake implementation that wraps a , which does not extend . + /// + class ReflectionParameterBuilderInfo : ParameterInfo + { + + readonly ParameterBuilder _builder; + + /// + /// Initialies a new instance. + /// + /// + /// + public ReflectionParameterBuilderInfo(ParameterBuilder builder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + public override ParameterAttributes Attributes => (ParameterAttributes)_builder.Attributes; + + /// + public override MemberInfo Member => _builder.GetMethodBuilder(); + + /// + public override string? Name => _builder.Name; + + /// + public override int Position => _builder.Position; + + /// + public override int MetadataToken => _builder.GetMetadataToken(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 197211f65a..586138398e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -227,10 +227,20 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) } /// - public void Finish() + void Complete(Type type) { - var sym = ReflectionSymbol; - sym.FinishType(_builder.CreateType()); + ReflectionSymbol.Complete(type); + } + + /// + public void Complete() + { + if (_builder.IsCreated() == false) + { + var type = _builder.CreateType(); + if (type != null) + Complete(type); + } } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index 8f51202536..ef66d94d12 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -3,9 +3,11 @@ using System.Diagnostics; using System.Linq; using System.Reflection; -using System.Runtime.CompilerServices; +using System.Threading; -using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Threading; namespace IKVM.CoreLib.Symbols.Reflection { @@ -13,8 +15,10 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionAssemblySymbol : ReflectionSymbol, IAssemblySymbol { - readonly Assembly _assembly; - readonly ConditionalWeakTable _modules = new(); + Assembly _assembly; + + IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); + ReaderWriterLockSlim? _moduleLock; /// /// Initializes a new instance. @@ -40,21 +44,22 @@ internal ReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) if (module is null) throw new ArgumentNullException(nameof(module)); - Debug.Assert(module.Assembly == _assembly); - return _modules.GetValue(module, _ => new ReflectionModuleSymbol(Context, _)); - } + Debug.Assert(AssemblyNameEqualityComparer.Instance.Equals(module.Assembly.GetName(), _assembly.GetName())); - /// - /// Gets or creates the cached for the module. - /// - /// - /// - internal ReflectionModuleSymbol GetOrCreateModuleSymbol(ReflectionModuleSymbolBuilder module) - { - if (module is null) - throw new ArgumentNullException(nameof(module)); + // create lock on demand + if (_moduleLock == null) + lock (this) + _moduleLock ??= new ReaderWriterLockSlim(); - throw new NotImplementedException(); + using (_moduleLock.CreateUpgradeableReadLock()) + { + var row = module.GetMetadataTokenRowNumberSafe(); + if (_moduleSymbols[row] == null) + using (_moduleLock.CreateWriteLock()) + return _moduleSymbols[row] ??= new ReflectionModuleSymbol(Context, this, module); + else + return _moduleSymbols[row] ?? throw new InvalidOperationException(); + } } /// @@ -168,6 +173,15 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return _assembly.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, false); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(Assembly assembly) + { + Context.GetOrCreateAssemblySymbol(_assembly = assembly); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs index aba5e173f4..b4d8759e70 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs @@ -1,4 +1,5 @@ -using System.Reflection; +using System; +using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { @@ -10,17 +11,29 @@ class ReflectionConstructorSymbol : ReflectionMethodBaseSymbol, IConstructorSymb /// Initializes a new instance. /// /// - /// /// /// - public ReflectionConstructorSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, ReflectionTypeSymbol type, ConstructorInfo ctor) : - base(context, module, type, ctor) + public ReflectionConstructorSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, ConstructorInfo ctor) : + base(context, type, ctor) { } + /// + /// Gets the underlying wrapped by this symbol. + /// internal new ConstructorInfo ReflectionObject => (ConstructorInfo)base.ReflectionObject; + + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(ConstructorInfo type) + { + base.Complete(type); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs index 080785635e..81bcd813cb 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs @@ -7,7 +7,7 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionEventSymbol : ReflectionMemberSymbol, IEventSymbol { - readonly EventInfo _event; + EventInfo _event; /// /// Initializes a new instance. @@ -92,6 +92,16 @@ public IMethodSymbol[] GetOtherMethods(bool nonPublic) return ResolveMethodSymbols(_event.GetOtherMethods(nonPublic)); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(EventInfo @event) + { + ResolveEventSymbol(_event = @event); + base.Complete(_event); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index 61bfb54769..ca18fda1ab 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -7,7 +7,7 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionFieldSymbol : ReflectionMemberSymbol, IFieldSymbol { - readonly FieldInfo _field; + FieldInfo _field; /// /// Initializes a new instance. @@ -100,6 +100,16 @@ public ITypeSymbol[] GetRequiredCustomModifiers() return _field.GetRawConstantValue(); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(FieldInfo field) + { + ResolveFieldSymbol(_field = field); + base.Complete(_field); + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index f4bbd6c78a..52b19f9854 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -42,7 +42,7 @@ static T[] Concat(List? list) readonly ReflectionModuleSymbol _containingModule; readonly ReflectionTypeSymbol? _containingType; - readonly MemberInfo _member; + MemberInfo _member; CustomAttribute[]? _customAttributes; CustomAttribute[]? _inheritedCustomAttributes; @@ -252,6 +252,17 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return _member.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + protected void Complete(MemberInfo member) + { + ResolveMemberSymbol(_member = member); + _customAttributes = null; + _inheritedCustomAttributes = null; + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs index 8bd357f1dc..911580f57f 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs @@ -7,7 +7,7 @@ namespace IKVM.CoreLib.Symbols.Reflection abstract class ReflectionMethodBaseSymbol : ReflectionMemberSymbol, IMethodBaseSymbol { - readonly MethodBase _method; + MethodBase _method; /// /// Initializes a new instance. @@ -114,6 +114,20 @@ public IParameterSymbol[] GetParameters() return ResolveParameterSymbols(_method.GetParameters()); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(MethodBase method) + { + ResolveMethodBaseSymbol(_method = method); + base.Complete(_method); + + foreach (var i in _method.GetParameters()) + ResolveParameterSymbol(i).Complete(i); + + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 2f7a1cff79..40e7573443 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -34,7 +34,8 @@ static bool IsTypeDefinition(Type type) const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - readonly Module _module; + readonly ReflectionAssemblySymbol _containingAssembly; + Module _module; IndexRangeDictionary _typeTable = new(maxCapacity: MAX_CAPACITY); IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); @@ -64,14 +65,21 @@ static bool IsTypeDefinition(Type type) /// Initializes a new instance. /// /// + /// /// /// - public ReflectionModuleSymbol(ReflectionSymbolContext context, Module module) : + public ReflectionModuleSymbol(ReflectionSymbolContext context, ReflectionAssemblySymbol containingAssembly, Module module) : base(context) { + _containingAssembly = containingAssembly ?? throw new ArgumentNullException(nameof(containingAssembly)); _module = module ?? throw new ArgumentNullException(nameof(module)); } + /// + /// Gets the which contains the metadata of this member. + /// + internal ReflectionAssemblySymbol ContainingAssembly => _containingAssembly; + /// /// Gets the wrapped . /// @@ -178,7 +186,7 @@ internal ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase metho if (method is null) throw new ArgumentNullException(nameof(method)); - Debug.Assert(method.Module == _module); + Debug.Assert(method.Module.GetMetadataTokenSafe() == _module.GetMetadataTokenSafe()); // create lock on demand if (_methodLock == null) @@ -548,6 +556,16 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return _module.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, false); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(Module module) + { + ResolveModuleSymbol(_module = module); + ContainingAssembly.Complete(_module.Assembly); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index d891bd5488..931bb03ce5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -11,8 +11,7 @@ class ReflectionParameterSymbol : ReflectionSymbol, IParameterSymbol { readonly ReflectionMethodBaseSymbol _containingMethod; - ParameterInfo? _parameter; - ReflectionParameterSymbolBuilder? _builder; + ParameterInfo _parameter; CustomAttribute[]? _customAttributes; @@ -29,76 +28,51 @@ public ReflectionParameterSymbol(ReflectionSymbolContext context, ReflectionMeth _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); } - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionParameterSymbol(ReflectionSymbolContext context, ReflectionMethodBaseSymbol containingMethod, ReflectionParameterSymbolBuilder builder) : - base(context) - { - _containingMethod = containingMethod ?? throw new ArgumentNullException(nameof(containingMethod)); - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - internal ReflectionMethodBaseSymbol ContainingMethod => _containingMethod; /// - public ParameterAttributes Attributes => _parameter is { } p ? p.Attributes : _builder is { } b ? (ParameterAttributes)b.ReflectionBuilder.Attributes : throw new InvalidOperationException(); + public ParameterAttributes Attributes => _parameter.Attributes; /// - public object? DefaultValue => _parameter is { } p ? p.DefaultValue : _builder is { } b ? b.GetConstant() : throw new InvalidOperationException(); + public object? DefaultValue => _parameter.DefaultValue; /// - public bool HasDefaultValue => (Attributes & ParameterAttributes.HasDefault) != 0; + public bool HasDefaultValue => _parameter.HasDefaultValue; /// - public bool IsIn => (Attributes & ParameterAttributes.In) != 0; + public bool IsIn => _parameter.IsIn; /// - public bool IsLcid => (Attributes & ParameterAttributes.Lcid) != 0; + public bool IsLcid => _parameter.IsLcid; /// - public bool IsOptional => (Attributes & ParameterAttributes.Optional) != 0; + public bool IsOptional => _parameter.IsOptional; /// - public bool IsOut => (Attributes & ParameterAttributes.Out) != 0; + public bool IsOut => _parameter.IsOut; /// - public bool IsRetval => (Attributes & ParameterAttributes.Retval) != 0; + public bool IsRetval => _parameter.IsRetval; /// - public IMemberSymbol Member => _parameter is { } p ? ResolveMemberSymbol(p.Member) : _containingMethod; - -#if NETFRAMEWORK + public IMemberSymbol Member => ResolveMemberSymbol(_parameter.Member); /// - public int MetadataToken => _parameter is { } p ? p.MetadataToken : _builder is { } b ? b.ReflectionBuilder.GetToken().Token : throw new InvalidOperationException(); - -#else - - /// - public int MetadataToken => _parameter is { } p ? p.MetadataToken : _builder is { } b ? throw new NotSupportedException() : throw new InvalidOperationException(); - -#endif + public int MetadataToken => _parameter.MetadataToken; /// - public string? Name => _parameter is { } p ? p.Name : _builder is { } b ? b.ReflectionBuilder.Name : throw new InvalidOperationException(); + public string? Name => _parameter.Name; /// - public ITypeSymbol ParameterType => _parameter is { } p ? ResolveTypeSymbol(p.ParameterType) : _builder is { } b ? throw new NotSupportedException() : throw new InvalidOperationException(); + public ITypeSymbol ParameterType => ResolveTypeSymbol(_parameter.ParameterType); /// - public int Position => _parameter is { } p ? p.Position : _builder is { } b ? b.ReflectionBuilder.Position : throw new InvalidOperationException(); + public int Position => _parameter.Position; /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - if (_parameter is not null) - return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); - - throw new NotSupportedException(); + return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); } /// @@ -116,39 +90,29 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - if (_parameter is not null) - return _parameter.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); - - throw new NotSupportedException(); + return _parameter.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); } /// public ITypeSymbol[] GetOptionalCustomModifiers() { - if (_parameter is not null) - return ResolveTypeSymbols(_parameter.GetOptionalCustomModifiers()); - - throw new NotSupportedException(); + return ResolveTypeSymbols(_parameter.GetOptionalCustomModifiers()); } /// public ITypeSymbol[] GetRequiredCustomModifiers() { - if (_parameter is not null) - return ResolveTypeSymbols(_parameter.GetRequiredCustomModifiers()); - - throw new NotSupportedException(); + return ResolveTypeSymbols(_parameter.GetRequiredCustomModifiers()); } /// - /// Finishes the symbol by replacing the builder. + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. /// /// - /// - internal void Finish(ParameterInfo parameter) + internal void Complete(ParameterInfo parameter) { - _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); - _builder = null; + ResolveParameterSymbol(_parameter = parameter); + _customAttributes = null; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs index 8e82493beb..8e39abaeb6 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs @@ -7,7 +7,7 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionPropertySymbol : ReflectionMemberSymbol, IPropertySymbol { - readonly PropertyInfo _property; + PropertyInfo _property; /// /// Initializes a new instance. @@ -16,7 +16,7 @@ class ReflectionPropertySymbol : ReflectionMemberSymbol, IPropertySymbol /// /// public ReflectionPropertySymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, PropertyInfo property) : - base(context, type.ContainingModule, type, property) + base(context, type, property) { _property = property ?? throw new ArgumentNullException(nameof(property)); } @@ -112,6 +112,17 @@ public ITypeSymbol[] GetRequiredCustomModifiers() { return ResolveTypeSymbols(_property.GetRequiredCustomModifiers()); } + + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(PropertyInfo property) + { + ResolvePropertySymbol(_property = property); + base.Complete(_property); + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index 6a65e95473..f4e809e2f3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -1,8 +1,10 @@ using System; +using System.Collections.Concurrent; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection @@ -14,7 +16,8 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionSymbolContext { - readonly ConditionalWeakTable _assemblies = new(); + readonly ConcurrentDictionary> _symbolByName = new(AssemblyNameEqualityComparer.Instance); + readonly ConditionalWeakTable _symbolByAssembly = new(); /// /// Initializes a new instance. @@ -24,6 +27,30 @@ public ReflectionSymbolContext() } + /// + /// Gets or creates a indexed based on the assembly's name. + /// + /// + /// + ReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) + { + var r = _symbolByName.GetOrAdd(assembly.GetName(), _ => new WeakReference(new ReflectionAssemblySymbol(this, assembly))); + + // reference has valid symbol + if (r.TryGetTarget(out var s)) + return s; + + // no valid symbol, must have been released, lock to restore + lock (r) + { + // still gone, recreate + if (r.TryGetTarget(out s) == false) + r.SetTarget(s = new ReflectionAssemblySymbol(this, assembly)); + + return s; + } + } + /// /// Gets or creates a for the specified . /// @@ -31,7 +58,7 @@ public ReflectionSymbolContext() /// public ReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) { - return _assemblies.GetValue(assembly, _ => new ReflectionAssemblySymbol(this, _)); + return _symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index b49dbe0287..652a3c8fce 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -692,10 +692,27 @@ public ITypeSymbol MakePointerType() /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. /// /// - /// - internal void FinishType(Type type) + internal void Complete(Type type) { - _type = type; + ResolveTypeSymbol(_type = type); + base.Complete(_type); + + ContainingModule.Complete(_type.Module); + + foreach (var i in _type.GetConstructors(DefaultBindingFlags)) + ResolveConstructorSymbol(i).Complete(i); + + foreach (var i in _type.GetMethods(DefaultBindingFlags)) + ResolveMethodSymbol(i).Complete(i); + + foreach (var i in _type.GetFields(DefaultBindingFlags)) + ResolveFieldSymbol(i).Complete(i); + + foreach (var i in _type.GetProperties(DefaultBindingFlags)) + ResolvePropertySymbol(i).Complete(i); + + foreach (var i in _type.GetEvents(DefaultBindingFlags)) + ResolveEventSymbol(i).Complete(i); } } diff --git a/src/IKVM.CoreLib/System/TypeExtensions.cs b/src/IKVM.CoreLib/System/TypeExtensions.cs index 1abd007c2b..ea2a69932b 100644 --- a/src/IKVM.CoreLib/System/TypeExtensions.cs +++ b/src/IKVM.CoreLib/System/TypeExtensions.cs @@ -3,8 +3,6 @@ using System.Reflection.Emit; using System.Reflection.Metadata.Ecma335; -using IKVM.CoreLib.Symbols.Reflection.Emit; - namespace System { @@ -94,6 +92,30 @@ static class TypeExtensions _eventBuilderParameter) .Compile(); + /// + /// Gets the metadata token for the specified . + /// + /// + /// + public static int GetMetadataTokenSafe(this Module module) + { + var t = module.MetadataToken; + if (t == 0) + throw new InvalidOperationException(); + + return t; + } + + /// + /// Gets the metadata row number for the specified . + /// + /// + /// + public static int GetMetadataTokenRowNumberSafe(this Module module) + { + return MetadataTokens.GetRowNumber(MetadataTokens.EntityHandle(module.GetMetadataTokenSafe())); + } + /// /// Gets the metadata token for the specified . /// @@ -292,13 +314,6 @@ public static int GetMetadataTokenRowNumberSafe(this PropertyInfo property) /// public static int GetMetadataTokenSafe(this EventInfo @event) { - if (@event is ReflectionEventBuilderInfo b) - { - var t = b.GetMetadataToken(); - if (t == 0) - throw new InvalidOperationException(); - } - return @event.GetMetadataToken(); } From 635ca5fc8c5d674dd18fd965a1fcb13d7f82dbf2 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 15 Sep 2024 22:59:54 -0500 Subject: [PATCH 04/59] Fixes. --- .../Reflection/ReflectionSymbolTests.cs | 16 + .../Symbols/Emit/IAssemblySymbolBuilder.cs | 21 +- .../Symbols/Emit/IConstructorSymbolBuilder.cs | 12 +- src/IKVM.CoreLib/Symbols/ITypeSymbol.cs | 54 ++ .../IkvmReflectionAssemblySymbolBuilder.cs | 79 +++ .../IkvmReflectionConstructorSymbolBuilder.cs | 74 +++ .../IkvmReflectionCustomAttributeBuilder.cs | 29 + .../Emit/IkvmReflectionEventSymbolBuilder.cs | 70 +++ .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 88 +++ .../IkvmReflectionMethodBaseSymbolBuilder.cs | 49 ++ .../Emit/IkvmReflectionMethodSymbolBuilder.cs | 107 ++++ .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 98 +++ .../IkvmReflectionParameterBuilderInfo.cs | 68 +++ .../IkvmReflectionParameterSymbolBuilder.cs | 106 ++++ .../IkvmReflectionAssemblySymbol.cs | 81 +-- .../IkvmReflectionConstructorSymbol.cs | 17 +- .../IkvmReflectionEventSymbol.cs | 53 +- .../IkvmReflectionFieldSymbol.cs | 58 +- .../IkvmReflectionMemberSymbol.cs | 102 ++-- .../IkvmReflectionMethodBaseSymbol.cs | 78 +-- .../IkvmReflectionMethodSymbol.cs | 94 +-- .../IkvmReflectionModuleSymbol.cs | 383 +++++++++--- .../IkvmReflectionParameterSymbol.cs | 22 +- .../IkvmReflectionPropertySymbol.cs | 50 +- .../IkvmReflection/IkvmReflectionSymbol.cs | 118 ++-- .../IkvmReflectionSymbolContext.cs | 97 +-- .../IkvmReflectionTypeSymbol.cs | 558 ++++-------------- .../IkvmReflection/IkvmReflectionUtil.cs | 195 ++++++ .../Emit/ReflectionAssemblySymbolBuilder.cs | 20 + .../ReflectionConstructorSymbolBuilder.cs | 4 +- .../Reflection/ReflectionMethodSymbol.cs | 89 +-- .../Reflection/ReflectionModuleSymbol.cs | 73 ++- .../Symbols/Reflection/ReflectionSymbol.cs | 14 + .../Reflection/ReflectionTypeSymbol.cs | 138 ++--- .../Symbols/TypeSymbolListEqualityComparer.cs | 49 ++ src/IKVM.Reflection/BuiltinArrayMethod.cs | 2 +- src/IKVM.Reflection/Emit/MethodBuilder.cs | 2 +- src/IKVM.Reflection/Emit/ParameterBuilder.cs | 1 - .../GenericParameterInfoImpl.cs | 2 +- src/IKVM.Reflection/MissingMethod.cs | 2 +- src/IKVM.Reflection/ParameterInfo.cs | 6 +- src/IKVM.Reflection/PropertyInfo.cs | 2 +- .../Reader/ParameterInfoImpl.cs | 2 +- src/IKVM.Reflection/Type.cs | 15 + 44 files changed, 2098 insertions(+), 1100 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index f01a0bf35c..c275119379 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -1,4 +1,5 @@ using System; +using System.Linq; using System.Reflection; using System.Reflection.Emit; @@ -145,6 +146,21 @@ public void CanResolveMethod() m.IsPrivate.Should().BeFalse(); } + [TestMethod] + public void CanResolveGenericMethod() + { + var c = new ReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(typeof(ValueTuple)); + var m = s.GetMethods().FirstOrDefault(i => i.Name == "Create" && i.GetGenericArguments().Length == 1); + m.Name.Should().Be("Create"); + m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(ValueTuple<>)).MakeGenericType(m.GetGenericArguments()[0])); + m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(ValueTuple<>)).MakeGenericType(m.GetGenericArguments()[0])); + m.IsGenericMethod.Should().BeTrue(); + m.IsGenericMethodDefinition.Should().BeTrue(); + m.IsPublic.Should().BeTrue(); + m.IsPrivate.Should().BeFalse(); + } + [TestMethod] public void CanResolveParameters() { diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs index e4d72dc17d..1bac977b72 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs @@ -1,4 +1,6 @@ -namespace IKVM.CoreLib.Symbols.Emit +using System.Xml.Linq; + +namespace IKVM.CoreLib.Symbols.Emit { interface IAssemblySymbolBuilder : ISymbolBuilder @@ -11,6 +13,23 @@ interface IAssemblySymbolBuilder : ISymbolBuilder /// IModuleSymbolBuilder DefineModule(string name); + /// + /// Defines a named module in this assembly. + /// + /// + /// + /// + IModuleSymbolBuilder DefineModule(string name, string fileName); + + /// + /// Defines a named module in this assembly. + /// + /// + /// + /// + /// + IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo); + /// /// Set a custom attribute using a custom attribute builder. /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs index 72d628579c..e98f8e7708 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs @@ -1,4 +1,6 @@ -namespace IKVM.CoreLib.Symbols.Emit +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit { interface IConstructorSymbolBuilder : ISymbolBuilder @@ -8,7 +10,7 @@ interface IConstructorSymbolBuilder : ISymbolBuilder /// Sets the method implementation flags for this constructor. /// /// - void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes); + void SetImplementationFlags(MethodImplAttributes attributes); /// /// Defines a parameter of this constructor. @@ -17,20 +19,20 @@ interface IConstructorSymbolBuilder : ISymbolBuilder /// /// /// - IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection.ParameterAttributes attributes, string? strParamName); + IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName); /// /// Gets an ILGenerator object, with the specified MSIL stream size, that can be used to build a method body for this constructor. /// /// /// - System.Reflection.Emit.ILGenerator GetILGenerator(int streamSize); + IILGenerator GetILGenerator(int streamSize); /// /// Gets an ILGenerator for this constructor. /// /// - System.Reflection.Emit.ILGenerator GetILGenerator(); + IILGenerator GetILGenerator(); /// /// Set a custom attribute using a custom attribute builder. diff --git a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs index 0df2185f3e..21926c44b1 100644 --- a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs @@ -453,6 +453,60 @@ interface ITypeSymbol : IMemberSymbol /// IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types); + /// + /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints and the specified calling convention. + /// + /// + /// + /// + /// + /// + /// + IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers); + + /// + /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints and the specified calling convention. + /// + /// + /// + /// + /// + /// + /// + /// + IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers); + + /// + /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints. + /// + /// + /// + /// + /// + /// + /// + IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers); + + /// + /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints. + /// + /// + /// + /// + /// + /// + IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers); + + /// + /// Searches for the specified public method whose parameters match the specified generic parameter count, argument types and modifiers. + /// + /// + /// + /// + /// + /// + IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers); + /// /// Returns all the public methods of the current . /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs new file mode 100644 index 0000000000..ccb5a77f4b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -0,0 +1,79 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionAssemblySymbolBuilder : IkvmReflectionSymbolBuilder, IAssemblySymbolBuilder + { + + readonly AssemblyBuilder _builder; + IkvmReflectionAssemblySymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + public IkvmReflectionAssemblySymbolBuilder(IkvmReflectionSymbolContext context, AssemblyBuilder builder) : + base(context) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + internal sealed override IkvmReflectionAssemblySymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateAssemblySymbol(_builder); + + /// + public IModuleSymbolBuilder DefineModule(string name) + { + return new IkvmReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, name + ".dll")); + } + + /// + public IModuleSymbolBuilder DefineModule(string name, string fileName) + { + return new IkvmReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName)); + } + + /// + public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo) + { + return new IkvmReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName, emitSymbolInfo)); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + /// + public void Complete() + { + foreach (var module in _builder.GetModules()) + { + if (module is ModuleBuilder moduleBuilder) + { + moduleBuilder.CreateGlobalFunctions(); + + foreach (var type in moduleBuilder.GetTypes()) + if (type is TypeBuilder typeBuilder) + if (typeBuilder.IsCreated() == false) + if (typeBuilder.CreateType() is { } t) + ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); + } + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs new file mode 100644 index 0000000000..2d0fc2e7cc --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs @@ -0,0 +1,74 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionConstructorSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder + { + + readonly ConstructorBuilder _builder; + IkvmReflectionConstructorSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionConstructorSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, ConstructorBuilder builder) : + base(context, containingTypeBuilder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the containing . + /// + protected internal new IkvmReflectionTypeSymbolBuilder ContainingTypeBuilder => base.ContainingTypeBuilder ?? throw new NullReferenceException(); + + /// + internal override IkvmReflectionConstructorSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateConstructorSymbol(_builder); + + /// + public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + { + _builder.SetImplementationFlags((MethodImplAttributes)attributes); + } + + /// + public IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection.ParameterAttributes attributes, string? strParamName) + { + return new IkvmReflectionParameterSymbolBuilder(Context, this, _builder, _builder.DefineParameter(iSequence, (ParameterAttributes)attributes, strParamName)); + } + + /// + public IILGenerator GetILGenerator() + { + throw new NotImplementedException(); + } + + /// + public IILGenerator GetILGenerator(int streamSize) + { + throw new NotImplementedException(); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs new file mode 100644 index 0000000000..39adf50404 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs @@ -0,0 +1,29 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionCustomAttributeBuilder : ICustomAttributeBuilder + { + + readonly CustomAttributeBuilder _builder; + + /// + /// Initializes a new instance. + /// + public IkvmReflectionCustomAttributeBuilder(CustomAttributeBuilder builder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the underlying reflection . + /// + internal CustomAttributeBuilder ReflectionBuilder => _builder; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs new file mode 100644 index 0000000000..c1b5800558 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs @@ -0,0 +1,70 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionEventSymbolBuilder : IkvmReflectionSymbolBuilder, IEventSymbolBuilder + { + + readonly IkvmReflectionTypeSymbolBuilder _containingTypeBuilder; + readonly EventBuilder _builder; + IkvmReflectionEventSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionEventSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, EventBuilder builder) : + base(context) + { + _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + internal override IkvmReflectionEventSymbol ReflectionSymbol => _symbol ??= _containingTypeBuilder.ReflectionSymbol.ResolveEventSymbol(_builder); + + /// + public void SetAddOnMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.SetAddOnMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void SetRemoveOnMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.SetRemoveOnMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void SetRaiseMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.SetRaiseMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) + { + _builder.AddOtherMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs new file mode 100644 index 0000000000..75d2bc47cc --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs @@ -0,0 +1,88 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionFieldSymbolBuilder : IkvmReflectionSymbolBuilder, IFieldSymbolBuilder + { + + readonly IkvmReflectionModuleSymbolBuilder _containingModuleBuilder; + readonly IkvmReflectionTypeSymbolBuilder? _containingTypeBuilder; + readonly FieldBuilder _builder; + IkvmReflectionFieldSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbolBuilder containingModuleBuilder, FieldBuilder builder) : + base(context) + { + _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, FieldBuilder builder) : + base(context) + { + _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); + _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the containing . + /// + internal IkvmReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; + + /// + /// Gets the containing . + /// + internal IkvmReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; + + /// + /// Gets the underlying + /// + internal FieldBuilder ReflectionBuilder => _builder; + + /// + internal override IkvmReflectionFieldSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateFieldSymbol(_builder); + + /// + public void SetConstant(object? defaultValue) + { + _builder.SetConstant(defaultValue); + } + + /// + public void SetOffset(int iOffset) + { + _builder.SetOffset(iOffset); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs new file mode 100644 index 0000000000..1fe558174a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs @@ -0,0 +1,49 @@ +using System; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + abstract class IkvmReflectionMethodBaseSymbolBuilder : IkvmReflectionSymbolBuilder + where TSymbol : ISymbol + where TReflectionSymbol : IkvmReflectionSymbol, TSymbol + { + + readonly IkvmReflectionModuleSymbolBuilder _containingModuleBuilder; + readonly IkvmReflectionTypeSymbolBuilder? _containingTypeBuilder; + + /// + /// Initializes a new instance. + /// + /// + /// + protected IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder) : + base(context) + { + _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); + _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; + } + + /// + /// Initializes a new instance. + /// + /// + /// + protected IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbolBuilder containingModuleBuilder) : + base(context) + { + _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); + } + + /// + /// Gets the containing . + /// + protected internal IkvmReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; + + /// + /// Gets the containing . + /// + protected internal IkvmReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs new file mode 100644 index 0000000000..e01792a357 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs @@ -0,0 +1,107 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionMethodSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder + { + + readonly MethodBuilder _builder; + IkvmReflectionMethodSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbolBuilder containingModuleBuilder, MethodBuilder builder) : + base(context, containingModuleBuilder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, MethodBuilder builder) : + base(context, containingTypeBuilder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the that underlies this instance. + /// + internal MethodBuilder ReflectionBuilder => _builder; + + /// + internal override IkvmReflectionMethodSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateMethodSymbol(_builder); + + /// + public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + { + _builder.SetImplementationFlags((MethodImplAttributes)attributes); + } + + /// + public void SetParameters(params ITypeSymbol[] parameterTypes) + { + _builder.SetParameters(parameterTypes.Unpack()); + } + + /// + public void SetReturnType(ITypeSymbol? returnType) + { + _builder.SetReturnType(returnType?.Unpack()); + } + + /// + public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + _builder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); + } + + public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) + { + throw new NotImplementedException(); + } + + /// + public IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) + { + return new IkvmReflectionParameterSymbolBuilder(Context, this, _builder, _builder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); + } + + public IILGenerator GetILGenerator() + { + throw new NotImplementedException(); + } + + public IILGenerator GetILGenerator(int size) + { + throw new NotImplementedException(); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs new file mode 100644 index 0000000000..6064c7e88f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -0,0 +1,98 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionModuleSymbolBuilder : IkvmReflectionSymbolBuilder, IModuleSymbolBuilder + { + + readonly ModuleBuilder _builder; + IkvmReflectionModuleSymbol? _symbol; + + /// + /// Initializes a new instance. + /// + /// + /// + public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, ModuleBuilder builder) : + base(context) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + internal override IkvmReflectionModuleSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateModuleSymbol(_builder); + + /// + public ITypeSymbolBuilder DefineType(string name) + { + return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typesize) + { + return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), typesize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent) + { + return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr) + { + return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packsize) + { + return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packsize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packingSize, int typesize) + { + return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packingSize, typesize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) + { + return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), interfaces?.Unpack())); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + /// + public void Complete() + { + _builder.CreateGlobalFunctions(); + + foreach (var type in _builder.GetTypes()) + if (type is TypeBuilder typeBuilder) + if (typeBuilder.IsCreated() == false) + if (typeBuilder.CreateType() is { } t) + ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs new file mode 100644 index 0000000000..66e07f7e08 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs @@ -0,0 +1,68 @@ +using System; + +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + /// + /// Fake implementation that wraps a , which does not extend . + /// + class IkvmReflectionParameterBuilderInfo : ParameterInfo + { + + readonly MemberInfo _member; + readonly ParameterBuilder _parameter; + + /// + /// Initialies a new instance. + /// + /// + /// + /// + public IkvmReflectionParameterBuilderInfo(MemberInfo member, ParameterBuilder parameter) + { + _member = member ?? throw new ArgumentNullException(nameof(member)); + _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); + } + + /// + public override ParameterAttributes Attributes => (ParameterAttributes)_parameter.Attributes; + + /// + public override Module Module => _member.Module; + + /// + public override MemberInfo Member => _member; + + /// + public override string? Name => _parameter.Name; + + /// + public override int Position => _parameter.Position; + + /// + public override int MetadataToken => throw new NotImplementedException(); + + /// + public override Type ParameterType => throw new NotImplementedException(); + + /// + public override object RawDefaultValue => throw new NotImplementedException(); + + public override CustomModifiers __GetCustomModifiers() + { + throw new NotSupportedException(); + } + + public override bool __TryGetFieldMarshal(out FieldMarshal fieldMarshal) + { + throw new NotSupportedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs new file mode 100644 index 0000000000..21ba94fa2e --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs @@ -0,0 +1,106 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + abstract class IkvmReflectionParameterSymbolBuilder : IkvmReflectionSymbolBuilder, IParameterSymbolBuilder + { + + readonly MemberInfo _member; + readonly ParameterBuilder _builder; + readonly IkvmReflectionParameterBuilderInfo _info; + IkvmReflectionParameterSymbol? _symbol; + + object? _constant; + + /// + /// Initializes a new instance. + /// + /// + protected IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, MemberInfo member, ParameterBuilder builder) : + base(context) + { + _member = member ?? throw new ArgumentNullException(nameof(member)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _info = new IkvmReflectionParameterBuilderInfo(_member, _builder); + } + + /// + /// Gets the wrapped . + /// + internal ParameterBuilder ReflectionBuilder => _builder; + + /// + internal override IkvmReflectionParameterSymbol ReflectionSymbol => _symbol ??= GetOrCreateSymbol(_info); + + /// + /// Gets or creates the . + /// + /// + protected internal abstract IkvmReflectionParameterSymbol GetOrCreateSymbol(IkvmReflectionParameterBuilderInfo info); + + /// + public void SetConstant(object? defaultValue) + { + _builder.SetConstant(_constant = defaultValue); + } + + /// + /// Saves the constant value so it can be retrieved as a symbol. + /// + /// + internal object? GetConstant() + { + return _constant; + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + } + + } + + class IkvmReflectionParameterSymbolBuilder : IkvmReflectionParameterSymbolBuilder + where TContainingSymbol : IMethodBaseSymbol + where TContainingReflectionSymbol : IkvmReflectionMethodBaseSymbol, TContainingSymbol + where TContainingBuilder : IkvmReflectionMethodBaseSymbolBuilder + { + + readonly TContainingBuilder _containingMethodBuilder; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, TContainingBuilder containingMethodBuilder, MemberInfo member, ParameterBuilder builder) : + base(context, member, builder) + { + _containingMethodBuilder = containingMethodBuilder ?? throw new ArgumentNullException(nameof(containingMethodBuilder)); + } + + /// + /// Gets the containing . + /// + internal TContainingBuilder ContainingMethodBuilder => _containingMethodBuilder; + + /// + protected internal override IkvmReflectionParameterSymbol GetOrCreateSymbol(IkvmReflectionParameterBuilderInfo info) => ContainingMethodBuilder.ReflectionSymbol.ResolveParameterSymbol(info); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 19b75b9931..50bb64af92 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -2,10 +2,14 @@ using System.Collections.Generic; using System.Diagnostics; using System.Linq; -using System.Runtime.CompilerServices; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Threading; using Assembly = IKVM.Reflection.Assembly; -using AssemblyName = IKVM.Reflection.AssemblyName; using Module = IKVM.Reflection.Module; using Type = IKVM.Reflection.Type; @@ -15,11 +19,12 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionAssemblySymbol : IkvmReflectionSymbol, IAssemblySymbol { - readonly Assembly _assembly; - readonly ConditionalWeakTable _modules = new(); - + Assembly _assembly; System.Reflection.AssemblyName? _assemblyName; + IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); + ReaderWriterLockSlim? _moduleLock; + /// /// Initializes a new instance. /// @@ -31,6 +36,8 @@ public IkvmReflectionAssemblySymbol(IkvmReflectionSymbolContext context, Assembl _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); } + internal Assembly ReflectionObject => _assembly; + /// /// Gets or creates the cached for the module. /// @@ -39,14 +46,26 @@ public IkvmReflectionAssemblySymbol(IkvmReflectionSymbolContext context, Assembl /// internal IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) { - Debug.Assert(module.Assembly == _assembly); - return _modules.GetValue(module, _ => new IkvmReflectionModuleSymbol(Context, _)); - } + if (module is null) + throw new ArgumentNullException(nameof(module)); - /// - /// Gets the wrapped . - /// - internal Assembly ReflectionObject => _assembly; + Debug.Assert(AssemblyNameEqualityComparer.Instance.Equals(module.Assembly.GetName().ToAssemblyName(), _assembly.GetName().ToAssemblyName())); + + // create lock on demand + if (_moduleLock == null) + lock (this) + _moduleLock ??= new ReaderWriterLockSlim(); + + using (_moduleLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.ModuleReferenceHandle(module.MetadataToken)); + if (_moduleSymbols[row] == null) + using (_moduleLock.CreateWriteLock()) + return _moduleSymbols[row] ??= new IkvmReflectionModuleSymbol(Context, this, module); + else + return _moduleSymbols[row] ?? throw new InvalidOperationException(); + } + } /// public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); @@ -69,12 +88,6 @@ internal IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) /// public IEnumerable Modules => ResolveModuleSymbols(_assembly.Modules); - /// - public override bool IsMissing => _assembly.__IsMissing; - - /// - public override bool ContainsMissing => GetModules().Any(i => i.IsMissing || i.ContainsMissing); - /// public ITypeSymbol[] GetExportedTypes() { @@ -99,31 +112,16 @@ public IModuleSymbol[] GetModules(bool getResourceModules) return ResolveModuleSymbols(_assembly.GetModules(getResourceModules)); } - System.Reflection.AssemblyName ToName(AssemblyName src) - { -#pragma warning disable SYSLIB0037 // Type or member is obsolete - return new System.Reflection.AssemblyName() - { - Name = src.Name, - Version = src.Version, - CultureName = src.CultureName, - HashAlgorithm = (System.Configuration.Assemblies.AssemblyHashAlgorithm)src.HashAlgorithm, - Flags = (System.Reflection.AssemblyNameFlags)src.Flags, - ContentType = (System.Reflection.AssemblyContentType)src.ContentType, - }; -#pragma warning restore SYSLIB0037 // Type or member is obsolete - } - /// public System.Reflection.AssemblyName GetName() { - return _assemblyName ??= ToName(_assembly.GetName()); + return _assemblyName ??= _assembly.GetName().ToAssemblyName(); } /// public System.Reflection.AssemblyName GetName(bool copiedName) { - return ToName(_assembly.GetName()); + return _assembly.GetName().ToAssemblyName(); } /// @@ -132,7 +130,7 @@ public System.Reflection.AssemblyName[] GetReferencedAssemblies() var l = _assembly.GetReferencedAssemblies(); var a = new System.Reflection.AssemblyName[l.Length]; for (int i = 0; i < l.Length; i++) - a[i] = ToName(l[i]); + a[i] = l[i].ToAssemblyName(); return a; } @@ -170,7 +168,7 @@ public CustomAttribute[] GetCustomAttributes(bool inherit = false) /// public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_assembly.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false)); + return ResolveCustomAttributes(_assembly.GetCustomAttributesData().Where(i => i.AttributeType == ((IkvmReflectionTypeSymbol)attributeType).ReflectionObject)); } /// @@ -185,6 +183,15 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return _assembly.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(Assembly assembly) + { + Context.GetOrCreateAssemblySymbol(_assembly = assembly); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs index 4a312beb3f..a991bdfa5a 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs @@ -10,17 +10,28 @@ class IkvmReflectionConstructorSymbol : IkvmReflectionMethodBaseSymbol, IConstru /// Initializes a new instance. /// /// - /// /// /// - public IkvmReflectionConstructorSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, IkvmReflectionTypeSymbol type, ConstructorInfo ctor) : - base(context, module, type, ctor) + public IkvmReflectionConstructorSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, ConstructorInfo ctor) : + base(context, type, ctor) { } + /// + /// Gets the underlying wrapped by this symbol. + /// internal new ConstructorInfo ReflectionObject => (ConstructorInfo)base.ReflectionObject; + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(ConstructorInfo type) + { + base.Complete(type); + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs index 6ba509c128..f3e8e95465 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs @@ -8,7 +8,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionEventSymbol : IkvmReflectionMemberSymbol, IEventSymbol { - readonly EventInfo _event; + EventInfo _event; /// /// Initializes a new instance. @@ -17,61 +17,90 @@ class IkvmReflectionEventSymbol : IkvmReflectionMemberSymbol, IEventSymbol /// /// public IkvmReflectionEventSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, EventInfo @event) : - base(context, type.ContainingModule, type, @event) + base(context, type, @event) { _event = @event ?? throw new ArgumentNullException(nameof(@event)); } - public IMethodSymbol? AddMethod => _event.AddMethod is { } m ? ResolveMethodSymbol(m) : null; + /// + /// Gets the underlying wrapped by this symbol. + /// + internal new EventInfo ReflectionObject => _event; + /// public System.Reflection.EventAttributes Attributes => (System.Reflection.EventAttributes)_event.Attributes; + /// public ITypeSymbol? EventHandlerType => _event.EventHandlerType is { } m ? ResolveTypeSymbol(m) : null; + /// public bool IsSpecialName => _event.IsSpecialName; - public IMethodSymbol? RaiseMethod => _event.RaiseMethod is { } m ? ResolveMethodSymbol(m) : null; + /// + public IMethodSymbol? AddMethod => _event.AddMethod is { } m ? ResolveMethodSymbol(m) : null; + /// public IMethodSymbol? RemoveMethod => _event.RemoveMethod is { } m ? ResolveMethodSymbol(m) : null; + /// + public IMethodSymbol? RaiseMethod => _event.RaiseMethod is { } m ? ResolveMethodSymbol(m) : null; + + /// public IMethodSymbol? GetAddMethod() { return _event.GetAddMethod() is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetAddMethod(bool nonPublic) { return _event.GetAddMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; } - public IMethodSymbol[] GetOtherMethods() + /// + public IMethodSymbol? GetRemoveMethod() { - return ResolveMethodSymbols(_event.GetOtherMethods()); + return _event.GetRemoveMethod() is { } m ? ResolveMethodSymbol(m) : null; } - public IMethodSymbol[] GetOtherMethods(bool nonPublic) + /// + public IMethodSymbol? GetRemoveMethod(bool nonPublic) { - return ResolveMethodSymbols(_event.GetOtherMethods(nonPublic)); + return _event.GetRemoveMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetRaiseMethod() { return _event.GetRaiseMethod() is { } m ? ResolveMethodSymbol(m) : null; } + /// public IMethodSymbol? GetRaiseMethod(bool nonPublic) { return _event.GetRaiseMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; } - public IMethodSymbol? GetRemoveMethod(bool nonPublic) + /// + public IMethodSymbol[] GetOtherMethods() { - return _event.GetRemoveMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbols(_event.GetOtherMethods()); } - public IMethodSymbol? GetRemoveMethod() + /// + public IMethodSymbol[] GetOtherMethods(bool nonPublic) { - return _event.GetRemoveMethod() is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbols(_event.GetOtherMethods(nonPublic)); + } + + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(EventInfo @event) + { + ResolveEventSymbol(_event = @event); + base.Complete(_event); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs index 2696069963..4e9448e3ed 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs @@ -8,65 +8,107 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionFieldSymbol : IkvmReflectionMemberSymbol, IFieldSymbol { - readonly FieldInfo _field; + FieldInfo _field; /// /// Initializes a new instance. /// /// - /// + /// /// - public IkvmReflectionFieldSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, FieldInfo field) : - base(context, type.ContainingModule, type, field) + public IkvmReflectionFieldSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol containingModule, FieldInfo field) : + base(context, containingModule, field) { _field = field ?? throw new ArgumentNullException(nameof(field)); } + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionFieldSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol containingType, FieldInfo field) : + base(context, containingType, field) + { + _field = field ?? throw new ArgumentNullException(nameof(field)); + } + + /// + /// Gets the underlying wrapped by this symbol. + /// internal new FieldInfo ReflectionObject => (FieldInfo)base.ReflectionObject; + /// public System.Reflection.FieldAttributes Attributes => (System.Reflection.FieldAttributes)_field.Attributes; + /// public ITypeSymbol FieldType => ResolveTypeSymbol(_field.FieldType); + /// + public bool IsSpecialName => _field.IsSpecialName; + + /// public bool IsAssembly => _field.IsAssembly; + /// public bool IsFamily => _field.IsFamily; + /// public bool IsFamilyAndAssembly => _field.IsFamilyAndAssembly; + /// public bool IsFamilyOrAssembly => _field.IsFamilyOrAssembly; + /// public bool IsInitOnly => _field.IsInitOnly; + /// public bool IsLiteral => _field.IsLiteral; #pragma warning disable SYSLIB0050 // Type or member is obsolete + /// public bool IsNotSerialized => _field.IsNotSerialized; #pragma warning restore SYSLIB0050 // Type or member is obsolete + /// public bool IsPinvokeImpl => _field.IsPinvokeImpl; + /// public bool IsPrivate => _field.IsPrivate; + /// public bool IsPublic => _field.IsPublic; - public bool IsSpecialName => _field.IsSpecialName; - + /// public bool IsStatic => _field.IsStatic; + /// public ITypeSymbol[] GetOptionalCustomModifiers() { return ResolveTypeSymbols(_field.GetOptionalCustomModifiers()); } + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(_field.GetRequiredCustomModifiers()); + } + + /// public object? GetRawConstantValue() { return _field.GetRawConstantValue(); } - public ITypeSymbol[] GetRequiredCustomModifiers() + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(FieldInfo field) { - return ResolveTypeSymbols(_field.GetRequiredCustomModifiers()); + ResolveFieldSymbol(_field = field); + base.Complete(_field); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index c01581bda7..654f928055 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -13,6 +13,9 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection { + /// + /// Obtains information about the attributes of a member and provides access to member metadata. + /// abstract class IkvmReflectionMemberSymbol : IkvmReflectionSymbol, IMemberSymbol { @@ -44,9 +47,9 @@ static T[] Concat(List? list) return a; } - readonly IkvmReflectionModuleSymbol _module; - readonly IkvmReflectionTypeSymbol? _type; - readonly MemberInfo _member; + readonly IkvmReflectionModuleSymbol _containingModule; + readonly IkvmReflectionTypeSymbol? _containingType; + MemberInfo _member; CustomAttribute[]? _customAttributes; CustomAttribute[]? _inheritedCustomAttributes; @@ -55,17 +58,27 @@ static T[] Concat(List? list) /// Initializes a new instance. /// /// - /// - /// + /// /// - public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, IkvmReflectionTypeSymbol? type, MemberInfo member) : + public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol containingModule, MemberInfo member) : base(context) { - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type; + _containingModule = containingModule ?? throw new ArgumentNullException(nameof(containingModule)); _member = member ?? throw new ArgumentNullException(nameof(member)); } + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol containingType, MemberInfo member) : + this(context, containingType.ContainingModule, member) + { + _containingType = containingType ?? throw new ArgumentNullException(nameof(containingType)); + } + /// /// Resolves the symbol for the specified type. /// @@ -73,10 +86,10 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IkvmRefle /// protected internal override IkvmReflectionTypeSymbol ResolveTypeSymbol(Type type) { - if (_type != null && type == _type.ReflectionObject) - return _type; + if (_containingType != null && type == _containingType.ReflectionObject) + return _containingType; else if (type.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(type); + return _containingModule.GetOrCreateTypeSymbol(type); else return base.ResolveTypeSymbol(type); } @@ -88,10 +101,8 @@ protected internal override IkvmReflectionTypeSymbol ResolveTypeSymbol(Type type /// protected internal override IkvmReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) { - if (_type != null && ctor.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateConstructorSymbol(ctor); - else if (ctor.DeclaringType != null && ctor.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(ctor.DeclaringType).GetOrCreateConstructorSymbol(ctor); + if (ctor.Module == _member.Module) + return _containingModule.GetOrCreateConstructorSymbol(ctor); else return base.ResolveConstructorSymbol(ctor); } @@ -103,10 +114,8 @@ protected internal override IkvmReflectionConstructorSymbol ResolveConstructorSy /// protected internal override IkvmReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) { - if (_type != null && method.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateMethodSymbol(method); - else if (method.DeclaringType != null && method.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(method.DeclaringType).GetOrCreateMethodSymbol(method); + if (method.Module == _member.Module) + return _containingModule.GetOrCreateMethodSymbol(method); else return base.ResolveMethodSymbol(method); } @@ -118,10 +127,8 @@ protected internal override IkvmReflectionMethodSymbol ResolveMethodSymbol(Metho /// protected internal override IkvmReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) { - if (_type != null && field.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateFieldSymbol(field); - else if (field.DeclaringType != null && field.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(field.DeclaringType).GetOrCreateFieldSymbol(field); + if (field.Module == _member.Module) + return _containingModule.GetOrCreateFieldSymbol(field); else return base.ResolveFieldSymbol(field); } @@ -134,11 +141,8 @@ protected internal override IkvmReflectionFieldSymbol ResolveFieldSymbol(FieldIn /// protected internal override IkvmReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) { - - if (_type != null && property.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreatePropertySymbol(property); - else if (property.DeclaringType != null && property.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(property.DeclaringType).GetOrCreatePropertySymbol(property); + if (property.Module == _member.Module) + return _containingModule.GetOrCreatePropertySymbol(property); else return base.ResolvePropertySymbol(property); } @@ -150,27 +154,32 @@ protected internal override IkvmReflectionPropertySymbol ResolvePropertySymbol(P /// protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventInfo @event) { - if (_type != null && @event.DeclaringType == _type.ReflectionObject) - return _type.GetOrCreateEventSymbol(@event); - else if (@event.DeclaringType != null && @event.Module == _member.Module) - return _module.GetOrCreateTypeSymbol(@event.DeclaringType).GetOrCreateEventSymbol(@event); + if (@event.Module == _member.Module) + return _containingModule.GetOrCreateEventSymbol(@event); else return base.ResolveEventSymbol(@event); } /// - /// Gets the wrapped . + /// Gets the underlying wrapped by this symbol. /// internal MemberInfo ReflectionObject => _member; - /// - internal IkvmReflectionModuleSymbol ContainingModule => _module; + /// + /// Gets the which contains the metadata of this member. + /// + internal IkvmReflectionModuleSymbol ContainingModule => _containingModule; + + /// + /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. + /// + internal IkvmReflectionTypeSymbol? ContainingType => _containingType; /// - internal IkvmReflectionTypeSymbol? ContainingType => _type; + public virtual IModuleSymbol Module => Context.GetOrCreateModuleSymbol(_member.Module); /// - public virtual ITypeSymbol? DeclaringType => _member.DeclaringType is Type t ? Context.GetOrCreateTypeSymbol(t) : null; + public virtual ITypeSymbol? DeclaringType => _member.DeclaringType is { } t ? Context.GetOrCreateTypeSymbol(t) : null; /// public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)_member.MemberType; @@ -178,15 +187,9 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn /// public virtual int MetadataToken => _member.MetadataToken; - /// - public virtual IModuleSymbol Module => Context.GetOrCreateModuleSymbol(_member.Module); - /// public virtual string Name => _member.Name; - /// - public override bool IsMissing => _member.__IsMissing; - /// public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) { @@ -241,7 +244,7 @@ public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) /// public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_member.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit)); + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); } /// @@ -256,6 +259,17 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return _member.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + protected void Complete(MemberInfo member) + { + ResolveMemberSymbol(_member = member); + _customAttributes = null; + _inheritedCustomAttributes = null; + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs index f62f4d444c..20f097683a 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs @@ -1,10 +1,6 @@ using System; -using System.Diagnostics; -using System.Linq; -using System.Threading; using MethodBase = IKVM.Reflection.MethodBase; -using ParameterInfo = IKVM.Reflection.ParameterInfo; namespace IKVM.CoreLib.Symbols.IkvmReflection { @@ -12,67 +8,34 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection abstract class IkvmReflectionMethodBaseSymbol : IkvmReflectionMemberSymbol, IMethodBaseSymbol { - readonly MethodBase _method; - - ParameterInfo[]? _parametersSource; - IkvmReflectionParameterSymbol?[]? _parameters; - IkvmReflectionParameterSymbol? _returnParameter; + MethodBase _method; /// /// Initializes a new instance. /// /// /// - /// /// - public IkvmReflectionMethodBaseSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, IkvmReflectionTypeSymbol? type, MethodBase method) : - base(context, module, type, method) + public IkvmReflectionMethodBaseSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, MethodBase method) : + base(context, module, method) { _method = method ?? throw new ArgumentNullException(nameof(method)); } /// - /// Gets or creates the cached for the type by method. + /// Initializes a new instance. /// - /// - /// - internal IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + /// + /// + /// + public IkvmReflectionMethodBaseSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, MethodBase method) : + this(context, type.ContainingModule, method) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - Debug.Assert(parameter.Member == _method); - if (_parametersSource == null) - Interlocked.CompareExchange(ref _parametersSource, _method.GetParameters().OrderBy(i => i.Position).ToArray(), null); - if (_parameters == null) - Interlocked.CompareExchange(ref _parameters, new IkvmReflectionParameterSymbol?[_parametersSource.Length], null); - - // index of current record - var idx = parameter.Position; - Debug.Assert(idx >= -1); - Debug.Assert(idx < _parametersSource.Length); - - // check that our list is long enough to contain the entire table - if (idx >= 0 && _parameters.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _returnParameter; - if (idx >= 0) - rec = ref _parameters[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new IkvmReflectionParameterSymbol(Context, this, parameter), null); - - // this should never happen - if (rec is not IkvmReflectionParameterSymbol sym) - throw new InvalidOperationException(); - - return sym; } /// - /// Gets the wrapped . + /// Gets the underlying wrapped by this symbol. /// internal new MethodBase ReflectionObject => _method; @@ -121,9 +84,6 @@ internal IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo /// public bool IsPublic => _method.IsPublic; - /// - public bool IsSpecialName => _method.IsSpecialName; - /// public bool IsStatic => _method.IsStatic; @@ -131,10 +91,10 @@ internal IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo public bool IsVirtual => _method.IsVirtual; /// - public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)_method.MethodImplementationFlags; + public bool IsSpecialName => _method.IsSpecialName; /// - public override bool ContainsMissing => GetGenericArguments().Any(i => i.IsMissing || i.ContainsMissing) || GetParameters().Any(i => i.IsMissing || i.ContainsMissing); + public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)_method.MethodImplementationFlags; /// public ITypeSymbol[] GetGenericArguments() @@ -154,6 +114,20 @@ public IParameterSymbol[] GetParameters() return ResolveParameterSymbols(_method.GetParameters()); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(MethodBase method) + { + ResolveMethodBaseSymbol(_method = method); + base.Complete(_method); + + foreach (var i in _method.GetParameters()) + ResolveParameterSymbol(i).Complete(i); + + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs index c18969aa21..472021fa7d 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs @@ -1,11 +1,6 @@ using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.Linq; -using System.Threading; using MethodInfo = IKVM.Reflection.MethodInfo; -using Type = IKVM.Reflection.Type; namespace IKVM.CoreLib.Symbols.IkvmReflection { @@ -15,115 +10,60 @@ class IkvmReflectionMethodSymbol : IkvmReflectionMethodBaseSymbol, IMethodSymbol readonly MethodInfo _method; - Type[]? _genericParametersSource; - IkvmReflectionTypeSymbol?[]? _genericParameters; - List<(Type[] Arguments, IkvmReflectionMethodSymbol Symbol)>? _genericTypes; - /// /// Initializes a new instance. /// /// /// - /// /// - public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, IkvmReflectionTypeSymbol? type, MethodInfo method) : - base(context, module, type, method) + public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, MethodInfo method) : + base(context, module, method) { _method = method ?? throw new ArgumentNullException(nameof(method)); } /// - /// Gets or creates the cached for the generic parameter type. + /// Initializes a new instance. /// - /// - /// - /// - internal IkvmReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericParameterType) + /// + /// + /// + public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, MethodInfo method) : + this(context, type.ContainingModule, method) { - if (genericParameterType is null) - throw new ArgumentNullException(nameof(genericParameterType)); - - Debug.Assert(genericParameterType.DeclaringMethod == _method); - - // initialize tables - _genericParametersSource ??= _method.GetGenericArguments(); - _genericParameters ??= new IkvmReflectionTypeSymbol?[_genericParametersSource.Length]; - // position of the parameter in the list - var idx = genericParameterType.GenericParameterPosition; - - // check that our list is long enough to contain the entire table - if (_genericParameters.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _genericParameters[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new IkvmReflectionTypeSymbol(Context, ContainingModule, genericParameterType), null); - - // this should never happen - if (rec is not IkvmReflectionTypeSymbol sym) - throw new InvalidOperationException(); - - return sym; } /// - /// Gets or creates the cached for the generic parameter type. + /// Gets the underlying wrapped by this symbol. /// - /// - /// - /// - internal IkvmReflectionMethodSymbol GetOrCreateGenericTypeSymbol(Type[] genericMethodArguments) - { - if (genericMethodArguments is null) - throw new ArgumentNullException(nameof(genericMethodArguments)); - - if (_method.IsGenericMethodDefinition == false) - throw new InvalidOperationException(); - - // initialize the available parameters - _genericParametersSource ??= _method.GetGenericArguments(); - if (_genericParametersSource.Length != genericMethodArguments.Length) - throw new InvalidOperationException(); - - // initialize generic type map, and lock on it since we're potentially adding items - _genericTypes ??= []; - lock (_genericTypes) - { - // find existing entry - foreach (var i in _genericTypes) - if (i.Arguments.SequenceEqual(genericMethodArguments)) - return i.Symbol; - - // generate new symbol - var sym = new IkvmReflectionMethodSymbol(Context, ContainingModule, ContainingType, _method.MakeGenericMethod(genericMethodArguments)); - _genericTypes.Add((genericMethodArguments, sym)); - return sym; - } - } - - internal new MethodInfo ReflectionObject => (MethodInfo)base.ReflectionObject; + internal new MethodInfo ReflectionObject => _method; + /// public IParameterSymbol ReturnParameter => ResolveParameterSymbol(_method.ReturnParameter); + /// public ITypeSymbol ReturnType => ResolveTypeSymbol(_method.ReturnType); + /// public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + /// public IMethodSymbol GetBaseDefinition() { return ResolveMethodSymbol(_method.GetBaseDefinition()); } + /// public IMethodSymbol GetGenericMethodDefinition() { return ResolveMethodSymbol(_method.GetGenericMethodDefinition()); } + /// public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) { - return ResolveMethodSymbol(_method.MakeGenericMethod(UnpackTypeSymbols(typeArguments))); + return ResolveMethodSymbol(_method.MakeGenericMethod(typeArguments.Unpack())); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index eacc58c3b0..daafbe9ac6 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -2,9 +2,10 @@ using System.Diagnostics; using System.Linq; using System.Reflection.Metadata.Ecma335; -using System.Runtime.InteropServices; using System.Threading; +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Threading; using IKVM.Reflection; using Module = IKVM.Reflection.Module; @@ -29,31 +30,66 @@ static bool IsTypeDefinition(Type type) return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; } - readonly Module _module; + const int MAX_CAPACITY = 65536 * 2; - Type[]? _typesSource; - int _typesBaseRow; - IkvmReflectionTypeSymbol?[]? _types; + const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; + + readonly IkvmReflectionAssemblySymbol _containingAssembly; + Module _module; + + IndexRangeDictionary _typeTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _typeLock; + + IndexRangeDictionary _methodTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _methodLock; + + IndexRangeDictionary _fieldTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _fieldLock; + + IndexRangeDictionary _propertyTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _propertyLock; + + IndexRangeDictionary _eventTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _eventLock; + + IndexRangeDictionary _parameterTable = new(); + IndexRangeDictionary _parameterSymbols = new(); + ReaderWriterLockSlim? _parameterLock; + + IndexRangeDictionary _genericParameterSymbols = new(); + ReaderWriterLockSlim? _genericParameterLock; /// /// Initializes a new instance. /// /// + /// /// /// - public IkvmReflectionModuleSymbol(IkvmReflectionSymbolContext context, Module module) : + public IkvmReflectionModuleSymbol(IkvmReflectionSymbolContext context, IkvmReflectionAssemblySymbol containingAssembly, Module module) : base(context) { + _containingAssembly = containingAssembly ?? throw new ArgumentNullException(nameof(containingAssembly)); _module = module ?? throw new ArgumentNullException(nameof(module)); } + /// + /// Gets the which contains the metadata of this member. + /// + internal IkvmReflectionAssemblySymbol ContainingAssembly => _containingAssembly; + /// /// Gets the wrapped . /// internal Module ReflectionObject => _module; /// - /// Gets or creates the cached for the module by type. + /// Gets or creates the cached for the module by type. /// /// /// @@ -65,49 +101,41 @@ internal IkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) Debug.Assert(type.Module == _module); - // type is not a definition, but is substituted + // type is a generic parameter (GenericParam) + if (type.IsGenericParameter) + return GetOrCreateGenericParameterSymbol(type); + + // type is not a type definition (TypeDef) if (IsTypeDefinition(type) == false) return GetOrCreateTypeSymbolForSpecification(type); - // look up handle and row - var hnd = MetadataTokens.TypeDefinitionHandle(type.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); + // create lock on demand + if (_typeLock == null) + lock (this) + _typeLock ??= new ReaderWriterLockSlim(); - // initialize source table - if (_typesSource == null) + using (_typeLock.CreateUpgradeableReadLock()) { - _typesSource = _module.GetTypes().OrderBy(i => i.MetadataToken).ToArray(); - _typesBaseRow = _typesSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_typesSource[0].MetadataToken)) : 0; + var row = MetadataTokens.GetRowNumber(MetadataTokens.TypeDefinitionHandle(type.MetadataToken)); + if (_typeTable[row] != type) + using (_typeLock.CreateWriteLock()) + _typeTable[row] = type; + + if (_typeSymbols[row] == null) + using (_typeLock.CreateWriteLock()) + return _typeSymbols[row] ??= new IkvmReflectionTypeSymbol(Context, this, type); + else + return _typeSymbols[row] ?? throw new InvalidOperationException(); } - - // initialize cache table - _types ??= new IkvmReflectionTypeSymbol?[_typesSource.Length]; - - // index of current record is specified row - base - var idx = row - _typesBaseRow - 1; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _typesSource.Length); - - // check that our type list is long enough to contain the entire table - if (_types.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - if (_types[idx] == null) - Interlocked.CompareExchange(ref _types[idx], new IkvmReflectionTypeSymbol(Context, this, type), null); - - // this should never happen - if (_types[idx] is not IkvmReflectionTypeSymbol sym) - throw new InvalidOperationException(); - - return sym; } /// - /// For a given + /// Gets or creates a for the specification type: array, pointer, etc. /// /// - /// + /// + /// + /// IkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) { if (type is null) @@ -117,7 +145,7 @@ IkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) if (type.GetElementType() is { } elementType) { - var elementTypeSymbol = GetOrCreateTypeSymbol(elementType); + var elementTypeSymbol = ResolveTypeSymbol(elementType); // handles both SZ arrays and normal arrays if (type.IsArray) @@ -134,26 +162,234 @@ IkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) if (type.IsGenericType) { - var definitionType = type.GetGenericTypeDefinition(); - var definitionTypeSymbol = GetOrCreateTypeSymbol(definitionType); - return definitionTypeSymbol.GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + var definitionTypeSymbol = ResolveTypeSymbol(type.GetGenericTypeDefinition()); + return definitionTypeSymbol.GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); } - // generic type parameter - if (type.IsGenericParameter && type.DeclaringMethod is null && type.DeclaringType is not null) + throw new InvalidOperationException(); + } + + /// + /// Gets or creates the cached fqor the type by method. + /// + /// + /// + internal IkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + Debug.Assert(method.Module.MetadataToken == _module.MetadataToken); + + // create lock on demand + if (_methodLock == null) + lock (this) + _methodLock ??= new ReaderWriterLockSlim(); + + using (_methodLock.CreateUpgradeableReadLock()) { - var declaringType = GetOrCreateTypeSymbol(type.DeclaringType); - return declaringType.GetOrCreateGenericParameterSymbol(type); + var row = MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(method.MetadataToken)); + if (_methodTable[row] != method) + using (_methodLock.CreateWriteLock()) + _methodTable[row] = method; + + if (_methodSymbols[row] == null) + using (_methodLock.CreateWriteLock()) + if (method is ConstructorInfo c) + return _methodSymbols[row] ??= new IkvmReflectionConstructorSymbol(Context, ResolveTypeSymbol(c.DeclaringType ?? throw new InvalidOperationException()), c); + else if (method is MethodInfo m) + if (method.DeclaringType is { } dt) + return _methodSymbols[row] ??= new IkvmReflectionMethodSymbol(Context, ResolveTypeSymbol(dt), m); + else + return _methodSymbols[row] ??= new IkvmReflectionMethodSymbol(Context, this, m); + else + throw new InvalidOperationException(); + else + return _methodSymbols[row] ?? throw new InvalidOperationException(); } + } + + /// + /// Gets or creates the cached for the type by ctor. + /// + /// + /// + internal IkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return (IkvmReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + internal IkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return (IkvmReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + /// + internal IkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + + Debug.Assert(field.Module == _module); - // generic method parameter - if (type.IsGenericParameter && type.DeclaringMethod is not null && type.DeclaringMethod.DeclaringType is not null) + // create lock on demand + if (_fieldLock == null) + lock (this) + _fieldLock ??= new ReaderWriterLockSlim(); + + using (_fieldLock.CreateUpgradeableReadLock()) { - var declaringMethod = GetOrCreateTypeSymbol(type.DeclaringMethod.DeclaringType); - return declaringMethod.GetOrCreateGenericParameterSymbol(type); + var row = MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(field.MetadataToken)); + if (_fieldTable[row] != field) + using (_fieldLock.CreateWriteLock()) + _fieldTable[row] = field; + + if (_fieldSymbols[row] == null) + using (_fieldLock.CreateWriteLock()) + if (field.DeclaringType is { } dt) + return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbol(Context, ResolveTypeSymbol(dt), field); + else + return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbol(Context, this, field); + else + return _fieldSymbols[row] ?? throw new InvalidOperationException(); } + } - throw new InvalidOperationException(); + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + /// + internal IkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + Debug.Assert(property.Module == _module); + + // create lock on demand + if (_propertyLock == null) + lock (this) + _propertyLock ??= new ReaderWriterLockSlim(); + + using (_propertyLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(property.MetadataToken)); + if (_propertyTable[row] != property) + using (_propertyLock.CreateWriteLock()) + _propertyTable[row] = property; + + if (_propertySymbols[row] == null) + using (_propertyLock.CreateWriteLock()) + return _propertySymbols[row] ??= new IkvmReflectionPropertySymbol(Context, ResolveTypeSymbol(property.DeclaringType!), property); + else + return _propertySymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + /// + internal IkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + Debug.Assert(@event.Module == _module); + + // create lock on demand + if (_eventLock == null) + lock (this) + _eventLock ??= new ReaderWriterLockSlim(); + + using (_eventLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.MetadataToken)); + if (_eventTable[row] is not EventInfo i || i != @event) + using (_eventLock.CreateWriteLock()) + _eventTable[row] = @event; + + if (_eventSymbols[row] == null) + using (_eventLock.CreateWriteLock()) + return _eventSymbols[row] ??= new IkvmReflectionEventSymbol(Context, ResolveTypeSymbol(@event.DeclaringType!), @event); + else + return _eventSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + internal IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + Debug.Assert(parameter.Member.Module == _module); + + // create lock on demand + if (_parameterLock == null) + lock (this) + _parameterLock ??= new ReaderWriterLockSlim(); + + using (_parameterLock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_parameterTable[position] != parameter) + using (_parameterLock.CreateWriteLock()) + _parameterTable[position] = parameter; + + if (_parameterSymbols[position] == null) + using (_parameterLock.CreateWriteLock()) + return _parameterSymbols[position] ??= new IkvmReflectionParameterSymbol(Context, ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); + else + return _parameterSymbols[position] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + /// + internal IkvmReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericParameterType) + { + if (genericParameterType is null) + throw new ArgumentNullException(nameof(genericParameterType)); + + Debug.Assert(genericParameterType.Module == _module); + + // create lock on demand + if (_genericParameterLock == null) + Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); + + using (_genericParameterLock.CreateUpgradeableReadLock()) + { + var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.MetadataToken); + var row = MetadataTokens.GetRowNumber(hnd); + if (_genericParameterSymbols[row] == null) + using (_genericParameterLock.CreateWriteLock()) + return _genericParameterSymbols[row] ??= new IkvmReflectionTypeSymbol(Context, this, genericParameterType); + else + return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); + } } /// @@ -174,12 +410,6 @@ IkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) /// public string ScopeName => _module.ScopeName; - /// - public override bool IsMissing => _module.__IsMissing; - - /// - public override bool ContainsMissing => GetTypes().Any(t => t.IsMissing || t.ContainsMissing); - /// public IFieldSymbol? GetField(string name) { @@ -213,16 +443,13 @@ public IFieldSymbol[] GetFields() /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _module.GetMethod(name, UnpackTypeSymbols(types)) is { } m ? ResolveMethodSymbol(m) : null; + return _module.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; } /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - if (modifiers != null) - throw new NotImplementedException(); - - return _module.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, UnpackTypeSymbols(types), null) is { } m ? ResolveMethodSymbol(m) : null; + throw new NotImplementedException(); } /// @@ -236,8 +463,8 @@ public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingFlags) { return ResolveMethodSymbols(_module.GetMethods((BindingFlags)bindingFlags)); } - /// + /// public ITypeSymbol? GetType(string className) { return _module.GetType(className) is { } t ? ResolveTypeSymbol(t) : null; @@ -276,9 +503,7 @@ public bool IsResource() /// public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return _module.ResolveField(metadataToken, _genericTypeArguments, _genericMethodArguments) is { } f ? ResolveFieldSymbol(f) : null; + return _module.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } f ? ResolveFieldSymbol(f) : null; } /// @@ -290,17 +515,13 @@ public bool IsResource() /// public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return _module.ResolveMember(metadataToken, _genericTypeArguments, _genericMethodArguments) is { } m ? ResolveMemberSymbol(m) : null; + return _module.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMemberSymbol(m) : null; } /// public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return _module.ResolveMethod(metadataToken, _genericTypeArguments, _genericMethodArguments) is { } m ? ResolveMethodBaseSymbol(m) : null; + return _module.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMethodBaseSymbol(m) : null; } /// @@ -330,9 +551,7 @@ public ITypeSymbol ResolveType(int metadataToken) /// public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - var _genericTypeArguments = genericTypeArguments != null ? UnpackTypeSymbols(genericTypeArguments) : null; - var _genericMethodArguments = genericMethodArguments != null ? UnpackTypeSymbols(genericMethodArguments) : null; - return ResolveTypeSymbol(_module.ResolveType(metadataToken, _genericTypeArguments, _genericMethodArguments)); + return ResolveTypeSymbol(_module.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); } /// @@ -344,7 +563,7 @@ public CustomAttribute[] GetCustomAttributes(bool inherit = false) /// public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_module.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false)); + return ResolveCustomAttributes(_module.GetCustomAttributesData().Where(i => i.AttributeType == ((IkvmReflectionTypeSymbol)attributeType).ReflectionObject)); } /// @@ -359,6 +578,16 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return _module.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(Module module) + { + ResolveModuleSymbol(_module = module); + ContainingAssembly.Complete(_module.Assembly); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs index cc3e18be62..a0dca46268 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs @@ -10,7 +10,9 @@ class IkvmReflectionParameterSymbol : IkvmReflectionSymbol, IParameterSymbol { readonly IkvmReflectionMethodBaseSymbol _containingMethod; - readonly ParameterInfo _parameter; + ParameterInfo _parameter; + + CustomAttribute[]? _customAttributes; /// /// Initializes a new instance. @@ -28,10 +30,10 @@ public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IkvmRe internal IkvmReflectionMethodBaseSymbol ContainingMethod => _containingMethod; /// - public System.Reflection.ParameterAttributes Attributes => (System.Reflection.ParameterAttributes)_parameter.Attributes; + public System.Reflection.ParameterAttributes Attributes =>(System.Reflection.ParameterAttributes)_parameter.Attributes; /// - public object DefaultValue => _parameter.RawDefaultValue; + public object? DefaultValue => _parameter.RawDefaultValue; /// public bool HasDefaultValue => _parameter.HasDefaultValue; @@ -69,13 +71,13 @@ public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IkvmRe /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return ResolveCustomAttributes(_parameter.GetCustomAttributesData()); + return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); } /// public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_parameter.__GetCustomAttributes(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit)); + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); } /// @@ -102,6 +104,16 @@ public ITypeSymbol[] GetRequiredCustomModifiers() return ResolveTypeSymbols(_parameter.GetRequiredCustomModifiers()); } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(ParameterInfo parameter) + { + ResolveParameterSymbol(_parameter = parameter); + _customAttributes = null; + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs index f16d0b9a08..a257b00159 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs @@ -10,7 +10,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionPropertySymbol : IkvmReflectionMemberSymbol, IPropertySymbol { - readonly PropertyInfo _property; + PropertyInfo _property; /// /// Initializes a new instance. @@ -19,19 +19,19 @@ class IkvmReflectionPropertySymbol : IkvmReflectionMemberSymbol, IPropertySymbol /// /// public IkvmReflectionPropertySymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, PropertyInfo property) : - base(context, type.ContainingModule, type, property) + base(context, type, property) { _property = property ?? throw new ArgumentNullException(nameof(property)); } - public new PropertyInfo ReflectionObject => (PropertyInfo)base.ReflectionObject; + /// + /// Gets the underlying wrapped by this symbol. + /// + internal new PropertyInfo ReflectionObject => _property; /// public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)_property.Attributes; - /// - public ITypeSymbol PropertyType => ResolveTypeSymbol(_property.PropertyType); - /// public bool CanRead => _property.CanRead; @@ -41,6 +41,9 @@ public IkvmReflectionPropertySymbol(IkvmReflectionSymbolContext context, IkvmRef /// public bool IsSpecialName => _property.IsSpecialName; + /// + public ITypeSymbol PropertyType => ResolveTypeSymbol(_property.PropertyType); + /// public IMethodSymbol? GetMethod => _property.GetMethod is { } m ? ResolveMethodSymbol(m) : null; @@ -54,27 +57,21 @@ public IkvmReflectionPropertySymbol(IkvmReflectionSymbolContext context, IkvmRef } /// - public IParameterSymbol[] GetIndexParameters() - { - return ResolveParameterSymbols(_property.GetIndexParameters()); - } - - /// - public ITypeSymbol GetModifiedPropertyType() + public IMethodSymbol[] GetAccessors() { - throw new NotImplementedException(); + return ResolveMethodSymbols(_property.GetAccessors()); } /// - public IMethodSymbol[] GetAccessors() + public IMethodSymbol[] GetAccessors(bool nonPublic) { - return ResolveMethodSymbols(_property.GetAccessors()); + return ResolveMethodSymbols(_property.GetAccessors(nonPublic)); } /// - public IMethodSymbol[] GetAccessors(bool nonPublic) + public IParameterSymbol[] GetIndexParameters() { - throw new NotImplementedException(); + return ResolveParameterSymbols(_property.GetIndexParameters()); } /// @@ -101,6 +98,12 @@ public IMethodSymbol[] GetAccessors(bool nonPublic) return _property.GetSetMethod(nonPublic) is MethodInfo m ? ResolveMethodSymbol(m) : null; } + /// + public ITypeSymbol GetModifiedPropertyType() + { + throw new NotImplementedException(); + } + /// public ITypeSymbol[] GetOptionalCustomModifiers() { @@ -112,6 +115,17 @@ public ITypeSymbol[] GetRequiredCustomModifiers() { return ResolveTypeSymbols(_property.GetRequiredCustomModifiers()); } + + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(PropertyInfo property) + { + ResolvePropertySymbol(_property = property); + base.Complete(_property); + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index f0d642b569..a469bb9464 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -18,6 +18,9 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection { + /// + /// Base class for managed symbols. + /// abstract class IkvmReflectionSymbol : ISymbol { @@ -38,10 +41,10 @@ public IkvmReflectionSymbol(IkvmReflectionSymbolContext context) protected IkvmReflectionSymbolContext Context => _context; /// - public virtual bool IsMissing => false; + public bool IsMissing => false; /// - public virtual bool ContainsMissing => false; + public bool ContainsMissing => false; /// /// Resolves the symbol for the specified type. @@ -78,20 +81,6 @@ protected internal IEnumerable ResolveModuleSymbols( yield return ResolveModuleSymbol(module); } - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - protected internal Module[] UnpackModuleSymbols(IModuleSymbol[] modules) - { - var a = new Module[modules.Length]; - for (int i = 0; i < modules.Length; i++) - a[i] = ((IkvmReflectionModuleSymbol)modules[i]).ReflectionObject; - - return a; - } - /// /// Resolves the symbol for the specified type. /// @@ -128,20 +117,6 @@ protected internal IkvmReflectionMemberSymbol[] ResolveMemberSymbols(MemberInfo[ return a; } - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - protected internal MemberInfo[] UnpackMemberSymbols(IMemberSymbol[] members) - { - var a = new MemberInfo[members.Length]; - for (int i = 0; i < members.Length; i++) - a[i] = ((IkvmReflectionMemberSymbol)members[i]).ReflectionObject; - - return a; - } - /// /// Resolves the symbol for the specified type. /// @@ -177,20 +152,6 @@ protected internal IEnumerable ResolveTypeSymbols(IEnu yield return ResolveTypeSymbol(type); } - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - protected internal Type[] UnpackTypeSymbols(ITypeSymbol[] types) - { - var a = new Type[types.Length]; - for (int i = 0; i < types.Length; i++) - a[i] = ((IkvmReflectionTypeSymbol)types[i]).ReflectionObject; - - return a; - } - /// /// Resolves the symbol for the specified method. /// @@ -252,30 +213,6 @@ protected internal IkvmReflectionMethodSymbol[] ResolveMethodSymbols(MethodInfo[ return a; } - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - protected virtual internal IkvmReflectionParameterSymbol ResolveParameterSymbol(ParameterInfo parameter) - { - return _context.GetOrCreateParameterSymbol(parameter); - } - - /// - /// Resolves the symbols for the specified parameters. - /// - /// - /// - protected internal IkvmReflectionParameterSymbol[] ResolveParameterSymbols(ParameterInfo[] parameters) - { - var a = new IkvmReflectionParameterSymbol[parameters.Length]; - for (int i = 0; i < parameters.Length; i++) - a[i] = ResolveParameterSymbol(parameters[i]); - - return a; - } - /// /// Resolves the symbol for the specified field. /// @@ -348,6 +285,30 @@ protected internal IkvmReflectionEventSymbol[] ResolveEventSymbols(EventInfo[] e return a; } + /// + /// Resolves the symbol for the specified parameter. + /// + /// + /// + protected virtual internal IkvmReflectionParameterSymbol ResolveParameterSymbol(ParameterInfo parameter) + { + return _context.GetOrCreateParameterSymbol(parameter); + } + + /// + /// Resolves the symbols for the specified parameters. + /// + /// + /// + protected internal IkvmReflectionParameterSymbol[] ResolveParameterSymbols(ParameterInfo[] parameters) + { + var a = new IkvmReflectionParameterSymbol[parameters.Length]; + for (int i = 0; i < parameters.Length; i++) + a[i] = ResolveParameterSymbol(parameters[i]); + + return a; + } + /// /// Transforms a custom set of custom attribute data records to a symbol record. /// @@ -362,12 +323,25 @@ protected internal CustomAttribute[] ResolveCustomAttributes(IList + /// Transforms a custom set of custom attribute data records to a symbol record. + /// + /// + /// + protected internal CustomAttribute[] ResolveCustomAttributes(IEnumerable attributes) + { + var a = new List(); + foreach (var i in attributes) + a.Add(ResolveCustomAttribute(i)); + + return a.ToArray(); + } + /// /// Transforms a custom attribute data record to a symbol record. /// /// /// - /// protected internal CustomAttribute ResolveCustomAttribute(CustomAttributeData customAttributeData) { return new CustomAttribute( @@ -408,7 +382,7 @@ CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Reflection /// object? ResolveCustomAttributeTypedValue(object? value) { - if (value is IKVM.Reflection.Type v) + if (value is Type v) return ResolveTypeSymbol(v); return value; @@ -425,11 +399,11 @@ ImmutableArray ResolveCustomAttributeNamedArgument for (int i = 0; i < args.Count; i++) a[i] = ResolveCustomAttributeNamedArgument(args[i]); - return a.ToImmutableArray(); + return ImmutableArray.Create(a); } /// - /// Transforms a values into a symbol. + /// Transforms a values into a symbol. /// /// /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs index fcbc6d34d1..53ce1511fb 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -1,6 +1,11 @@ using System; +using System.Collections.Concurrent; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection.Emit; + using Assembly = IKVM.Reflection.Assembly; using ConstructorInfo = IKVM.Reflection.ConstructorInfo; using EventInfo = IKVM.Reflection.EventInfo; @@ -21,7 +26,8 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionSymbolContext { - readonly ConditionalWeakTable _assemblies = new(); + readonly ConcurrentDictionary> _symbolByName = new(AssemblyNameEqualityComparer.Instance); + readonly ConditionalWeakTable _symbolByAssembly = new(); /// /// Initializes a new instance. @@ -31,6 +37,30 @@ public IkvmReflectionSymbolContext() } + /// + /// Gets or creates a indexed based on the assembly's name. + /// + /// + /// + IkvmReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) + { + var r = _symbolByName.GetOrAdd(assembly.GetName().ToAssemblyName(), _ => new WeakReference(new IkvmReflectionAssemblySymbol(this, assembly))); + + // reference has valid symbol + if (r.TryGetTarget(out var s)) + return s; + + // no valid symbol, must have been released, lock to restore + lock (r) + { + // still gone, recreate + if (r.TryGetTarget(out s) == false) + r.SetTarget(s = new IkvmReflectionAssemblySymbol(this, assembly)); + + return s; + } + } + /// /// Gets or creates a for the specified . /// @@ -38,10 +68,7 @@ public IkvmReflectionSymbolContext() /// public IkvmReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) { - if (assembly is null) - throw new ArgumentNullException(nameof(assembly)); - - return _assemblies.GetValue(assembly, _ => new IkvmReflectionAssemblySymbol(this, _)); + return _symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); } /// @@ -51,9 +78,6 @@ public IkvmReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) /// public IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) { - if (module is null) - throw new ArgumentNullException(nameof(module)); - return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); } @@ -64,12 +88,22 @@ public IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) /// public IkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) { - if (type is null) - throw new ArgumentNullException(nameof(type)); - return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); } + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is ConstructorInfo ctor) + return GetOrCreateConstructorSymbol(ctor); + else + return GetOrCreateMethodSymbol((MethodInfo)method); + } + /// /// Gets or creates a for the specified . /// @@ -77,23 +111,17 @@ public IkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) /// public IkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { - if (ctor is null) - throw new ArgumentNullException(nameof(ctor)); - - return GetOrCreateAssemblySymbol(ctor.Module.Assembly).GetOrCreateModuleSymbol(ctor.Module).GetOrCreateTypeSymbol(ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); + return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// public IkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - return GetOrCreateAssemblySymbol(method.Module.Assembly).GetOrCreateModuleSymbol(method.Module).GetOrCreateTypeSymbol(method.DeclaringType!).GetOrCreateMethodSymbol(method); + return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); } /// @@ -103,10 +131,7 @@ public IkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) /// public IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - return GetOrCreateAssemblySymbol(parameter.Member.Module.Assembly).GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateTypeSymbol(parameter.Member.DeclaringType!).GetOrCreateMethodBaseSymbol((MethodBase)parameter.Member).GetOrCreateParameterSymbol(parameter); + return GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateParameterSymbol(parameter); } /// @@ -116,10 +141,7 @@ public IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo pa /// public IkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - return GetOrCreateAssemblySymbol(field.Module.Assembly).GetOrCreateModuleSymbol(field.Module).GetOrCreateTypeSymbol(field.DeclaringType!).GetOrCreateFieldSymbol(field); + return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); } /// @@ -129,10 +151,7 @@ public IkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) /// public IkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - return GetOrCreateAssemblySymbol(property.Module.Assembly).GetOrCreateModuleSymbol(property.Module).GetOrCreateTypeSymbol(property.DeclaringType!).GetOrCreatePropertySymbol(property); + return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); } /// @@ -142,10 +161,18 @@ public IkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo prope /// public IkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); + return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + } - return GetOrCreateAssemblySymbol(@event.Module.Assembly).GetOrCreateModuleSymbol(@event.Module).GetOrCreateTypeSymbol(@event.DeclaringType!).GetOrCreateEventSymbol(@event); + /// + /// Gets or creates a for the specified . + /// + /// + /// + /// + public IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(MethodBuilder method, ParameterBuilder parameter) + { + return GetOrCreateParameterSymbol(new IkvmReflectionParameterBuilderInfo(method, parameter)); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index aad2c19796..a3d3ef7c54 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -1,18 +1,16 @@ using System; +using System.Collections.Concurrent; using System.Collections.Generic; using System.Diagnostics; using System.Linq; -using System.Reflection.Metadata.Ecma335; using System.Threading; +using IKVM.CoreLib.Symbols.Reflection; using IKVM.Reflection; using ConstructorInfo = IKVM.Reflection.ConstructorInfo; -using EventInfo = IKVM.Reflection.EventInfo; using FieldInfo = IKVM.Reflection.FieldInfo; -using MethodBase = IKVM.Reflection.MethodBase; using MethodInfo = IKVM.Reflection.MethodInfo; -using PropertyInfo = IKVM.Reflection.PropertyInfo; using Type = IKVM.Reflection.Type; namespace IKVM.CoreLib.Symbols.IkvmReflection @@ -21,35 +19,17 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionTypeSymbol : IkvmReflectionMemberSymbol, ITypeSymbol { - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - - readonly Type _type; - - MethodBase[]? _methodsSource; - int _methodsBaseRow; - IkvmReflectionMethodBaseSymbol?[]? _methods; - - FieldInfo[]? _fieldsSource; - int _fieldsBaseRow; - IkvmReflectionFieldSymbol?[]? _fields; + const int MAX_CAPACITY = 65536 * 2; - PropertyInfo[]? _propertiesSource; - int _propertiesBaseRow; - IkvmReflectionPropertySymbol?[]? _properties; + const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - EventInfo[]? _eventsSource; - int _eventsBaseRow; - IkvmReflectionEventSymbol?[]? _events; + Type _type; IkvmReflectionTypeSymbol?[]? _asArray; IkvmReflectionTypeSymbol? _asSZArray; IkvmReflectionTypeSymbol? _asPointer; IkvmReflectionTypeSymbol? _asByRef; - - Type[]? _genericParametersSource; - IkvmReflectionTypeSymbol?[]? _genericParameters; - List<(Type[] Arguments, IkvmReflectionTypeSymbol Symbol)>? _genericTypes; - ReaderWriterLockSlim? _genericTypesLock; + ConcurrentDictionary? _genericTypeSymbols; /// /// Initializes a new instance. @@ -58,278 +38,18 @@ class IkvmReflectionTypeSymbol : IkvmReflectionMemberSymbol, ITypeSymbol /// /// public IkvmReflectionTypeSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, Type type) : - base(context, module, null, type) + base(context, module, type) { Debug.Assert(module.ReflectionObject == type.Module); _type = type ?? throw new ArgumentNullException(nameof(type)); } - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal IkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return (IkvmReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - internal IkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return (IkvmReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal IkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - Debug.Assert(method.DeclaringType == _type); - - var hnd = MetadataTokens.MethodDefinitionHandle(method.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source table - if (_methodsSource == null) - { - Interlocked.CompareExchange(ref _methodsSource, _type.GetConstructors(DefaultBindingFlags).Cast().Concat(_type.GetMethods(DefaultBindingFlags)).OrderBy(i => i.MetadataToken).ToArray(), null); - _methodsBaseRow = _methodsSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_methodsSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_methods == null) - Interlocked.CompareExchange(ref _methods, new IkvmReflectionMethodBaseSymbol?[_methodsSource.Length], null); - - // index of current record is specified row - base - var idx = row - _methodsBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _methodsSource.Length); - - // check that our list is long enough to contain the entire table - if (_methods.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _methods[idx]; - if (rec == null) - { - switch (method) - { - case ConstructorInfo c: - Interlocked.CompareExchange(ref rec, new IkvmReflectionConstructorSymbol(Context, ContainingModule, this, c), null); - break; - case MethodInfo m: - Interlocked.CompareExchange(ref rec, new IkvmReflectionMethodSymbol(Context, ContainingModule, this, m), null); - break; - } - } - - // this should never happen - if (rec is not IkvmReflectionMethodBaseSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - /// - internal IkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - Debug.Assert(field.DeclaringType == _type); - - var hnd = MetadataTokens.FieldDefinitionHandle(field.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source table - if (_fieldsSource == null) - { - Interlocked.CompareExchange(ref _fieldsSource, _type.GetFields(DefaultBindingFlags).OrderBy(i => i.MetadataToken).ToArray(), null); - _fieldsBaseRow = _fieldsSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_fieldsSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_fields == null) - Interlocked.CompareExchange(ref _fields, new IkvmReflectionFieldSymbol?[_fieldsSource.Length], null); - - // index of current field is specified row - base - var idx = row - _fieldsBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _fieldsSource.Length); - - // check that our list is long enough to contain the entire table - if (_fields.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _fields[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new IkvmReflectionFieldSymbol(Context, this, field), null); - - // this should never happen - if (rec is not IkvmReflectionFieldSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - /// - internal IkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - Debug.Assert(property.DeclaringType == _type); - - var hnd = MetadataTokens.PropertyDefinitionHandle(property.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source table - if (_propertiesSource == null) - { - Interlocked.CompareExchange(ref _propertiesSource, _type.GetProperties(DefaultBindingFlags).OrderBy(i => i.MetadataToken).ToArray(), null); - _propertiesBaseRow = _propertiesSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(_propertiesSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_properties == null) - Interlocked.CompareExchange(ref _properties, new IkvmReflectionPropertySymbol?[_propertiesSource.Length], null); - - // index of current property is specified row - base - var idx = row - _propertiesBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _propertiesSource.Length); - - // check that our list is long enough to contain the entire table - if (_properties.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _properties[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new IkvmReflectionPropertySymbol(Context, this, property), null); - - // this should never happen - if (rec is not IkvmReflectionPropertySymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - /// - internal IkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - Debug.Assert(@event.DeclaringType == _type); - - var hnd = MetadataTokens.PropertyDefinitionHandle(@event.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - - // initialize source events - if (_eventsSource == null) - { - Interlocked.CompareExchange(ref _eventsSource, _type.GetEvents(DefaultBindingFlags).OrderBy(i => i.MetadataToken).ToArray(), null); - _eventsBaseRow = _eventsSource.Length != 0 ? MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(_eventsSource[0].MetadataToken)) : 0; - } - - // initialize cache table - if (_events == null) - Interlocked.CompareExchange(ref _events, new IkvmReflectionEventSymbol?[_eventsSource.Length], null); - - // index of current event is specified row - base - var idx = row - _eventsBaseRow; - Debug.Assert(idx >= 0); - Debug.Assert(idx < _eventsSource.Length); - - // check that our list is long enough to contain the entire table - if (_events.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _events[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new IkvmReflectionEventSymbol(Context, this, @event), null); - - // this should never happen - if (rec is not IkvmReflectionEventSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - /// - internal IkvmReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericTypeParameterType) - { - if (genericTypeParameterType is null) - throw new ArgumentNullException(nameof(genericTypeParameterType)); - - Debug.Assert(genericTypeParameterType.DeclaringType == _type); - - // initialize tables - if (_genericParametersSource == null) - Interlocked.CompareExchange(ref _genericParametersSource, _type.GetGenericArguments(), null); - if (_genericParameters == null) - Interlocked.CompareExchange(ref _genericParameters, new IkvmReflectionTypeSymbol?[_genericParametersSource.Length], null); - - // position of the parameter in the list - var idx = genericTypeParameterType.GenericParameterPosition; - - // check that our list is long enough to contain the entire table - if (_genericParameters.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _genericParameters[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new IkvmReflectionTypeSymbol(Context, ContainingModule, genericTypeParameterType), null); - - // this should never happen - if (rec is not IkvmReflectionTypeSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - /// /// Gets or creates the cached for the generic parameter type. /// /// /// - /// - internal IkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArguments) + internal IkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) { if (genericTypeArguments is null) throw new ArgumentNullException(nameof(genericTypeArguments)); @@ -337,45 +57,12 @@ internal IkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTyp if (_type.IsGenericTypeDefinition == false) throw new InvalidOperationException(); - // initialize the available parameters - if (_genericParametersSource == null) - Interlocked.CompareExchange(ref _genericParametersSource, _type.GetGenericArguments(), null); - if (_genericParametersSource.Length != genericTypeArguments.Length) - throw new InvalidOperationException(); + if (_genericTypeSymbols == null) + Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); - // initialize generic type map, and lock on it since we're potentially adding items - if (_genericTypes == null) - Interlocked.CompareExchange(ref _genericTypes, [], null); - if (_genericTypesLock == null) - Interlocked.CompareExchange(ref _genericTypesLock, new(), null); - - try - { - _genericTypesLock.EnterUpgradeableReadLock(); - - // find existing entry - foreach (var i in _genericTypes) - if (i.Arguments.SequenceEqual(genericTypeArguments)) - return i.Symbol; - - try - { - _genericTypesLock.EnterWriteLock(); - - // generate new symbol - var sym = new IkvmReflectionTypeSymbol(Context, ContainingModule, _type.MakeGenericType(genericTypeArguments)); - _genericTypes.Add((genericTypeArguments, sym)); - return sym; - } - finally - { - _genericTypesLock.ExitWriteLock(); - } - } - finally - { - _genericTypesLock.ExitUpgradeableReadLock(); - } + return _genericTypeSymbols.GetOrAdd( + genericTypeArguments, + _ => new IkvmReflectionTypeSymbol(Context, ContainingModule, _type.MakeGenericType(genericTypeArguments.Unpack()))); } /// @@ -391,71 +78,6 @@ protected internal override IkvmReflectionTypeSymbol ResolveTypeSymbol(Type type return base.ResolveTypeSymbol(type); } - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - protected internal override IkvmReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) - { - if (ctor.DeclaringType == _type) - return GetOrCreateConstructorSymbol(ctor); - else - return base.ResolveConstructorSymbol(ctor); - } - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected internal override IkvmReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) - { - if (method.DeclaringType == _type) - return GetOrCreateMethodSymbol(method); - else - return base.ResolveMethodSymbol(method); - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override IkvmReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) - { - if (field.DeclaringType == _type) - return GetOrCreateFieldSymbol(field); - else - return base.ResolveFieldSymbol(field); - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override IkvmReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) - { - if (property.DeclaringType == _type) - return GetOrCreatePropertySymbol(property); - else - return base.ResolvePropertySymbol(property); - } - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventInfo @event) - { - if (@event.DeclaringType == _type) - return GetOrCreateEventSymbol(@event); - else - return base.ResolveEventSymbol(@event); - } - /// /// Gets the wrapped . /// @@ -468,7 +90,7 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn public string? AssemblyQualifiedName => _type.AssemblyQualifiedName; /// - public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)(int)_type.Attributes; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)_type.Attributes; /// public ITypeSymbol? BaseType => _type.BaseType != null ? ResolveTypeSymbol(_type.BaseType) : null; @@ -486,7 +108,7 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn public string? Namespace => _type.Namespace; /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)(int)_type.GenericParameterAttributes; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)_type.GenericParameterAttributes; /// public int GenericParameterPosition => _type.GenericParameterPosition; @@ -497,12 +119,29 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn /// public bool HasElementType => _type.HasElementType; + /// + public TypeCode TypeCode => Type.GetTypeCode(_type); + /// public bool IsAbstract => _type.IsAbstract; +#if NETFRAMEWORK + + /// + /// + /// There's no API to distinguish an array of rank 1 from a vector, + /// so we check if the type name ends in [], which indicates it's a vector + /// (non-vectors will have [*] or [,]). + /// + public bool IsSZArray => _type.IsArray && _type.Name.EndsWith("[]"); + +#else + /// public bool IsSZArray => _type.IsSZArray; +#endif + /// public bool IsArray => _type.IsArray; @@ -519,10 +158,13 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn public bool IsClass => _type.IsClass; /// - public bool IsConstructedGenericType => _type.IsConstructedGenericType; + public bool IsEnum => _type.IsEnum; /// - public bool IsEnum => _type.IsEnum; + public bool IsInterface => _type.IsInterface; + + /// + public bool IsConstructedGenericType => _type.IsConstructedGenericType; /// public bool IsGenericParameter => _type.IsGenericParameter; @@ -533,9 +175,6 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn /// public bool IsGenericTypeDefinition => _type.IsGenericTypeDefinition; - /// - public bool IsInterface => _type.IsInterface; - /// public bool IsLayoutSequential => _type.IsLayoutSequential; @@ -566,12 +205,24 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn /// public bool IsPointer => _type.IsPointer; +#if NET8_0_OR_GREATER + /// public bool IsFunctionPointer => _type.IsFunctionPointer; /// public bool IsUnmanagedFunctionPointer => _type.IsUnmanagedFunctionPointer; +#else + + /// + public bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif + /// public bool IsPrimitive => _type.IsPrimitive; @@ -581,10 +232,8 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn /// public bool IsSealed => _type.IsSealed; -#pragma warning disable SYSLIB0050 // Type or member is obsolete /// public bool IsSerializable => _type.IsSerializable; -#pragma warning restore SYSLIB0050 // Type or member is obsolete /// public bool IsValueType => _type.IsValueType; @@ -598,18 +247,9 @@ protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventIn /// public bool IsSpecialName => _type.IsSpecialName; - /// - public TypeCode TypeCode => Type.GetTypeCode(_type); - /// public IConstructorSymbol? TypeInitializer => _type.TypeInitializer is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; - /// - public override bool IsMissing => _type.__IsMissing; - - /// - public override bool ContainsMissing => _type.__ContainsMissingType; - /// public int GetArrayRank() { @@ -619,13 +259,13 @@ public int GetArrayRank() /// public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _type.GetConstructor((BindingFlags)bindingAttr, binder: null, UnpackTypeSymbols(types), modifiers: null) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; + return _type.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; } /// public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _type.GetConstructor(UnpackTypeSymbols(types)) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; + return _type.GetConstructor(types.Unpack()) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; } /// @@ -670,10 +310,16 @@ public ITypeSymbol GetEnumUnderlyingType() return ResolveTypeSymbol(_type.GetEnumUnderlyingType()); } + /// + public Array GetEnumValues() + { + return _type.GetEnumValues(); + } + /// public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _type.GetEvent(name, (BindingFlags)bindingAttr) is { } f ? ResolveEventSymbol(f) : null; + throw new NotImplementedException(); } /// @@ -760,7 +406,7 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) if (inherit) return ResolveTypeSymbols(_type.GetInterfaces()); else - return ResolveTypeSymbols(_type.__GetDeclaredInterfaces()); + throw new NotImplementedException(); } /// @@ -800,15 +446,15 @@ public IMemberSymbol[] GetMembers() } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _type.GetMethod(name, (BindingFlags)bindingAttr, null, UnpackTypeSymbols(types), null) is { } m ? ResolveMethodSymbol(m) : null; + return _type.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _type.GetMethod(name, UnpackTypeSymbols(types)) is { } m ? ResolveMethodSymbol(m) : null; + return _type.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null) is { } m ? ResolveMethodSymbol(m) : null; } /// @@ -818,12 +464,33 @@ public IMemberSymbol[] GetMembers() } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - if (modifiers != null) - throw new NotImplementedException(); + return _type.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } - return _type.GetMethod(name, UnpackTypeSymbols(types), null) is { } m ? ResolveMethodSymbol(m) : null; + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _type.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); } /// @@ -874,27 +541,16 @@ public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAtt return ResolvePropertySymbols(_type.GetProperties((BindingFlags)bindingAttr)); } - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - if (modifiers != null) - throw new NotImplementedException(); - - var _returnType = returnType != null ? ((IkvmReflectionTypeSymbol)returnType).ReflectionObject : null; - return _type.GetProperty(name, _returnType, UnpackTypeSymbols(types), null) is { } p ? ResolvePropertySymbol(p) : null; - } - /// public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _type.GetProperty(name, UnpackTypeSymbols(types)) is { } p ? ResolvePropertySymbol(p) : null; + return _type.GetProperty(name, types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; } /// public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - var _returnType = returnType != null ? ((IkvmReflectionTypeSymbol)returnType).ReflectionObject : null; - return _type.GetProperty(name, _returnType, UnpackTypeSymbols(types)) is { } p ? ResolvePropertySymbol(p) : null; + return _type.GetProperty(name, returnType?.Unpack(), types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; } /// @@ -912,15 +568,13 @@ public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAtt /// public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - var _returnType = returnType != null ? ((IkvmReflectionTypeSymbol)returnType).ReflectionObject : null; - - return _type.GetProperty(name, _returnType) is { } p ? ResolvePropertySymbol(p) : null; + return _type.GetProperty(name, returnType?.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; } /// public bool IsAssignableFrom(ITypeSymbol? c) { - return _type.IsAssignableFrom(c != null ? ((IkvmReflectionTypeSymbol)c).ReflectionObject : null); + return _type.IsAssignableFrom(c?.Unpack()); } /// @@ -932,7 +586,7 @@ public bool IsEnumDefined(object value) /// public bool IsSubclassOf(ITypeSymbol c) { - return _type.IsSubclassOf(((IkvmReflectionTypeSymbol)c).ReflectionObject); + return _type.IsSubclassOf(c.Unpack()); } /// @@ -984,6 +638,32 @@ public ITypeSymbol MakePointerType() return _asPointer; } + /// + /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. + /// + /// + internal void Complete(Type type) + { + ResolveTypeSymbol(_type = type); + base.Complete(_type); + + ContainingModule.Complete(_type.Module); + + foreach (var i in _type.GetConstructors(DefaultBindingFlags)) + ResolveConstructorSymbol(i).Complete(i); + + foreach (var i in _type.GetMethods(DefaultBindingFlags)) + ResolveMethodSymbol(i).Complete(i); + + foreach (var i in _type.GetFields(DefaultBindingFlags)) + ResolveFieldSymbol(i).Complete(i); + + foreach (var i in _type.GetProperties(DefaultBindingFlags)) + ResolvePropertySymbol(i).Complete(i); + + foreach (var i in _type.GetEvents(DefaultBindingFlags)) + ResolveEventSymbol(i).Complete(i); + } } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs new file mode 100644 index 0000000000..d00e0ff60c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -0,0 +1,195 @@ +using System; + +using IKVM.Reflection; + +using ConstructorInfo = IKVM.Reflection.ConstructorInfo; +using MethodInfo = IKVM.Reflection.MethodInfo; +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + static class IkvmReflectionUtil + { + + /// + /// Converts the to a . + /// + /// + /// + public static System.Reflection.AssemblyName ToAssemblyName(this AssemblyName src) + { +#pragma warning disable SYSLIB0037 // Type or member is obsolete + return new System.Reflection.AssemblyName() + { + Name = src.Name, + Version = src.Version, + CultureName = src.CultureName, + HashAlgorithm = (System.Configuration.Assemblies.AssemblyHashAlgorithm)src.HashAlgorithm, + Flags = (System.Reflection.AssemblyNameFlags)src.Flags, + ContentType = (System.Reflection.AssemblyContentType)src.ContentType, + }; +#pragma warning restore SYSLIB0037 // Type or member is obsolete + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static Module Unpack(this IModuleSymbol module) + { + return ((IkvmReflectionModuleSymbol)module).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Module[] Unpack(this IModuleSymbol[] modules) + { + var a = new Module[modules.Length]; + for (int i = 0; i < modules.Length; i++) + a[i] = modules[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static Type Unpack(this ITypeSymbol type) + { + return ((IkvmReflectionTypeSymbol)type).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Type[] Unpack(this ITypeSymbol[] types) + { + var a = new Type[types.Length]; + for (int i = 0; i < types.Length; i++) + a[i] = types[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Type[][] Unpack(this ITypeSymbol[][] types) + { + var a = new Type[types.Length][]; + for (int i = 0; i < types.Length; i++) + a[i] = types[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static MemberInfo Unpack(this IMemberSymbol member) + { + return ((IkvmReflectionMemberSymbol)member).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static MemberInfo[] Unpack(this IMemberSymbol[] members) + { + var a = new MemberInfo[members.Length]; + for (int i = 0; i < members.Length; i++) + a[i] = members[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static ConstructorInfo Unpack(this IConstructorSymbol ctor) + { + return ((IkvmReflectionConstructorSymbol)ctor).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static ConstructorInfo[] Unpack(this IConstructorSymbol[] ctor) + { + var a = new ConstructorInfo[ctor.Length]; + for (int i = 0; i < ctor.Length; i++) + a[i] = ctor[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static MethodInfo Unpack(this IMethodSymbol ctor) + { + return ((IkvmReflectionMethodSymbol)ctor).ReflectionObject; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static MethodInfo[] Unpack(this IMethodSymbol[] ctor) + { + var a = new MethodInfo[ctor.Length]; + for (int i = 0; i < ctor.Length; i++) + a[i] = ctor[i].Unpack(); + + return a; + } + + /// + /// Unpacks the modifier into their original type. + /// + /// + /// + public static ParameterModifier Unpack(this System.Reflection.ParameterModifier modifier) + { + throw new NotImplementedException(); + } + + /// + /// Unpacks the modifiers into their original types. + /// + /// + /// + public static ParameterModifier[] Unpack(this System.Reflection.ParameterModifier[] ctor) + { + var a = new ParameterModifier[ctor.Length]; + for (int i = 0; i < ctor.Length; i++) + a[i] = ctor[i].Unpack(); + + return a; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index 25f8018f33..ee05a37cea 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -32,6 +32,26 @@ public IModuleSymbolBuilder DefineModule(string name) return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name)); } + /// + public IModuleSymbolBuilder DefineModule(string name, string fileName) + { +#if NETFRAMEWORK + return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName)); +#else + return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name)); +#endif + } + + /// + public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo) + { +#if NETFRAMEWORK + return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName, emitSymbolInfo)); +#else + return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name)); +#endif + } + /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index e351e1813c..80c895b09d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -46,13 +46,13 @@ public IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttribute } /// - public ILGenerator GetILGenerator() + public IILGenerator GetILGenerator() { throw new NotImplementedException(); } /// - public ILGenerator GetILGenerator(int streamSize) + public IILGenerator GetILGenerator(int streamSize) { throw new NotImplementedException(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index 56030a0d76..dd970e657c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -1,9 +1,5 @@ using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.Linq; using System.Reflection; -using System.Threading; namespace IKVM.CoreLib.Symbols.Reflection { @@ -13,10 +9,6 @@ class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IMethodSymbol readonly MethodInfo _method; - Type[]? _genericParametersSource; - ReflectionTypeSymbol?[]? _genericParameters; - List<(Type[] Arguments, ReflectionMethodSymbol Symbol)>? _genericTypes; - /// /// Initializes a new instance. /// @@ -42,85 +34,6 @@ public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionTypeSym } - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - /// - internal ReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericParameterType) - { - if (genericParameterType is null) - throw new ArgumentNullException(nameof(genericParameterType)); - - Debug.Assert(genericParameterType.DeclaringMethod == _method); - - // initialize tables - _genericParametersSource ??= _method.GetGenericArguments(); - _genericParameters ??= new ReflectionTypeSymbol?[_genericParametersSource.Length]; - - // position of the parameter in the list - var idx = genericParameterType.GenericParameterPosition; - - // check that our list is long enough to contain the entire table - if (_genericParameters.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _genericParameters[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new ReflectionTypeSymbol(Context, ContainingModule, genericParameterType), null); - - // this should never happen - if (rec is not ReflectionTypeSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - /// - internal ReflectionMethodSymbol GetOrCreateGenericTypeSymbol(Type[] genericMethodArguments) - { - if (genericMethodArguments is null) - throw new ArgumentNullException(nameof(genericMethodArguments)); - - if (_method.IsGenericMethodDefinition == false) - throw new InvalidOperationException(); - - // initialize the available parameters - if (_genericParametersSource == null) - Interlocked.CompareExchange(ref _genericParametersSource, _method.GetGenericArguments(), null); - if (_genericParametersSource.Length != genericMethodArguments.Length) - throw new InvalidOperationException(); - - // initialize generic type map, and lock on it since we're potentially adding items - if (_genericTypes == null) - Interlocked.CompareExchange(ref _genericTypes, [], null); - - lock (_genericTypes) - { - // find existing entry - foreach (var i in _genericTypes) - if (i.Arguments.SequenceEqual(genericMethodArguments)) - return i.Symbol; - - // generate new symbol - ReflectionMethodSymbol sym; - if (ContainingType != null) - sym = new ReflectionMethodSymbol(Context, ContainingType, _method.MakeGenericMethod(genericMethodArguments)); - else - sym = new ReflectionMethodSymbol(Context, ContainingModule, _method.MakeGenericMethod(genericMethodArguments)); - - _genericTypes.Add((genericMethodArguments, sym)); - return sym; - } - } - /// /// Gets the underlying wrapped by this symbol. /// @@ -155,4 +68,4 @@ public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 40e7573443..f09c9748c6 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -2,6 +2,7 @@ using System.Diagnostics; using System.Linq; using System.Reflection; +using System.Reflection.Metadata.Ecma335; using System.Threading; using IKVM.CoreLib.Collections; @@ -61,6 +62,9 @@ static bool IsTypeDefinition(Type type) IndexRangeDictionary _parameterSymbols = new(); ReaderWriterLockSlim? _parameterLock; + IndexRangeDictionary _genericParameterSymbols = new(); + ReaderWriterLockSlim? _genericParameterLock; + /// /// Initializes a new instance. /// @@ -98,14 +102,17 @@ internal ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) Debug.Assert(type.Module == _module); - // type is not a definition, but is substituted + // type is a generic parameter (GenericParam) + if (type.IsGenericParameter) + return GetOrCreateGenericParameterSymbol(type); + + // type is not a type definition (TypeDef) if (IsTypeDefinition(type) == false) return GetOrCreateTypeSymbolForSpecification(type); // create lock on demand if (_typeLock == null) - lock (this) - _typeLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); using (_typeLock.CreateUpgradeableReadLock()) { @@ -156,21 +163,7 @@ ReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) if (type.IsGenericType) { var definitionTypeSymbol = ResolveTypeSymbol(type.GetGenericTypeDefinition()); - return definitionTypeSymbol.GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); - } - - // generic type parameter - if (type.IsGenericParameter && type.DeclaringMethod is null && type.DeclaringType is not null) - { - var declaringType = ResolveTypeSymbol(type.DeclaringType); - return declaringType.GetOrCreateGenericParameterSymbol(type); - } - - // generic method parameter - if (type.IsGenericParameter && type.DeclaringMethod is not null && type.DeclaringMethod.DeclaringType is not null) - { - var declaringMethod = ResolveTypeSymbol(type.DeclaringMethod.DeclaringType); - return declaringMethod.GetOrCreateGenericParameterSymbol(type); + return definitionTypeSymbol.GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); } throw new InvalidOperationException(); @@ -190,8 +183,7 @@ internal ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase metho // create lock on demand if (_methodLock == null) - lock (this) - _methodLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); using (_methodLock.CreateUpgradeableReadLock()) { @@ -251,8 +243,7 @@ internal ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) // create lock on demand if (_fieldLock == null) - lock (this) - _fieldLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); using (_fieldLock.CreateUpgradeableReadLock()) { @@ -287,8 +278,7 @@ internal ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo propert // create lock on demand if (_propertyLock == null) - lock (this) - _propertyLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); using (_propertyLock.CreateUpgradeableReadLock()) { @@ -320,8 +310,7 @@ internal ReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) // create lock on demand if (_eventLock == null) - lock (this) - _eventLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); using (_eventLock.CreateUpgradeableReadLock()) { @@ -352,8 +341,7 @@ internal ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo para // create lock on demand if (_parameterLock == null) - lock (this) - _parameterLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); using (_parameterLock.CreateUpgradeableReadLock()) { @@ -370,6 +358,35 @@ internal ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo para } } + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + /// + internal ReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericParameterType) + { + if (genericParameterType is null) + throw new ArgumentNullException(nameof(genericParameterType)); + + Debug.Assert(genericParameterType.Module == _module); + + // create lock on demand + if (_genericParameterLock == null) + Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); + + using (_genericParameterLock.CreateUpgradeableReadLock()) + { + var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.GetMetadataTokenSafe()); + var row = MetadataTokens.GetRowNumber(hnd); + if (_genericParameterSymbols[row] == null) + using (_genericParameterLock.CreateWriteLock()) + return _genericParameterSymbols[row] ??= new ReflectionTypeSymbol(Context, this, genericParameterType); + else + return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); + } + } + /// public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_module.Assembly); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index 8ee7be1096..5ad5fe2ab0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -297,6 +297,20 @@ protected internal ReflectionParameterSymbol[] ResolveParameterSymbols(Parameter return a; } + /// + /// Resolves the symbols for the specified parameters. + /// + /// + /// + protected internal ReflectionParameterSymbol[] ResolveGenericParameterSymbols(ParameterInfo[] parameters) + { + var a = new ReflectionParameterSymbol[parameters.Length]; + for (int i = 0; i < parameters.Length; i++) + a[i] = ResolveParameterSymbol(parameters[i]); + + return a; + } + /// /// Transforms a custom set of custom attribute data records to a symbol record. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index 652a3c8fce..d59075d06d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -1,7 +1,6 @@ using System; -using System.Collections.Generic; +using System.Collections.Concurrent; using System.Diagnostics; -using System.Linq; using System.Reflection; using System.Threading; @@ -21,12 +20,7 @@ class ReflectionTypeSymbol : ReflectionMemberSymbol, ITypeSymbol ReflectionTypeSymbol? _asSZArray; ReflectionTypeSymbol? _asPointer; ReflectionTypeSymbol? _asByRef; - - Type[]? _genericParameterList; - ReflectionTypeSymbol?[]? _genericParameterSymbols; - - List<(Type[] Arguments, ReflectionTypeSymbol Symbol)>? _genericTypeSymbols; - ReaderWriterLockSlim? _genericTypeLock; + ConcurrentDictionary? _genericTypeSymbols; /// /// Initializes a new instance. @@ -41,51 +35,12 @@ public ReflectionTypeSymbol(ReflectionSymbolContext context, ReflectionModuleSym _type = type ?? throw new ArgumentNullException(nameof(type)); } - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - /// - internal ReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericTypeParameterType) - { - if (genericTypeParameterType is null) - throw new ArgumentNullException(nameof(genericTypeParameterType)); - - Debug.Assert(genericTypeParameterType.DeclaringType == _type); - - // initialize tables - if (_genericParameterList == null) - Interlocked.CompareExchange(ref _genericParameterList, _type.GetGenericArguments(), null); - if (_genericParameterSymbols == null) - Interlocked.CompareExchange(ref _genericParameterSymbols, new ReflectionTypeSymbol?[_genericParameterList.Length], null); - - // position of the parameter in the list - var idx = genericTypeParameterType.GenericParameterPosition; - - // check that our list is long enough to contain the entire table - if (_genericParameterSymbols.Length < idx) - throw new IndexOutOfRangeException(); - - // if not yet created, create, allow multiple instances, but only one is eventually inserted - ref var rec = ref _genericParameterSymbols[idx]; - if (rec == null) - Interlocked.CompareExchange(ref rec, new ReflectionTypeSymbol(Context, ContainingModule, genericTypeParameterType), null); - - // this should never happen - if (rec is not ReflectionTypeSymbol sym) - throw new InvalidOperationException(); - - return sym; - } - /// /// Gets or creates the cached for the generic parameter type. /// /// /// - /// - internal ReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArguments) + internal ReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) { if (genericTypeArguments is null) throw new ArgumentNullException(nameof(genericTypeArguments)); @@ -93,45 +48,12 @@ internal ReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArg if (_type.IsGenericTypeDefinition == false) throw new InvalidOperationException(); - // initialize the available parameters - if (_genericParameterList == null) - Interlocked.CompareExchange(ref _genericParameterList, _type.GetGenericArguments(), null); - if (_genericParameterList.Length != genericTypeArguments.Length) - throw new InvalidOperationException(); - - // initialize generic type map, and lock on it since we're potentially adding items if (_genericTypeSymbols == null) - Interlocked.CompareExchange(ref _genericTypeSymbols, [], null); - if (_genericTypeLock == null) - Interlocked.CompareExchange(ref _genericTypeLock, new(), null); - - try - { - _genericTypeLock.EnterUpgradeableReadLock(); - - // find existing entry - foreach (var i in _genericTypeSymbols) - if (i.Arguments.SequenceEqual(genericTypeArguments)) - return i.Symbol; - - try - { - _genericTypeLock.EnterWriteLock(); - - // generate new symbol - var sym = new ReflectionTypeSymbol(Context, ContainingModule, _type.MakeGenericType(genericTypeArguments)); - _genericTypeSymbols.Add((genericTypeArguments, sym)); - return sym; - } - finally - { - _genericTypeLock.ExitWriteLock(); - } - } - finally - { - _genericTypeLock.ExitUpgradeableReadLock(); - } + Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); + + return _genericTypeSymbols.GetOrAdd( + genericTypeArguments, + _ => new ReflectionTypeSymbol(Context, ContainingModule, _type.MakeGenericType(genericTypeArguments.Unpack()))); } /// @@ -543,6 +465,48 @@ public IMemberSymbol[] GetMembers() return _type.GetMethod(name) is { } m ? ResolveMethodSymbol(m) : null; } + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _type.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { +#if NETFRAMEWORK + throw new NotImplementedException(); +#else + return _type.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; +#endif + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { +#if NETFRAMEWORK + throw new NotImplementedException(); +#else + return _type.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; +#endif + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _type.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { +#if NETFRAMEWORK + throw new NotImplementedException(); +#else + return _type.GetMethod(name, genericParameterCount, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; +#endif + } + /// public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) { @@ -676,7 +640,7 @@ public ITypeSymbol MakeByRefType() /// public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - throw new NotImplementedException(); + return GetOrCreateGenericTypeSymbol(typeArguments); } /// diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs new file mode 100644 index 0000000000..f4a39c701b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs @@ -0,0 +1,49 @@ +using System.Collections.Generic; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Compares two ReflectionTypeSymbol array instances for equality. + /// + class TypeSymbolListEqualityComparer : IEqualityComparer + { + + public static readonly TypeSymbolListEqualityComparer Instance = new(); + + public bool Equals(ITypeSymbol[]? x, ITypeSymbol[]? y) + { + if (x == y) + return true; + + if (x == null || y == null) + return false; + + if (x.Length != y.Length) + return false; + + for (int i = 0; i < x.Length; i++) + if (x[i] != y[i]) + return false; + + return true; + } + + public int GetHashCode(ITypeSymbol[] obj) + { + int result = 17; + + for (int i = 0; i < obj.Length; i++) + { + unchecked + { + result = result * 23 + obj[i].GetHashCode(); + } + } + + return result; + } + + } + +} diff --git a/src/IKVM.Reflection/BuiltinArrayMethod.cs b/src/IKVM.Reflection/BuiltinArrayMethod.cs index 1785c0f206..b008e05206 100644 --- a/src/IKVM.Reflection/BuiltinArrayMethod.cs +++ b/src/IKVM.Reflection/BuiltinArrayMethod.cs @@ -94,7 +94,7 @@ public override int MetadataToken get { return 0x08000000; } } - internal override Module Module + public override Module Module { get { return method.Module; } } diff --git a/src/IKVM.Reflection/Emit/MethodBuilder.cs b/src/IKVM.Reflection/Emit/MethodBuilder.cs index a7271bffc7..db75abaf6b 100644 --- a/src/IKVM.Reflection/Emit/MethodBuilder.cs +++ b/src/IKVM.Reflection/Emit/MethodBuilder.cs @@ -510,7 +510,7 @@ public override int MetadataToken } } - internal override Module Module + public override Module Module { get { return method.Module; } } diff --git a/src/IKVM.Reflection/Emit/ParameterBuilder.cs b/src/IKVM.Reflection/Emit/ParameterBuilder.cs index dd9831b57d..153c18cd50 100644 --- a/src/IKVM.Reflection/Emit/ParameterBuilder.cs +++ b/src/IKVM.Reflection/Emit/ParameterBuilder.cs @@ -22,7 +22,6 @@ Jeroen Frijters */ using System.Reflection.Metadata; -using System.Reflection.Metadata.Ecma335; namespace IKVM.Reflection.Emit { diff --git a/src/IKVM.Reflection/GenericParameterInfoImpl.cs b/src/IKVM.Reflection/GenericParameterInfoImpl.cs index 18b3c28575..45f48a7e04 100644 --- a/src/IKVM.Reflection/GenericParameterInfoImpl.cs +++ b/src/IKVM.Reflection/GenericParameterInfoImpl.cs @@ -86,7 +86,7 @@ public override int MetadataToken get { return parameterInfo.MetadataToken; } } - internal override Module Module + public override Module Module { get { return method.Module; } } diff --git a/src/IKVM.Reflection/MissingMethod.cs b/src/IKVM.Reflection/MissingMethod.cs index 67e9bd0c26..6f06daf4d3 100644 --- a/src/IKVM.Reflection/MissingMethod.cs +++ b/src/IKVM.Reflection/MissingMethod.cs @@ -157,7 +157,7 @@ public override int MetadataToken get { return Forwarder.MetadataToken; } } - internal override Module Module + public override Module Module { get { return method.Module; } } diff --git a/src/IKVM.Reflection/ParameterInfo.cs b/src/IKVM.Reflection/ParameterInfo.cs index 655f54efc6..2d2a8aa5f8 100644 --- a/src/IKVM.Reflection/ParameterInfo.cs +++ b/src/IKVM.Reflection/ParameterInfo.cs @@ -32,7 +32,7 @@ public abstract class ParameterInfo : ICustomAttributeProvider /// /// Initializes a new instance. /// - internal ParameterInfo() + public ParameterInfo() { } @@ -76,7 +76,7 @@ public sealed override int GetHashCode() public abstract int MetadataToken { get; } - internal abstract Module Module { get; } + public abstract Module Module { get; } public Type[] GetOptionalCustomModifiers() { @@ -201,7 +201,7 @@ public override int MetadataToken get { return forward.MetadataToken; } } - internal override Module Module + public override Module Module { get { return member.Module; } } diff --git a/src/IKVM.Reflection/PropertyInfo.cs b/src/IKVM.Reflection/PropertyInfo.cs index 7ee8f82899..ab053a03fb 100644 --- a/src/IKVM.Reflection/PropertyInfo.cs +++ b/src/IKVM.Reflection/PropertyInfo.cs @@ -125,7 +125,7 @@ public override int MetadataToken get { return 0x08000000; } } - internal override Module Module + public override Module Module { get { return property.Module; } } diff --git a/src/IKVM.Reflection/Reader/ParameterInfoImpl.cs b/src/IKVM.Reflection/Reader/ParameterInfoImpl.cs index e73bc63ea3..451995e574 100644 --- a/src/IKVM.Reflection/Reader/ParameterInfoImpl.cs +++ b/src/IKVM.Reflection/Reader/ParameterInfoImpl.cs @@ -144,7 +144,7 @@ public override int MetadataToken } } - internal override Module Module + public override Module Module { get { return method.Module; } } diff --git a/src/IKVM.Reflection/Type.cs b/src/IKVM.Reflection/Type.cs index 4d90961cf6..38bea7747b 100644 --- a/src/IKVM.Reflection/Type.cs +++ b/src/IKVM.Reflection/Type.cs @@ -553,6 +553,21 @@ public bool IsEnumDefined(object value) return false; } + public Array GetEnumValues() + { + if (!IsEnum) + throw new ArgumentException(); + + var l = __GetDeclaredFields(); + var a = new object[l.Length]; + + for (int i = 0; i < l.Length; i++) + if (l[i].IsLiteral) + a[i] = l[i]; + + return a; + } + public override string ToString() { return FullName; From 5eeefa0517c279a0f9dfcc5d5dda5b4d4b48d875 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 15 Sep 2024 23:28:14 -0500 Subject: [PATCH 05/59] ! --- .../Reflection/ReflectionSymbolTests.cs | 54 ------------------- .../IkvmReflectionAssemblySymbol.cs | 3 +- .../IkvmReflectionModuleSymbol.cs | 24 ++++----- .../Reflection/ReflectionModuleSymbol.cs | 41 +++----------- 4 files changed, 18 insertions(+), 104 deletions(-) diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index c275119379..93ce79548e 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -420,60 +420,6 @@ public void CanCompleteTypeBuilder() moduleSymbol.GetType("DynamicType1").Should().BeSameAs(type1SymbolAgain); } - [TestMethod] - public void CanCreateAndResolveDynamicMethodOnModule() - { - var c = new ReflectionSymbolContext(); - - var method1 = new DynamicMethod("DynamicMethod1", null, null, typeof(ReflectionSymbolTests).Module); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - } - - [TestMethod] - public void CanCreateAndResolveMultipleDynamicMethodsOnModule() - { - var c = new ReflectionSymbolContext(); - - var method1 = new DynamicMethod("DynamicMethod1", null, null, typeof(ReflectionSymbolTests).Module); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - - var method2 = new DynamicMethod("DynamicMethod2", null, null, typeof(ReflectionSymbolTests).Module); - var method2Symbol = c.GetOrCreateMethodSymbol(method2); - method2Symbol.Should().BeOfType(); - method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); - } - - [TestMethod] - public void CanCreateAndResolveDynamicMethodOnType() - { - var c = new ReflectionSymbolContext(); - - var method1 = new DynamicMethod("DynamicMethod", null, null, typeof(ReflectionSymbolTests)); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - } - - [TestMethod] - public void CanCreateAndResolveMultipleDynamicMethodsOnType() - { - var c = new ReflectionSymbolContext(); - - var method1 = new DynamicMethod("DynamicMethod1", null, null, typeof(ReflectionSymbolTests)); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - - var method2 = new DynamicMethod("DynamicMethod2", null, null, typeof(ReflectionSymbolTests)); - var method2Symbol = c.GetOrCreateMethodSymbol(method2); - method2Symbol.Should().BeOfType(); - method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 50bb64af92..239580c9b6 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -53,8 +53,7 @@ internal IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) // create lock on demand if (_moduleLock == null) - lock (this) - _moduleLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _moduleLock, new ReaderWriterLockSlim(), null); using (_moduleLock.CreateUpgradeableReadLock()) { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index daafbe9ac6..e1ad04c5dc 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -57,11 +57,11 @@ static bool IsTypeDefinition(Type type) IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _eventLock; - IndexRangeDictionary _parameterTable = new(); - IndexRangeDictionary _parameterSymbols = new(); + IndexRangeDictionary _parameterTable = new(maxCapacity: MAX_CAPACITY); + IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _parameterLock; - IndexRangeDictionary _genericParameterSymbols = new(); + IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _genericParameterLock; /// @@ -111,8 +111,7 @@ internal IkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) // create lock on demand if (_typeLock == null) - lock (this) - _typeLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); using (_typeLock.CreateUpgradeableReadLock()) { @@ -183,8 +182,7 @@ internal IkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase m // create lock on demand if (_methodLock == null) - lock (this) - _methodLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); using (_methodLock.CreateUpgradeableReadLock()) { @@ -244,8 +242,7 @@ internal IkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) // create lock on demand if (_fieldLock == null) - lock (this) - _fieldLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); using (_fieldLock.CreateUpgradeableReadLock()) { @@ -280,8 +277,7 @@ internal IkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo pro // create lock on demand if (_propertyLock == null) - lock (this) - _propertyLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); using (_propertyLock.CreateUpgradeableReadLock()) { @@ -313,8 +309,7 @@ internal IkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) // create lock on demand if (_eventLock == null) - lock (this) - _eventLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); using (_eventLock.CreateUpgradeableReadLock()) { @@ -345,8 +340,7 @@ internal IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo // create lock on demand if (_parameterLock == null) - lock (this) - _parameterLock ??= new ReaderWriterLockSlim(); + Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); using (_parameterLock.CreateUpgradeableReadLock()) { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index f09c9748c6..57717f7bc5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -2,6 +2,7 @@ using System.Diagnostics; using System.Linq; using System.Reflection; +using System.Reflection.Emit; using System.Reflection.Metadata.Ecma335; using System.Threading; @@ -38,31 +39,25 @@ static bool IsTypeDefinition(Type type) readonly ReflectionAssemblySymbol _containingAssembly; Module _module; - IndexRangeDictionary _typeTable = new(maxCapacity: MAX_CAPACITY); IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _typeLock; - IndexRangeDictionary _methodTable = new(maxCapacity: MAX_CAPACITY); IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _methodLock; - IndexRangeDictionary _fieldTable = new(maxCapacity: MAX_CAPACITY); IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _fieldLock; - IndexRangeDictionary _propertyTable = new(maxCapacity: MAX_CAPACITY); IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _propertyLock; - IndexRangeDictionary _eventTable = new(maxCapacity: MAX_CAPACITY); IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _eventLock; - IndexRangeDictionary _parameterTable = new(); - IndexRangeDictionary _parameterSymbols = new(); + IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _parameterLock; - IndexRangeDictionary _genericParameterSymbols = new(); + IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); ReaderWriterLockSlim? _genericParameterLock; /// @@ -117,10 +112,6 @@ internal ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) using (_typeLock.CreateUpgradeableReadLock()) { var row = type.GetMetadataTokenRowNumberSafe(); - if (_typeTable[row] != type) - using (_typeLock.CreateWriteLock()) - _typeTable[row] = type; - if (_typeSymbols[row] == null) using (_typeLock.CreateWriteLock()) return _typeSymbols[row] ??= new ReflectionTypeSymbol(Context, this, type); @@ -170,7 +161,7 @@ ReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) } /// - /// Gets or creates the cached fqor the type by method. + /// Gets or creates the cached for the type by method. /// /// /// @@ -181,6 +172,10 @@ internal ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase metho Debug.Assert(method.Module.GetMetadataTokenSafe() == _module.GetMetadataTokenSafe()); + // they are methods, but they are associated differently + if (method is DynamicMethod) + throw new ArgumentException("Dynamic methods cannot be attached to context."); + // create lock on demand if (_methodLock == null) Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); @@ -188,10 +183,6 @@ internal ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase metho using (_methodLock.CreateUpgradeableReadLock()) { var row = method.GetMetadataTokenRowNumberSafe(); - if (_methodTable[row] != method) - using (_methodLock.CreateWriteLock()) - _methodTable[row] = method; - if (_methodSymbols[row] == null) using (_methodLock.CreateWriteLock()) if (method is ConstructorInfo c) @@ -248,10 +239,6 @@ internal ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) using (_fieldLock.CreateUpgradeableReadLock()) { var row = field.GetMetadataTokenRowNumberSafe(); - if (_fieldTable[row] != field) - using (_fieldLock.CreateWriteLock()) - _fieldTable[row] = field; - if (_fieldSymbols[row] == null) using (_fieldLock.CreateWriteLock()) if (field.DeclaringType is { } dt) @@ -283,10 +270,6 @@ internal ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo propert using (_propertyLock.CreateUpgradeableReadLock()) { var row = property.GetMetadataTokenRowNumberSafe(); - if (_propertyTable[row] != property) - using (_propertyLock.CreateWriteLock()) - _propertyTable[row] = property; - if (_propertySymbols[row] == null) using (_propertyLock.CreateWriteLock()) return _propertySymbols[row] ??= new ReflectionPropertySymbol(Context, ResolveTypeSymbol(property.DeclaringType!), property); @@ -315,10 +298,6 @@ internal ReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) using (_eventLock.CreateUpgradeableReadLock()) { var row = @event.GetMetadataTokenRowNumberSafe(); - if (_eventTable[row] is not EventInfo i || i != @event) - using (_eventLock.CreateWriteLock()) - _eventTable[row] = @event; - if (_eventSymbols[row] == null) using (_eventLock.CreateWriteLock()) return _eventSymbols[row] ??= new ReflectionEventSymbol(Context, ResolveTypeSymbol(@event.DeclaringType!), @event); @@ -346,10 +325,6 @@ internal ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo para using (_parameterLock.CreateUpgradeableReadLock()) { var position = parameter.Position; - if (_parameterTable[position] != parameter) - using (_parameterLock.CreateWriteLock()) - _parameterTable[position] = parameter; - if (_parameterSymbols[position] == null) using (_parameterLock.CreateWriteLock()) return _parameterSymbols[position] ??= new ReflectionParameterSymbol(Context, ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); From cc527085c5ce81c85f53d36f1d41caa7d0abaa07 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 18 Sep 2024 10:51:40 -0500 Subject: [PATCH 06/59] Rebuild. --- .../IkvmReflectionSymbolTests.cs | 451 ++++++------ .../Reflection/ReflectionSymbolTests.cs | 51 +- src/IKVM.CoreLib/IKVM.CoreLib.csproj | 12 + .../ReflectionExtensions.cs} | 128 +++- .../Symbols/Emit/IAssemblySymbolBuilder.cs | 11 +- .../Symbols/Emit/IConstructorSymbolBuilder.cs | 2 +- .../Symbols/Emit/IEventSymbolBuilder.cs | 2 +- .../Symbols/Emit/IFieldSymbolBuilder.cs | 2 +- .../IGenericTypeParameterSymbolBuilder.cs | 21 +- src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs | 257 +++++++ src/IKVM.CoreLib/Symbols/Emit/ILabel.cs | 6 + .../Symbols/Emit/ILocalBuilder.cs | 42 ++ .../Symbols/Emit/IMemberSymbolBuilder.cs | 11 + .../Symbols/Emit/IMethodBaseSymbolBuilder.cs | 11 + .../Symbols/Emit/IMethodSymbolBuilder.cs | 2 +- .../Symbols/Emit/IModuleSymbolBuilder.cs | 7 +- .../Symbols/Emit/IParameterSymbolBuilder.cs | 2 +- .../Symbols/Emit/IPropertySymbolBuilder.cs | 26 +- .../Symbols/Emit/ISignatureHelper.cs | 6 + .../Symbols/Emit/ISymbolBuilder.cs | 10 +- .../Symbols/Emit/ITypeSymbolBuilder.cs | 9 +- src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs | 2 + src/IKVM.CoreLib/Symbols/IEventSymbol.cs | 2 + src/IKVM.CoreLib/Symbols/IFieldSymbol.cs | 2 + src/IKVM.CoreLib/Symbols/IMethodSymbol.cs | 4 +- src/IKVM.CoreLib/Symbols/IParameterSymbol.cs | 2 + src/IKVM.CoreLib/Symbols/IPropertySymbol.cs | 2 + src/IKVM.CoreLib/Symbols/ISymbol.cs | 5 + src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 48 ++ .../IkvmReflectionAssemblySymbolBuilder.cs | 79 --- .../IkvmReflectionConstructorSymbolBuilder.cs | 74 -- .../IkvmReflectionCustomAttributeBuilder.cs | 29 - .../Emit/IkvmReflectionEventSymbolBuilder.cs | 70 -- .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 88 --- .../IkvmReflectionMethodBaseSymbolBuilder.cs | 49 -- .../Emit/IkvmReflectionMethodSymbolBuilder.cs | 107 --- .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 98 --- .../IkvmReflectionParameterBuilderInfo.cs | 68 -- .../IkvmReflectionParameterSymbolBuilder.cs | 106 --- .../IkvmReflectionAssemblySymbol.cs | 196 ----- .../IkvmReflectionConstructorSymbol.cs | 37 - .../IkvmReflectionEventSymbol.cs | 108 --- .../IkvmReflectionFieldSymbol.cs | 116 --- .../IkvmReflectionMemberSymbol.cs | 275 ------- .../IkvmReflectionMethodBaseSymbol.cs | 133 ---- .../IkvmReflectionMethodSymbol.cs | 71 -- .../IkvmReflectionModuleSymbol.cs | 587 --------------- .../IkvmReflectionParameterSymbol.cs | 119 ---- .../IkvmReflectionPropertySymbol.cs | 131 ---- .../IkvmReflection/IkvmReflectionSymbol.cs | 417 ----------- .../IkvmReflectionSymbolContext.cs | 180 ----- .../IkvmReflectionTypeSymbol.cs | 669 ------------------ .../IkvmReflection/IkvmReflectionUtil.cs | 195 ----- .../Emit/IReflectionAssemblySymbolBuilder.cs | 18 + .../IReflectionConstructorSymbolBuilder.cs | 15 + .../Emit/IReflectionEventSymbolBuilder.cs | 15 + .../Emit/IReflectionFieldSymbolBuilder.cs | 15 + ...ectionGenericTypeParameterSymbolBuilder.cs | 24 + .../Emit/IReflectionMemberSymbolBuilder.cs | 17 + .../IReflectionMethodBaseSymbolBuilder.cs | 13 + .../Emit/IReflectionMethodSymbolBuilder.cs | 18 + .../Emit/IReflectionModuleSymbolBuilder.cs | 18 + .../Emit/IReflectionParameterSymbolBuilder.cs | 23 + .../Emit/IReflectionPropertySymbolBuilder.cs | 15 + .../Emit/IReflectionSymbolBuilder.cs | 19 + .../Emit/IReflectionTypeSymbolBuilder.cs | 18 + .../Emit/ReflectionAssemblySymbolBuilder.cs | 168 ++++- .../ReflectionConstructorSymbolBuilder.cs | 53 +- .../Emit/ReflectionCustomAttributeBuilder.cs | 2 +- .../Emit/ReflectionEventBuilderInfo.cs | 1 + .../Emit/ReflectionEventSymbolBuilder.cs | 125 +++- .../Emit/ReflectionFieldSymbolBuilder.cs | 141 ++-- ...ectionGenericTypeParameterSymbolBuilder.cs | 583 +++++++++++++++ .../Emit/ReflectionMemberSymbolBuilder.cs | 392 ++++++++++ .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 131 +++- .../Emit/ReflectionMethodSymbolBuilder.cs | 103 ++- .../Emit/ReflectionModuleSymbolBuilder.cs | 323 ++++++++- .../Emit/ReflectionParameterBuilderInfo.cs | 9 +- .../Emit/ReflectionParameterSymbolBuilder.cs | 160 +++-- .../Emit/ReflectionPropertySymbolBuilder.cs | 161 ++++- .../Emit/ReflectionSymbolBuilder.cs | 74 +- .../Emit/ReflectionTypeSymbolBuilder.cs | 660 +++++++++++++++-- .../Reflection/IReflectionAssemblySymbol.cs | 33 + .../IReflectionConstructorSymbol.cs | 16 + .../Reflection/IReflectionEventSymbol.cs | 11 + .../Reflection/IReflectionFieldSymbol.cs | 16 + .../Reflection/IReflectionMemberSymbol.cs | 26 + .../Reflection/IReflectionMethodBaseSymbol.cs | 16 + .../Reflection/IReflectionMethodSymbol.cs | 16 + .../Reflection/IReflectionModuleSymbol.cs | 123 ++++ .../Reflection/IReflectionParameterSymbol.cs | 26 + .../Reflection/IReflectionPropertySymbol.cs | 16 + .../Symbols/Reflection/IReflectionSymbol.cs | 335 +++++++++ .../Reflection/IReflectionTypeSymbol.cs | 16 + .../Reflection/ReflectionAssemblyMetadata.cs | 66 ++ .../Reflection/ReflectionAssemblySymbol.cs | 76 +- .../Reflection/ReflectionConstructorSymbol.cs | 29 +- .../Reflection/ReflectionEventSymbol.cs | 53 +- .../Reflection/ReflectionFieldSymbol.cs | 73 +- .../ReflectionGenericTypeParameterSymbol.cs | 562 +++++++++++++++ .../Reflection/ReflectionMemberSymbol.cs | 346 +++++---- .../Reflection/ReflectionMethodBaseSymbol.cs | 85 +-- .../Reflection/ReflectionMethodSymbol.cs | 34 +- .../Reflection/ReflectionModuleMetadata.cs | 488 +++++++++++++ .../Reflection/ReflectionModuleSymbol.cs | 504 ++++--------- .../Reflection/ReflectionParameterSymbol.cs | 72 +- .../Reflection/ReflectionPropertySymbol.cs | 59 +- .../Symbols/Reflection/ReflectionSymbol.cs | 527 ++++++++------ .../Reflection/ReflectionSymbolContext.cs | 214 ++++-- .../Reflection/ReflectionSymbolExtensions.cs | 11 + .../Symbols/Reflection/ReflectionTypeImpl.cs | 633 +++++++++++++++++ .../Reflection/ReflectionTypeSymbol.cs | 486 +++++-------- .../Symbols/Reflection/ReflectionUtil.cs | 79 ++- src/IKVM.Runtime/Annotation.cs | 15 +- src/IKVM.Runtime/AttributeHelper.cs | 289 ++++---- .../Attributes/EnclosingMethodAttribute.cs | 3 +- src/IKVM.Runtime/BootstrapClassLoader.cs | 6 +- src/IKVM.Runtime/CodeEmitter.cs | 659 ++++++++--------- src/IKVM.Runtime/CodeEmitterLabel.cs | 11 +- src/IKVM.Runtime/DefineMethodHelper.cs | 30 +- src/IKVM.Runtime/DynamicClassLoader.cs | 94 +-- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 23 + src/IKVM.Runtime/ReflectUtil.cs | 10 +- src/IKVM.Runtime/RuntimeArrayJavaType.cs | 11 +- .../RuntimeByteCodeJavaType.DynamicImpl.cs | 11 +- ...untimeByteCodeJavaType.FinishedTypeImpl.cs | 19 +- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 106 ++- src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 172 ++--- .../RuntimeByteCodePropertyJavaField.cs | 39 +- src/IKVM.Runtime/RuntimeClassLoader.cs | 9 +- src/IKVM.Runtime/RuntimeClassLoaderFactory.cs | 21 +- src/IKVM.Runtime/RuntimeGhostJavaMethod.cs | 13 +- src/IKVM.Runtime/RuntimeJavaTypeFactory.cs | 3 +- ...anagedByteCodeJavaType.RemappedJavaType.cs | 5 +- .../RuntimeManagedByteCodeJavaType.cs | 29 +- ...tionJavaType.MultipleAnnotationJavaType.cs | 25 +- ...nJavaType.ReturnValueAnnotationJavaType.cs | 22 +- ...gedJavaType.AttributeAnnotationJavaType.cs | 36 +- ...ntimeManagedJavaType.DelegateJavaMethod.cs | 7 +- ...ntimeManagedJavaType.EnumValueJavaField.cs | 6 +- src/IKVM.Runtime/RuntimeManagedJavaType.cs | 2 +- .../RuntimeManagedJavaTypeFactory.cs | 2 +- .../RuntimeSimpleCallJavaMethod.cs | 3 +- src/IKVM.Runtime/RuntimeUnloadableJavaType.cs | 2 +- src/IKVM.Runtime/RuntimeVerifierJavaType.cs | 4 +- src/IKVM.Runtime/StubGen/StubGenerator.cs | 65 +- src/IKVM.Runtime/SymbolExtensions.cs | 77 ++ src/IKVM.Tools.Exporter/ExportImpl.cs | 7 +- src/IKVM.Tools.Exporter/FakeTypes.cs | 15 +- .../ManagedTypeResolver.cs | 62 +- .../RuntimeBootstrapClassLoader.cs | 12 +- .../RuntimeStubJavaType.cs | 5 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 8 +- .../RuntimeImportByteCodeJavaType.cs | 160 +++-- 154 files changed, 8562 insertions(+), 7035 deletions(-) rename src/IKVM.CoreLib/{System/TypeExtensions.cs => Reflection/ReflectionExtensions.cs} (76%) create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ILabel.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs create mode 100644 src/IKVM.CoreLib/Symbols/ISymbolContext.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index 22936c64dd..47eb9aed49 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -1,230 +1,221 @@ -using System.IO; - -using FluentAssertions; - -using IKVM.CoreLib.Symbols.IkvmReflection; -using IKVM.Reflection; - -using Microsoft.VisualStudio.TestPlatform.PlatformAbstractions; -using Microsoft.VisualStudio.TestTools.UnitTesting; - -namespace IKVM.CoreLib.Tests.Symbols.IkvmReflection -{ - - [TestClass] - public class IkvmReflectionSymbolTests - { - - class Foo - { - - T? field; - - bool Method(int p1) => true; - - } - - Universe? universe; - Assembly? coreAssembly; - Assembly? thisAssembly; - - [TestInitialize] - public void Setup() - { - universe = new Universe(typeof(object).Assembly.GetName().Name); - universe.AssemblyResolve += Universe_AssemblyResolve; - coreAssembly = universe.LoadFile(typeof(object).Assembly.GetAssemblyLocation()); - thisAssembly = universe.LoadFile(typeof(IkvmReflectionSymbolTests).Assembly.GetAssemblyLocation()); - } - - /// - /// Attempt to load assembly from system. - /// - /// - /// - /// - Assembly? Universe_AssemblyResolve(object sender, ResolveEventArgs args) - { - try - { - var asm = System.Reflection.Assembly.Load(args.Name); - if (asm != null && File.Exists(asm.Location)) - return universe!.LoadFile(asm.Location); - } - catch - { - - } - - return null; - } - - [TestMethod] - public void SameTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Object")); - var s2 = c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Object")); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void GenericTypeDefinitionShouldBeSame() - { - var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1"); - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(t); - var s2 = c.GetOrCreateTypeSymbol(t); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void GenericTypeShouldBeSame() - { - var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(universe!.GetBuiltInType("System", "Int32")); - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(t); - var s2 = c.GetOrCreateTypeSymbol(t); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void ArrayTypeShouldBeSame() - { - var t = universe!.GetBuiltInType("System", "Object").MakeArrayType(2); - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(t); - var s2 = c.GetOrCreateTypeSymbol(t); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void SZArrayTypeShouldBeSame() - { - var t = universe!.GetBuiltInType("System", "Object").MakeArrayType(); - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(t); - var s2 = c.GetOrCreateTypeSymbol(t); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public unsafe void PointerTypeShouldBeSame() - { - var t = universe!.GetBuiltInType("System", "Int32").MakePointerType(); - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(t); - var s2 = c.GetOrCreateTypeSymbol(t); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public unsafe void ByRefTypeShouldBeSame() - { - var t = universe!.GetBuiltInType("System", "Int32").MakeByRefType(); - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(t); - var s2 = c.GetOrCreateTypeSymbol(t); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void EnumTypeShouldBeSame() - { - var a = universe!.Load(typeof(System.AttributeTargets).Assembly.FullName); - var t = a.GetType("System.AttributeTargets"); - var c = new IkvmReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(t); - var s2 = c.GetOrCreateTypeSymbol(t); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void CanGetType() - { - var t = universe!.GetBuiltInType("System", "Object"); - var c = new IkvmReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(t); - s.Name.Should().Be("Object"); - s.FullName.Should().Be("System.Object"); - } - - [TestMethod] - public void CanGetFieldOfGenericTypeDefinition() - { - var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1"); - var c = new IkvmReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(t); - s.IsGenericType.Should().BeTrue(); - s.IsGenericTypeDefinition.Should().BeTrue(); - var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); - f.Name.Should().Be("field"); - f.FieldType.IsGenericType.Should().BeFalse(); - f.FieldType.IsGenericParameter.Should().BeTrue(); - } - - [TestMethod] - public void CanGetFieldOfGenericType() - { - var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(universe!.GetBuiltInType("System", "Int32")); - var c = new IkvmReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(t); - s.IsGenericType.Should().BeTrue(); - s.IsGenericTypeDefinition.Should().BeFalse(); - var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); - f.Name.Should().Be("field"); - f.FieldType.IsGenericType.Should().BeFalse(); - f.FieldType.IsGenericParameter.Should().BeFalse(); - f.FieldType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Int32"))); - } - - [TestMethod] - public void CanGetMethod() - { - var t = universe!.GetBuiltInType("System", "Object"); - var c = new IkvmReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(t); - var m = s.GetMethod("ToString"); - m.Name.Should().Be("ToString"); - m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "String"))); - m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "String"))); - m.IsGenericMethod.Should().BeFalse(); - m.IsGenericMethodDefinition.Should().BeFalse(); - m.IsPublic.Should().BeTrue(); - m.IsPrivate.Should().BeFalse(); - } - - [System.AttributeUsage(System.AttributeTargets.Class)] - class AttributeWithType : System.Attribute - { - - public AttributeWithType(System.Type type) - { - Type = type; - } - - public System.Type Type { get; } - - } - - [AttributeWithType(typeof(object))] - class ClassWithAttributeWithType - { - - - - } - - [TestMethod] - public void CanReadCustomAttributes() - { - var c = new IkvmReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); - var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); - var v = a.Value.ConstructorArguments[0].Value; - v.Should().BeOfType(); - } - - } - -} +//using System.IO; + +//using FluentAssertions; + +//using IKVM.CoreLib.Symbols.IkvmReflection; +//using IKVM.Reflection; + +//using Microsoft.VisualStudio.TestPlatform.PlatformAbstractions; +//using Microsoft.VisualStudio.TestTools.UnitTesting; + +//namespace IKVM.CoreLib.Tests.Symbols.IkvmReflection +//{ + +// [TestClass] +// public class IkvmReflectionSymbolTests +// { + +// class Foo +// { + +// T? field; + +// bool Method(int p1) => true; + +// } + +// Universe? universe; +// Assembly? coreAssembly; +// Assembly? thisAssembly; + +// [TestInitialize] +// public void Setup() +// { +// universe = new Universe(typeof(object).Assembly.GetName().Name); +// universe.AssemblyResolve += Universe_AssemblyResolve; +// coreAssembly = universe.LoadFile(typeof(object).Assembly.GetAssemblyLocation()); +// thisAssembly = universe.LoadFile(typeof(IkvmReflectionSymbolTests).Assembly.GetAssemblyLocation()); +// } + +// /// +// /// Attempt to load assembly from system. +// /// +// /// +// /// +// /// +// Assembly? Universe_AssemblyResolve(object sender, ResolveEventArgs args) +// { +// try +// { +// var asm = System.Reflection.Assembly.Load(args.Name); +// if (asm != null && File.Exists(asm.Location)) +// return universe!.LoadFile(asm.Location); +// } +// catch +// { + +// } + +// return null; +// } + +// [TestMethod] +// public void SameTypeShouldBeSame() +// { +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Object")); +// var s2 = c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Object")); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public void GenericTypeDefinitionShouldBeSame() +// { +// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1"); +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(t); +// var s2 = c.GetOrCreateTypeSymbol(t); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public void GenericTypeShouldBeSame() +// { +// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(universe!.GetBuiltInType("System", "Int32")); +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(t); +// var s2 = c.GetOrCreateTypeSymbol(t); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public void ArrayTypeShouldBeSame() +// { +// var t = universe!.GetBuiltInType("System", "Object").MakeArrayType(2); +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(t); +// var s2 = c.GetOrCreateTypeSymbol(t); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public void SZArrayTypeShouldBeSame() +// { +// var t = universe!.GetBuiltInType("System", "Object").MakeArrayType(); +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(t); +// var s2 = c.GetOrCreateTypeSymbol(t); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public unsafe void PointerTypeShouldBeSame() +// { +// var t = universe!.GetBuiltInType("System", "Int32").MakePointerType(); +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(t); +// var s2 = c.GetOrCreateTypeSymbol(t); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public unsafe void ByRefTypeShouldBeSame() +// { +// var t = universe!.GetBuiltInType("System", "Int32").MakeByRefType(); +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(t); +// var s2 = c.GetOrCreateTypeSymbol(t); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public void EnumTypeShouldBeSame() +// { +// var a = universe!.Load(typeof(System.AttributeTargets).Assembly.FullName); +// var t = a.GetType("System.AttributeTargets"); +// var c = new IkvmReflectionSymbolContext(); +// var s1 = c.GetOrCreateTypeSymbol(t); +// var s2 = c.GetOrCreateTypeSymbol(t); +// s1.Should().BeSameAs(s2); +// } + +// [TestMethod] +// public void CanGetType() +// { +// var t = universe!.GetBuiltInType("System", "Object"); +// var c = new IkvmReflectionSymbolContext(); +// var s = c.GetOrCreateTypeSymbol(t); +// s.Name.Should().Be("Object"); +// s.FullName.Should().Be("System.Object"); +// } + +// [TestMethod] +// public void CanGetFieldOfGenericTypeDefinition() +// { +// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1"); +// var c = new IkvmReflectionSymbolContext(); +// var s = c.GetOrCreateTypeSymbol(t); +// s.IsGenericType.Should().BeTrue(); +// s.IsGenericTypeDefinition.Should().BeTrue(); +// var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); +// f.Name.Should().Be("field"); +// f.FieldType.IsGenericType.Should().BeFalse(); +// f.FieldType.IsGenericParameter.Should().BeTrue(); +// } + +// [TestMethod] +// public void CanGetFieldOfGenericType() +// { +// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(universe!.GetBuiltInType("System", "Int32")); +// var c = new IkvmReflectionSymbolContext(); +// var s = c.GetOrCreateTypeSymbol(t); +// s.IsGenericType.Should().BeTrue(); +// s.IsGenericTypeDefinition.Should().BeFalse(); +// var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); +// f.Name.Should().Be("field"); +// f.FieldType.IsGenericType.Should().BeFalse(); +// f.FieldType.IsGenericParameter.Should().BeFalse(); +// f.FieldType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Int32"))); +// } + +// [TestMethod] +// public void CanGetMethod() +// { +// var t = universe!.GetBuiltInType("System", "Object"); +// var c = new IkvmReflectionSymbolContext(); +// var s = c.GetOrCreateTypeSymbol(t); +// var m = s.GetMethod("ToString"); +// m.Name.Should().Be("ToString"); +// m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "String"))); +// m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "String"))); +// m.IsGenericMethod.Should().BeFalse(); +// m.IsGenericMethodDefinition.Should().BeFalse(); +// m.IsPublic.Should().BeTrue(); +// m.IsPrivate.Should().BeFalse(); +// } + +// [System.AttributeUsage(System.AttributeTargets.Class)] +// class AttributeWithType : System.Attribute +// { + +// public AttributeWithType(System.Type type) +// { +// Type = type; +// } + +// public System.Type Type { get; } + +// } +// [TestMethod] +// public void CanReadCustomAttributes() +// { +// var c = new IkvmReflectionSymbolContext(); +// var s = c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); +// var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); +// var v = a.Value.ConstructorArguments[0].Value; +// v.Should().BeOfType(); +// } + +// } + +//} diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index 93ce79548e..5d01df9423 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -5,6 +5,7 @@ using FluentAssertions; +using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Reflection; using IKVM.CoreLib.Symbols.Reflection.Emit; @@ -219,7 +220,7 @@ public void CanResolveAssemblyBuilder() var c = new ReflectionSymbolContext(); var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); var assemblySymbol = c.GetOrCreateAssemblySymbol(a); - assemblySymbol.Should().BeOfType(); + assemblySymbol.Should().BeOfType(); assemblySymbol.Should().BeSameAs(c.GetOrCreateAssemblySymbol(a)); } @@ -230,7 +231,7 @@ public void CanResolveModuleBuilder() var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); var module = a.DefineDynamicModule("Test"); var moduleSymbol = c.GetOrCreateModuleSymbol(module); - moduleSymbol.Should().BeOfType(); + moduleSymbol.Should().BeOfType(); moduleSymbol.Should().BeSameAs(c.GetOrCreateModuleSymbol(module)); } @@ -243,7 +244,7 @@ public void CanResolveTypeBuilder() var type1 = m.DefineType("DynamicType1"); var type1Symbol = c.GetOrCreateTypeSymbol(type1); - type1Symbol.Should().BeOfType(); + type1Symbol.Should().BeOfType(); type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); } @@ -256,13 +257,13 @@ public void CanResolveMultipleTypeBuilders() var type1 = m.DefineType("DynamicType1"); var type1Symbol = c.GetOrCreateTypeSymbol(type1); - type1Symbol.Should().BeOfType(); + type1Symbol.Should().BeOfType(); type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); type1.CreateType(); var type2 = m.DefineType("DynamicType2"); var type2Symbol = c.GetOrCreateTypeSymbol(type2); - type2Symbol.Should().BeOfType(); + type2Symbol.Should().BeOfType(); type2Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type2)); } @@ -276,7 +277,7 @@ public void CanResolveMethodBuilder() var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeOfType(); method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); } @@ -290,12 +291,12 @@ public void CanResolveMultipleMethodBuilders() var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeOfType(); method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); var method2 = t.DefineMethod("DynamicMethod2", MethodAttributes.Public | MethodAttributes.Static); var method2Symbol = c.GetOrCreateMethodSymbol(method2); - method2Symbol.Should().BeOfType(); + method2Symbol.Should().BeOfType(); method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); } @@ -309,7 +310,7 @@ public void CanResolveFieldBuilder() var field = t.DefineField("dynamicField", typeof(object), FieldAttributes.Public); var fieldSymbol = c.GetOrCreateFieldSymbol(field); - fieldSymbol.Should().BeOfType(); + fieldSymbol.Should().BeOfType(); fieldSymbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field)); } @@ -323,12 +324,12 @@ public void CanResolveMultipleFieldBuilders() var field1 = t.DefineField("dynamicField1", typeof(object), FieldAttributes.Public); var field1Symbol = c.GetOrCreateFieldSymbol(field1); - field1Symbol.Should().BeOfType(); + field1Symbol.Should().BeOfType(); field1Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field1)); var field2 = t.DefineField("dynamicField2", typeof(object), FieldAttributes.Public); var field2Symbol = c.GetOrCreateFieldSymbol(field2); - field2Symbol.Should().BeOfType(); + field2Symbol.Should().BeOfType(); field2Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field2)); } @@ -342,7 +343,7 @@ public void CanResolvePropertyBuilder() var property = t.DefineProperty("DynamicProperty", PropertyAttributes.None, typeof(object), []); var propertySymbol = c.GetOrCreatePropertySymbol(property); - propertySymbol.Should().BeOfType(); + propertySymbol.Should().BeOfType(); propertySymbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property)); } @@ -356,12 +357,12 @@ public void CanResolveMultiplePropertyBuilders() var property1 = t.DefineProperty("DynamicProperty1", PropertyAttributes.None, typeof(object), []); var property1Symbol = c.GetOrCreatePropertySymbol(property1); - property1Symbol.Should().BeOfType(); + property1Symbol.Should().BeOfType(); property1Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property1)); var property2 = t.DefineProperty("DynamicProperty2", PropertyAttributes.None, typeof(object), []); var property2Symbol = c.GetOrCreatePropertySymbol(property2); - property2Symbol.Should().BeOfType(); + property2Symbol.Should().BeOfType(); property2Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property2)); } @@ -375,7 +376,7 @@ public void CanResolveEventBuilder() var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); var event1Symbol = c.GetOrCreateEventSymbol(event1); - event1Symbol.Should().BeOfType(); + event1Symbol.Should().BeOfType(); event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); } @@ -389,12 +390,12 @@ public void CanResolveMultipleEventBuilders() var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); var event1Symbol = c.GetOrCreateEventSymbol(event1); - event1Symbol.Should().BeOfType(); + event1Symbol.Should().BeOfType(); event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); var event2 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); var event2Symbol = c.GetOrCreateEventSymbol(event2); - event2Symbol.Should().BeOfType(); + event2Symbol.Should().BeOfType(); event2Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event2)); } @@ -402,22 +403,22 @@ public void CanResolveMultipleEventBuilders() public void CanCompleteTypeBuilder() { var c = new ReflectionSymbolContext(); - var a = new ReflectionAssemblySymbolBuilder(c, AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect)); + var a = c.GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect)); var moduleBuilder = a.DefineModule("DynamicModule"); - var moduleSymbol = moduleBuilder.Symbol; + var moduleSymbol = (IModuleSymbol)moduleBuilder; var type1Builder = moduleBuilder.DefineType("DynamicType1"); - var type1Symbol = type1Builder.Symbol; - type1Symbol.Should().BeOfType(); + var type1Symbol = (ITypeSymbol)type1Builder; + type1Symbol.Should().BeOfType(); type1Builder.Complete(); - var type1SymbolAgain = type1Builder.Symbol; - type1SymbolAgain.Should().BeSameAs(type1Symbol); - type1SymbolAgain.Name.Should().Be("DynamicType1"); + var type1Again = moduleBuilder.GetType("DynamicType1"); + type1Again.Should().BeSameAs(type1Symbol); + type1Again.Name.Should().Be("DynamicType1"); // check that we can relookup type - moduleSymbol.GetType("DynamicType1").Should().BeSameAs(type1SymbolAgain); + moduleSymbol.GetType("DynamicType1").Should().BeSameAs(type1Symbol); } } diff --git a/src/IKVM.CoreLib/IKVM.CoreLib.csproj b/src/IKVM.CoreLib/IKVM.CoreLib.csproj index 5e31c90e3d..13b96c3da6 100644 --- a/src/IKVM.CoreLib/IKVM.CoreLib.csproj +++ b/src/IKVM.CoreLib/IKVM.CoreLib.csproj @@ -20,6 +20,10 @@ + + all + runtime; build; native; contentfiles; analyzers; buildtransitive + @@ -102,4 +106,12 @@ + + + + PreserveNewest + + + + diff --git a/src/IKVM.CoreLib/System/TypeExtensions.cs b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs similarity index 76% rename from src/IKVM.CoreLib/System/TypeExtensions.cs rename to src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs index ea2a69932b..0defa18ab2 100644 --- a/src/IKVM.CoreLib/System/TypeExtensions.cs +++ b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs @@ -1,24 +1,45 @@ -using System.Linq.Expressions; +using System; +using System.Linq.Expressions; using System.Reflection; using System.Reflection.Emit; using System.Reflection.Metadata.Ecma335; -namespace System +namespace IKVM.CoreLib.Reflection { - static class TypeExtensions + static class ReflectionExtensions { + static readonly ParameterExpression _assemblyBuilderRuntimeAssemblyParameter = Expression.Parameter(typeof(AssemblyBuilder), "p"); static readonly ParameterExpression _propertyBuilderParameter = Expression.Parameter(typeof(PropertyBuilder), "p"); static readonly ParameterExpression _eventBuilderParameter = Expression.Parameter(typeof(EventBuilder), "p"); static readonly ParameterExpression _parameterBuilderParameter = Expression.Parameter(typeof(ParameterBuilder), "p"); #if NET +#if NET8_0_OR_GREATER + + static readonly Type _assemblyBuilderType = typeof(AssemblyBuilder).Assembly.GetType("System.Reflection.Emit.RuntimeAssemblyBuilder", true)!; static readonly Type _propertyBuilderType = typeof(PropertyBuilder).Assembly.GetType("System.Reflection.Emit.RuntimePropertyBuilder", true)!; static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.RuntimeEventBuilder", true)!; static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.RuntimeParameterBuilder", true)!; +#else + + static readonly Type _assemblyBuilderType = typeof(AssemblyBuilder).Assembly.GetType("System.Reflection.Emit.AssemblyBuilder", true)!; + static readonly Type _propertyBuilderType = typeof(PropertyBuilder).Assembly.GetType("System.Reflection.Emit.PropertyBuilder", true)!; + static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.EventBuilder", true)!; + static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.ParameterBuilder", true)!; + +#endif + + static readonly Func _getAssemblyBuilderRuntimeAssemblyFunc = Expression.Lambda>( + Expression.Property( + Expression.ConvertChecked(_assemblyBuilderRuntimeAssemblyParameter, _assemblyBuilderType), + _assemblyBuilderType.GetProperty("InternalAssembly", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _assemblyBuilderRuntimeAssemblyParameter) + .Compile(); + static readonly Func _getPropertyMetadataTokenFunc = Expression.Lambda>( Expression.Field( Expression.ConvertChecked(_propertyBuilderParameter, _propertyBuilderType), @@ -26,7 +47,6 @@ static class TypeExtensions _propertyBuilderParameter) .Compile(); - static readonly Func _getEventMetadataTokenFunc = Expression.Lambda>( Expression.Field( Expression.ConvertChecked(_eventBuilderParameter, _eventBuilderType), @@ -50,9 +70,17 @@ static class TypeExtensions #else + static readonly Type _assemblyBuilderType = typeof(AssemblyBuilder).Assembly.GetType("System.Reflection.Emit.AssemblyBuilder", true)!; static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.EventBuilder", true)!; static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.ParameterBuilder", true)!; + static readonly Func _getAssemblyBuilderRuntimeAssemblyFunc = Expression.Lambda>( + Expression.Call( + Expression.ConvertChecked(_assemblyBuilderRuntimeAssemblyParameter, _assemblyBuilderType), + _assemblyBuilderType.GetMethod("GetNativeHandle", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _assemblyBuilderRuntimeAssemblyParameter) + .Compile(); + static readonly Func _getParameterMethodBuilderFunc = Expression.Lambda>( Expression.Field( Expression.ConvertChecked(_parameterBuilderParameter, _parameterBuilderType), @@ -116,6 +144,24 @@ public static int GetMetadataTokenRowNumberSafe(this Module module) return MetadataTokens.GetRowNumber(MetadataTokens.EntityHandle(module.GetMetadataTokenSafe())); } + /// + /// Gets the metadata token for the specified . + /// + /// + /// + public static int GetMetadataTokenSafe(this MemberInfo member) + { + return member switch + { + Type t => t.GetMetadataTokenSafe(), + MethodBase m => m.GetMetadataTokenSafe(), + FieldInfo f => f.GetMetadataTokenSafe(), + PropertyInfo p => p.GetMetadataTokenSafe(), + EventInfo e => e.GetMetadataTokenSafe(), + _ => throw new InvalidOperationException(), + }; + } + /// /// Gets the metadata token for the specified . /// @@ -352,7 +398,7 @@ public static int GetMetadataToken(this EventBuilder @event) /// public static int GetMetadataTokenSafe(this EventBuilder @event) { - var t = GetMetadataToken(@event); + var t = @event.GetMetadataToken(); if (t == 0) throw new InvalidOperationException(); @@ -410,6 +456,76 @@ public static int GetMetadataToken(this ParameterBuilder parameter) #endif } + /// + /// Gets the associated with a . + /// + /// + /// + public static Assembly GetRuntimeAssembly(this AssemblyBuilder assembly) + { + return _getAssemblyBuilderRuntimeAssemblyFunc(assembly); + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static ModuleBuilder GetModuleBuilder(this ParameterBuilder parameter) + { + return (ModuleBuilder)_getParameterMethodBuilderFunc(parameter).Module; + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static TypeBuilder GetTypeBuilder(this ParameterBuilder parameter) + { + return (TypeBuilder?)_getParameterMethodBuilderFunc(parameter).DeclaringType ?? throw new InvalidOperationException(); + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static ModuleBuilder GetModuleBuilder(this FieldBuilder field) + { + return (ModuleBuilder)field.Module; + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static TypeBuilder GetTypeBuilder(this FieldBuilder field) + { + return (TypeBuilder?)field.DeclaringType ?? throw new InvalidOperationException(); + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static ModuleBuilder GetModuleBuilder(this PropertyBuilder property) + { + return (ModuleBuilder)property.Module; + } + + /// + /// Gets the associated with a . + /// + /// + /// + public static TypeBuilder GetTypeBuilder(this PropertyBuilder property) + { + return (TypeBuilder)property.DeclaringType!; + } + /// /// Gets the associated with a . /// @@ -455,7 +571,7 @@ public static EventAttributes GetEventAttributes(this EventBuilder @event) /// /// /// - public static MemberInfo GetMethodBuilder(this ParameterBuilder parameter) + public static MethodBuilder GetMethodBuilder(this ParameterBuilder parameter) { return _getParameterMethodBuilderFunc(parameter); } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs index 1bac977b72..d99608a52e 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs @@ -1,9 +1,7 @@ -using System.Xml.Linq; - -namespace IKVM.CoreLib.Symbols.Emit +namespace IKVM.CoreLib.Symbols.Emit { - interface IAssemblySymbolBuilder : ISymbolBuilder + interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySymbol { /// @@ -43,11 +41,6 @@ interface IAssemblySymbolBuilder : ISymbolBuilder /// void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - /// - /// Finishes all modules of the assembly, updating the associated symbols. - /// - void Complete(); - } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs index e98f8e7708..e3ca768853 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs @@ -3,7 +3,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IConstructorSymbolBuilder : ISymbolBuilder + interface IConstructorSymbolBuilder : ISymbolBuilder, IMethodBaseSymbolBuilder, IConstructorSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs index b5378a41d9..36b7257650 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs @@ -1,7 +1,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IEventSymbolBuilder : ISymbolBuilder + interface IEventSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IEventSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs index 5b6706e3f2..ad3048c16a 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs @@ -1,7 +1,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IFieldSymbolBuilder : ISymbolBuilder + interface IFieldSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IFieldSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs index 38bcde8376..cfd742441a 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs @@ -1,11 +1,28 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IGenericTypeParameterSymbolBuilder : ISymbolBuilder + interface IGenericTypeParameterSymbolBuilder : ISymbolBuilder, ITypeSymbol { + /// + /// Sets the base type that a type must inherit in order to be substituted for the type parameter. + /// + /// + void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint); + + /// + /// Sets the variance characteristics and special constraints of the generic parameter, such as the parameterless constructor constraint. + /// + /// + void SetGenericParameterAttributes(System.Reflection.GenericParameterAttributes genericParameterAttributes); + + /// + /// Sets the interfaces a type must implement in order to be substituted for the type parameter. + /// + /// + void SetInterfaceConstraints(params ITypeSymbol[]? interfaceConstraints); } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs index 69f29dfa36..1677d70764 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs @@ -4,7 +4,264 @@ interface IILGenerator { + /// + /// Gets the current offset, in bytes, in the Microsoft intermediate language (MSIL) stream that is being emitted by the . + /// + int ILOffset { get; } + /// + /// Begins a lexical scope. + /// + void BeginScope(); + + /// + /// Specifies the namespace to be used in evaluating locals and watches for the current active lexical scope. + /// + /// + void UsingNamespace(string usingNamespace); + + /// + /// Ends a lexical scope. + /// + void EndScope(); + + /// + /// Marks a sequence point in the Microsoft intermediate language (MSIL) stream. + /// + /// + /// + /// + /// + /// + void MarkSequencePoint(System.Diagnostics.SymbolStore.ISymbolDocumentWriter document, int startLine, int startColumn, int endLine, int endColumn); + + /// + /// Declares a local variable of the specified type, optionally pinning the object referred to by the variable. + /// + /// + /// + /// + ILocalBuilder DeclareLocal(ITypeSymbol localType, bool pinned); + + /// + /// Declares a local variable of the specified type. + /// + /// + /// + ILocalBuilder DeclareLocal(ITypeSymbol localType); + + /// + /// Declares a new label. + /// + /// + System.Reflection.Emit.Label DefineLabel(); + + /// + /// Begins an exception block for a non-filtered exception. + /// + /// + System.Reflection.Emit.Label BeginExceptionBlock(); + + /// + /// Marks the Microsoft intermediate language (MSIL) stream's current position with the given label. + /// + /// + void MarkLabel(System.Reflection.Emit.Label loc); + + /// + /// Begins an exception block for a filtered exception. + /// + void BeginExceptFilterBlock(); + + /// + /// Begins a catch block. + /// + /// + void BeginCatchBlock(ITypeSymbol? exceptionType); + + /// + /// Begins an exception fault block in the Microsoft intermediate language (MSIL) stream. + /// + void BeginFaultBlock(); + + /// + /// Begins a finally block in the Microsoft intermediate language (MSIL) instruction stream. + /// + void BeginFinallyBlock(); + + /// + /// Ends an exception block. + /// + void EndExceptionBlock(); + + /// + /// Emits an instruction to throw an exception. + /// + /// + void ThrowException(ITypeSymbol excType); + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the index of the given local variable. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, ILocalBuilder local); + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the metadata token for the given type. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, ITypeSymbol cls); + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the metadata token for the given string. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, string str); + + /// + /// Puts the specified instruction and numerical argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, float arg); + + /// + /// Puts the specified instruction and character argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, sbyte arg); + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the metadata token for the given method. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, IMethodSymbol meth); + + /// + /// Puts the specified instruction and a signature token onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, ISignatureHelper signature); + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream and leaves space to include a label when fixes are done. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, ILabel[] labels); + + /// + /// Puts the specified instruction and metadata token for the specified field onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, IFieldSymbol field); + + /// + /// Puts the specified instruction and metadata token for the specified constructor onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, IConstructorSymbol con); + + /// + /// Puts the specified instruction and numerical argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, long arg); + + /// + /// Puts the specified instruction and numerical argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, int arg); + + /// + /// Puts the specified instruction and numerical argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, short arg); + + /// + /// Puts the specified instruction and numerical argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, double arg); + + /// + /// Puts the specified instruction and character argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, byte arg); + + /// + /// Puts the specified instruction onto the stream of instructions. + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode); + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream and leaves space to include a label when fixes are done. + /// + /// + /// + void Emit(System.Reflection.Emit.OpCode opcode, ILabel label); + + /// + /// Puts a call or callvirt instruction onto the Microsoft intermediate language (MSIL) stream to call a varargs method. + /// + /// + /// + /// + void EmitCall(System.Reflection.Emit.OpCode opcode, IMethodSymbol methodInfo, ITypeSymbol[]? optionalParameterTypes); + + /// + /// Puts a Calli instruction onto the Microsoft intermediate language (MSIL) stream, specifying an unmanaged calling convention for the indirect call. + /// + /// + /// + /// + /// + void EmitCalli(System.Reflection.Emit.OpCode opcode, System.Runtime.InteropServices.CallingConvention unmanagedCallConv, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + + /// + /// Puts a Calli instruction onto the Microsoft intermediate language (MSIL) stream, specifying a managed calling convention for the indirect call. + /// + /// + /// + /// + /// + /// + void EmitCalli(System.Reflection.Emit.OpCode opcode, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, ITypeSymbol[]? optionalParameterTypes); + + /// + /// Emits the Microsoft intermediate language (MSIL) to call with a string. + /// + /// + void EmitWriteLine(string value); + + /// + /// Emits the Microsoft intermediate language (MSIL) necessary to call with the given field. + /// + /// + void EmitWriteLine(IFieldSymbol fld); + + /// + /// Emits the Microsoft intermediate language (MSIL) necessary to call with the given local variable. + /// + /// + void EmitWriteLine(ILocalBuilder localBuilder); } diff --git a/src/IKVM.CoreLib/Symbols/Emit/ILabel.cs b/src/IKVM.CoreLib/Symbols/Emit/ILabel.cs new file mode 100644 index 0000000000..c36f9d801f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ILabel.cs @@ -0,0 +1,6 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + public interface ILabel + { + } +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs new file mode 100644 index 0000000000..650edcb8dd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs @@ -0,0 +1,42 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + /// + /// Represents a local variable within a method or constructor. + /// + interface ILocalBuilder + { + + /// + /// Gets a value indicating whether the object referred to by the local variable is pinned in memory. + /// + bool IsPinned { get; } + + /// + /// Gets the zero-based index of the local variable within the method body. + /// + int LocalIndex { get; } + + /// + /// Gets the type of the local variable. + /// + ITypeSymbol LocalType { get; } + + /// + /// Sets the name of this local variable. + /// + /// + void SetLocalSymInfo(string name); + + /// + /// Sets the name and lexical scope of this local variable. + /// + /// + /// + /// + void SetLocalSymInfo(string name, int startOffset, int endOffset); + + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs new file mode 100644 index 0000000000..b787c9ced2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IMemberSymbolBuilder : ISymbolBuilder, IMemberSymbol + { + + + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs new file mode 100644 index 0000000000..894c8e9b12 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IMethodBaseSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IMethodBaseSymbol + { + + + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs index 9e251bed28..8220de2960 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs @@ -1,7 +1,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IMethodSymbolBuilder : ISymbolBuilder + interface IMethodSymbolBuilder : ISymbolBuilder, IMethodBaseSymbolBuilder, IMethodSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index 4ffa0fdb15..72bb9e7d7e 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IModuleSymbolBuilder : ISymbolBuilder + interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol { /// @@ -85,11 +85,6 @@ interface IModuleSymbolBuilder : ISymbolBuilder /// void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - /// - /// Finishes all types of the module, updating the associated symbols. - /// - void Complete(); - } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs index 9ac13b3847..860f872f79 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs @@ -1,7 +1,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IParameterSymbolBuilder : ISymbolBuilder + interface IParameterSymbolBuilder : ISymbolBuilder, IParameterSymbol { /// /// Sets the default value of the parameter. diff --git a/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs index 6c2d9ade91..c1f200f2ff 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs @@ -1,9 +1,33 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IPropertySymbolBuilder : ISymbolBuilder + interface IPropertySymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IPropertySymbol { + /// + /// Sets the default value of this property. + /// + /// + void SetConstant(object? defaultValue); + + /// + /// Sets the method that gets the property value. + /// + /// + void SetGetMethod(IMethodSymbolBuilder mdBuilder); + + /// + /// Sets the method that sets the property value. + /// + /// + void SetSetMethod(IMethodSymbolBuilder mdBuilder); + + /// + /// Adds one of the other methods associated with this property. + /// + /// + void AddOtherMethod(IMethodSymbolBuilder mdBuilder); + /// /// Set a custom attribute using a custom attribute builder. /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs b/src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs new file mode 100644 index 0000000000..f7be27ef9b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs @@ -0,0 +1,6 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + public interface ISignatureHelper + { + } +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs index 8b7b295feb..3e952aae98 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs @@ -7,10 +7,7 @@ interface ISymbolBuilder { - /// - /// Gets the that is currently being built. Portions of this interface will be non-functional until the build is completed. - /// - ISymbol Symbol { get; } + } @@ -22,10 +19,7 @@ interface ISymbolBuilder : ISymbolBuilder where TSymbol : ISymbol { - /// - /// Gets the that is currently being built. Portions of this interface will be non-functional until the build is completed. - /// - new TSymbol Symbol { get; } + } diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs index 7bed9beb7b..6b4b44107c 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs @@ -3,7 +3,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface ITypeSymbolBuilder : ISymbolBuilder + interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, ITypeSymbol { /// @@ -140,6 +140,13 @@ interface ITypeSymbolBuilder : ISymbolBuilder /// IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + /// + /// Specifies a given method body that implements a given method declaration, potentially with a different name. + /// + /// + /// + void DefineMethodOverride(IMethodSymbolBuilder methodInfoBody, IMethodSymbol methodInfoDeclaration); + /// /// Defines a nested type, given its name, attributes, the type that it extends, and the interfaces that it implements. /// diff --git a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs index a87909ae33..3d3d399759 100644 --- a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs @@ -1,6 +1,8 @@ using System.Collections.Generic; using System.Reflection; +using IKVM.CoreLib.Symbols.Emit; + namespace IKVM.CoreLib.Symbols { diff --git a/src/IKVM.CoreLib/Symbols/IEventSymbol.cs b/src/IKVM.CoreLib/Symbols/IEventSymbol.cs index 220a74891c..50ee2179af 100644 --- a/src/IKVM.CoreLib/Symbols/IEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IEventSymbol.cs @@ -1,5 +1,7 @@ using System.Reflection; +using IKVM.CoreLib.Symbols.Emit; + namespace IKVM.CoreLib.Symbols { diff --git a/src/IKVM.CoreLib/Symbols/IFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/IFieldSymbol.cs index 1eee20fe92..c927898a57 100644 --- a/src/IKVM.CoreLib/Symbols/IFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IFieldSymbol.cs @@ -1,5 +1,7 @@ using System.Reflection; +using IKVM.CoreLib.Symbols.Emit; + namespace IKVM.CoreLib.Symbols { diff --git a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs index c3c8d5c9e0..06709a3679 100644 --- a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs @@ -1,4 +1,6 @@ -namespace IKVM.CoreLib.Symbols +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols { /// diff --git a/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs index 18e855157e..e1008c96c6 100644 --- a/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs @@ -1,5 +1,7 @@ using System.Reflection; +using IKVM.CoreLib.Symbols.Reflection; + namespace IKVM.CoreLib.Symbols { diff --git a/src/IKVM.CoreLib/Symbols/IPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/IPropertySymbol.cs index 0b73fbf861..5f47a277b5 100644 --- a/src/IKVM.CoreLib/Symbols/IPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IPropertySymbol.cs @@ -1,5 +1,7 @@ using System.Reflection; +using IKVM.CoreLib.Symbols.Emit; + namespace IKVM.CoreLib.Symbols { diff --git a/src/IKVM.CoreLib/Symbols/ISymbol.cs b/src/IKVM.CoreLib/Symbols/ISymbol.cs index 7fae6f73ea..33f2a500d7 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbol.cs @@ -17,6 +17,11 @@ interface ISymbol /// bool ContainsMissing { get; } + /// + /// Returns true if the symbol is complete. That is, was created with a builder and completed. + /// + bool IsComplete { get; } + } } diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs new file mode 100644 index 0000000000..81457295e8 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -0,0 +1,48 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols +{ + + interface ISymbolContext + { + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. + /// + /// + /// + /// + ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs); + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, and a set of named field/value pairs. + /// + /// + /// + /// + /// + ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues); + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, and a set of named property or value pairs. + /// + /// + /// + /// + /// + ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues); + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, a set of named property or value pairs, and a set of named field or value pairs. + /// + /// + /// + /// + /// + /// + /// + ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs deleted file mode 100644 index ccb5a77f4b..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ /dev/null @@ -1,79 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionAssemblySymbolBuilder : IkvmReflectionSymbolBuilder, IAssemblySymbolBuilder - { - - readonly AssemblyBuilder _builder; - IkvmReflectionAssemblySymbol? _symbol; - - /// - /// Initializes a new instance. - /// - /// - /// - public IkvmReflectionAssemblySymbolBuilder(IkvmReflectionSymbolContext context, AssemblyBuilder builder) : - base(context) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - internal sealed override IkvmReflectionAssemblySymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateAssemblySymbol(_builder); - - /// - public IModuleSymbolBuilder DefineModule(string name) - { - return new IkvmReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, name + ".dll")); - } - - /// - public IModuleSymbolBuilder DefineModule(string name, string fileName) - { - return new IkvmReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName)); - } - - /// - public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo) - { - return new IkvmReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName, emitSymbolInfo)); - } - - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); - } - - /// - public void Complete() - { - foreach (var module in _builder.GetModules()) - { - if (module is ModuleBuilder moduleBuilder) - { - moduleBuilder.CreateGlobalFunctions(); - - foreach (var type in moduleBuilder.GetTypes()) - if (type is TypeBuilder typeBuilder) - if (typeBuilder.IsCreated() == false) - if (typeBuilder.CreateType() is { } t) - ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); - } - } - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs deleted file mode 100644 index 2d0fc2e7cc..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs +++ /dev/null @@ -1,74 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionConstructorSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder - { - - readonly ConstructorBuilder _builder; - IkvmReflectionConstructorSymbol? _symbol; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionConstructorSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, ConstructorBuilder builder) : - base(context, containingTypeBuilder) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Gets the containing . - /// - protected internal new IkvmReflectionTypeSymbolBuilder ContainingTypeBuilder => base.ContainingTypeBuilder ?? throw new NullReferenceException(); - - /// - internal override IkvmReflectionConstructorSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateConstructorSymbol(_builder); - - /// - public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) - { - _builder.SetImplementationFlags((MethodImplAttributes)attributes); - } - - /// - public IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection.ParameterAttributes attributes, string? strParamName) - { - return new IkvmReflectionParameterSymbolBuilder(Context, this, _builder, _builder.DefineParameter(iSequence, (ParameterAttributes)attributes, strParamName)); - } - - /// - public IILGenerator GetILGenerator() - { - throw new NotImplementedException(); - } - - /// - public IILGenerator GetILGenerator(int streamSize) - { - throw new NotImplementedException(); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); - } - - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs deleted file mode 100644 index 39adf50404..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionCustomAttributeBuilder : ICustomAttributeBuilder - { - - readonly CustomAttributeBuilder _builder; - - /// - /// Initializes a new instance. - /// - public IkvmReflectionCustomAttributeBuilder(CustomAttributeBuilder builder) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Gets the underlying reflection . - /// - internal CustomAttributeBuilder ReflectionBuilder => _builder; - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs deleted file mode 100644 index c1b5800558..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs +++ /dev/null @@ -1,70 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionEventSymbolBuilder : IkvmReflectionSymbolBuilder, IEventSymbolBuilder - { - - readonly IkvmReflectionTypeSymbolBuilder _containingTypeBuilder; - readonly EventBuilder _builder; - IkvmReflectionEventSymbol? _symbol; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionEventSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, EventBuilder builder) : - base(context) - { - _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - internal override IkvmReflectionEventSymbol ReflectionSymbol => _symbol ??= _containingTypeBuilder.ReflectionSymbol.ResolveEventSymbol(_builder); - - /// - public void SetAddOnMethod(IMethodSymbolBuilder mdBuilder) - { - _builder.SetAddOnMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); - } - - /// - public void SetRemoveOnMethod(IMethodSymbolBuilder mdBuilder) - { - _builder.SetRemoveOnMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); - } - - /// - public void SetRaiseMethod(IMethodSymbolBuilder mdBuilder) - { - _builder.SetRaiseMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); - } - - /// - public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) - { - _builder.AddOtherMethod(((IkvmReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); - } - - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs deleted file mode 100644 index 75d2bc47cc..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs +++ /dev/null @@ -1,88 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionFieldSymbolBuilder : IkvmReflectionSymbolBuilder, IFieldSymbolBuilder - { - - readonly IkvmReflectionModuleSymbolBuilder _containingModuleBuilder; - readonly IkvmReflectionTypeSymbolBuilder? _containingTypeBuilder; - readonly FieldBuilder _builder; - IkvmReflectionFieldSymbol? _symbol; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbolBuilder containingModuleBuilder, FieldBuilder builder) : - base(context) - { - _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, FieldBuilder builder) : - base(context) - { - _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); - _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Gets the containing . - /// - internal IkvmReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; - - /// - /// Gets the containing . - /// - internal IkvmReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; - - /// - /// Gets the underlying - /// - internal FieldBuilder ReflectionBuilder => _builder; - - /// - internal override IkvmReflectionFieldSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateFieldSymbol(_builder); - - /// - public void SetConstant(object? defaultValue) - { - _builder.SetConstant(defaultValue); - } - - /// - public void SetOffset(int iOffset) - { - _builder.SetOffset(iOffset); - } - - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs deleted file mode 100644 index 1fe558174a..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs +++ /dev/null @@ -1,49 +0,0 @@ -using System; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - abstract class IkvmReflectionMethodBaseSymbolBuilder : IkvmReflectionSymbolBuilder - where TSymbol : ISymbol - where TReflectionSymbol : IkvmReflectionSymbol, TSymbol - { - - readonly IkvmReflectionModuleSymbolBuilder _containingModuleBuilder; - readonly IkvmReflectionTypeSymbolBuilder? _containingTypeBuilder; - - /// - /// Initializes a new instance. - /// - /// - /// - protected IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder) : - base(context) - { - _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); - _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; - } - - /// - /// Initializes a new instance. - /// - /// - /// - protected IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbolBuilder containingModuleBuilder) : - base(context) - { - _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); - } - - /// - /// Gets the containing . - /// - protected internal IkvmReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; - - /// - /// Gets the containing . - /// - protected internal IkvmReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs deleted file mode 100644 index e01792a357..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs +++ /dev/null @@ -1,107 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionMethodSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder - { - - readonly MethodBuilder _builder; - IkvmReflectionMethodSymbol? _symbol; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbolBuilder containingModuleBuilder, MethodBuilder builder) : - base(context, containingModuleBuilder) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbolBuilder containingTypeBuilder, MethodBuilder builder) : - base(context, containingTypeBuilder) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Gets the that underlies this instance. - /// - internal MethodBuilder ReflectionBuilder => _builder; - - /// - internal override IkvmReflectionMethodSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateMethodSymbol(_builder); - - /// - public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) - { - _builder.SetImplementationFlags((MethodImplAttributes)attributes); - } - - /// - public void SetParameters(params ITypeSymbol[] parameterTypes) - { - _builder.SetParameters(parameterTypes.Unpack()); - } - - /// - public void SetReturnType(ITypeSymbol? returnType) - { - _builder.SetReturnType(returnType?.Unpack()); - } - - /// - public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) - { - _builder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); - } - - public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) - { - throw new NotImplementedException(); - } - - /// - public IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) - { - return new IkvmReflectionParameterSymbolBuilder(Context, this, _builder, _builder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); - } - - public IILGenerator GetILGenerator() - { - throw new NotImplementedException(); - } - - public IILGenerator GetILGenerator(int size) - { - throw new NotImplementedException(); - } - - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs deleted file mode 100644 index 6064c7e88f..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs +++ /dev/null @@ -1,98 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionModuleSymbolBuilder : IkvmReflectionSymbolBuilder, IModuleSymbolBuilder - { - - readonly ModuleBuilder _builder; - IkvmReflectionModuleSymbol? _symbol; - - /// - /// Initializes a new instance. - /// - /// - /// - public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, ModuleBuilder builder) : - base(context) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - internal override IkvmReflectionModuleSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateModuleSymbol(_builder); - - /// - public ITypeSymbolBuilder DefineType(string name) - { - return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name)); - } - - /// - public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typesize) - { - return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), typesize)); - } - - /// - public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent) - { - return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack())); - } - - /// - public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr) - { - return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr)); - } - - /// - public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packsize) - { - return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packsize)); - } - - /// - public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packingSize, int typesize) - { - return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packingSize, typesize)); - } - - /// - public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) - { - return new IkvmReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), interfaces?.Unpack())); - } - - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); - } - - /// - public void Complete() - { - _builder.CreateGlobalFunctions(); - - foreach (var type in _builder.GetTypes()) - if (type is TypeBuilder typeBuilder) - if (typeBuilder.IsCreated() == false) - if (typeBuilder.CreateType() is { } t) - ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs deleted file mode 100644 index 66e07f7e08..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; - -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - /// - /// Fake implementation that wraps a , which does not extend . - /// - class IkvmReflectionParameterBuilderInfo : ParameterInfo - { - - readonly MemberInfo _member; - readonly ParameterBuilder _parameter; - - /// - /// Initialies a new instance. - /// - /// - /// - /// - public IkvmReflectionParameterBuilderInfo(MemberInfo member, ParameterBuilder parameter) - { - _member = member ?? throw new ArgumentNullException(nameof(member)); - _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); - } - - /// - public override ParameterAttributes Attributes => (ParameterAttributes)_parameter.Attributes; - - /// - public override Module Module => _member.Module; - - /// - public override MemberInfo Member => _member; - - /// - public override string? Name => _parameter.Name; - - /// - public override int Position => _parameter.Position; - - /// - public override int MetadataToken => throw new NotImplementedException(); - - /// - public override Type ParameterType => throw new NotImplementedException(); - - /// - public override object RawDefaultValue => throw new NotImplementedException(); - - public override CustomModifiers __GetCustomModifiers() - { - throw new NotSupportedException(); - } - - public override bool __TryGetFieldMarshal(out FieldMarshal fieldMarshal) - { - throw new NotSupportedException(); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs deleted file mode 100644 index 21ba94fa2e..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs +++ /dev/null @@ -1,106 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - abstract class IkvmReflectionParameterSymbolBuilder : IkvmReflectionSymbolBuilder, IParameterSymbolBuilder - { - - readonly MemberInfo _member; - readonly ParameterBuilder _builder; - readonly IkvmReflectionParameterBuilderInfo _info; - IkvmReflectionParameterSymbol? _symbol; - - object? _constant; - - /// - /// Initializes a new instance. - /// - /// - protected IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, MemberInfo member, ParameterBuilder builder) : - base(context) - { - _member = member ?? throw new ArgumentNullException(nameof(member)); - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _info = new IkvmReflectionParameterBuilderInfo(_member, _builder); - } - - /// - /// Gets the wrapped . - /// - internal ParameterBuilder ReflectionBuilder => _builder; - - /// - internal override IkvmReflectionParameterSymbol ReflectionSymbol => _symbol ??= GetOrCreateSymbol(_info); - - /// - /// Gets or creates the . - /// - /// - protected internal abstract IkvmReflectionParameterSymbol GetOrCreateSymbol(IkvmReflectionParameterBuilderInfo info); - - /// - public void SetConstant(object? defaultValue) - { - _builder.SetConstant(_constant = defaultValue); - } - - /// - /// Saves the constant value so it can be retrieved as a symbol. - /// - /// - internal object? GetConstant() - { - return _constant; - } - - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); - } - - } - - class IkvmReflectionParameterSymbolBuilder : IkvmReflectionParameterSymbolBuilder - where TContainingSymbol : IMethodBaseSymbol - where TContainingReflectionSymbol : IkvmReflectionMethodBaseSymbol, TContainingSymbol - where TContainingBuilder : IkvmReflectionMethodBaseSymbolBuilder - { - - readonly TContainingBuilder _containingMethodBuilder; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, TContainingBuilder containingMethodBuilder, MemberInfo member, ParameterBuilder builder) : - base(context, member, builder) - { - _containingMethodBuilder = containingMethodBuilder ?? throw new ArgumentNullException(nameof(containingMethodBuilder)); - } - - /// - /// Gets the containing . - /// - internal TContainingBuilder ContainingMethodBuilder => _containingMethodBuilder; - - /// - protected internal override IkvmReflectionParameterSymbol GetOrCreateSymbol(IkvmReflectionParameterBuilderInfo info) => ContainingMethodBuilder.ReflectionSymbol.ResolveParameterSymbol(info); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs deleted file mode 100644 index 239580c9b6..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ /dev/null @@ -1,196 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.Linq; -using System.Reflection.Metadata.Ecma335; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Threading; - -using Assembly = IKVM.Reflection.Assembly; -using Module = IKVM.Reflection.Module; -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionAssemblySymbol : IkvmReflectionSymbol, IAssemblySymbol - { - - Assembly _assembly; - System.Reflection.AssemblyName? _assemblyName; - - IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); - ReaderWriterLockSlim? _moduleLock; - - /// - /// Initializes a new instance. - /// - /// - /// - public IkvmReflectionAssemblySymbol(IkvmReflectionSymbolContext context, Assembly assembly) : - base(context) - { - _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); - } - - internal Assembly ReflectionObject => _assembly; - - /// - /// Gets or creates the cached for the module. - /// - /// - /// - /// - internal IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - if (module is null) - throw new ArgumentNullException(nameof(module)); - - Debug.Assert(AssemblyNameEqualityComparer.Instance.Equals(module.Assembly.GetName().ToAssemblyName(), _assembly.GetName().ToAssemblyName())); - - // create lock on demand - if (_moduleLock == null) - Interlocked.CompareExchange(ref _moduleLock, new ReaderWriterLockSlim(), null); - - using (_moduleLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.ModuleReferenceHandle(module.MetadataToken)); - if (_moduleSymbols[row] == null) - using (_moduleLock.CreateWriteLock()) - return _moduleSymbols[row] ??= new IkvmReflectionModuleSymbol(Context, this, module); - else - return _moduleSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); - - /// - public IMethodSymbol? EntryPoint => _assembly.EntryPoint is { } m ? ResolveMethodSymbol(m) : null; - - /// - public IEnumerable ExportedTypes => ResolveTypeSymbols(_assembly.ExportedTypes); - - /// - public string? FullName => _assembly.FullName; - - /// - public string ImageRuntimeVersion => _assembly.ImageRuntimeVersion; - - /// - public IModuleSymbol ManifestModule => ResolveModuleSymbol(_assembly.ManifestModule); - - /// - public IEnumerable Modules => ResolveModuleSymbols(_assembly.Modules); - - /// - public ITypeSymbol[] GetExportedTypes() - { - return ResolveTypeSymbols(_assembly.GetExportedTypes()); - } - - /// - public IModuleSymbol? GetModule(string name) - { - return _assembly.GetModule(name) is Module m ? GetOrCreateModuleSymbol(m) : null; - } - - /// - public IModuleSymbol[] GetModules() - { - return ResolveModuleSymbols(_assembly.GetModules()); - } - - /// - public IModuleSymbol[] GetModules(bool getResourceModules) - { - return ResolveModuleSymbols(_assembly.GetModules(getResourceModules)); - } - - /// - public System.Reflection.AssemblyName GetName() - { - return _assemblyName ??= _assembly.GetName().ToAssemblyName(); - } - - /// - public System.Reflection.AssemblyName GetName(bool copiedName) - { - return _assembly.GetName().ToAssemblyName(); - } - - /// - public System.Reflection.AssemblyName[] GetReferencedAssemblies() - { - var l = _assembly.GetReferencedAssemblies(); - var a = new System.Reflection.AssemblyName[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = l[i].ToAssemblyName(); - - return a; - } - - /// - public ITypeSymbol? GetType(string name, bool throwOnError) - { - return _assembly.GetType(name, throwOnError) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; - } - - /// - public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) - { - return _assembly.GetType(name, throwOnError, ignoreCase) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; - } - - /// - public ITypeSymbol? GetType(string name) - { - return _assembly.GetType(name) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; - } - - /// - public ITypeSymbol[] GetTypes() - { - return ResolveTypeSymbols(_assembly.GetTypes()); - } - - /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); - } - - /// - public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - return ResolveCustomAttributes(_assembly.GetCustomAttributesData().Where(i => i.AttributeType == ((IkvmReflectionTypeSymbol)attributeType).ReflectionObject)); - } - - /// - public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); - } - - /// - public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return _assembly.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(Assembly assembly) - { - Context.GetOrCreateAssemblySymbol(_assembly = assembly); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs deleted file mode 100644 index a991bdfa5a..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs +++ /dev/null @@ -1,37 +0,0 @@ -using ConstructorInfo = IKVM.Reflection.ConstructorInfo; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionConstructorSymbol : IkvmReflectionMethodBaseSymbol, IConstructorSymbol - { - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionConstructorSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, ConstructorInfo ctor) : - base(context, type, ctor) - { - - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new ConstructorInfo ReflectionObject => (ConstructorInfo)base.ReflectionObject; - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(ConstructorInfo type) - { - base.Complete(type); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs deleted file mode 100644 index f3e8e95465..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs +++ /dev/null @@ -1,108 +0,0 @@ -using System; - -using EventInfo = IKVM.Reflection.EventInfo; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionEventSymbol : IkvmReflectionMemberSymbol, IEventSymbol - { - - EventInfo _event; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionEventSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, EventInfo @event) : - base(context, type, @event) - { - _event = @event ?? throw new ArgumentNullException(nameof(@event)); - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new EventInfo ReflectionObject => _event; - - /// - public System.Reflection.EventAttributes Attributes => (System.Reflection.EventAttributes)_event.Attributes; - - /// - public ITypeSymbol? EventHandlerType => _event.EventHandlerType is { } m ? ResolveTypeSymbol(m) : null; - - /// - public bool IsSpecialName => _event.IsSpecialName; - - /// - public IMethodSymbol? AddMethod => _event.AddMethod is { } m ? ResolveMethodSymbol(m) : null; - - /// - public IMethodSymbol? RemoveMethod => _event.RemoveMethod is { } m ? ResolveMethodSymbol(m) : null; - - /// - public IMethodSymbol? RaiseMethod => _event.RaiseMethod is { } m ? ResolveMethodSymbol(m) : null; - - /// - public IMethodSymbol? GetAddMethod() - { - return _event.GetAddMethod() is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetAddMethod(bool nonPublic) - { - return _event.GetAddMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetRemoveMethod() - { - return _event.GetRemoveMethod() is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetRemoveMethod(bool nonPublic) - { - return _event.GetRemoveMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetRaiseMethod() - { - return _event.GetRaiseMethod() is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetRaiseMethod(bool nonPublic) - { - return _event.GetRaiseMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol[] GetOtherMethods() - { - return ResolveMethodSymbols(_event.GetOtherMethods()); - } - - /// - public IMethodSymbol[] GetOtherMethods(bool nonPublic) - { - return ResolveMethodSymbols(_event.GetOtherMethods(nonPublic)); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(EventInfo @event) - { - ResolveEventSymbol(_event = @event); - base.Complete(_event); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs deleted file mode 100644 index 4e9448e3ed..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs +++ /dev/null @@ -1,116 +0,0 @@ -using System; - -using FieldInfo = IKVM.Reflection.FieldInfo; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionFieldSymbol : IkvmReflectionMemberSymbol, IFieldSymbol - { - - FieldInfo _field; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionFieldSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol containingModule, FieldInfo field) : - base(context, containingModule, field) - { - _field = field ?? throw new ArgumentNullException(nameof(field)); - } - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionFieldSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol containingType, FieldInfo field) : - base(context, containingType, field) - { - _field = field ?? throw new ArgumentNullException(nameof(field)); - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new FieldInfo ReflectionObject => (FieldInfo)base.ReflectionObject; - - /// - public System.Reflection.FieldAttributes Attributes => (System.Reflection.FieldAttributes)_field.Attributes; - - /// - public ITypeSymbol FieldType => ResolveTypeSymbol(_field.FieldType); - - /// - public bool IsSpecialName => _field.IsSpecialName; - - /// - public bool IsAssembly => _field.IsAssembly; - - /// - public bool IsFamily => _field.IsFamily; - - /// - public bool IsFamilyAndAssembly => _field.IsFamilyAndAssembly; - - /// - public bool IsFamilyOrAssembly => _field.IsFamilyOrAssembly; - - /// - public bool IsInitOnly => _field.IsInitOnly; - - /// - public bool IsLiteral => _field.IsLiteral; - -#pragma warning disable SYSLIB0050 // Type or member is obsolete - /// - public bool IsNotSerialized => _field.IsNotSerialized; -#pragma warning restore SYSLIB0050 // Type or member is obsolete - - /// - public bool IsPinvokeImpl => _field.IsPinvokeImpl; - - /// - public bool IsPrivate => _field.IsPrivate; - - /// - public bool IsPublic => _field.IsPublic; - - /// - public bool IsStatic => _field.IsStatic; - - /// - public ITypeSymbol[] GetOptionalCustomModifiers() - { - return ResolveTypeSymbols(_field.GetOptionalCustomModifiers()); - } - - /// - public ITypeSymbol[] GetRequiredCustomModifiers() - { - return ResolveTypeSymbols(_field.GetRequiredCustomModifiers()); - } - - /// - public object? GetRawConstantValue() - { - return _field.GetRawConstantValue(); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(FieldInfo field) - { - ResolveFieldSymbol(_field = field); - base.Complete(_field); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs deleted file mode 100644 index 654f928055..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ /dev/null @@ -1,275 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; - -using ConstructorInfo = IKVM.Reflection.ConstructorInfo; -using EventInfo = IKVM.Reflection.EventInfo; -using FieldInfo = IKVM.Reflection.FieldInfo; -using MemberInfo = IKVM.Reflection.MemberInfo; -using MethodInfo = IKVM.Reflection.MethodInfo; -using PropertyInfo = IKVM.Reflection.PropertyInfo; -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - /// - /// Obtains information about the attributes of a member and provides access to member metadata. - /// - abstract class IkvmReflectionMemberSymbol : IkvmReflectionSymbol, IMemberSymbol - { - - /// - /// Concatinates the list of arrays. - /// - /// - /// - static T[] Concat(List? list) - { - if (list == null) - return []; - - var c = 0; - foreach (var i in list) - c += i.Length; - - if (c == 0) - return []; - - var t = 0; - var a = new T[c]; - foreach (var i in list) - { - Array.Copy(i, 0, a, t, i.Length); - t += i.Length; - } - - return a; - } - - readonly IkvmReflectionModuleSymbol _containingModule; - readonly IkvmReflectionTypeSymbol? _containingType; - MemberInfo _member; - - CustomAttribute[]? _customAttributes; - CustomAttribute[]? _inheritedCustomAttributes; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol containingModule, MemberInfo member) : - base(context) - { - _containingModule = containingModule ?? throw new ArgumentNullException(nameof(containingModule)); - _member = member ?? throw new ArgumentNullException(nameof(member)); - } - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol containingType, MemberInfo member) : - this(context, containingType.ContainingModule, member) - { - _containingType = containingType ?? throw new ArgumentNullException(nameof(containingType)); - } - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected internal override IkvmReflectionTypeSymbol ResolveTypeSymbol(Type type) - { - if (_containingType != null && type == _containingType.ReflectionObject) - return _containingType; - else if (type.Module == _member.Module) - return _containingModule.GetOrCreateTypeSymbol(type); - else - return base.ResolveTypeSymbol(type); - } - - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - protected internal override IkvmReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) - { - if (ctor.Module == _member.Module) - return _containingModule.GetOrCreateConstructorSymbol(ctor); - else - return base.ResolveConstructorSymbol(ctor); - } - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected internal override IkvmReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) - { - if (method.Module == _member.Module) - return _containingModule.GetOrCreateMethodSymbol(method); - else - return base.ResolveMethodSymbol(method); - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override IkvmReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) - { - if (field.Module == _member.Module) - return _containingModule.GetOrCreateFieldSymbol(field); - else - return base.ResolveFieldSymbol(field); - } - - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override IkvmReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) - { - if (property.Module == _member.Module) - return _containingModule.GetOrCreatePropertySymbol(property); - else - return base.ResolvePropertySymbol(property); - } - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - protected internal override IkvmReflectionEventSymbol ResolveEventSymbol(EventInfo @event) - { - if (@event.Module == _member.Module) - return _containingModule.GetOrCreateEventSymbol(@event); - else - return base.ResolveEventSymbol(@event); - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal MemberInfo ReflectionObject => _member; - - /// - /// Gets the which contains the metadata of this member. - /// - internal IkvmReflectionModuleSymbol ContainingModule => _containingModule; - - /// - /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. - /// - internal IkvmReflectionTypeSymbol? ContainingType => _containingType; - - /// - public virtual IModuleSymbol Module => Context.GetOrCreateModuleSymbol(_member.Module); - - /// - public virtual ITypeSymbol? DeclaringType => _member.DeclaringType is { } t ? Context.GetOrCreateTypeSymbol(t) : null; - - /// - public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)_member.MemberType; - - /// - public virtual int MetadataToken => _member.MetadataToken; - - /// - public virtual string Name => _member.Name; - - /// - public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - if (inherit) - { - // check that we've already processed this - if (_inheritedCustomAttributes != null) - return _inheritedCustomAttributes; - - var self = _member; - var list = default(List?); - for (; ; ) - { - // get attribute for current member and append to list - var attr = ResolveMemberSymbol(self).GetCustomAttributes(false); - if (attr.Length > 0) - { - list ??= []; - list.Add(attr); - } - - var type = self as Type; - if (type != null) - { - type = type.BaseType; - if (type == null) - return _inheritedCustomAttributes ??= Concat(list); - - self = type; - continue; - } - - var method = self as MethodInfo; - if (method != null) - { - var prev = self; - method = method.GetBaseDefinition(); - if (method == null || method == prev) - return _inheritedCustomAttributes ??= Concat(list); - - self = method; - continue; - } - - return _inheritedCustomAttributes ??= Concat(list); - } - } - - return _customAttributes ??= ResolveCustomAttributes(_member.GetCustomAttributesData()); - } - - /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); - } - - /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); - } - - /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return _member.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - protected void Complete(MemberInfo member) - { - ResolveMemberSymbol(_member = member); - _customAttributes = null; - _inheritedCustomAttributes = null; - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs deleted file mode 100644 index 20f097683a..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs +++ /dev/null @@ -1,133 +0,0 @@ -using System; - -using MethodBase = IKVM.Reflection.MethodBase; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - abstract class IkvmReflectionMethodBaseSymbol : IkvmReflectionMemberSymbol, IMethodBaseSymbol - { - - MethodBase _method; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMethodBaseSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, MethodBase method) : - base(context, module, method) - { - _method = method ?? throw new ArgumentNullException(nameof(method)); - } - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMethodBaseSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, MethodBase method) : - this(context, type.ContainingModule, method) - { - - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new MethodBase ReflectionObject => _method; - - /// - public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)_method.Attributes; - - /// - public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)_method.CallingConvention; - - /// - public bool ContainsGenericParameters => _method.ContainsGenericParameters; - - /// - public bool IsAbstract => _method.IsAbstract; - - /// - public bool IsAssembly => _method.IsAssembly; - - /// - public bool IsConstructor => _method.IsConstructor; - - /// - public bool IsFamily => _method.IsFamily; - - /// - public bool IsFamilyAndAssembly => _method.IsFamilyAndAssembly; - - /// - public bool IsFamilyOrAssembly => _method.IsFamilyOrAssembly; - - /// - public bool IsFinal => _method.IsFinal; - - /// - public bool IsGenericMethod => _method.IsGenericMethod; - - /// - public bool IsGenericMethodDefinition => _method.IsGenericMethodDefinition; - - /// - public bool IsHideBySig => _method.IsHideBySig; - - /// - public bool IsPrivate => _method.IsPrivate; - - /// - public bool IsPublic => _method.IsPublic; - - /// - public bool IsStatic => _method.IsStatic; - - /// - public bool IsVirtual => _method.IsVirtual; - - /// - public bool IsSpecialName => _method.IsSpecialName; - - /// - public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)_method.MethodImplementationFlags; - - /// - public ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(_method.GetGenericArguments()); - } - - /// - public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() - { - return (System.Reflection.MethodImplAttributes)_method.GetMethodImplementationFlags(); - } - - /// - public IParameterSymbol[] GetParameters() - { - return ResolveParameterSymbols(_method.GetParameters()); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(MethodBase method) - { - ResolveMethodBaseSymbol(_method = method); - base.Complete(_method); - - foreach (var i in _method.GetParameters()) - ResolveParameterSymbol(i).Complete(i); - - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs deleted file mode 100644 index 472021fa7d..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs +++ /dev/null @@ -1,71 +0,0 @@ -using System; - -using MethodInfo = IKVM.Reflection.MethodInfo; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionMethodSymbol : IkvmReflectionMethodBaseSymbol, IMethodSymbol - { - - readonly MethodInfo _method; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, MethodInfo method) : - base(context, module, method) - { - _method = method ?? throw new ArgumentNullException(nameof(method)); - } - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, MethodInfo method) : - this(context, type.ContainingModule, method) - { - - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new MethodInfo ReflectionObject => _method; - - /// - public IParameterSymbol ReturnParameter => ResolveParameterSymbol(_method.ReturnParameter); - - /// - public ITypeSymbol ReturnType => ResolveTypeSymbol(_method.ReturnType); - - /// - public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); - - /// - public IMethodSymbol GetBaseDefinition() - { - return ResolveMethodSymbol(_method.GetBaseDefinition()); - } - - /// - public IMethodSymbol GetGenericMethodDefinition() - { - return ResolveMethodSymbol(_method.GetGenericMethodDefinition()); - } - - /// - public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) - { - return ResolveMethodSymbol(_method.MakeGenericMethod(typeArguments.Unpack())); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs deleted file mode 100644 index e1ad04c5dc..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ /dev/null @@ -1,587 +0,0 @@ -using System; -using System.Diagnostics; -using System.Linq; -using System.Reflection.Metadata.Ecma335; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Threading; -using IKVM.Reflection; - -using Module = IKVM.Reflection.Module; -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - /// - /// Implementation of derived from System.Reflection. - /// - class IkvmReflectionModuleSymbol : IkvmReflectionSymbol, IModuleSymbol - { - - /// - /// Returns true if the given is a TypeDef. That is, not a modified or substituted or generic parameter type. - /// - /// - /// - static bool IsTypeDefinition(Type type) - { - return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; - } - - const int MAX_CAPACITY = 65536 * 2; - - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - - readonly IkvmReflectionAssemblySymbol _containingAssembly; - Module _module; - - IndexRangeDictionary _typeTable = new(maxCapacity: MAX_CAPACITY); - IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _typeLock; - - IndexRangeDictionary _methodTable = new(maxCapacity: MAX_CAPACITY); - IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _methodLock; - - IndexRangeDictionary _fieldTable = new(maxCapacity: MAX_CAPACITY); - IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _fieldLock; - - IndexRangeDictionary _propertyTable = new(maxCapacity: MAX_CAPACITY); - IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _propertyLock; - - IndexRangeDictionary _eventTable = new(maxCapacity: MAX_CAPACITY); - IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _eventLock; - - IndexRangeDictionary _parameterTable = new(maxCapacity: MAX_CAPACITY); - IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _parameterLock; - - IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _genericParameterLock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public IkvmReflectionModuleSymbol(IkvmReflectionSymbolContext context, IkvmReflectionAssemblySymbol containingAssembly, Module module) : - base(context) - { - _containingAssembly = containingAssembly ?? throw new ArgumentNullException(nameof(containingAssembly)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - } - - /// - /// Gets the which contains the metadata of this member. - /// - internal IkvmReflectionAssemblySymbol ContainingAssembly => _containingAssembly; - - /// - /// Gets the wrapped . - /// - internal Module ReflectionObject => _module; - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - /// - internal IkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - - Debug.Assert(type.Module == _module); - - // type is a generic parameter (GenericParam) - if (type.IsGenericParameter) - return GetOrCreateGenericParameterSymbol(type); - - // type is not a type definition (TypeDef) - if (IsTypeDefinition(type) == false) - return GetOrCreateTypeSymbolForSpecification(type); - - // create lock on demand - if (_typeLock == null) - Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); - - using (_typeLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.TypeDefinitionHandle(type.MetadataToken)); - if (_typeTable[row] != type) - using (_typeLock.CreateWriteLock()) - _typeTable[row] = type; - - if (_typeSymbols[row] == null) - using (_typeLock.CreateWriteLock()) - return _typeSymbols[row] ??= new IkvmReflectionTypeSymbol(Context, this, type); - else - return _typeSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates a for the specification type: array, pointer, etc. - /// - /// - /// - /// - /// - IkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - - Debug.Assert(type.Module == _module); - - if (type.GetElementType() is { } elementType) - { - var elementTypeSymbol = ResolveTypeSymbol(elementType); - - // handles both SZ arrays and normal arrays - if (type.IsArray) - return (IkvmReflectionTypeSymbol)elementTypeSymbol.MakeArrayType(type.GetArrayRank()); - - if (type.IsPointer) - return (IkvmReflectionTypeSymbol)elementTypeSymbol.MakePointerType(); - - if (type.IsByRef) - return (IkvmReflectionTypeSymbol)elementTypeSymbol.MakeByRefType(); - - throw new InvalidOperationException(); - } - - if (type.IsGenericType) - { - var definitionTypeSymbol = ResolveTypeSymbol(type.GetGenericTypeDefinition()); - return definitionTypeSymbol.GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); - } - - throw new InvalidOperationException(); - } - - /// - /// Gets or creates the cached fqor the type by method. - /// - /// - /// - internal IkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - Debug.Assert(method.Module.MetadataToken == _module.MetadataToken); - - // create lock on demand - if (_methodLock == null) - Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); - - using (_methodLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(method.MetadataToken)); - if (_methodTable[row] != method) - using (_methodLock.CreateWriteLock()) - _methodTable[row] = method; - - if (_methodSymbols[row] == null) - using (_methodLock.CreateWriteLock()) - if (method is ConstructorInfo c) - return _methodSymbols[row] ??= new IkvmReflectionConstructorSymbol(Context, ResolveTypeSymbol(c.DeclaringType ?? throw new InvalidOperationException()), c); - else if (method is MethodInfo m) - if (method.DeclaringType is { } dt) - return _methodSymbols[row] ??= new IkvmReflectionMethodSymbol(Context, ResolveTypeSymbol(dt), m); - else - return _methodSymbols[row] ??= new IkvmReflectionMethodSymbol(Context, this, m); - else - throw new InvalidOperationException(); - else - return _methodSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - internal IkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return (IkvmReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal IkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return (IkvmReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - /// - internal IkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - Debug.Assert(field.Module == _module); - - // create lock on demand - if (_fieldLock == null) - Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); - - using (_fieldLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(field.MetadataToken)); - if (_fieldTable[row] != field) - using (_fieldLock.CreateWriteLock()) - _fieldTable[row] = field; - - if (_fieldSymbols[row] == null) - using (_fieldLock.CreateWriteLock()) - if (field.DeclaringType is { } dt) - return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbol(Context, ResolveTypeSymbol(dt), field); - else - return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbol(Context, this, field); - else - return _fieldSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - /// - internal IkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - Debug.Assert(property.Module == _module); - - // create lock on demand - if (_propertyLock == null) - Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); - - using (_propertyLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(property.MetadataToken)); - if (_propertyTable[row] != property) - using (_propertyLock.CreateWriteLock()) - _propertyTable[row] = property; - - if (_propertySymbols[row] == null) - using (_propertyLock.CreateWriteLock()) - return _propertySymbols[row] ??= new IkvmReflectionPropertySymbol(Context, ResolveTypeSymbol(property.DeclaringType!), property); - else - return _propertySymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - /// - internal IkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - Debug.Assert(@event.Module == _module); - - // create lock on demand - if (_eventLock == null) - Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); - - using (_eventLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.MetadataToken)); - if (_eventTable[row] is not EventInfo i || i != @event) - using (_eventLock.CreateWriteLock()) - _eventTable[row] = @event; - - if (_eventSymbols[row] == null) - using (_eventLock.CreateWriteLock()) - return _eventSymbols[row] ??= new IkvmReflectionEventSymbol(Context, ResolveTypeSymbol(@event.DeclaringType!), @event); - else - return _eventSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - Debug.Assert(parameter.Member.Module == _module); - - // create lock on demand - if (_parameterLock == null) - Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); - - using (_parameterLock.CreateUpgradeableReadLock()) - { - var position = parameter.Position; - if (_parameterTable[position] != parameter) - using (_parameterLock.CreateWriteLock()) - _parameterTable[position] = parameter; - - if (_parameterSymbols[position] == null) - using (_parameterLock.CreateWriteLock()) - return _parameterSymbols[position] ??= new IkvmReflectionParameterSymbol(Context, ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); - else - return _parameterSymbols[position] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - /// - internal IkvmReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericParameterType) - { - if (genericParameterType is null) - throw new ArgumentNullException(nameof(genericParameterType)); - - Debug.Assert(genericParameterType.Module == _module); - - // create lock on demand - if (_genericParameterLock == null) - Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); - - using (_genericParameterLock.CreateUpgradeableReadLock()) - { - var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - if (_genericParameterSymbols[row] == null) - using (_genericParameterLock.CreateWriteLock()) - return _genericParameterSymbols[row] ??= new IkvmReflectionTypeSymbol(Context, this, genericParameterType); - else - return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_module.Assembly); - - /// - public string FullyQualifiedName => _module.FullyQualifiedName; - - /// - public int MetadataToken => _module.MetadataToken; - - /// - public Guid ModuleVersionId => _module.ModuleVersionId; - - /// - public string Name => _module.Name; - - /// - public string ScopeName => _module.ScopeName; - - /// - public IFieldSymbol? GetField(string name) - { - return _module.GetField(name) is { } f ? ResolveFieldSymbol(f) : null; - } - - /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) - { - return _module.GetField(name, (BindingFlags)bindingAttr) is { } f ? ResolveFieldSymbol(f) : null; - } - - /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingFlags) - { - return ResolveFieldSymbols(_module.GetFields((BindingFlags)bindingFlags)); - } - - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(_module.GetFields()); - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return _module.GetMethod(name) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return _module.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(_module.GetMethods()); - } - - /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingFlags) - { - return ResolveMethodSymbols(_module.GetMethods((BindingFlags)bindingFlags)); - } - - /// - public ITypeSymbol? GetType(string className) - { - return _module.GetType(className) is { } t ? ResolveTypeSymbol(t) : null; - } - - /// - public ITypeSymbol? GetType(string className, bool ignoreCase) - { - return _module.GetType(className, ignoreCase) is { } t ? ResolveTypeSymbol(t) : null; - } - - /// - public ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase) - { - return _module.GetType(className, throwOnError, ignoreCase) is { } t ? ResolveTypeSymbol(t) : null; - } - - /// - public ITypeSymbol[] GetTypes() - { - return ResolveTypeSymbols(_module.GetTypes()); - } - - /// - public bool IsResource() - { - return _module.IsResource(); - } - - /// - public IFieldSymbol? ResolveField(int metadataToken) - { - return _module.ResolveField(metadataToken) is { } f ? ResolveFieldSymbol(f) : null; - } - - /// - public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return _module.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } f ? ResolveFieldSymbol(f) : null; - } - - /// - public IMemberSymbol? ResolveMember(int metadataToken) - { - return _module.ResolveMember(metadataToken) is { } m ? ResolveMemberSymbol(m) : null; - } - - /// - public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return _module.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMemberSymbol(m) : null; - } - - /// - public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return _module.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMethodBaseSymbol(m) : null; - } - - /// - public IMethodBaseSymbol? ResolveMethod(int metadataToken) - { - return _module.ResolveMethod(metadataToken) is { } m ? ResolveMethodBaseSymbol(m) : null; - } - - /// - public byte[] ResolveSignature(int metadataToken) - { - return _module.ResolveSignature(metadataToken); - } - - /// - public string ResolveString(int metadataToken) - { - return _module.ResolveString(metadataToken); - } - - /// - public ITypeSymbol ResolveType(int metadataToken) - { - return ResolveTypeSymbol(_module.ResolveType(metadataToken)); - } - - /// - public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveTypeSymbol(_module.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return ResolveCustomAttributes(_module.GetCustomAttributesData()); - } - - /// - public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - return ResolveCustomAttributes(_module.GetCustomAttributesData().Where(i => i.AttributeType == ((IkvmReflectionTypeSymbol)attributeType).ReflectionObject)); - } - - /// - public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); - } - - /// - public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return _module.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, false); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(Module module) - { - ResolveModuleSymbol(_module = module); - ContainingAssembly.Complete(_module.Assembly); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs deleted file mode 100644 index a0dca46268..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs +++ /dev/null @@ -1,119 +0,0 @@ -using System; -using System.Linq; - -using ParameterInfo = IKVM.Reflection.ParameterInfo; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionParameterSymbol : IkvmReflectionSymbol, IParameterSymbol - { - - readonly IkvmReflectionMethodBaseSymbol _containingMethod; - ParameterInfo _parameter; - - CustomAttribute[]? _customAttributes; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IkvmReflectionMethodBaseSymbol containingMethod, ParameterInfo parameter) : - base(context) - { - _containingMethod = containingMethod ?? throw new ArgumentNullException(nameof(containingMethod)); - _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); - } - - internal IkvmReflectionMethodBaseSymbol ContainingMethod => _containingMethod; - - /// - public System.Reflection.ParameterAttributes Attributes =>(System.Reflection.ParameterAttributes)_parameter.Attributes; - - /// - public object? DefaultValue => _parameter.RawDefaultValue; - - /// - public bool HasDefaultValue => _parameter.HasDefaultValue; - - /// - public bool IsIn => _parameter.IsIn; - - /// - public bool IsLcid => _parameter.IsLcid; - - /// - public bool IsOptional => _parameter.IsOptional; - - /// - public bool IsOut => _parameter.IsOut; - - /// - public bool IsRetval => _parameter.IsRetval; - - /// - public IMemberSymbol Member => ResolveMemberSymbol(_parameter.Member); - - /// - public int MetadataToken => _parameter.MetadataToken; - - /// - public string? Name => _parameter.Name; - - /// - public ITypeSymbol ParameterType => ResolveTypeSymbol(_parameter.ParameterType); - - /// - public int Position => _parameter.Position; - - /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); - } - - /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); - } - - /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); - } - - /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return _parameter.IsDefined(((IkvmReflectionTypeSymbol)attributeType).ReflectionObject, inherit); - } - - /// - public ITypeSymbol[] GetOptionalCustomModifiers() - { - return ResolveTypeSymbols(_parameter.GetOptionalCustomModifiers()); - } - - /// - public ITypeSymbol[] GetRequiredCustomModifiers() - { - return ResolveTypeSymbols(_parameter.GetRequiredCustomModifiers()); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(ParameterInfo parameter) - { - ResolveParameterSymbol(_parameter = parameter); - _customAttributes = null; - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs deleted file mode 100644 index a257b00159..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs +++ /dev/null @@ -1,131 +0,0 @@ -using System; - -using IKVM.Reflection; - -using PropertyInfo = IKVM.Reflection.PropertyInfo; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionPropertySymbol : IkvmReflectionMemberSymbol, IPropertySymbol - { - - PropertyInfo _property; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionPropertySymbol(IkvmReflectionSymbolContext context, IkvmReflectionTypeSymbol type, PropertyInfo property) : - base(context, type, property) - { - _property = property ?? throw new ArgumentNullException(nameof(property)); - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new PropertyInfo ReflectionObject => _property; - - /// - public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)_property.Attributes; - - /// - public bool CanRead => _property.CanRead; - - /// - public bool CanWrite => _property.CanWrite; - - /// - public bool IsSpecialName => _property.IsSpecialName; - - /// - public ITypeSymbol PropertyType => ResolveTypeSymbol(_property.PropertyType); - - /// - public IMethodSymbol? GetMethod => _property.GetMethod is { } m ? ResolveMethodSymbol(m) : null; - - /// - public IMethodSymbol? SetMethod => _property.SetMethod is { } m ? ResolveMethodSymbol(m) : null; - - /// - public object? GetRawConstantValue() - { - return _property.GetRawConstantValue(); - } - - /// - public IMethodSymbol[] GetAccessors() - { - return ResolveMethodSymbols(_property.GetAccessors()); - } - - /// - public IMethodSymbol[] GetAccessors(bool nonPublic) - { - return ResolveMethodSymbols(_property.GetAccessors(nonPublic)); - } - - /// - public IParameterSymbol[] GetIndexParameters() - { - return ResolveParameterSymbols(_property.GetIndexParameters()); - } - - /// - public IMethodSymbol? GetGetMethod() - { - return _property.GetGetMethod() is MethodInfo m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetGetMethod(bool nonPublic) - { - return _property.GetGetMethod(nonPublic) is MethodInfo m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetSetMethod() - { - return _property.GetSetMethod() is MethodInfo m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetSetMethod(bool nonPublic) - { - return _property.GetSetMethod(nonPublic) is MethodInfo m ? ResolveMethodSymbol(m) : null; - } - - /// - public ITypeSymbol GetModifiedPropertyType() - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol[] GetOptionalCustomModifiers() - { - return ResolveTypeSymbols(_property.GetOptionalCustomModifiers()); - } - - /// - public ITypeSymbol[] GetRequiredCustomModifiers() - { - return ResolveTypeSymbols(_property.GetRequiredCustomModifiers()); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(PropertyInfo property) - { - ResolvePropertySymbol(_property = property); - base.Complete(_property); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs deleted file mode 100644 index a469bb9464..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ /dev/null @@ -1,417 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Collections.Immutable; - -using IKVM.Reflection; - -using ConstructorInfo = IKVM.Reflection.ConstructorInfo; -using EventInfo = IKVM.Reflection.EventInfo; -using FieldInfo = IKVM.Reflection.FieldInfo; -using MemberInfo = IKVM.Reflection.MemberInfo; -using MethodBase = IKVM.Reflection.MethodBase; -using MethodInfo = IKVM.Reflection.MethodInfo; -using Module = IKVM.Reflection.Module; -using ParameterInfo = IKVM.Reflection.ParameterInfo; -using PropertyInfo = IKVM.Reflection.PropertyInfo; -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - /// - /// Base class for managed symbols. - /// - abstract class IkvmReflectionSymbol : ISymbol - { - - readonly IkvmReflectionSymbolContext _context; - - /// - /// Initializes a new instance. - /// - /// - public IkvmReflectionSymbol(IkvmReflectionSymbolContext context) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - } - - /// - /// Gets the associated . - /// - protected IkvmReflectionSymbolContext Context => _context; - - /// - public bool IsMissing => false; - - /// - public bool ContainsMissing => false; - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected virtual internal IkvmReflectionModuleSymbol ResolveModuleSymbol(Module module) - { - return _context.GetOrCreateModuleSymbol(module); - } - - /// - /// Resolves the symbols for the specified modules. - /// - /// - /// - protected internal IkvmReflectionModuleSymbol[] ResolveModuleSymbols(Module[] modules) - { - var a = new IkvmReflectionModuleSymbol[modules.Length]; - for (int i = 0; i < modules.Length; i++) - a[i] = ResolveModuleSymbol(modules[i]); - - return a; - } - - /// - /// Resolves the symbols for the specified modules. - /// - /// - /// - protected internal IEnumerable ResolveModuleSymbols(IEnumerable modules) - { - foreach (var module in modules) - yield return ResolveModuleSymbol(module); - } - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected virtual IkvmReflectionMemberSymbol ResolveMemberSymbol(MemberInfo member) - { - return member.MemberType switch - { - MemberTypes.Constructor => ResolveConstructorSymbol((ConstructorInfo)member), - MemberTypes.Event => ResolveEventSymbol((EventInfo)member), - MemberTypes.Field => ResolveFieldSymbol((FieldInfo)member), - MemberTypes.Method => ResolveMethodSymbol((MethodInfo)member), - MemberTypes.Property => ResolvePropertySymbol((PropertyInfo)member), - MemberTypes.TypeInfo => ResolveTypeSymbol((Type)member), - MemberTypes.NestedType => ResolveTypeSymbol((Type)member), - MemberTypes.Custom => throw new NotImplementedException(), - MemberTypes.All => throw new NotImplementedException(), - _ => throw new InvalidOperationException(), - }; - } - - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - protected internal IkvmReflectionMemberSymbol[] ResolveMemberSymbols(MemberInfo[] types) - { - var a = new IkvmReflectionMemberSymbol[types.Length]; - for (int i = 0; i < types.Length; i++) - a[i] = ResolveMemberSymbol(types[i]); - - return a; - } - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected virtual internal IkvmReflectionTypeSymbol ResolveTypeSymbol(Type type) - { - return _context.GetOrCreateTypeSymbol(type); - } - - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - protected internal IkvmReflectionTypeSymbol[] ResolveTypeSymbols(Type[] types) - { - var a = new IkvmReflectionTypeSymbol[types.Length]; - for (int i = 0; i < types.Length; i++) - a[i] = ResolveTypeSymbol(types[i]); - - return a; - } - - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - protected internal IEnumerable ResolveTypeSymbols(IEnumerable types) - { - foreach (var type in types) - yield return ResolveTypeSymbol(type); - } - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected virtual internal IkvmReflectionMethodBaseSymbol ResolveMethodBaseSymbol(MethodBase method) - { - if (method.IsConstructor) - return ResolveConstructorSymbol((ConstructorInfo)method); - else - return ResolveMethodSymbol((MethodInfo)method); - } - - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - protected virtual internal IkvmReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) - { - return _context.GetOrCreateConstructorSymbol(ctor); - } - - /// - /// Resolves the symbols for the specified constructors. - /// - /// - /// - protected internal IkvmReflectionConstructorSymbol[] ResolveConstructorSymbols(ConstructorInfo[] ctors) - { - var a = new IkvmReflectionConstructorSymbol[ctors.Length]; - for (int i = 0; i < ctors.Length; i++) - a[i] = ResolveConstructorSymbol(ctors[i]); - - return a; - } - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected virtual internal IkvmReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) - { - return _context.GetOrCreateMethodSymbol(method); - } - - /// - /// Resolves the symbols for the specified methods. - /// - /// - /// - protected internal IkvmReflectionMethodSymbol[] ResolveMethodSymbols(MethodInfo[] methods) - { - var a = new IkvmReflectionMethodSymbol[methods.Length]; - for (int i = 0; i < methods.Length; i++) - a[i] = ResolveMethodSymbol(methods[i]); - - return a; - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected virtual internal IkvmReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) - { - return _context.GetOrCreateFieldSymbol(field); - } - - /// - /// Resolves the symbols for the specified fields. - /// - /// - /// - protected internal IkvmReflectionFieldSymbol[] ResolveFieldSymbols(FieldInfo[] fields) - { - var a = new IkvmReflectionFieldSymbol[fields.Length]; - for (int i = 0; i < fields.Length; i++) - a[i] = ResolveFieldSymbol(fields[i]); - - return a; - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected virtual internal IkvmReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) - { - return _context.GetOrCreatePropertySymbol(property); - } - - /// - /// Resolves the symbols for the specified properties. - /// - /// - /// - protected internal IkvmReflectionPropertySymbol[] ResolvePropertySymbols(PropertyInfo[] properties) - { - var a = new IkvmReflectionPropertySymbol[properties.Length]; - for (int i = 0; i < properties.Length; i++) - a[i] = ResolvePropertySymbol(properties[i]); - - return a; - } - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - protected virtual internal IkvmReflectionEventSymbol ResolveEventSymbol(EventInfo @event) - { - return _context.GetOrCreateEventSymbol(@event); - } - - /// - /// Resolves the symbols for the specified events. - /// - /// - /// - protected internal IkvmReflectionEventSymbol[] ResolveEventSymbols(EventInfo[] events) - { - var a = new IkvmReflectionEventSymbol[events.Length]; - for (int i = 0; i < events.Length; i++) - a[i] = ResolveEventSymbol(events[i]); - - return a; - } - - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - protected virtual internal IkvmReflectionParameterSymbol ResolveParameterSymbol(ParameterInfo parameter) - { - return _context.GetOrCreateParameterSymbol(parameter); - } - - /// - /// Resolves the symbols for the specified parameters. - /// - /// - /// - protected internal IkvmReflectionParameterSymbol[] ResolveParameterSymbols(ParameterInfo[] parameters) - { - var a = new IkvmReflectionParameterSymbol[parameters.Length]; - for (int i = 0; i < parameters.Length; i++) - a[i] = ResolveParameterSymbol(parameters[i]); - - return a; - } - - /// - /// Transforms a custom set of custom attribute data records to a symbol record. - /// - /// - /// - protected internal CustomAttribute[] ResolveCustomAttributes(IList attributes) - { - var a = new CustomAttribute[attributes.Count]; - for (int i = 0; i < attributes.Count; i++) - a[i] = ResolveCustomAttribute(attributes[i]); - - return a; - } - - /// - /// Transforms a custom set of custom attribute data records to a symbol record. - /// - /// - /// - protected internal CustomAttribute[] ResolveCustomAttributes(IEnumerable attributes) - { - var a = new List(); - foreach (var i in attributes) - a.Add(ResolveCustomAttribute(i)); - - return a.ToArray(); - } - - /// - /// Transforms a custom attribute data record to a symbol record. - /// - /// - /// - protected internal CustomAttribute ResolveCustomAttribute(CustomAttributeData customAttributeData) - { - return new CustomAttribute( - ResolveTypeSymbol(customAttributeData.AttributeType), - ResolveConstructorSymbol(customAttributeData.Constructor), - ResolveCustomAttributeTypedArguments(customAttributeData.ConstructorArguments), - ResolveCustomAttributeNamedArguments(customAttributeData.NamedArguments)); - } - - /// - /// Transforms a list of values into symbols. - /// - /// - /// - ImmutableArray ResolveCustomAttributeTypedArguments(IList args) - { - var a = new CustomAttributeTypedArgument[args.Count]; - for (int i = 0; i < args.Count; i++) - a[i] = ResolveCustomAttributeTypedArgument(args[i]); - - return a.ToImmutableArray(); - } - - /// - /// Transforms a values into a symbol. - /// - /// - /// - CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Reflection.CustomAttributeTypedArgument arg) - { - return new CustomAttributeTypedArgument(ResolveTypeSymbol(arg.ArgumentType), ResolveCustomAttributeTypedValue(arg.Value)); - } - - /// - /// Transforms the type as appropriate. - /// - /// - /// - object? ResolveCustomAttributeTypedValue(object? value) - { - if (value is Type v) - return ResolveTypeSymbol(v); - - return value; - } - - /// - /// Transforms a list of values into symbols. - /// - /// - /// - ImmutableArray ResolveCustomAttributeNamedArguments(IList args) - { - var a = new CustomAttributeNamedArgument[args.Count]; - for (int i = 0; i < args.Count; i++) - a[i] = ResolveCustomAttributeNamedArgument(args[i]); - - return ImmutableArray.Create(a); - } - - /// - /// Transforms a values into a symbol. - /// - /// - /// - CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(IKVM.Reflection.CustomAttributeNamedArgument arg) - { - return new CustomAttributeNamedArgument(arg.IsField, ResolveMemberSymbol(arg.MemberInfo), arg.MemberName, ResolveCustomAttributeTypedArgument(arg.TypedValue)); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs deleted file mode 100644 index 53ce1511fb..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ /dev/null @@ -1,180 +0,0 @@ -using System; -using System.Collections.Concurrent; -using System.Runtime.CompilerServices; - -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; -using IKVM.Reflection.Emit; - -using Assembly = IKVM.Reflection.Assembly; -using ConstructorInfo = IKVM.Reflection.ConstructorInfo; -using EventInfo = IKVM.Reflection.EventInfo; -using FieldInfo = IKVM.Reflection.FieldInfo; -using MethodBase = IKVM.Reflection.MethodBase; -using MethodInfo = IKVM.Reflection.MethodInfo; -using Module = IKVM.Reflection.Module; -using ParameterInfo = IKVM.Reflection.ParameterInfo; -using PropertyInfo = IKVM.Reflection.PropertyInfo; -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - /// - /// Holds references to symbols derived from System.Reflection. - /// - class IkvmReflectionSymbolContext - { - - readonly ConcurrentDictionary> _symbolByName = new(AssemblyNameEqualityComparer.Instance); - readonly ConditionalWeakTable _symbolByAssembly = new(); - - /// - /// Initializes a new instance. - /// - public IkvmReflectionSymbolContext() - { - - } - - /// - /// Gets or creates a indexed based on the assembly's name. - /// - /// - /// - IkvmReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) - { - var r = _symbolByName.GetOrAdd(assembly.GetName().ToAssemblyName(), _ => new WeakReference(new IkvmReflectionAssemblySymbol(this, assembly))); - - // reference has valid symbol - if (r.TryGetTarget(out var s)) - return s; - - // no valid symbol, must have been released, lock to restore - lock (r) - { - // still gone, recreate - if (r.TryGetTarget(out s) == false) - r.SetTarget(s = new IkvmReflectionAssemblySymbol(this, assembly)); - - return s; - } - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) - { - return _symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is ConstructorInfo ctor) - return GetOrCreateConstructorSymbol(ctor); - else - return GetOrCreateMethodSymbol((MethodInfo)method); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - return GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateParameterSymbol(parameter); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); - } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - /// - public IkvmReflectionParameterSymbol GetOrCreateParameterSymbol(MethodBuilder method, ParameterBuilder parameter) - { - return GetOrCreateParameterSymbol(new IkvmReflectionParameterBuilderInfo(method, parameter)); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs deleted file mode 100644 index a3d3ef7c54..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ /dev/null @@ -1,669 +0,0 @@ -using System; -using System.Collections.Concurrent; -using System.Collections.Generic; -using System.Diagnostics; -using System.Linq; -using System.Threading; - -using IKVM.CoreLib.Symbols.Reflection; -using IKVM.Reflection; - -using ConstructorInfo = IKVM.Reflection.ConstructorInfo; -using FieldInfo = IKVM.Reflection.FieldInfo; -using MethodInfo = IKVM.Reflection.MethodInfo; -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - class IkvmReflectionTypeSymbol : IkvmReflectionMemberSymbol, ITypeSymbol - { - - const int MAX_CAPACITY = 65536 * 2; - - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - - Type _type; - - IkvmReflectionTypeSymbol?[]? _asArray; - IkvmReflectionTypeSymbol? _asSZArray; - IkvmReflectionTypeSymbol? _asPointer; - IkvmReflectionTypeSymbol? _asByRef; - ConcurrentDictionary? _genericTypeSymbols; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public IkvmReflectionTypeSymbol(IkvmReflectionSymbolContext context, IkvmReflectionModuleSymbol module, Type type) : - base(context, module, type) - { - Debug.Assert(module.ReflectionObject == type.Module); - _type = type ?? throw new ArgumentNullException(nameof(type)); - } - - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - internal IkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) - { - if (genericTypeArguments is null) - throw new ArgumentNullException(nameof(genericTypeArguments)); - - if (_type.IsGenericTypeDefinition == false) - throw new InvalidOperationException(); - - if (_genericTypeSymbols == null) - Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); - - return _genericTypeSymbols.GetOrAdd( - genericTypeArguments, - _ => new IkvmReflectionTypeSymbol(Context, ContainingModule, _type.MakeGenericType(genericTypeArguments.Unpack()))); - } - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected internal override IkvmReflectionTypeSymbol ResolveTypeSymbol(Type type) - { - if (type == _type) - return this; - else - return base.ResolveTypeSymbol(type); - } - - /// - /// Gets the wrapped . - /// - internal new Type ReflectionObject => _type; - - /// - public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_type.Assembly); - - /// - public string? AssemblyQualifiedName => _type.AssemblyQualifiedName; - - /// - public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)_type.Attributes; - - /// - public ITypeSymbol? BaseType => _type.BaseType != null ? ResolveTypeSymbol(_type.BaseType) : null; - - /// - public bool ContainsGenericParameters => _type.ContainsGenericParameters; - - /// - public IMethodBaseSymbol? DeclaringMethod => _type.DeclaringMethod is MethodInfo m ? ResolveMethodSymbol(m) : null; - - /// - public string? FullName => _type.FullName; - - /// - public string? Namespace => _type.Namespace; - - /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)_type.GenericParameterAttributes; - - /// - public int GenericParameterPosition => _type.GenericParameterPosition; - - /// - public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(_type.GenericTypeArguments); - - /// - public bool HasElementType => _type.HasElementType; - - /// - public TypeCode TypeCode => Type.GetTypeCode(_type); - - /// - public bool IsAbstract => _type.IsAbstract; - -#if NETFRAMEWORK - - /// - /// - /// There's no API to distinguish an array of rank 1 from a vector, - /// so we check if the type name ends in [], which indicates it's a vector - /// (non-vectors will have [*] or [,]). - /// - public bool IsSZArray => _type.IsArray && _type.Name.EndsWith("[]"); - -#else - - /// - public bool IsSZArray => _type.IsSZArray; - -#endif - - /// - public bool IsArray => _type.IsArray; - - /// - public bool IsAutoLayout => _type.IsAutoLayout; - - /// - public bool IsExplicitLayout => _type.IsExplicitLayout; - - /// - public bool IsByRef => _type.IsByRef; - - /// - public bool IsClass => _type.IsClass; - - /// - public bool IsEnum => _type.IsEnum; - - /// - public bool IsInterface => _type.IsInterface; - - /// - public bool IsConstructedGenericType => _type.IsConstructedGenericType; - - /// - public bool IsGenericParameter => _type.IsGenericParameter; - - /// - public bool IsGenericType => _type.IsGenericType; - - /// - public bool IsGenericTypeDefinition => _type.IsGenericTypeDefinition; - - /// - public bool IsLayoutSequential => _type.IsLayoutSequential; - - /// - public bool IsNested => _type.IsNested; - - /// - public bool IsNestedAssembly => _type.IsNestedAssembly; - - /// - public bool IsNestedFamANDAssem => _type.IsNestedFamANDAssem; - - /// - public bool IsNestedFamORAssem => _type.IsNestedFamORAssem; - - /// - public bool IsNestedFamily => _type.IsNestedFamily; - - /// - public bool IsNestedPrivate => _type.IsNestedPrivate; - - /// - public bool IsNestedPublic => _type.IsNestedPublic; - - /// - public bool IsNotPublic => _type.IsNotPublic; - - /// - public bool IsPointer => _type.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public bool IsFunctionPointer => _type.IsFunctionPointer; - - /// - public bool IsUnmanagedFunctionPointer => _type.IsUnmanagedFunctionPointer; - -#else - - /// - public bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public bool IsPrimitive => _type.IsPrimitive; - - /// - public bool IsPublic => _type.IsPublic; - - /// - public bool IsSealed => _type.IsSealed; - - /// - public bool IsSerializable => _type.IsSerializable; - - /// - public bool IsValueType => _type.IsValueType; - - /// - public bool IsVisible => _type.IsVisible; - - /// - public bool IsSignatureType => throw new NotImplementedException(); - - /// - public bool IsSpecialName => _type.IsSpecialName; - - /// - public IConstructorSymbol? TypeInitializer => _type.TypeInitializer is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; - - /// - public int GetArrayRank() - { - return _type.GetArrayRank(); - } - - /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return _type.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; - } - - /// - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return _type.GetConstructor(types.Unpack()) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; - } - - /// - public IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(_type.GetConstructors()); - } - - /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(_type.GetConstructors((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetDefaultMembers() - { - return ResolveMemberSymbols(_type.GetDefaultMembers()); - } - - /// - public ITypeSymbol? GetElementType() - { - return _type.GetElementType() is Type t ? ResolveTypeSymbol(t) : null; - } - - /// - public string? GetEnumName(object value) - { - return _type.GetEnumName(value); - } - - /// - public string[] GetEnumNames() - { - return _type.GetEnumNames(); - } - - /// - public ITypeSymbol GetEnumUnderlyingType() - { - return ResolveTypeSymbol(_type.GetEnumUnderlyingType()); - } - - /// - public Array GetEnumValues() - { - return _type.GetEnumValues(); - } - - /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) - { - throw new NotImplementedException(); - } - - /// - public IEventSymbol? GetEvent(string name) - { - return _type.GetEvent(name) is { } f ? ResolveEventSymbol(f) : null; - } - - /// - public IEventSymbol[] GetEvents() - { - return ResolveEventSymbols(_type.GetEvents()); - } - - /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) - { - return ResolveEventSymbols(_type.GetEvents((BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol? GetField(string name) - { - return _type.GetField(name) is FieldInfo f ? ResolveFieldSymbol(f) : null; - } - - /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) - { - return _type.GetField(name, (BindingFlags)bindingAttr) is FieldInfo f ? ResolveFieldSymbol(f) : null; - } - - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(_type.GetFields()); - } - - /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbols(_type.GetFields((BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(_type.GetGenericArguments()); - } - - /// - public ITypeSymbol[] GetGenericParameterConstraints() - { - return ResolveTypeSymbols(_type.GetGenericParameterConstraints()); - } - - /// - public ITypeSymbol GetGenericTypeDefinition() - { - return ResolveTypeSymbol(_type.GetGenericTypeDefinition()); - } - - /// - public ITypeSymbol? GetInterface(string name) - { - return _type.GetInterface(name) is { } i ? ResolveTypeSymbol(i) : null; - } - - /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return _type.GetInterface(name, ignoreCase) is { } i ? ResolveTypeSymbol(i) : null; - } - - /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return ResolveTypeSymbols(_type.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public IMemberSymbol[] GetMember(string name) - { - return ResolveMemberSymbols(_type.GetMember(name)); - } - - /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(_type.GetMember(name, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(_type.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(_type.GetMembers((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers() - { - return ResolveMemberSymbols(_type.GetMembers()); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) - { - return _type.GetMethod(name, (BindingFlags)bindingAttr) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return _type.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return _type.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return _type.GetMethod(name) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return _type.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return _type.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMethodSymbols(_type.GetMethods((BindingFlags)bindingAttr)); - } - - /// - public IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(_type.GetMethods()); - } - - /// - public ITypeSymbol? GetNestedType(string name) - { - return _type.GetNestedType(name) is Type t ? ResolveTypeSymbol(t) : null; - } - - /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) - { - return _type.GetNestedType(name, (BindingFlags)bindingAttr) is Type t ? ResolveTypeSymbol(t) : null; - } - - /// - public ITypeSymbol[] GetNestedTypes() - { - return ResolveTypeSymbols(_type.GetNestedTypes()); - } - - /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbols(_type.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol[] GetProperties() - { - return ResolvePropertySymbols(_type.GetProperties()); - } - - /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbols(_type.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return _type.GetProperty(name, types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return _type.GetProperty(name, returnType?.Unpack(), types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; - } - - /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) - { - return _type.GetProperty(name, (BindingFlags)bindingAttr) is { } p ? ResolvePropertySymbol(p) : null; - } - - /// - public IPropertySymbol? GetProperty(string name) - { - return _type.GetProperty(name) is { } p ? ResolvePropertySymbol(p) : null; - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return _type.GetProperty(name, returnType?.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; - } - - /// - public bool IsAssignableFrom(ITypeSymbol? c) - { - return _type.IsAssignableFrom(c?.Unpack()); - } - - /// - public bool IsEnumDefined(object value) - { - return _type.IsEnumDefined(value); - } - - /// - public bool IsSubclassOf(ITypeSymbol c) - { - return _type.IsSubclassOf(c.Unpack()); - } - - /// - public ITypeSymbol MakeArrayType() - { - if (_asSZArray == null) - Interlocked.CompareExchange(ref _asSZArray, new IkvmReflectionTypeSymbol(Context, ContainingModule, _type.MakeArrayType()), null); - - return _asSZArray; - } - - /// - public ITypeSymbol MakeArrayType(int rank) - { - if (rank == 1) - return MakeArrayType(); - - if (_asArray == null) - Interlocked.CompareExchange(ref _asArray, new IkvmReflectionTypeSymbol?[32], null); - - ref var asArray = ref _asArray[rank]; - if (asArray == null) - Interlocked.CompareExchange(ref asArray, new IkvmReflectionTypeSymbol(Context, ContainingModule, _type.MakeArrayType(rank)), null); - - return asArray; - } - - /// - public ITypeSymbol MakeByRefType() - { - if (_asByRef == null) - Interlocked.CompareExchange(ref _asByRef, new IkvmReflectionTypeSymbol(Context, ContainingModule, _type.MakeByRefType()), null); - - return _asByRef; - } - - /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol MakePointerType() - { - if (_asPointer == null) - Interlocked.CompareExchange(ref _asPointer, new IkvmReflectionTypeSymbol(Context, ContainingModule, _type.MakePointerType()), null); - - return _asPointer; - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(Type type) - { - ResolveTypeSymbol(_type = type); - base.Complete(_type); - - ContainingModule.Complete(_type.Module); - - foreach (var i in _type.GetConstructors(DefaultBindingFlags)) - ResolveConstructorSymbol(i).Complete(i); - - foreach (var i in _type.GetMethods(DefaultBindingFlags)) - ResolveMethodSymbol(i).Complete(i); - - foreach (var i in _type.GetFields(DefaultBindingFlags)) - ResolveFieldSymbol(i).Complete(i); - - foreach (var i in _type.GetProperties(DefaultBindingFlags)) - ResolvePropertySymbol(i).Complete(i); - - foreach (var i in _type.GetEvents(DefaultBindingFlags)) - ResolveEventSymbol(i).Complete(i); - } - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs deleted file mode 100644 index d00e0ff60c..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs +++ /dev/null @@ -1,195 +0,0 @@ -using System; - -using IKVM.Reflection; - -using ConstructorInfo = IKVM.Reflection.ConstructorInfo; -using MethodInfo = IKVM.Reflection.MethodInfo; -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - static class IkvmReflectionUtil - { - - /// - /// Converts the to a . - /// - /// - /// - public static System.Reflection.AssemblyName ToAssemblyName(this AssemblyName src) - { -#pragma warning disable SYSLIB0037 // Type or member is obsolete - return new System.Reflection.AssemblyName() - { - Name = src.Name, - Version = src.Version, - CultureName = src.CultureName, - HashAlgorithm = (System.Configuration.Assemblies.AssemblyHashAlgorithm)src.HashAlgorithm, - Flags = (System.Reflection.AssemblyNameFlags)src.Flags, - ContentType = (System.Reflection.AssemblyContentType)src.ContentType, - }; -#pragma warning restore SYSLIB0037 // Type or member is obsolete - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static Module Unpack(this IModuleSymbol module) - { - return ((IkvmReflectionModuleSymbol)module).ReflectionObject; - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static Module[] Unpack(this IModuleSymbol[] modules) - { - var a = new Module[modules.Length]; - for (int i = 0; i < modules.Length; i++) - a[i] = modules[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static Type Unpack(this ITypeSymbol type) - { - return ((IkvmReflectionTypeSymbol)type).ReflectionObject; - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static Type[] Unpack(this ITypeSymbol[] types) - { - var a = new Type[types.Length]; - for (int i = 0; i < types.Length; i++) - a[i] = types[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static Type[][] Unpack(this ITypeSymbol[][] types) - { - var a = new Type[types.Length][]; - for (int i = 0; i < types.Length; i++) - a[i] = types[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static MemberInfo Unpack(this IMemberSymbol member) - { - return ((IkvmReflectionMemberSymbol)member).ReflectionObject; - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static MemberInfo[] Unpack(this IMemberSymbol[] members) - { - var a = new MemberInfo[members.Length]; - for (int i = 0; i < members.Length; i++) - a[i] = members[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static ConstructorInfo Unpack(this IConstructorSymbol ctor) - { - return ((IkvmReflectionConstructorSymbol)ctor).ReflectionObject; - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static ConstructorInfo[] Unpack(this IConstructorSymbol[] ctor) - { - var a = new ConstructorInfo[ctor.Length]; - for (int i = 0; i < ctor.Length; i++) - a[i] = ctor[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static MethodInfo Unpack(this IMethodSymbol ctor) - { - return ((IkvmReflectionMethodSymbol)ctor).ReflectionObject; - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static MethodInfo[] Unpack(this IMethodSymbol[] ctor) - { - var a = new MethodInfo[ctor.Length]; - for (int i = 0; i < ctor.Length; i++) - a[i] = ctor[i].Unpack(); - - return a; - } - - /// - /// Unpacks the modifier into their original type. - /// - /// - /// - public static ParameterModifier Unpack(this System.Reflection.ParameterModifier modifier) - { - throw new NotImplementedException(); - } - - /// - /// Unpacks the modifiers into their original types. - /// - /// - /// - public static ParameterModifier[] Unpack(this System.Reflection.ParameterModifier[] ctor) - { - var a = new ParameterModifier[ctor.Length]; - for (int i = 0; i < ctor.Length; i++) - a[i] = ctor[i].Unpack(); - - return a; - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs new file mode 100644 index 0000000000..6652e1af14 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs @@ -0,0 +1,18 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionAssemblySymbolBuilder : IReflectionSymbolBuilder, IAssemblySymbolBuilder, IReflectionAssemblySymbol + { + + /// + /// Gets the underlying . + /// + AssemblyBuilder UnderlyingAssemblyBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs new file mode 100644 index 0000000000..0572b3bdfb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs @@ -0,0 +1,15 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionConstructorSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder, IReflectionConstructorSymbol + { + + ConstructorBuilder UnderlyingConstructorBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs new file mode 100644 index 0000000000..f9c48d0bec --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs @@ -0,0 +1,15 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionEventSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IEventSymbolBuilder, IReflectionEventSymbol + { + + EventBuilder UnderlyingEventBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs new file mode 100644 index 0000000000..ecd263c1bd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs @@ -0,0 +1,15 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionFieldSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IFieldSymbolBuilder, IReflectionFieldSymbol + { + + FieldBuilder UnderlyingFieldBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs new file mode 100644 index 0000000000..20917942a9 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs @@ -0,0 +1,24 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface IReflectionGenericTypeParameterSymbolBuilder : IReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IReflectionTypeSymbol + { + + /// + /// Gets the underlying . + /// + GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder { get; } + + /// + /// Invoked when the type containing this generic type parameter is completed. + /// + void OnComplete(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs new file mode 100644 index 0000000000..4eb323b30b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs @@ -0,0 +1,17 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionMemberSymbolBuilder : IReflectionSymbolBuilder, IMemberSymbolBuilder, IReflectionMemberSymbol + { + + /// + /// Invoked when the type responsible for this builder is completed. Implementations should update their + /// underlying type, and optionally dispatch the OnComplete invocation to downstream elements. + /// + void OnComplete(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs new file mode 100644 index 0000000000..0d757111d6 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs @@ -0,0 +1,13 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionMethodBaseSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IReflectionMethodBaseSymbol + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs new file mode 100644 index 0000000000..cc19efa3d2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs @@ -0,0 +1,18 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionMethodSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder, IReflectionMethodSymbol + { + + /// + /// Gets the underlying . + /// + MethodBuilder UnderlyingMethodBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs new file mode 100644 index 0000000000..9fbd1c7c1c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs @@ -0,0 +1,18 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionModuleSymbolBuilder : IReflectionSymbolBuilder, IModuleSymbolBuilder, IReflectionModuleSymbol + { + + /// + /// Gets the underlying . + /// + ModuleBuilder UnderlyingModuleBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs new file mode 100644 index 0000000000..679ac84294 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs @@ -0,0 +1,23 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionParameterSymbolBuilder : IReflectionSymbolBuilder, IParameterSymbolBuilder, IReflectionParameterSymbol + { + + /// + /// Gets the underlying . + /// + ParameterBuilder UnderlyingParameterBuilder { get; } + + /// + /// Invoked when the owning method of this parameter is completed. + /// + void OnComplete(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs new file mode 100644 index 0000000000..1a10c8c6cd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs @@ -0,0 +1,15 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionPropertySymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IPropertySymbolBuilder, IReflectionPropertySymbol + { + + PropertyBuilder UnderlyingPropertyBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs new file mode 100644 index 0000000000..45123999fd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs @@ -0,0 +1,19 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionSymbolBuilder : ISymbolBuilder + { + + } + + interface IReflectionSymbolBuilder : IReflectionSymbolBuilder, ISymbolBuilder + where TSymbol : IReflectionSymbol + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs new file mode 100644 index 0000000000..ee86b9734b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs @@ -0,0 +1,18 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionTypeSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, ITypeSymbolBuilder, IReflectionTypeSymbol + { + + /// + /// Gets the underlying . + /// + TypeBuilder UnderlyingTypeBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index ee05a37cea..2d3e9e071b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -1,4 +1,7 @@ using System; +using System.Collections.Generic; +using System.Linq; +using System.Reflection; using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -6,11 +9,11 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionAssemblySymbolBuilder : ReflectionSymbolBuilder, IAssemblySymbolBuilder + class ReflectionAssemblySymbolBuilder : ReflectionSymbolBuilder, IReflectionAssemblySymbolBuilder { readonly AssemblyBuilder _builder; - ReflectionAssemblySymbol? _symbol; + ReflectionAssemblyMetadata _metadata; /// /// Initializes a new instance. @@ -21,24 +24,30 @@ public ReflectionAssemblySymbolBuilder(ReflectionSymbolContext context, Assembly base(context) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _metadata = new ReflectionAssemblyMetadata(this); } /// - internal sealed override ReflectionAssemblySymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateAssemblySymbol(_builder); + public Assembly UnderlyingAssembly => UnderlyingAssemblyBuilder; + + /// + public AssemblyBuilder UnderlyingAssemblyBuilder => _builder; + + #region IAssemblySymbolBuilder /// public IModuleSymbolBuilder DefineModule(string name) { - return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name)); + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name)); } /// public IModuleSymbolBuilder DefineModule(string name, string fileName) { #if NETFRAMEWORK - return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName)); + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName)); #else - return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name)); + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name)); #endif } @@ -46,9 +55,9 @@ public IModuleSymbolBuilder DefineModule(string name, string fileName) public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo) { #if NETFRAMEWORK - return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name, fileName, emitSymbolInfo)); + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName, emitSymbolInfo)); #else - return new ReflectionModuleSymbolBuilder(Context, _builder.DefineDynamicModule(name)); + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name)); #endif } @@ -61,25 +70,140 @@ public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } + #endregion + + #region IAssemblySymbol + + /// + public IEnumerable DefinedTypes => ResolveTypeSymbols(UnderlyingAssembly.DefinedTypes); + + /// + public IMethodSymbol? EntryPoint => ResolveMethodSymbol(UnderlyingAssembly.EntryPoint); + + /// + public IEnumerable ExportedTypes => ResolveTypeSymbols(UnderlyingAssembly.ExportedTypes); + /// - public void Complete() + public string? FullName => UnderlyingAssembly.FullName; + + /// + public string ImageRuntimeVersion => UnderlyingAssembly.ImageRuntimeVersion; + + /// + public IModuleSymbol ManifestModule => ResolveModuleSymbol(UnderlyingAssembly.ManifestModule); + + /// + public IEnumerable Modules => ResolveModuleSymbols(UnderlyingAssembly.Modules); + + /// + public override bool IsComplete => _builder == null; + + /// + public ITypeSymbol[] GetExportedTypes() { - foreach (var module in _builder.GetModules()) - { - if (module is ModuleBuilder moduleBuilder) - { - moduleBuilder.CreateGlobalFunctions(); + return ResolveTypeSymbols(UnderlyingAssembly.GetExportedTypes()); + } - foreach (var type in moduleBuilder.GetTypes()) - if (type is TypeBuilder typeBuilder) - if (typeBuilder.IsCreated() == false) - if (typeBuilder.CreateType() is { } t) - ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); - } - } + /// + public IModuleSymbol? GetModule(string name) + { + return ResolveModuleSymbol(UnderlyingAssembly.GetModule(name)); + } + + /// + public IModuleSymbol[] GetModules() + { + return ResolveModuleSymbols(UnderlyingAssembly.GetModules()); + } + + /// + public IModuleSymbol[] GetModules(bool getResourceModules) + { + return ResolveModuleSymbols(UnderlyingAssembly.GetModules(getResourceModules)); + } + + /// + public AssemblyName GetName() + { + return UnderlyingAssembly.GetName(); + } + + /// + public AssemblyName GetName(bool copiedName) + { + return UnderlyingAssembly.GetName(copiedName); + } + + /// + public AssemblyName[] GetReferencedAssemblies() + { + return UnderlyingAssembly.GetReferencedAssemblies(); + } + + /// + public ITypeSymbol? GetType(string name, bool throwOnError) + { + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError)); + } + + /// + public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError, ignoreCase)); + } + + /// + public ITypeSymbol? GetType(string name) + { + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name)); + } + + /// + public ITypeSymbol[] GetTypes() + { + return ResolveTypeSymbols(UnderlyingAssembly.GetTypes()); + } + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData()); + } + + /// + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); + } + + /// + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + + /// + public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _metadata.GetOrCreateModuleSymbol(module); + } + + /// + public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return (IReflectionModuleSymbolBuilder)_metadata.GetOrCreateModuleSymbol(module); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index 80c895b09d..2dbde97d2e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -7,42 +7,48 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder + class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflectionConstructorSymbolBuilder { - readonly ConstructorBuilder _builder; - ReflectionConstructorSymbol? _symbol; + ConstructorBuilder? _builder; + ConstructorInfo _ctor; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, ConstructorBuilder builder) : - base(context, containingTypeBuilder) + /// + public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, ConstructorBuilder builder) : + base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _ctor = _builder; } - /// - /// Gets the containing . - /// - protected internal new ReflectionTypeSymbolBuilder ContainingTypeBuilder => base.ContainingTypeBuilder ?? throw new NullReferenceException(); + /// + public ConstructorInfo UnderlyingConstructor => _ctor; + + /// + public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; /// - internal override ReflectionConstructorSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateConstructorSymbol(_builder); + public ConstructorBuilder UnderlyingConstructorBuilder => _builder ?? throw new InvalidOperationException(); + + #region IConstructorSymbolBuilder /// public void SetImplementationFlags(MethodImplAttributes attributes) { - _builder.SetImplementationFlags(attributes); + UnderlyingConstructorBuilder.SetImplementationFlags(attributes); } /// public IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) { - return new ReflectionParameterSymbolBuilder(Context, this, _builder.DefineParameter(iSequence, attributes, strParamName)); + return new ReflectionParameterSymbolBuilder(Context, ResolvingModule, this, UnderlyingConstructorBuilder.DefineParameter(iSequence, attributes, strParamName)); } /// @@ -60,13 +66,30 @@ public IILGenerator GetILGenerator(int streamSize) /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + UnderlyingConstructorBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingConstructorBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + #endregion + + #region IConstructorSymbol + + /// + public override bool IsComplete => _builder == null; + + #endregion + + /// + public override void OnComplete() + { + _ctor = (ConstructorInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs index bb1978ec30..eed10e2cb1 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs @@ -22,7 +22,7 @@ public ReflectionCustomAttributeBuilder(CustomAttributeBuilder builder) /// /// Gets the underlying reflection . /// - internal CustomAttributeBuilder ReflectionBuilder => _builder; + internal CustomAttributeBuilder UnderlyingBuilder => _builder; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs index 771ff97570..7a87c506d2 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs @@ -1,6 +1,7 @@ using System; using System.Reflection; using System.Reflection.Emit; +using IKVM.CoreLib.Reflection; namespace IKVM.CoreLib.Symbols.Reflection.Emit { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs index fbc7ea865b..d583458d9e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs @@ -1,4 +1,5 @@ using System; +using System.Reflection; using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -6,65 +7,155 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionEventSymbolBuilder : ReflectionSymbolBuilder, IEventSymbolBuilder + class ReflectionEventSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionEventSymbolBuilder { - readonly ReflectionTypeSymbolBuilder _containingTypeBuilder; - readonly EventBuilder _builder; - readonly ReflectionEventBuilderInfo _info; - ReflectionEventSymbol? _symbol; + EventBuilder? _builder; + EventInfo _event; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionEventSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, EventBuilder builder) : - base(context) + /// + public ReflectionEventSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, EventBuilder builder) : + base(context, resolvingModule, resolvingType) { - _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _info = new ReflectionEventBuilderInfo(_builder); + _event = new ReflectionEventBuilderInfo(_builder); } /// - internal override ReflectionEventSymbol ReflectionSymbol => _symbol ??= _containingTypeBuilder.ReflectionSymbol.ResolveEventSymbol(_info); + public EventInfo UnderlyingEvent => _event; + + /// + public EventBuilder UnderlyingEventBuilder => _builder ?? throw new NotImplementedException(); + + /// + public override MemberInfo UnderlyingMember => UnderlyingEvent; + + #region IEventSymbolBuilder /// public void SetAddOnMethod(IMethodSymbolBuilder mdBuilder) { - _builder.SetAddOnMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + UnderlyingEventBuilder.SetAddOnMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } /// public void SetRemoveOnMethod(IMethodSymbolBuilder mdBuilder) { - _builder.SetRemoveOnMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + UnderlyingEventBuilder.SetRemoveOnMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } /// public void SetRaiseMethod(IMethodSymbolBuilder mdBuilder) { - _builder.SetRaiseMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + UnderlyingEventBuilder.SetRaiseMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } /// public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) { - _builder.AddOtherMethod(((ReflectionMethodSymbolBuilder)mdBuilder).ReflectionBuilder); + UnderlyingEventBuilder.AddOtherMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingEventBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + UnderlyingEventBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IEventSymbol + + /// + public EventAttributes Attributes => UnderlyingEvent.Attributes; + + /// + public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); + + /// + public bool IsSpecialName => UnderlyingEvent.IsSpecialName; + + /// + public IMethodSymbol? AddMethod => ResolveMethodSymbol(UnderlyingEvent.AddMethod); + + /// + public IMethodSymbol? RemoveMethod => ResolveMethodSymbol(UnderlyingEvent.RemoveMethod); + + /// + public IMethodSymbol? RaiseMethod => ResolveMethodSymbol(UnderlyingEvent.RaiseMethod); + + /// + public override bool IsComplete => _builder == null; + + /// + public IMethodSymbol? GetAddMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod()); + } + + /// + public IMethodSymbol? GetAddMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetRemoveMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod()); + } + + /// + public IMethodSymbol? GetRemoveMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetRaiseMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod()); + } + + /// + public IMethodSymbol? GetRaiseMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod(nonPublic)); + } + + /// + public IMethodSymbol[] GetOtherMethods() + { + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods()); + } + + /// + public IMethodSymbol[] GetOtherMethods(bool nonPublic) + { + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods(nonPublic)); + } + + #endregion + + /// + public override void OnComplete() + { + _event = (EventInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs index 241fbf8ed8..5aa337c85f 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs @@ -1,4 +1,5 @@ using System; +using System.Reflection; using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -6,81 +7,139 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionFieldSymbolBuilder : ReflectionSymbolBuilder, IFieldSymbolBuilder + class ReflectionFieldSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionFieldSymbolBuilder { - readonly ReflectionModuleSymbolBuilder _containingModuleBuilder; - readonly ReflectionTypeSymbolBuilder? _containingTypeBuilder; - readonly FieldBuilder _builder; - ReflectionFieldSymbol? _symbol; + FieldBuilder? _builder; + FieldInfo _field; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder, FieldBuilder builder) : - base(context) + /// + public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, FieldBuilder builder) : + base(context, resolvingModule, resolvingType) { - _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _field = _builder; } - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, FieldBuilder builder) : - base(context) - { - _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); - _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Gets the containing . - /// - internal ReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; - - /// - /// Gets the containing . - /// - internal ReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; + /// + public FieldInfo UnderlyingField => _field; - /// - /// Gets the underlying - /// - internal FieldBuilder ReflectionBuilder => _builder; + /// + public override MemberInfo UnderlyingMember => UnderlyingField; /// - internal override ReflectionFieldSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateFieldSymbol(_builder); + public FieldBuilder UnderlyingFieldBuilder => _builder ?? throw new InvalidOperationException(); + + #region IFieldSymbolBuilder /// public void SetConstant(object? defaultValue) { - _builder.SetConstant(defaultValue); + UnderlyingFieldBuilder.SetConstant(defaultValue); } /// public void SetOffset(int iOffset) { - _builder.SetOffset(iOffset); + UnderlyingFieldBuilder.SetOffset(iOffset); } /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingFieldBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + UnderlyingFieldBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IFieldSymbol + + /// + public FieldAttributes Attributes => UnderlyingField.Attributes; + + /// + public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); + + /// + public bool IsSpecialName => UnderlyingField.IsSpecialName; + + /// + public bool IsAssembly => UnderlyingField.IsAssembly; + + /// + public bool IsFamily => UnderlyingField.IsFamily; + + /// + public bool IsFamilyAndAssembly => UnderlyingField.IsFamilyAndAssembly; + + /// + public bool IsFamilyOrAssembly => UnderlyingField.IsFamilyOrAssembly; + + /// + public bool IsInitOnly => UnderlyingField.IsInitOnly; + + /// + public bool IsLiteral => UnderlyingField.IsLiteral; + +#pragma warning disable SYSLIB0050 // Type or member is obsolete + /// + public bool IsNotSerialized => UnderlyingField.IsNotSerialized; +#pragma warning restore SYSLIB0050 // Type or member is obsolete + + /// + public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; + + /// + public bool IsPrivate => UnderlyingField.IsPrivate; + + /// + public bool IsPublic => UnderlyingField.IsPublic; + + /// + public bool IsStatic => UnderlyingField.IsStatic; + + /// + public override bool IsComplete => _builder == null; + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); + } + + /// + public object? GetRawConstantValue() + { + return UnderlyingField.GetRawConstantValue(); + } + + #endregion + + /// + public override void OnComplete() + { + _field = ResolvingModule.UnderlyingModule.ResolveField(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs new file mode 100644 index 0000000000..2ea5707553 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs @@ -0,0 +1,583 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionGenericTypeParameterSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionGenericTypeParameterSymbolBuilder + { + + readonly IReflectionMethodSymbol? _resolvingMethod; + + GenericTypeParameterBuilder? _builder; + Type _type; + ReflectionTypeImpl _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, IReflectionMethodSymbol? resolvingMethod, GenericTypeParameterBuilder builder) : + base(context, resolvingModule, resolvingType) + { + _resolvingMethod = resolvingMethod; + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _type = _builder; + _impl = new ReflectionTypeImpl(this); + } + + /// + public Type UnderlyingType => _type; + + /// + public override MemberInfo UnderlyingMember => UnderlyingType; + + /// + public GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder => _builder ?? throw new InvalidOperationException(); + + #region ITypeSymbolBuilder + + /// + public void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint) + { + UnderlyingGenericTypeParameterBuilder.SetBaseTypeConstraint(baseTypeConstraint?.Unpack()); + } + + /// + public void SetGenericParameterAttributes(GenericParameterAttributes genericParameterAttributes) + { + UnderlyingGenericTypeParameterBuilder.SetGenericParameterAttributes(genericParameterAttributes); + } + + /// + public void SetInterfaceConstraints(params ITypeSymbol[]? interfaceConstraints) + { + UnderlyingGenericTypeParameterBuilder.SetInterfaceConstraints(interfaceConstraints?.Unpack()); + } + + #endregion + + #region ITypeSymbol + + /// + public TypeAttributes Attributes => _impl.Attributes; + + /// + public IAssemblySymbol Assembly => _impl.Assembly; + + /// + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + + /// + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + + /// + public string? FullName => _impl.FullName; + + /// + public string? Namespace => _impl.Namespace; + + /// + public TypeCode TypeCode => _impl.TypeCode; + + /// + public ITypeSymbol? BaseType => _impl.BaseType; + + /// + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + + /// + public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + + /// + public int GenericParameterPosition => _impl.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + + /// + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + + /// + public bool IsGenericType => _impl.IsGenericType; + + /// + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + + /// + public bool IsGenericParameter => _impl.IsGenericParameter; + + /// + public bool IsAutoLayout => _impl.IsAutoLayout; + + /// + public bool IsExplicitLayout => _impl.IsExplicitLayout; + + /// + public bool IsLayoutSequential => _impl.IsLayoutSequential; + + /// + public bool HasElementType => _impl.HasElementType; + + /// + public bool IsClass => _impl.IsClass; + + /// + public bool IsValueType => _impl.IsValueType; + + /// + public bool IsInterface => _impl.IsInterface; + + /// + public bool IsPrimitive => _impl.IsPrimitive; + + /// + public bool IsSZArray => _impl.IsSZArray; + + /// + public bool IsArray => _impl.IsArray; + + /// + public bool IsEnum => _impl.IsEnum; + + /// + public bool IsPointer => _impl.IsPointer; + + /// + public bool IsFunctionPointer => _impl.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + + /// + public bool IsByRef => _impl.IsByRef; + + /// + public bool IsAbstract => _impl.IsAbstract; + + /// + public bool IsSealed => _impl.IsSealed; + + /// + public bool IsVisible => _impl.IsVisible; + + /// + public bool IsPublic => _impl.IsPublic; + + /// + public bool IsNotPublic => _impl.IsNotPublic; + + /// + public bool IsNested => _impl.IsNested; + + /// + public bool IsNestedAssembly => _impl.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + + /// + public bool IsNestedFamily => _impl.IsNestedFamily; + + /// + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + + /// + public bool IsNestedPrivate => _impl.IsNestedPrivate; + + /// + public bool IsNestedPublic => _impl.IsNestedPublic; + + /// + public bool IsSerializable => _impl.IsSerializable; + + /// + public bool IsSignatureType => _impl.IsSignatureType; + + /// + public bool IsSpecialName => _impl.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + + /// + public override bool IsComplete => _builder == null; + + /// + public int GetArrayRank() + { + return _impl.GetArrayRank(); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return _impl.GetDefaultMembers(); + } + + /// + public ITypeSymbol? GetElementType() + { + return _impl.GetElementType(); + } + + /// + public string? GetEnumName(object value) + { + return _impl.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return _impl.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return _impl.GetEnumUnderlyingType(); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return _impl.GetGenericArguments(); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return _impl.GetGenericParameterConstraints(); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return _impl.GetGenericTypeDefinition(); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return _impl.GetInterface(name); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _impl.GetInterface(name, ignoreCase); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + return _impl.GetInterfaces(inherit); + } + + /// + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return _impl.GetInterfaceMap(interfaceType); + } + + /// + public IMemberSymbol[] GetMember(string name) + { + return _impl.GetMember(name); + } + + /// + public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + { + return _impl.GetMember(name, bindingAttr); + } + + /// + public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + { + return _impl.GetMember(name, type, bindingAttr); + } + + /// + public IMemberSymbol[] GetMembers() + { + return _impl.GetMembers(); + } + + /// + public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + { + return _impl.GetMembers(bindingAttr); + } + + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _impl.GetConstructor(types); + } + + /// + public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetConstructor(bindingAttr, types); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return _impl.GetConstructors(); + } + + /// + public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + { + return _impl.GetConstructors(bindingAttr); + } + + /// + public IFieldSymbol? GetField(string name) + { + return _impl.GetField(name); + } + + /// + public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + return _impl.GetField(name, bindingAttr); + } + + /// + public IFieldSymbol[] GetFields() + { + return _impl.GetFields(); + } + + /// + public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + { + return _impl.GetFields(bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return _impl.GetMethod(name); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _impl.GetMethod(name, types); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + { + return _impl.GetMethod(name, bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetMethod(name, bindingAttr, types); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); + } + + /// + public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + { + return _impl.GetMethods(bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return _impl.GetProperty(name); + } + + /// + public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + { + return _impl.GetProperty(name, bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _impl.GetProperty(name, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _impl.GetProperty(name, returnType, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _impl.GetProperty(name, returnType); + } + + /// + public IPropertySymbol[] GetProperties() + { + return _impl.GetProperties(); + } + + /// + public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + { + return _impl.GetProperties(bindingAttr); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return _impl.GetEvent(name); + } + + /// + public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + { + return _impl.GetEvent(name, bindingAttr); + } + + /// + public IEventSymbol[] GetEvents() + { + return _impl.GetEvents(); + } + + /// + public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + { + return _impl.GetEvents(bindingAttr); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return _impl.GetNestedType(name); + } + + /// + public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + { + return _impl.GetNestedType(name, bindingAttr); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return _impl.GetNestedTypes(); + } + + /// + public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + { + return _impl.GetNestedTypes(); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return _impl.IsAssignableFrom(c); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return _impl.IsSubclassOf(c); + } + + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); + } + + /// + public ITypeSymbol MakeArrayType() + { + return _impl.MakeArrayType(); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return _impl.MakeGenericType(typeArguments); + } + + /// + public ITypeSymbol MakePointerType() + { + return _impl.MakePointerType(); + } + + /// + public ITypeSymbol MakeByRefType() + { + return _impl.MakeByRefType(); + } + + #endregion + + /// + public override void OnComplete() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs new file mode 100644 index 0000000000..8727613762 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs @@ -0,0 +1,392 @@ +using System; +using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; +using System.Linq; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + abstract class ReflectionMemberSymbolBuilder : ReflectionSymbolBuilder, IReflectionMemberSymbolBuilder + { + + /// + /// Concatinates the list of arrays. + /// + /// + /// + static T[] Concat(List? list) + { + if (list == null) + return []; + + var c = 0; + foreach (var i in list) + c += i.Length; + + if (c == 0) + return []; + + var t = 0; + var a = new T[c]; + foreach (var i in list) + { + Array.Copy(i, 0, a, t, i.Length); + t += i.Length; + } + + return a; + } + + readonly IReflectionModuleSymbol _resolvingModule; + readonly IReflectionTypeSymbol? _resolvingType; + + CustomAttribute[]? _customAttributes; + CustomAttribute[]? _inheritedCustomAttributes; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionMemberSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : + base(context) + { + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingType = resolvingType; + } + + #region IMemberSymbol + + /// + public abstract MemberInfo UnderlyingMember { get; } + + /// + public IReflectionModuleSymbol ResolvingModule => _resolvingModule; + + /// + public IReflectionTypeSymbol? ResolvingType => ResolvingType; + + /// + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + + /// + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + + /// + public virtual MemberTypes MemberType => UnderlyingMember.MemberType; + + /// + public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); + + /// + public virtual string Name => UnderlyingMember.Name; + + /// + public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + if (inherit) + { + // check that we've already processed this + if (_inheritedCustomAttributes != null) + return _inheritedCustomAttributes; + + var self = UnderlyingMember; + var list = default(List?); + for (; ; ) + { + if (self == null) + throw new InvalidOperationException(); + + // get attribute for current member and append to list + var attr = ResolveMemberSymbol(self)!.GetCustomAttributes(false); + if (attr.Length > 0) + { + list ??= []; + list.Add(attr); + } + + var type = self as Type; + if (type != null) + { + type = type.BaseType; + if (type == null) + return _inheritedCustomAttributes ??= Concat(list); + + self = type; + continue; + } + + var method = self as MethodInfo; + if (method != null) + { + var prev = self; + method = method.GetBaseDefinition(); + if (method == null || method == prev) + return _inheritedCustomAttributes ??= Concat(list); + + self = method; + continue; + } + + return _inheritedCustomAttributes ??= Concat(list); + } + } + + return _customAttributes ??= ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData())!; + } + + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + } + + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + } + + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + + /// + [return: NotNullIfNotNull(nameof(type))] + public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + if (type is null) + return null; + + if (UnderlyingMember == type) + return (IReflectionTypeSymbol)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return _resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull("type")] + public override IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + + if (UnderlyingMember == type) + return (IReflectionTypeSymbolBuilder)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return (IReflectionTypeSymbolBuilder)_resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) + { + if (ctor is null) + return null; + + if (UnderlyingMember == ctor) + return (IReflectionConstructorSymbol)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) + { + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + + if (UnderlyingMember == ctor) + return (IReflectionConstructorSymbolBuilder)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) + { + if (method is null) + return null; + + if (UnderlyingMember == method) + return (IReflectionMethodSymbol)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + if (UnderlyingMember == method) + return (IReflectionMethodSymbolBuilder)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) + { + if (field is null) + return null; + + if (UnderlyingMember == field) + return (IReflectionFieldSymbol)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + + if (UnderlyingMember == field) + return (IReflectionFieldSymbolBuilder)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) + { + if (property is null) + return null; + + if (UnderlyingMember == property) + return (IReflectionPropertySymbol)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (UnderlyingMember == property) + return (IReflectionPropertySymbolBuilder)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) + { + if (@event is null) + return null; + + if (UnderlyingMember == @event) + return (IReflectionEventSymbol)this; + + if (@event.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + if (@event.GetModuleBuilder() == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.Member.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.GetModuleBuilder() == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); + } + + /// + public virtual void OnComplete() + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs index f260f68197..b662e1a597 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs @@ -1,48 +1,123 @@ -using System; +using System.Reflection; + +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { - abstract class ReflectionMethodBaseSymbolBuilder : ReflectionSymbolBuilder - where TSymbol : ISymbol - where TReflectionSymbol : ReflectionSymbol, TSymbol + abstract class ReflectionMethodBaseSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionMethodBaseSymbolBuilder { - readonly ReflectionModuleSymbolBuilder _containingModuleBuilder; - readonly ReflectionTypeSymbolBuilder? _containingTypeBuilder; - /// /// Initializes a new instance. /// /// - /// - protected ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder) : - base(context) + /// + /// + public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : + base(context, resolvingModule, resolvingType) { - _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); - _containingModuleBuilder = containingTypeBuilder.ContainingModuleBuilder; + } - /// - /// Initializes a new instance. - /// - /// - /// - protected ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder) : - base(context) + /// + public abstract MethodBase UnderlyingMethodBase { get; } + + /// + public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + + #region IMethodBaseSymbol + + /// + public MethodAttributes Attributes => UnderlyingMethodBase.Attributes; + + /// + public CallingConventions CallingConvention => UnderlyingMethodBase.CallingConvention; + + /// + public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; + + /// + public bool IsAbstract => UnderlyingMethodBase.IsAbstract; + + /// + public bool IsAssembly => UnderlyingMethodBase.IsAssembly; + + /// + public bool IsConstructor => UnderlyingMethodBase.IsConstructor; + + /// + public bool IsFamily => UnderlyingMethodBase.IsFamily; + + /// + public bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; + + /// + public bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; + + /// + public bool IsFinal => UnderlyingMethodBase.IsFinal; + + /// + public bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; + + /// + public bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; + + /// + public bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; + + /// + public bool IsPrivate => UnderlyingMethodBase.IsPrivate; + + /// + public bool IsPublic => UnderlyingMethodBase.IsPublic; + + /// + public bool IsStatic => UnderlyingMethodBase.IsStatic; + + /// + public bool IsVirtual => UnderlyingMethodBase.IsVirtual; + + /// + public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; + + /// + public MethodImplAttributes MethodImplementationFlags => UnderlyingMethodBase.MethodImplementationFlags; + + /// + public ITypeSymbol[] GetGenericArguments() { - _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); + return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); } - /// - /// Gets the containing . - /// - protected internal ReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; + /// + public MethodImplAttributes GetMethodImplementationFlags() + { + return UnderlyingMethodBase.GetMethodImplementationFlags(); + } - /// - /// Gets the containing . - /// - protected internal ReflectionTypeSymbolBuilder? ContainingTypeBuilder => _containingTypeBuilder; + /// + public IParameterSymbol[] GetParameters() + { + return ResolveParameterSymbols(UnderlyingMethodBase.GetParameters()); + } + + #endregion + + /// + public override void OnComplete() + { + foreach (var i in GetGenericArguments()) + if (i is IReflectionGenericTypeParameterSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetParameters()) + if (i is IReflectionParameterSymbolBuilder b) + b.OnComplete(); + + base.OnComplete(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index ce4b912945..e0c2fb3e86 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -7,77 +7,76 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder + class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflectionMethodSymbolBuilder { - readonly MethodBuilder _builder; - ReflectionMethodSymbol? _symbol; + MethodBuilder? _builder; + MethodInfo _method; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder, MethodBuilder builder) : - base(context, containingModuleBuilder) + /// + public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, MethodBuilder builder) : + base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _method = _builder; } - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, MethodBuilder builder) : - base(context, containingTypeBuilder) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } + /// + public MethodInfo UnderlyingMethod => _method; - /// - /// Gets the that underlies this instance. - /// - internal MethodBuilder ReflectionBuilder => _builder; + /// + public override MethodBase UnderlyingMethodBase => UnderlyingMethod; /// - internal override ReflectionMethodSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateMethodSymbol(_builder); + public MethodBuilder UnderlyingMethodBuilder => _builder ?? throw new InvalidOperationException(); + + #region IMethodSymbolBuilder /// public void SetImplementationFlags(MethodImplAttributes attributes) { - _builder.SetImplementationFlags(attributes); + UnderlyingMethodBuilder.SetImplementationFlags(attributes); } /// public void SetParameters(params ITypeSymbol[] parameterTypes) { - _builder.SetParameters(parameterTypes.Unpack()); + UnderlyingMethodBuilder.SetParameters(parameterTypes.Unpack()); } /// public void SetReturnType(ITypeSymbol? returnType) { - _builder.SetReturnType(returnType?.Unpack()); + UnderlyingMethodBuilder.SetReturnType(returnType?.Unpack()); } /// public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - _builder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); + UnderlyingMethodBuilder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); } public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) { - throw new NotImplementedException(); + var l = UnderlyingMethodBuilder.DefineGenericParameters(names); + var a = new IGenericTypeParameterSymbolBuilder[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = new ReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, ResolvingType, this, l[i]); + + return a; } /// public IParameterSymbolBuilder DefineParameter(int position, ParameterAttributes attributes, string? strParamName) { - return new ReflectionParameterSymbolBuilder(Context, this, _builder.DefineParameter(position, attributes, strParamName)); + return new ReflectionParameterSymbolBuilder(Context, ResolvingModule, this, UnderlyingMethodBuilder.DefineParameter(position, attributes, strParamName)); } public IILGenerator GetILGenerator() @@ -93,13 +92,57 @@ public IILGenerator GetILGenerator(int size) /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + UnderlyingMethodBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IMethodSymbol + + /// + public IParameterSymbol ReturnParameter => ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); + + /// + public ITypeSymbol ReturnType => ResolveTypeSymbol(UnderlyingMethod.ReturnType); + + /// + public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + + /// + public override bool IsComplete => _builder == null; + + /// + public IMethodSymbol GetBaseDefinition() + { + return ResolveMethodSymbol(UnderlyingMethod.GetBaseDefinition()); + } + + /// + public IMethodSymbol GetGenericMethodDefinition() + { + return ResolveMethodSymbol(UnderlyingMethod.GetGenericMethodDefinition()); + } + + /// + public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) + { + return ResolveMethodSymbol(UnderlyingMethod.MakeGenericMethod(typeArguments.Unpack())); + } + + #endregion + + /// + public override void OnComplete() + { + _method = (MethodInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index 0861c2c9e7..3a64b5df35 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -1,4 +1,5 @@ using System; +using System.Linq; using System.Reflection; using System.Reflection.Emit; @@ -7,90 +8,372 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionModuleSymbolBuilder : ReflectionSymbolBuilder, IModuleSymbolBuilder + class ReflectionModuleSymbolBuilder : ReflectionSymbolBuilder, IReflectionModuleSymbolBuilder { + readonly IReflectionAssemblySymbol _resolvingAssembly; + readonly ModuleBuilder _builder; - ReflectionModuleSymbol? _symbol; + ReflectionModuleMetadata _metadata; /// /// Initializes a new instance. /// /// + /// /// - public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, ModuleBuilder builder) : + /// + public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, IReflectionAssemblySymbol resolvingAssembly, ModuleBuilder builder) : base(context) { + _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _metadata = new ReflectionModuleMetadata(this); } /// - internal override ReflectionModuleSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateModuleSymbol(_builder); + public Module UnderlyingModule => UnderlyingModuleBuilder; + + /// + public ModuleBuilder UnderlyingModuleBuilder => _builder; + + /// + public IReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; + + #region IModuleSymbolBuilder /// public ITypeSymbolBuilder DefineType(string name) { - return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name)); } /// public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, int typesize) { - return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), typesize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), typesize)); } /// public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent) { - return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack())); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack())); } /// public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr) { - return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr)); } /// public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packsize) { - return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), packsize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), packsize)); } /// public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packingSize, int typesize) { - return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), packingSize, typesize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), packingSize, typesize)); } /// public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) { - return new ReflectionTypeSymbolBuilder(Context, this, _builder.DefineType(name, attr, parent?.Unpack(), interfaces?.Unpack())); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), interfaces?.Unpack())); } /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingModuleBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + UnderlyingModuleBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IModuleSymbol + + /// + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingModule.Assembly); + + /// + public string FullyQualifiedName => UnderlyingModule.FullyQualifiedName; + + /// + public int MetadataToken => UnderlyingModule.MetadataToken; + + /// + public Guid ModuleVersionId => UnderlyingModule.ModuleVersionId; + + /// + public string Name => UnderlyingModule.Name; + + /// + public string ScopeName => UnderlyingModule.ScopeName; + + /// + public override bool IsComplete => _builder == null; + + /// + public IFieldSymbol? GetField(string name) + { + return ResolveFieldSymbol(UnderlyingModule.GetField(name)); + } + + /// + public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + return ResolveFieldSymbol(UnderlyingModule.GetField(name, bindingAttr)); + } + + /// + public IFieldSymbol[] GetFields(BindingFlags bindingFlags) + { + return ResolveFieldSymbols(UnderlyingModule.GetFields(bindingFlags))!; + } + + /// + public IFieldSymbol[] GetFields() + { + return ResolveFieldSymbols(UnderlyingModule.GetFields())!; + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name)); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, types.Unpack())); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers)); + } + + /// + public IMethodSymbol[] GetMethods() + { + return ResolveMethodSymbols(UnderlyingModule.GetMethods())!; + } + + /// + public IMethodSymbol[] GetMethods(BindingFlags bindingFlags) + { + return ResolveMethodSymbols(UnderlyingModule.GetMethods(bindingFlags))!; + } + + /// + public ITypeSymbol? GetType(string className) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className)); + } + + /// + public ITypeSymbol? GetType(string className, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className, ignoreCase)); + } + + /// + public ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className, throwOnError, ignoreCase)); + } + + /// + public ITypeSymbol[] GetTypes() + { + return ResolveTypeSymbols(UnderlyingModule.GetTypes())!; + } + + /// + public bool IsResource() + { + return UnderlyingModule.IsResource(); + } + + /// + public IFieldSymbol? ResolveField(int metadataToken) + { + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken)); + } + + /// + public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMemberSymbol? ResolveMember(int metadataToken) + { + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken)); + } + + /// + public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMethodBaseSymbol? ResolveMethod(int metadataToken) + { + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken)); + } + + /// + public byte[] ResolveSignature(int metadataToken) + { + return UnderlyingModule.ResolveSignature(metadataToken); + } + + /// + public string ResolveString(int metadataToken) + { + return UnderlyingModule.ResolveString(metadataToken); + } + + /// + public ITypeSymbol ResolveType(int metadataToken) + { + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken)); } /// - public void Complete() + public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - _builder.CreateGlobalFunctions(); + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData()); + } + + /// + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); + } + + /// + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingModule.IsDefined(attributeType.Unpack(), false); + } + + #endregion + + /// + public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + return _metadata.GetOrCreateTypeSymbol(type); + } + + /// + public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return _metadata.GetOrCreateTypeSymbol(type); + } - foreach (var type in _builder.GetTypes()) - if (type is TypeBuilder typeBuilder) - if (typeBuilder.IsCreated() == false) - if (typeBuilder.CreateType() is { } t) - ReflectionSymbol.ResolveTypeSymbol(t).Complete(t); + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _metadata.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return _metadata.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return _metadata.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return _metadata.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _metadata.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return _metadata.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _metadata.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return _metadata.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _metadata.GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return _metadata.GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _metadata.GetOrCreateParameterSymbol(parameter); + } + + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _metadata.GetOrCreateParameterSymbol(parameter); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs index bb28d0082e..816de787d3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs @@ -1,6 +1,7 @@ using System; using System.Reflection; using System.Reflection.Emit; +using IKVM.CoreLib.Reflection; namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -12,15 +13,18 @@ class ReflectionParameterBuilderInfo : ParameterInfo { readonly ParameterBuilder _builder; + readonly Func _getDefaultValue; /// /// Initialies a new instance. /// /// + /// /// - public ReflectionParameterBuilderInfo(ParameterBuilder builder) + public ReflectionParameterBuilderInfo(ParameterBuilder builder, Func getDefaultValue) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _getDefaultValue = getDefaultValue ?? throw new ArgumentNullException(nameof(getDefaultValue)); } /// @@ -38,6 +42,9 @@ public ReflectionParameterBuilderInfo(ParameterBuilder builder) /// public override int MetadataToken => _builder.GetMetadataToken(); + /// + public override object? DefaultValue => _getDefaultValue(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs index fa908dac80..5495e484bc 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs @@ -1,4 +1,6 @@ using System; +using System.Linq; +using System.Reflection; using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -6,12 +8,14 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - abstract class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder, IParameterSymbolBuilder + class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder, IReflectionParameterSymbolBuilder { - - readonly ParameterBuilder _builder; - readonly ReflectionParameterBuilderInfo _info; - ReflectionParameterSymbol? _symbol; + + readonly IReflectionModuleSymbol _resolvingModule; + readonly IReflectionMethodBaseSymbol _resolvingMethod; + + ParameterBuilder? _builder; + ParameterInfo _parameter; object? _constant; @@ -19,83 +23,141 @@ abstract class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder /// - protected ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, ParameterBuilder builder) : + /// + /// + /// + public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMethodBaseSymbol resolvingMethod, ParameterBuilder builder) : base(context) { + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _info = new ReflectionParameterBuilderInfo(_builder); + _parameter = new ReflectionParameterBuilderInfo(_builder, () => _constant); } - /// - /// Gets the wrapped . - /// - internal ParameterBuilder ReflectionBuilder => _builder; + /// + public IReflectionModuleSymbol ResolvingModule => _resolvingMethod.ResolvingModule; /// - internal override ReflectionParameterSymbol ReflectionSymbol => _symbol ??= GetOrCreateSymbol(_info); + public IReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; - /// - /// Gets or creates the . - /// - /// - protected internal abstract ReflectionParameterSymbol GetOrCreateSymbol(ReflectionParameterBuilderInfo info); + /// + public ParameterInfo UnderlyingParameter => _parameter; + + /// + public ParameterBuilder UnderlyingParameterBuilder => _builder ?? throw new InvalidOperationException(); + + #region IParameterSymbolBuilder /// public void SetConstant(object? defaultValue) { - _builder.SetConstant(_constant = defaultValue); + UnderlyingParameterBuilder.SetConstant(_constant = defaultValue); } - /// - /// Saves the constant value so it can be retrieved as a symbol. - /// - /// - internal object? GetConstant() + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - return _constant; + UnderlyingParameterBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingParameterBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } + #endregion + + #region IParameterSymbol + /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public ParameterAttributes Attributes => UnderlyingParameter.Attributes; + + /// + public object? DefaultValue => UnderlyingParameter.DefaultValue; + + /// + public bool HasDefaultValue => UnderlyingParameter.HasDefaultValue; + + /// + public bool IsIn => UnderlyingParameter.IsIn; + + /// + public bool IsLcid => UnderlyingParameter.IsLcid; + + /// + public bool IsOptional => UnderlyingParameter.IsOptional; + + /// + public bool IsOut => UnderlyingParameter.IsOut; + + /// + public bool IsRetval => UnderlyingParameter.IsRetval; + + /// + public IMemberSymbol Member => ResolveMemberSymbol(UnderlyingParameter.Member); + + /// + public int MetadataToken => UnderlyingParameter.MetadataToken; + + /// + public string? Name => UnderlyingParameter.Name; + + /// + public ITypeSymbol ParameterType => ResolveTypeSymbol(UnderlyingParameter.ParameterType); + + /// + public int Position => UnderlyingParameter.Position; + + /// + public override bool IsComplete => _builder == null; + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData()); } - } + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + } - class ReflectionParameterSymbolBuilder : ReflectionParameterSymbolBuilder - where TContainingSymbol : IMethodBaseSymbol - where TContainingReflectionSymbol : ReflectionMethodBaseSymbol, TContainingSymbol - where TContainingBuilder : ReflectionMethodBaseSymbolBuilder - { + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + } - readonly TContainingBuilder _containingMethodBuilder; + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingParameter.IsDefined(attributeType.Unpack(), inherit); + } - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, TContainingBuilder containingMethodBuilder, ParameterBuilder builder) : - base(context, builder) + /// + public ITypeSymbol[] GetOptionalCustomModifiers() { - _containingMethodBuilder = containingMethodBuilder ?? throw new ArgumentNullException(nameof(containingMethodBuilder)); + return ResolveTypeSymbols(UnderlyingParameter.GetOptionalCustomModifiers()); } - /// - /// Gets the containing . - /// - internal TContainingBuilder ContainingMethodBuilder => _containingMethodBuilder; + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingParameter.GetRequiredCustomModifiers()); + } + + #endregion /// - protected internal override ReflectionParameterSymbol GetOrCreateSymbol(ReflectionParameterBuilderInfo info) => ContainingMethodBuilder.ReflectionSymbol.ResolveParameterSymbol(info); + public void OnComplete() + { + var p = ResolvingMethod.UnderlyingMethodBase.GetParameters(); + _parameter = p[Position]; + _builder = null; + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs index 1d9a57c4b0..de0c8ac1c4 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs @@ -1,4 +1,5 @@ using System; +using System.Reflection; using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -6,40 +7,176 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionPropertySymbolBuilder : ReflectionSymbolBuilder, IPropertySymbolBuilder + class ReflectionPropertySymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionPropertySymbolBuilder { - readonly ReflectionTypeSymbolBuilder _containingTypeBuilder; - readonly PropertyBuilder _builder; - ReflectionPropertySymbol? _symbol; + PropertyBuilder? _builder; + PropertyInfo _property; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, ReflectionTypeSymbolBuilder containingTypeBuilder, PropertyBuilder builder) : - base(context) + /// + public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, PropertyBuilder builder) : + base(context, resolvingModule, resolvingType) { - _containingTypeBuilder = containingTypeBuilder ?? throw new ArgumentNullException(nameof(containingTypeBuilder)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _property = _builder; } - internal PropertyBuilder ReflectionBuilder => _builder; + /// + public PropertyInfo UnderlyingProperty => _property; + + /// + public PropertyBuilder UnderlyingPropertyBuilder => _builder ?? throw new InvalidOperationException(); + + /// + public override MemberInfo UnderlyingMember => UnderlyingProperty; + + #region IPropertySymbol + + /// + public void SetConstant(object? defaultValue) + { + UnderlyingPropertyBuilder.SetConstant(defaultValue); + } + + /// + public void SetGetMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingPropertyBuilder.SetGetMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } - internal override ReflectionPropertySymbol ReflectionSymbol => _symbol ??= _containingTypeBuilder.ReflectionSymbol.ResolvePropertySymbol(_builder); + /// + public void SetSetMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingPropertyBuilder.SetSetMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingPropertyBuilder.AddOtherMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingPropertyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + UnderlyingPropertyBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IPropertySymbol + + /// + public PropertyAttributes Attributes => UnderlyingProperty.Attributes; + + /// + public bool CanRead => UnderlyingProperty.CanRead; + + /// + public bool CanWrite => UnderlyingProperty.CanWrite; + + /// + public bool IsSpecialName => UnderlyingProperty.IsSpecialName; + + /// + public ITypeSymbol PropertyType => ResolveTypeSymbol(UnderlyingProperty.PropertyType); + + /// + public IMethodSymbol? GetMethod => ResolveMethodSymbol(UnderlyingProperty.GetMethod); + + /// + public IMethodSymbol? SetMethod => ResolveMethodSymbol(UnderlyingProperty.SetMethod); + + /// + public override bool IsComplete => _builder == null; + + /// + public object? GetRawConstantValue() + { + return UnderlyingProperty.GetRawConstantValue(); + } + + /// + public IMethodSymbol[] GetAccessors() + { + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors()); + } + + /// + public IMethodSymbol[] GetAccessors(bool nonPublic) + { + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors(nonPublic)); + } + + /// + public IParameterSymbol[] GetIndexParameters() + { + return ResolveParameterSymbols(UnderlyingProperty.GetIndexParameters()); + } + + /// + public IMethodSymbol? GetGetMethod() + { + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod()); + } + + /// + public IMethodSymbol? GetGetMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetSetMethod() + { + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod()); + } + + /// + public IMethodSymbol? GetSetMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod(nonPublic)); + } + + /// + public ITypeSymbol GetModifiedPropertyType() + { + throw new NotImplementedException(); + } + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingProperty.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); + } + +#endregion + + /// + public override void OnComplete() + { + _property = (PropertyInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs index 3ff29a8b2c..aff7f03006 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs @@ -1,6 +1,4 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -8,41 +6,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit /// /// Reflection-specific implementation of . /// - abstract class ReflectionSymbolBuilder : ISymbolBuilder - { - - readonly ReflectionSymbolContext _context; - - /// - /// Initializes a new instance. - /// - /// - protected ReflectionSymbolBuilder(ReflectionSymbolContext context) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - } - - /// - /// Gets the associated . - /// - public ReflectionSymbolContext Context => _context; - - /// - public ISymbol Symbol => GetSymbol(); - - /// - /// Implement to get the symbol. - /// - /// - protected abstract ISymbol GetSymbol(); - - } - - /// - /// Reflection-specific implementation of . - /// - abstract class ReflectionSymbolBuilder : ReflectionSymbolBuilder, ISymbolBuilder - where TSymbol : ISymbol + abstract class ReflectionSymbolBuilder : ReflectionSymbol, IReflectionSymbolBuilder { /// @@ -55,40 +19,6 @@ protected ReflectionSymbolBuilder(ReflectionSymbolContext context) : } - /// - public abstract new TSymbol Symbol { get; } - - /// - protected sealed override ISymbol GetSymbol() => Symbol; - - } - - /// - /// Base implementation for reflection symbol builders. - /// - abstract class ReflectionSymbolBuilder : ReflectionSymbolBuilder - where TSymbol : ISymbol - where TReflectionSymbol : ReflectionSymbol, TSymbol - { - - /// - /// Initializes a new instance. - /// - /// - protected ReflectionSymbolBuilder(ReflectionSymbolContext context) : - base(context) - { - - } - - /// - public sealed override TSymbol Symbol => ReflectionSymbol; - - /// - /// Gets the that is currently being built. Portions of this interface will be non-functional until the build is completed. - /// - internal abstract TReflectionSymbol ReflectionSymbol { get; } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 586138398e..27eb448524 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -8,241 +8,793 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionTypeSymbolBuilder : ReflectionSymbolBuilder, ITypeSymbolBuilder + class ReflectionTypeSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionTypeSymbolBuilder { - readonly ReflectionModuleSymbolBuilder _containingModuleBuilder; - readonly TypeBuilder _builder; - ReflectionTypeSymbol? _symbol; + TypeBuilder? _builder; + Type _type; + ReflectionTypeImpl _impl; /// /// Initializes a new instance. /// /// - /// + /// /// - public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, ReflectionModuleSymbolBuilder containingModuleBuilder, TypeBuilder builder) : - base(context) + public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, TypeBuilder builder) : + base(context, resolvingModule, null) { - _containingModuleBuilder = containingModuleBuilder ?? throw new ArgumentNullException(nameof(containingModuleBuilder)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _type = _builder; + _impl = new ReflectionTypeImpl(this); } - /// - /// Gets the containing . - /// - internal ReflectionModuleSymbolBuilder ContainingModuleBuilder => _containingModuleBuilder; + /// + public Type UnderlyingType => _type; - /// - /// Gets the underlying . - /// - internal TypeBuilder ReflectionBuilder => _builder; + /// + public override MemberInfo UnderlyingMember => UnderlyingType; /// - internal override ReflectionTypeSymbol ReflectionSymbol => _symbol ??= Context.GetOrCreateTypeSymbol(_builder); + public TypeBuilder UnderlyingTypeBuilder => _builder ?? throw new InvalidOperationException(); + + #region ITypeSymbolBuilder /// public void SetParent(ITypeSymbol? parent) { - _builder.SetParent(parent?.Unpack()); + UnderlyingTypeBuilder.SetParent(parent?.Unpack()); } /// public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) { - throw new NotImplementedException(); + var l = UnderlyingTypeBuilder.DefineGenericParameters(names); + var a = new IGenericTypeParameterSymbolBuilder[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = new ReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, this, null, l[i]); + + return a; } /// public void AddInterfaceImplementation(ITypeSymbol interfaceType) { - _builder.AddInterfaceImplementation(interfaceType.Unpack()); + UnderlyingTypeBuilder.AddInterfaceImplementation(interfaceType.Unpack()); } /// public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes) { - return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack())); + return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack())); } /// public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredCustomModifiers, ITypeSymbol[][]? optionalCustomModifiers) { - return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack())); + return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack())); } /// public IConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes) { - return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineDefaultConstructor(attributes)); + return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineDefaultConstructor(attributes)); } /// public IEventSymbolBuilder DefineEvent(string name, EventAttributes attributes, ITypeSymbol eventtype) { - return new ReflectionEventSymbolBuilder(Context, this, _builder.DefineEvent(name, attributes, eventtype.Unpack())); + return (IEventSymbolBuilder)ResolveEventSymbol(UnderlyingTypeBuilder.DefineEvent(name, attributes, eventtype.Unpack())); } /// public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, FieldAttributes attributes) { - return new ReflectionFieldSymbolBuilder(Context, this, _builder.DefineField(fieldName, type.Unpack(), attributes)); + return (IFieldSymbolBuilder)ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), attributes)); } /// public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, FieldAttributes attributes) { - return new ReflectionFieldSymbolBuilder(Context, this, _builder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), attributes)); + return (IFieldSymbolBuilder)ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), attributes)); } /// public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); } /// public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); } /// public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention) { - return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, callingConvention)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, callingConvention)); } /// public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes) { - return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes)); } /// public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return new ReflectionMethodSymbolBuilder(Context, this, _builder.DefineMethod(name, attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + } + + /// + public void DefineMethodOverride(IMethodSymbolBuilder methodInfoBody, IMethodSymbol methodInfoDeclaration) + { + UnderlyingTypeBuilder.DefineMethodOverride(methodInfoBody.Unpack(), methodInfoDeclaration.Unpack()); } /// public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) { - return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), interfaces?.Unpack())); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), interfaces?.Unpack())); } /// public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize) { - return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), packSize, typeSize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), packSize, typeSize)); } /// public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize) { - return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), packSize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), packSize)); } /// public ITypeSymbolBuilder DefineNestedType(string name) { - return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name)); } /// public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent) { - return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack())); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack())); } /// public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr) { - return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr)); } /// public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize) { - return new ReflectionTypeSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefineNestedType(name, attr, parent?.Unpack(), typeSize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), typeSize)); } /// public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) { - return new ReflectionMethodSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefinePInvokeMethod(name, dllName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); } /// public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) { - return new ReflectionMethodSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); } /// public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) { - return new ReflectionMethodSymbolBuilder(Context, ContainingModuleBuilder, _builder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack(), nativeCallConv, nativeCharSet)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack(), nativeCallConv, nativeCharSet)); } /// public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) { - return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, returnType.Unpack(), parameterTypes?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, returnType.Unpack(), parameterTypes?.Unpack())); } /// public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) { - return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), parameterTypes?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), parameterTypes?.Unpack())); } /// public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); } /// public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return new ReflectionPropertySymbolBuilder(Context, this, _builder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); } /// public IConstructorSymbolBuilder DefineTypeInitializer() { - return new ReflectionConstructorSymbolBuilder(Context, this, _builder.DefineTypeInitializer()); + return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineTypeInitializer()); } /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingTypeBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).ReflectionBuilder); + UnderlyingTypeBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region ITypeSymbol + + /// + public TypeAttributes Attributes => _impl.Attributes; + + /// + public IAssemblySymbol Assembly => _impl.Assembly; + + /// + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + + /// + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + + /// + public string? FullName => _impl.FullName; + + /// + public string? Namespace => _impl.Namespace; + + /// + public TypeCode TypeCode => _impl.TypeCode; + + /// + public ITypeSymbol? BaseType => _impl.BaseType; + + /// + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + + /// + public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + + /// + public int GenericParameterPosition => _impl.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + + /// + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + + /// + public bool IsGenericType => _impl.IsGenericType; + + /// + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + + /// + public bool IsGenericParameter => _impl.IsGenericParameter; + + /// + public bool IsAutoLayout => _impl.IsAutoLayout; + + /// + public bool IsExplicitLayout => _impl.IsExplicitLayout; + + /// + public bool IsLayoutSequential => _impl.IsLayoutSequential; + + /// + public bool HasElementType => _impl.HasElementType; + + /// + public bool IsClass => _impl.IsClass; + + /// + public bool IsValueType => _impl.IsValueType; + + /// + public bool IsInterface => _impl.IsInterface; + + /// + public bool IsPrimitive => _impl.IsPrimitive; + + /// + public bool IsSZArray => _impl.IsSZArray; + + /// + public bool IsArray => _impl.IsArray; + + /// + public bool IsEnum => _impl.IsEnum; + + /// + public bool IsPointer => _impl.IsPointer; + + /// + public bool IsFunctionPointer => _impl.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + + /// + public bool IsByRef => _impl.IsByRef; + + /// + public bool IsAbstract => _impl.IsAbstract; + + /// + public bool IsSealed => _impl.IsSealed; + + /// + public bool IsVisible => _impl.IsVisible; + + /// + public bool IsPublic => _impl.IsPublic; + + /// + public bool IsNotPublic => _impl.IsNotPublic; + + /// + public bool IsNested => _impl.IsNested; + + /// + public bool IsNestedAssembly => _impl.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + + /// + public bool IsNestedFamily => _impl.IsNestedFamily; + + /// + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + + /// + public bool IsNestedPrivate => _impl.IsNestedPrivate; + + /// + public bool IsNestedPublic => _impl.IsNestedPublic; + + /// + public bool IsSerializable => _impl.IsSerializable; + + /// + public bool IsSignatureType => _impl.IsSignatureType; + + /// + public bool IsSpecialName => _impl.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + + /// + public override bool IsComplete => _builder == null; + + /// + public int GetArrayRank() + { + return _impl.GetArrayRank(); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return _impl.GetDefaultMembers(); + } + + /// + public ITypeSymbol? GetElementType() + { + return _impl.GetElementType(); + } + + /// + public string? GetEnumName(object value) + { + return _impl.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return _impl.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return _impl.GetEnumUnderlyingType(); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return _impl.GetGenericArguments(); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return _impl.GetGenericParameterConstraints(); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return _impl.GetGenericTypeDefinition(); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return _impl.GetInterface(name); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _impl.GetInterface(name, ignoreCase); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + return _impl.GetInterfaces(inherit); } /// - void Complete(Type type) + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - ReflectionSymbol.Complete(type); + return _impl.GetInterfaceMap(interfaceType); } + /// + public IMemberSymbol[] GetMember(string name) + { + return _impl.GetMember(name); + } + + /// + public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + { + return _impl.GetMember(name, bindingAttr); + } + + /// + public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + { + return _impl.GetMember(name, type, bindingAttr); + } + + /// + public IMemberSymbol[] GetMembers() + { + return _impl.GetMembers(); + } + + /// + public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + { + return _impl.GetMembers(bindingAttr); + } + + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _impl.GetConstructor(types); + } + + /// + public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetConstructor(bindingAttr, types); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return _impl.GetConstructors(); + } + + /// + public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + { + return _impl.GetConstructors(bindingAttr); + } + + /// + public IFieldSymbol? GetField(string name) + { + return _impl.GetField(name); + } + + /// + public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + return _impl.GetField(name, bindingAttr); + } + + /// + public IFieldSymbol[] GetFields() + { + return _impl.GetFields(); + } + + /// + public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + { + return _impl.GetFields(bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return _impl.GetMethod(name); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _impl.GetMethod(name, types); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + { + return _impl.GetMethod(name, bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetMethod(name, bindingAttr, types); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); + } + + /// + public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + { + return _impl.GetMethods(bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return _impl.GetProperty(name); + } + + /// + public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + { + return _impl.GetProperty(name, bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _impl.GetProperty(name, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _impl.GetProperty(name, returnType, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _impl.GetProperty(name, returnType); + } + + /// + public IPropertySymbol[] GetProperties() + { + return _impl.GetProperties(); + } + + /// + public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + { + return _impl.GetProperties(bindingAttr); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return _impl.GetEvent(name); + } + + /// + public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + { + return _impl.GetEvent(name, bindingAttr); + } + + /// + public IEventSymbol[] GetEvents() + { + return _impl.GetEvents(); + } + + /// + public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + { + return _impl.GetEvents(bindingAttr); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return _impl.GetNestedType(name); + } + + /// + public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + { + return _impl.GetNestedType(name, bindingAttr); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return _impl.GetNestedTypes(); + } + + /// + public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + { + return _impl.GetNestedTypes(); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return _impl.IsAssignableFrom(c); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return _impl.IsSubclassOf(c); + } + + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); + } + + /// + public ITypeSymbol MakeArrayType() + { + return _impl.MakeArrayType(); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return _impl.MakeGenericType(typeArguments); + } + + /// + public ITypeSymbol MakePointerType() + { + return _impl.MakePointerType(); + } + + /// + public ITypeSymbol MakeByRefType() + { + return _impl.MakeByRefType(); + } + + #endregion + /// public void Complete() { - if (_builder.IsCreated() == false) + if (_builder != null) { - var type = _builder.CreateType(); - if (type != null) - Complete(type); + // complete type + if (_builder.IsCreated() == false) + _builder.CreateType(); + + // force module to reresolve + Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); + OnComplete(); } } + /// + public override void OnComplete() + { + const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static; + + _type = ResolvingModule.UnderlyingModule.ResolveType(MetadataToken); + _builder = null; + + foreach (var i in GetGenericArguments()) + if (i is IReflectionGenericTypeParameterSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetConstructors(DefaultBindingFlags)) + if (i is IReflectionConstructorSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetMethods(DefaultBindingFlags)) + if (i is IReflectionMethodSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetFields(DefaultBindingFlags)) + if (i is IReflectionFieldSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetProperties(DefaultBindingFlags)) + if (i is IReflectionPropertySymbolBuilder b) + b.OnComplete(); + + foreach (var m in GetEvents(DefaultBindingFlags)) + if (m is IReflectionPropertySymbolBuilder b) + b.OnComplete(); + + base.OnComplete(); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs new file mode 100644 index 0000000000..c16db0d745 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs @@ -0,0 +1,33 @@ +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionAssemblySymbol : IReflectionSymbol, IAssemblySymbol + { + + /// + /// Gets a reference to the underlying . + /// + Assembly UnderlyingAssembly { get; } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs new file mode 100644 index 0000000000..6da5dafb04 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs @@ -0,0 +1,16 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionConstructorSymbol : IReflectionMethodBaseSymbol, IConstructorSymbol + { + + /// + /// Gets the underlying . + /// + ConstructorInfo UnderlyingConstructor { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs new file mode 100644 index 0000000000..33eca5d428 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionEventSymbol : IReflectionMemberSymbol, IEventSymbol + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs new file mode 100644 index 0000000000..0ceb9e07cd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs @@ -0,0 +1,16 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionFieldSymbol : IReflectionMemberSymbol, IFieldSymbol + { + + /// + /// Gets the underlying . + /// + FieldInfo UnderlyingField { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs new file mode 100644 index 0000000000..a839713036 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs @@ -0,0 +1,26 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionMemberSymbol : IReflectionSymbol, IMemberSymbol + { + + /// + /// Gets the resolving module. + /// + IReflectionModuleSymbol ResolvingModule { get; } + + /// + /// Gets the resolving type. + /// + IReflectionTypeSymbol? ResolvingType { get; } + + /// + /// Gets the underlying . + /// + MemberInfo UnderlyingMember { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs new file mode 100644 index 0000000000..13ccd1ef96 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs @@ -0,0 +1,16 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionMethodBaseSymbol : IReflectionMemberSymbol, IMethodBaseSymbol + { + + /// + /// Gets the underlying . + /// + MethodBase UnderlyingMethodBase { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs new file mode 100644 index 0000000000..a806c91951 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs @@ -0,0 +1,16 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionMethodSymbol : IReflectionMethodBaseSymbol, IMethodSymbol + { + + /// + /// Gets the underlying . + /// + MethodInfo UnderlyingMethod { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs new file mode 100644 index 0000000000..c4b9361297 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs @@ -0,0 +1,123 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol + { + + /// + /// Gets the which contains this . + /// + IReflectionAssemblySymbol ResolvingAssembly { get; } + + /// + /// Gets the underlying . + /// + Module UnderlyingModule { get; } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs new file mode 100644 index 0000000000..20e1cb494c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs @@ -0,0 +1,26 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionParameterSymbol : IReflectionSymbol, IParameterSymbol + { + + /// + /// Gets the module that resolved the parameter. + /// + IReflectionModuleSymbol ResolvingModule { get; } + + /// + /// Gets the method that resolved the parameter. + /// + IReflectionMethodBaseSymbol ResolvingMethod { get; } + + /// + /// Gets the underlying . + /// + ParameterInfo UnderlyingParameter { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs new file mode 100644 index 0000000000..9309bf3ea5 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs @@ -0,0 +1,16 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionPropertySymbol : IReflectionMemberSymbol, IPropertySymbol + { + + /// + /// Gets the underlying . + /// + PropertyInfo UnderlyingProperty { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs new file mode 100644 index 0000000000..7db22745b1 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs @@ -0,0 +1,335 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionSymbol : ISymbol + { + + /// + /// Gets the that contains this symbol. + /// + ReflectionSymbolContext Context { get; } + + /// + /// Resolves the symbol for the specified assembly. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assembly))] + IReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly); + + /// + /// Resolves the symbol for the specified assembly builder. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assembly))] + IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); + + /// + /// Resolves the symbols for the specified assemblies. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assemblies))] + IReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies); + + /// + /// Resolves the symbol for the specified module. + /// + /// + /// + [return: NotNullIfNotNull(nameof(module))] + IReflectionModuleSymbol? ResolveModuleSymbol(Module? module); + + /// + /// Resolves the symbol for the specified module. + /// + /// + /// + [return: NotNullIfNotNull(nameof(module))] + IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); + + /// + /// Resolves the symbols for the specified modules. + /// + /// + /// + [return: NotNullIfNotNull(nameof(modules))] + IReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules); + + /// + /// Resolves the symbols for the specified modules. + /// + /// + /// + IEnumerable ResolveModuleSymbols(IEnumerable modules); + + /// + /// Resolves the symbol for the specified member. + /// + /// + /// + [return: NotNullIfNotNull(nameof(member))] + IReflectionMemberSymbol? ResolveMemberSymbol(MemberInfo? member); + + /// + /// Resolves the symbols for the specified members. + /// + /// + /// + [return: NotNullIfNotNull(nameof(types))] + IReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? types); + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + IReflectionTypeSymbol? ResolveTypeSymbol(Type? type); + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); + + /// + /// Resolves the symbols for the specified types. + /// + /// + /// + [return: NotNullIfNotNull(nameof(types))] + IReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types); + + /// + /// Resolves the symbols for the specified types. + /// + /// + /// + IEnumerable ResolveTypeSymbols(IEnumerable types); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IReflectionMethodBaseSymbol? ResolveMethodBaseSymbol(MethodBase? method); + + /// + /// Resolves the symbol for the specified constructor. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctor))] + IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor); + + /// + /// Resolves the symbol for the specified constructor. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctor))] + IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Resolves the symbols for the specified constructors. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctors))] + IReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); + + /// + /// Resolves the symbols for the specified methods. + /// + /// + /// + [return: NotNullIfNotNull(nameof(methods))] + IReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods); + + /// + /// Resolves the symbol for the specified field. + /// + /// + /// + [return: NotNullIfNotNull(nameof(field))] + IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field); + + /// + /// Resolves the symbol for the specified field. + /// + /// + /// + [return: NotNullIfNotNull(nameof(field))] + IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); + + /// + /// Resolves the symbols for the specified fields. + /// + /// + /// + [return: NotNullIfNotNull(nameof(fields))] + IReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields); + + /// + /// Resolves the symbol for the specified property. + /// + /// + /// + [return: NotNullIfNotNull(nameof(property))] + IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property); + + /// + /// Resolves the symbol for the specified property. + /// + /// + /// + [return: NotNullIfNotNull(nameof(property))] + IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); + + /// + /// Resolves the symbols for the specified properties. + /// + /// + /// + [return: NotNullIfNotNull(nameof(properties))] + IReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties); + + /// + /// Resolves the symbol for the specified event. + /// + /// + /// + [return: NotNullIfNotNull(nameof(@event))] + IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event); + + /// + /// Resolves the symbol for the specified event. + /// + /// + /// + [return: NotNullIfNotNull(nameof(@event))] + IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); + + /// + /// Resolves the symbols for the specified events. + /// + /// + /// + [return: NotNullIfNotNull(nameof(events))] + IReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events); + + /// + /// Resolves the symbol for the specified parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(parameter))] + IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter); + + /// + /// Resolves the symbol for the specified parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(parameter))] + IReflectionParameterSymbolBuilder? ResolveParameterSymbol(ParameterBuilder parameter); + + /// + /// Resolves the symbols for the specified parameters. + /// + /// + /// + [return: NotNullIfNotNull(nameof(parameters))] + IReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters); + + /// + /// Transforms a custom set of custom attribute data records to a symbol record. + /// + /// + /// + [return: NotNullIfNotNull(nameof(attributes))] + CustomAttribute[]? ResolveCustomAttributes(IList? attributes); + + /// + /// Transforms a custom set of custom attribute data records to a symbol record. + /// + /// + /// + IEnumerable ResolveCustomAttributes(IEnumerable attributes); + + /// + /// Transforms a custom attribute data record to a symbol record. + /// + /// + /// + [return: NotNullIfNotNull(nameof(customAttributeData))] + CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData); + + /// + /// Transforms a list of values into symbols. + /// + /// + /// + ImmutableArray ResolveCustomAttributeTypedArguments(IList args); + + /// + /// Transforms a values into a symbol. + /// + /// + /// + CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg); + + /// + /// Transforms the type as appropriate. + /// + /// + /// + object? ResolveCustomAttributeTypedValue(object? value); + + /// + /// Transforms a list of values into symbols. + /// + /// + /// + ImmutableArray ResolveCustomAttributeNamedArguments(IList args); + + /// + /// Transforms a values into a symbol. + /// + /// + /// + CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs new file mode 100644 index 0000000000..fa7dc4bbaf --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs @@ -0,0 +1,16 @@ +using System; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol + { + + /// + /// Gets the underlying . + /// + Type UnderlyingType { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs new file mode 100644 index 0000000000..7ba66dc3ed --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs @@ -0,0 +1,66 @@ +using System; +using System.Diagnostics; +using System.Reflection; +using System.Reflection.Emit; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionAssemblyMetadata + { + + readonly IReflectionAssemblySymbol _symbol; + + IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); + ReaderWriterLockSlim? _moduleLock; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReflectionAssemblyMetadata(IReflectionAssemblySymbol symbol) + { + _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + } + + /// + /// Gets or creates the cached for the module. + /// + /// + /// + /// + public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + if (module is null) + throw new ArgumentNullException(nameof(module)); + + Debug.Assert(AssemblyNameEqualityComparer.Instance.Equals(module.Assembly.GetName(), _symbol.UnderlyingAssembly.GetName())); + + // create lock on demand + if (_moduleLock == null) + Interlocked.CompareExchange(ref _moduleLock, new ReaderWriterLockSlim(), null); + + using (_moduleLock.CreateUpgradeableReadLock()) + { + var row = module.GetMetadataTokenRowNumberSafe(); + if (_moduleSymbols[row] == null) + using (_moduleLock.CreateWriteLock()) + if (module is ModuleBuilder builder) + return _moduleSymbols[row] = new ReflectionModuleSymbolBuilder(_symbol.Context, _symbol, builder); + else + return _moduleSymbols[row] = new ReflectionModuleSymbol(_symbol.Context, _symbol, module); + else + return _moduleSymbols[row] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index ef66d94d12..3280e999ba 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -1,24 +1,19 @@ using System; using System.Collections.Generic; -using System.Diagnostics; using System.Linq; using System.Reflection; -using System.Threading; +using System.Reflection.Emit; -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Threading; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionAssemblySymbol : ReflectionSymbol, IAssemblySymbol + class ReflectionAssemblySymbol : ReflectionSymbol, IReflectionAssemblySymbol { - Assembly _assembly; - - IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); - ReaderWriterLockSlim? _moduleLock; + readonly Assembly _assembly; + ReflectionAssemblyMetadata _impl; /// /// Initializes a new instance. @@ -29,44 +24,21 @@ public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly assemb base(context) { _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); + _impl = new ReflectionAssemblyMetadata(this); } - internal Assembly ReflectionObject => _assembly; - /// - /// Gets or creates the cached for the module. + /// Gets the underlying instance. /// - /// - /// - /// - internal ReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - if (module is null) - throw new ArgumentNullException(nameof(module)); - - Debug.Assert(AssemblyNameEqualityComparer.Instance.Equals(module.Assembly.GetName(), _assembly.GetName())); + public Assembly UnderlyingAssembly => _assembly; - // create lock on demand - if (_moduleLock == null) - lock (this) - _moduleLock ??= new ReaderWriterLockSlim(); - - using (_moduleLock.CreateUpgradeableReadLock()) - { - var row = module.GetMetadataTokenRowNumberSafe(); - if (_moduleSymbols[row] == null) - using (_moduleLock.CreateWriteLock()) - return _moduleSymbols[row] ??= new ReflectionModuleSymbol(Context, this, module); - else - return _moduleSymbols[row] ?? throw new InvalidOperationException(); - } - } + #region IAssemblySymbol /// public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); /// - public IMethodSymbol? EntryPoint => _assembly.EntryPoint is { } m ? ResolveMethodSymbol(m) : null; + public IMethodSymbol? EntryPoint => ResolveMethodSymbol(_assembly.EntryPoint); /// public IEnumerable ExportedTypes => ResolveTypeSymbols(_assembly.ExportedTypes); @@ -92,7 +64,7 @@ public ITypeSymbol[] GetExportedTypes() /// public IModuleSymbol? GetModule(string name) { - return _assembly.GetModule(name) is Module m ? GetOrCreateModuleSymbol(m) : null; + return ResolveModuleSymbol(_assembly.GetModule(name)); } /// @@ -128,19 +100,19 @@ public AssemblyName[] GetReferencedAssemblies() /// public ITypeSymbol? GetType(string name, bool throwOnError) { - return _assembly.GetType(name, throwOnError) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; + return ResolveTypeSymbol(_assembly.GetType(name, throwOnError)); } /// public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) { - return _assembly.GetType(name, throwOnError, ignoreCase) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; + return ResolveTypeSymbol(_assembly.GetType(name, throwOnError, ignoreCase)); } /// public ITypeSymbol? GetType(string name) { - return _assembly.GetType(name) is Type t ? Context.GetOrCreateTypeSymbol(t) : null; + return ResolveTypeSymbol(_assembly.GetType(name)); } /// @@ -158,7 +130,8 @@ public CustomAttribute[] GetCustomAttributes(bool inherit = false) /// public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_assembly.GetCustomAttributesData().Where(i => i.AttributeType == ((ReflectionTypeSymbol)attributeType).ReflectionObject)); + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttributes(_assembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); } /// @@ -170,16 +143,19 @@ public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inh /// public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _assembly.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, false); + return _assembly.IsDefined(attributeType.Unpack(), inherit); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(Assembly assembly) + #endregion + + public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _impl.GetOrCreateModuleSymbol(module); + } + + public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) { - Context.GetOrCreateAssemblySymbol(_assembly = assembly); + return (IReflectionModuleSymbolBuilder)_impl.GetOrCreateModuleSymbol(module); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs index b4d8759e70..6b30a2fc89 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs @@ -4,35 +4,26 @@ namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionConstructorSymbol : ReflectionMethodBaseSymbol, IConstructorSymbol + class ReflectionConstructorSymbol : ReflectionMethodBaseSymbol, IReflectionConstructorSymbol { + readonly ConstructorInfo _ctor; + /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionConstructorSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, ConstructorInfo ctor) : - base(context, type, ctor) + public ReflectionConstructorSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, ConstructorInfo ctor) : + base(context, resolvingModule, resolvingType, ctor) { - + _ctor = ctor ?? throw new ArgumentNullException(nameof(ctor)); } - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new ConstructorInfo ReflectionObject => (ConstructorInfo)base.ReflectionObject; - - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(ConstructorInfo type) - { - base.Complete(type); - } + /// + public ConstructorInfo UnderlyingConstructor => _ctor; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs index 81bcd813cb..dc1b0c8ee3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs @@ -4,19 +4,20 @@ namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionEventSymbol : ReflectionMemberSymbol, IEventSymbol + class ReflectionEventSymbol : ReflectionMemberSymbol, IReflectionEventSymbol { - EventInfo _event; + readonly EventInfo _event; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionEventSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, EventInfo @event) : - base(context, type, @event) + public ReflectionEventSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, EventInfo @event) : + base(context, resolvingModule, resolvingType, @event) { _event = @event ?? throw new ArgumentNullException(nameof(@event)); } @@ -24,83 +25,77 @@ public ReflectionEventSymbol(ReflectionSymbolContext context, ReflectionTypeSymb /// /// Gets the underlying wrapped by this symbol. /// - internal new EventInfo ReflectionObject => _event; + public EventInfo UnderlyingEvent => _event; + + #region IEventSymbol /// - public EventAttributes Attributes => _event.Attributes; + public EventAttributes Attributes => UnderlyingEvent.Attributes; /// - public ITypeSymbol? EventHandlerType => _event.EventHandlerType is { } m ? ResolveTypeSymbol(m) : null; + public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); /// - public bool IsSpecialName => _event.IsSpecialName; + public bool IsSpecialName => UnderlyingEvent.IsSpecialName; /// - public IMethodSymbol? AddMethod => _event.AddMethod is { } m ? ResolveMethodSymbol(m) : null; + public IMethodSymbol? AddMethod => ResolveMethodSymbol(UnderlyingEvent.AddMethod); /// - public IMethodSymbol? RemoveMethod => _event.RemoveMethod is { } m ? ResolveMethodSymbol(m) : null; + public IMethodSymbol? RemoveMethod => ResolveMethodSymbol(UnderlyingEvent.RemoveMethod); /// - public IMethodSymbol? RaiseMethod => _event.RaiseMethod is { } m ? ResolveMethodSymbol(m) : null; + public IMethodSymbol? RaiseMethod => ResolveMethodSymbol(UnderlyingEvent.RaiseMethod); /// public IMethodSymbol? GetAddMethod() { - return _event.GetAddMethod() is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod()); } /// public IMethodSymbol? GetAddMethod(bool nonPublic) { - return _event.GetAddMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod(nonPublic)); } /// public IMethodSymbol? GetRemoveMethod() { - return _event.GetRemoveMethod() is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod()); } /// public IMethodSymbol? GetRemoveMethod(bool nonPublic) { - return _event.GetRemoveMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod(nonPublic)); } /// public IMethodSymbol? GetRaiseMethod() { - return _event.GetRaiseMethod() is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod()); } /// public IMethodSymbol? GetRaiseMethod(bool nonPublic) { - return _event.GetRaiseMethod(nonPublic) is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod(nonPublic)); } /// public IMethodSymbol[] GetOtherMethods() { - return ResolveMethodSymbols(_event.GetOtherMethods()); + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods()); } /// public IMethodSymbol[] GetOtherMethods(bool nonPublic) { - return ResolveMethodSymbols(_event.GetOtherMethods(nonPublic)); + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods(nonPublic)); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(EventInfo @event) - { - ResolveEventSymbol(_event = @event); - base.Complete(_event); - } + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index ca18fda1ab..8e476d98e2 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -4,111 +4,92 @@ namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionFieldSymbol : ReflectionMemberSymbol, IFieldSymbol + class ReflectionFieldSymbol : ReflectionMemberSymbol, IReflectionFieldSymbol { - FieldInfo _field; + readonly FieldInfo _field; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionFieldSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol containingModule, FieldInfo field) : - base(context, containingModule, field) + public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, FieldInfo field) : + base(context, resolvingModule, resolvingType, field) { _field = field ?? throw new ArgumentNullException(nameof(field)); } - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionFieldSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol containingType, FieldInfo field) : - base(context, containingType, field) - { - _field = field ?? throw new ArgumentNullException(nameof(field)); - } + /// + public FieldInfo UnderlyingField => _field; - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new FieldInfo ReflectionObject => (FieldInfo)base.ReflectionObject; + #region IFieldSymbol /// - public FieldAttributes Attributes => _field.Attributes; + public FieldAttributes Attributes => UnderlyingField.Attributes; /// - public ITypeSymbol FieldType => ResolveTypeSymbol(_field.FieldType); + public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); /// - public bool IsSpecialName => _field.IsSpecialName; + public bool IsSpecialName => UnderlyingField.IsSpecialName; /// - public bool IsAssembly => _field.IsAssembly; + public bool IsAssembly => UnderlyingField.IsAssembly; /// - public bool IsFamily => _field.IsFamily; + public bool IsFamily => UnderlyingField.IsFamily; /// - public bool IsFamilyAndAssembly => _field.IsFamilyAndAssembly; + public bool IsFamilyAndAssembly => UnderlyingField.IsFamilyAndAssembly; /// - public bool IsFamilyOrAssembly => _field.IsFamilyOrAssembly; + public bool IsFamilyOrAssembly => UnderlyingField.IsFamilyOrAssembly; /// - public bool IsInitOnly => _field.IsInitOnly; + public bool IsInitOnly => UnderlyingField.IsInitOnly; /// - public bool IsLiteral => _field.IsLiteral; + public bool IsLiteral => UnderlyingField.IsLiteral; #pragma warning disable SYSLIB0050 // Type or member is obsolete /// - public bool IsNotSerialized => _field.IsNotSerialized; + public bool IsNotSerialized => UnderlyingField.IsNotSerialized; #pragma warning restore SYSLIB0050 // Type or member is obsolete /// - public bool IsPinvokeImpl => _field.IsPinvokeImpl; + public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; /// - public bool IsPrivate => _field.IsPrivate; + public bool IsPrivate => UnderlyingField.IsPrivate; /// - public bool IsPublic => _field.IsPublic; + public bool IsPublic => UnderlyingField.IsPublic; /// - public bool IsStatic => _field.IsStatic; + public bool IsStatic => UnderlyingField.IsStatic; /// public ITypeSymbol[] GetOptionalCustomModifiers() { - return ResolveTypeSymbols(_field.GetOptionalCustomModifiers()); + return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); } /// public ITypeSymbol[] GetRequiredCustomModifiers() { - return ResolveTypeSymbols(_field.GetRequiredCustomModifiers()); + return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); } /// public object? GetRawConstantValue() { - return _field.GetRawConstantValue(); + return UnderlyingField.GetRawConstantValue(); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(FieldInfo field) - { - ResolveFieldSymbol(_field = field); - base.Complete(_field); - } + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs new file mode 100644 index 0000000000..a851d2cf9a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs @@ -0,0 +1,562 @@ +using System; +using System.Diagnostics.CodeAnalysis; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionGenericTypeParameterSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol + { + + readonly IReflectionMethodSymbol? _resolvingMethod; + readonly Type _type; + ReflectionTypeImpl _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, IReflectionMethodSymbol? resolvingMethod, Type type) : + base(context, resolvingModule, resolvingType, type) + { + _resolvingMethod = resolvingMethod; + _type = type ?? throw new ArgumentNullException(nameof(type)); + _impl = new ReflectionTypeImpl(this); + } + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + if (type == _type) + return this; + else + return base.ResolveTypeSymbol(type); + } + + /// + /// Gets the underlying . + /// + public Type UnderlyingType => _type; + + /// + /// Gets the method base that declares this type parameter. + /// + public IReflectionMethodBaseSymbol? ResolvingMethodBase => _resolvingMethod; + + #region ITypeSymbol + + /// + public TypeAttributes Attributes => _impl.Attributes; + + /// + public IAssemblySymbol Assembly => _impl.Assembly; + + /// + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + + /// + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + + /// + public string? FullName => _impl.FullName; + + /// + public string? Namespace => _impl.Namespace; + + /// + public TypeCode TypeCode => _impl.TypeCode; + + /// + public ITypeSymbol? BaseType => _impl.BaseType; + + /// + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + + /// + public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + + /// + public int GenericParameterPosition => _impl.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + + /// + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + + /// + public bool IsGenericType => _impl.IsGenericType; + + /// + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + + /// + public bool IsGenericParameter => _impl.IsGenericParameter; + + /// + public bool IsAutoLayout => _impl.IsAutoLayout; + + /// + public bool IsExplicitLayout => _impl.IsExplicitLayout; + + /// + public bool IsLayoutSequential => _impl.IsLayoutSequential; + + /// + public bool HasElementType => _impl.HasElementType; + + /// + public bool IsClass => _impl.IsClass; + + /// + public bool IsValueType => _impl.IsValueType; + + /// + public bool IsInterface => _impl.IsInterface; + + /// + public bool IsPrimitive => _impl.IsPrimitive; + + /// + public bool IsSZArray => _impl.IsSZArray; + + /// + public bool IsArray => _impl.IsArray; + + /// + public bool IsEnum => _impl.IsEnum; + + /// + public bool IsPointer => _impl.IsPointer; + + /// + public bool IsFunctionPointer => _impl.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + + /// + public bool IsByRef => _impl.IsByRef; + + /// + public bool IsAbstract => _impl.IsAbstract; + + /// + public bool IsSealed => _impl.IsSealed; + + /// + public bool IsVisible => _impl.IsVisible; + + /// + public bool IsPublic => _impl.IsPublic; + + /// + public bool IsNotPublic => _impl.IsNotPublic; + + /// + public bool IsNested => _impl.IsNested; + + /// + public bool IsNestedAssembly => _impl.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + + /// + public bool IsNestedFamily => _impl.IsNestedFamily; + + /// + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + + /// + public bool IsNestedPrivate => _impl.IsNestedPrivate; + + /// + public bool IsNestedPublic => _impl.IsNestedPublic; + + /// + public bool IsSerializable => _impl.IsSerializable; + + /// + public bool IsSignatureType => _impl.IsSignatureType; + + /// + public bool IsSpecialName => _impl.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + + /// + public int GetArrayRank() + { + return _impl.GetArrayRank(); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return _impl.GetDefaultMembers(); + } + + /// + public ITypeSymbol? GetElementType() + { + return _impl.GetElementType(); + } + + /// + public string? GetEnumName(object value) + { + return _impl.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return _impl.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return _impl.GetEnumUnderlyingType(); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return _impl.GetGenericArguments(); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return _impl.GetGenericParameterConstraints(); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return _impl.GetGenericTypeDefinition(); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return _impl.GetInterface(name); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _impl.GetInterface(name, ignoreCase); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + return _impl.GetInterfaces(inherit); + } + + /// + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return _impl.GetInterfaceMap(interfaceType); + } + + /// + public IMemberSymbol[] GetMember(string name) + { + return _impl.GetMember(name); + } + + /// + public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + { + return _impl.GetMember(name, bindingAttr); + } + + /// + public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + { + return _impl.GetMember(name, type, bindingAttr); + } + + /// + public IMemberSymbol[] GetMembers() + { + return _impl.GetMembers(); + } + + /// + public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + { + return _impl.GetMembers(bindingAttr); + } + + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _impl.GetConstructor(types); + } + + /// + public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetConstructor(bindingAttr, types); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return _impl.GetConstructors(); + } + + /// + public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + { + return _impl.GetConstructors(bindingAttr); + } + + /// + public IFieldSymbol? GetField(string name) + { + return _impl.GetField(name); + } + + /// + public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + return _impl.GetField(name, bindingAttr); + } + + /// + public IFieldSymbol[] GetFields() + { + return _impl.GetFields(); + } + + /// + public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + { + return _impl.GetFields(bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return _impl.GetMethod(name); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _impl.GetMethod(name, types); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + { + return _impl.GetMethod(name, bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetMethod(name, bindingAttr, types); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); + } + + /// + public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + { + return _impl.GetMethods(bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return _impl.GetProperty(name); + } + + /// + public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + { + return _impl.GetProperty(name, bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _impl.GetProperty(name, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _impl.GetProperty(name, returnType, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _impl.GetProperty(name, returnType); + } + + /// + public IPropertySymbol[] GetProperties() + { + return _impl.GetProperties(); + } + + /// + public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + { + return _impl.GetProperties(bindingAttr); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return _impl.GetEvent(name); + } + + /// + public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + { + return _impl.GetEvent(name, bindingAttr); + } + + /// + public IEventSymbol[] GetEvents() + { + return _impl.GetEvents(); + } + + /// + public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + { + return _impl.GetEvents(bindingAttr); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return _impl.GetNestedType(name); + } + + /// + public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + { + return _impl.GetNestedType(name, bindingAttr); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return _impl.GetNestedTypes(); + } + + /// + public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + { + return _impl.GetNestedTypes(); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return _impl.IsAssignableFrom(c); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return _impl.IsSubclassOf(c); + } + + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); + } + + /// + public ITypeSymbol MakeArrayType() + { + return _impl.MakeArrayType(); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return _impl.MakeGenericType(typeArguments); + } + + /// + public ITypeSymbol MakePointerType() + { + return _impl.MakePointerType(); + } + + /// + public ITypeSymbol MakeByRefType() + { + return _impl.MakeByRefType(); + } + + #endregion + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 52b19f9854..7037880a35 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -1,7 +1,12 @@ using System; using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; using System.Linq; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -9,7 +14,7 @@ namespace IKVM.CoreLib.Symbols.Reflection /// /// Obtains information about the attributes of a member and provides access to member metadata. /// - abstract class ReflectionMemberSymbol : ReflectionSymbol, IMemberSymbol + abstract class ReflectionMemberSymbol : ReflectionSymbol, IReflectionMemberSymbol { /// @@ -40,9 +45,9 @@ static T[] Concat(List? list) return a; } - readonly ReflectionModuleSymbol _containingModule; - readonly ReflectionTypeSymbol? _containingType; - MemberInfo _member; + readonly IReflectionModuleSymbol _resolvingModule; + readonly IReflectionTypeSymbol? _resolvingType; + readonly MemberInfo _member; CustomAttribute[]? _customAttributes; CustomAttribute[]? _inheritedCustomAttributes; @@ -51,137 +56,46 @@ static T[] Concat(List? list) /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol containingModule, MemberInfo member) : + public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, MemberInfo member) : base(context) { - _containingModule = containingModule ?? throw new ArgumentNullException(nameof(containingModule)); + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingType = resolvingType; _member = member ?? throw new ArgumentNullException(nameof(member)); } - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionMemberSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol containingType, MemberInfo member) : - this(context, containingType.ContainingModule, member) - { - _containingType = containingType ?? throw new ArgumentNullException(nameof(containingType)); - } - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected internal override ReflectionTypeSymbol ResolveTypeSymbol(Type type) - { - if (_containingType != null && type == _containingType.ReflectionObject) - return _containingType; - else if (type.Module == _member.Module) - return _containingModule.GetOrCreateTypeSymbol(type); - else - return base.ResolveTypeSymbol(type); - } - - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - protected internal override ReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) - { - if (ctor.Module == _member.Module) - return _containingModule.GetOrCreateConstructorSymbol(ctor); - else - return base.ResolveConstructorSymbol(ctor); - } - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected internal override ReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) - { - if (method.Module == _member.Module) - return _containingModule.GetOrCreateMethodSymbol(method); - else - return base.ResolveMethodSymbol(method); - } - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override ReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) - { - if (field.Module == _member.Module) - return _containingModule.GetOrCreateFieldSymbol(field); - else - return base.ResolveFieldSymbol(field); - } - - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected internal override ReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) - { - if (property.Module == _member.Module) - return _containingModule.GetOrCreatePropertySymbol(property); - else - return base.ResolvePropertySymbol(property); - } - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - protected internal override ReflectionEventSymbol ResolveEventSymbol(EventInfo @event) - { - if (@event.Module == _member.Module) - return _containingModule.GetOrCreateEventSymbol(@event); - else - return base.ResolveEventSymbol(@event); - } + /// + public MemberInfo UnderlyingMember => _member; /// - /// Gets the underlying wrapped by this symbol. + /// Gets the which contains the metadata of this member. /// - internal MemberInfo ReflectionObject => _member; + public IReflectionModuleSymbol ResolvingModule => _resolvingModule; /// - /// Gets the which contains the metadata of this member. + /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. /// - internal ReflectionModuleSymbol ContainingModule => _containingModule; + public IReflectionTypeSymbol? ResolvingType => _resolvingType; - /// - /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. - /// - internal ReflectionTypeSymbol? ContainingType => _containingType; + #region IMemberSymbol /// - public virtual IModuleSymbol Module => Context.GetOrCreateModuleSymbol(_member.Module); + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; /// - public virtual ITypeSymbol? DeclaringType => _member.DeclaringType is Type t ? Context.GetOrCreateTypeSymbol(t) : null; + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; /// - public virtual MemberTypes MemberType => _member.MemberType; + public virtual MemberTypes MemberType => UnderlyingMember.MemberType; /// - public virtual int MetadataToken => _member.MetadataToken; + public virtual int MetadataToken => UnderlyingMember.MetadataToken; /// - public virtual string Name => _member.Name; + public virtual string Name => UnderlyingMember.Name; /// public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) @@ -196,8 +110,11 @@ public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) var list = default(List?); for (; ; ) { + if (self == null) + throw new InvalidOperationException(); + // get attribute for current member and append to list - var attr = ResolveMemberSymbol(self).GetCustomAttributes(false); + var attr = ResolveMemberSymbol(self)!.GetCustomAttributes(false); if (attr.Length > 0) { list ??= []; @@ -231,7 +148,7 @@ public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) } } - return _customAttributes ??= ResolveCustomAttributes(_member.GetCustomAttributesData()); + return _customAttributes ??= ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData())!; } /// @@ -249,20 +166,201 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _member.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - protected void Complete(MemberInfo member) + #endregion + + /// + [return: NotNullIfNotNull(nameof(type))] + public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) { - ResolveMemberSymbol(_member = member); - _customAttributes = null; - _inheritedCustomAttributes = null; + if (type is null) + return null; + + if (_member == type) + return (IReflectionTypeSymbol)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return _resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) + { + if (ctor is null) + return null; + + if (_member == ctor) + return (IReflectionConstructorSymbol)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) + { + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) + { + if (method is null) + return null; + + if (_member == method) + return (IReflectionMethodSymbol)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) + { + if (field is null) + return null; + + if (_member == field) + return (IReflectionFieldSymbol)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) + { + if (property is null) + return null; + + if (_member == property) + return (IReflectionPropertySymbol)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) + { + if (@event is null) + return null; + + if (_member == @event) + return (IReflectionEventSymbol)this; + + if (@event.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + if (@event.GetModuleBuilder() == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.Member.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.GetModuleBuilder() == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); } } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs index 911580f57f..76ae425fcf 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs @@ -1,132 +1,111 @@ using System; +using System.Diagnostics.CodeAnalysis; using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { - abstract class ReflectionMethodBaseSymbol : ReflectionMemberSymbol, IMethodBaseSymbol + abstract class ReflectionMethodBaseSymbol : ReflectionMemberSymbol, IReflectionMethodBaseSymbol { - MethodBase _method; + readonly MethodBase _method; /// /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, MethodBase method) : - base(context, module, method) + public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, MethodBase method) : + base(context, resolvingModule, resolvingType, method) { _method = method ?? throw new ArgumentNullException(nameof(method)); } - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, MethodBase method) : - this(context, type.ContainingModule, method) - { - - } + #region IMethodBaseSymbol /// /// Gets the underlying wrapped by this symbol. /// - internal new MethodBase ReflectionObject => _method; + public MethodBase UnderlyingMethodBase => _method; /// - public MethodAttributes Attributes => _method.Attributes; + public MethodAttributes Attributes => UnderlyingMethodBase.Attributes; /// - public CallingConventions CallingConvention => _method.CallingConvention; + public CallingConventions CallingConvention => UnderlyingMethodBase.CallingConvention; /// - public bool ContainsGenericParameters => _method.ContainsGenericParameters; + public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; /// - public bool IsAbstract => _method.IsAbstract; + public bool IsAbstract => UnderlyingMethodBase.IsAbstract; /// - public bool IsAssembly => _method.IsAssembly; + public bool IsAssembly => UnderlyingMethodBase.IsAssembly; /// - public bool IsConstructor => _method.IsConstructor; + public bool IsConstructor => UnderlyingMethodBase.IsConstructor; /// - public bool IsFamily => _method.IsFamily; + public bool IsFamily => UnderlyingMethodBase.IsFamily; /// - public bool IsFamilyAndAssembly => _method.IsFamilyAndAssembly; + public bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; /// - public bool IsFamilyOrAssembly => _method.IsFamilyOrAssembly; + public bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; /// - public bool IsFinal => _method.IsFinal; + public bool IsFinal => UnderlyingMethodBase.IsFinal; /// - public bool IsGenericMethod => _method.IsGenericMethod; + public bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; /// - public bool IsGenericMethodDefinition => _method.IsGenericMethodDefinition; + public bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; /// - public bool IsHideBySig => _method.IsHideBySig; + public bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; /// - public bool IsPrivate => _method.IsPrivate; + public bool IsPrivate => UnderlyingMethodBase.IsPrivate; /// - public bool IsPublic => _method.IsPublic; + public bool IsPublic => UnderlyingMethodBase.IsPublic; /// - public bool IsStatic => _method.IsStatic; + public bool IsStatic => UnderlyingMethodBase.IsStatic; /// - public bool IsVirtual => _method.IsVirtual; + public bool IsVirtual => UnderlyingMethodBase.IsVirtual; /// - public bool IsSpecialName => _method.IsSpecialName; + public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; /// - public MethodImplAttributes MethodImplementationFlags => _method.MethodImplementationFlags; + public MethodImplAttributes MethodImplementationFlags => UnderlyingMethodBase.MethodImplementationFlags; /// public ITypeSymbol[] GetGenericArguments() { - return ResolveTypeSymbols(_method.GetGenericArguments()); + return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); } /// public MethodImplAttributes GetMethodImplementationFlags() { - return _method.GetMethodImplementationFlags(); + return UnderlyingMethodBase.GetMethodImplementationFlags(); } /// public IParameterSymbol[] GetParameters() { - return ResolveParameterSymbols(_method.GetParameters()); + return ResolveParameterSymbols(UnderlyingMethodBase.GetParameters()); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(MethodBase method) - { - ResolveMethodBaseSymbol(_method = method); - base.Complete(_method); - - foreach (var i in _method.GetParameters()) - ResolveParameterSymbol(i).Complete(i); - - } + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index dd970e657c..4ee162e53c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IMethodSymbol + class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IReflectionMethodSymbol { readonly MethodInfo _method; @@ -16,34 +16,24 @@ class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IMethodSymbol /// /// /// - public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, MethodInfo method) : - base(context, module, method) + public ReflectionMethodSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type, MethodInfo method) : + base(context, module, type, method) { _method = method ?? throw new ArgumentNullException(nameof(method)); } /// - /// Initializes a new instance. + /// Gets the underlying wrapped by this symbol. /// - /// - /// - /// - public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, MethodInfo method) : - this(context, type.ContainingModule, method) - { + public MethodInfo UnderlyingMethod => _method; - } - - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new MethodInfo ReflectionObject => _method; + #region IMethodSymbol /// - public IParameterSymbol ReturnParameter => ResolveParameterSymbol(_method.ReturnParameter); + public IParameterSymbol ReturnParameter => ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); /// - public ITypeSymbol ReturnType => ResolveTypeSymbol(_method.ReturnType); + public ITypeSymbol ReturnType => ResolveTypeSymbol(UnderlyingMethod.ReturnType); /// public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); @@ -51,21 +41,23 @@ public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionTypeSym /// public IMethodSymbol GetBaseDefinition() { - return ResolveMethodSymbol(_method.GetBaseDefinition()); + return ResolveMethodSymbol(UnderlyingMethod.GetBaseDefinition()); } /// public IMethodSymbol GetGenericMethodDefinition() { - return ResolveMethodSymbol(_method.GetGenericMethodDefinition()); + return ResolveMethodSymbol(UnderlyingMethod.GetGenericMethodDefinition()); } /// public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) { - return ResolveMethodSymbol(_method.MakeGenericMethod(typeArguments.Unpack())); + return ResolveMethodSymbol(UnderlyingMethod.MakeGenericMethod(typeArguments.Unpack())); } + #endregion + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs new file mode 100644 index 0000000000..f517096799 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs @@ -0,0 +1,488 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + /// + /// Provides the metadata resolution implementation for a module. + /// + struct ReflectionModuleMetadata + { + + /// + /// Returns true if the given is a TypeDef. That is, not a modified or substituted or generic parameter type. + /// + /// + /// + static bool IsTypeDefinition(Type type) + { +#if NET + return type.IsTypeDefinition; +#else + return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; +#endif + } + + const int MAX_CAPACITY = 65536 * 2; + + readonly IReflectionModuleSymbol _symbol; + + IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _typeLock; + + IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _methodLock; + + IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _fieldLock; + + IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _propertyLock; + + IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _eventLock; + + IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _parameterLock; + + IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _genericParameterLock; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReflectionModuleMetadata(IReflectionModuleSymbol symbol) + { + _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + if (type.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(type)); + + // type is a generic parameter (GenericParam) + if (type.IsGenericParameter) + return GetOrCreateGenericTypeParameterSymbol(type); + + // type is not a type definition (TypeDef) + if (IsTypeDefinition(type) == false) + return GetOrCreateTypeSymbolForSpecification(type); + + // create lock on demand + if (_typeLock == null) + Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); + + using (_typeLock.CreateUpgradeableReadLock()) + { + var row = type.GetMetadataTokenRowNumberSafe(); + if (_typeSymbols[row] == null) + using (_typeLock.CreateWriteLock()) + if (type is TypeBuilder builder) + return _typeSymbols[row] ??= new ReflectionTypeSymbolBuilder(_symbol.Context, _symbol, builder); + else + return _typeSymbols[row] ??= new ReflectionTypeSymbol(_symbol.Context, _symbol, type); + else + return _typeSymbols[row] ?? throw new InvalidOperationException(); + } + } + + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return (IReflectionTypeSymbolBuilder)GetOrCreateTypeSymbol((Type)type); + } + + /// + /// Gets or creates a for the specification type: array, pointer, generic, etc. + /// + /// + /// + /// + /// + IReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + if (type.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(type)); + + if (type.GetElementType() is { } elementType) + { + var elementTypeSymbol = _symbol.ResolveTypeSymbol(elementType)!; + + // handles both SZ arrays and normal arrays + if (type.IsArray) + return (IReflectionTypeSymbol)elementTypeSymbol.MakeArrayType(type.GetArrayRank()); + + if (type.IsPointer) + return (IReflectionTypeSymbol)elementTypeSymbol.MakePointerType(); + + if (type.IsByRef) + return (IReflectionTypeSymbol)elementTypeSymbol.MakeByRefType(); + + throw new InvalidOperationException(); + } + + if (type.IsGenericType) + { + var definitionTypeSymbol = _symbol.GetOrCreateTypeSymbol(type.GetGenericTypeDefinition()); + return (IReflectionTypeSymbol)definitionTypeSymbol.MakeGenericType(definitionTypeSymbol.ResolveTypeSymbols(type.GetGenericArguments())!); + } + + throw new InvalidOperationException(); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + if (method.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(method)); + + // they are methods, but they are associated differently + if (method is DynamicMethod) + throw new ArgumentException("Dynamic methods cannot be attached to context."); + + // create lock on demand + if (_methodLock == null) + Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); + + using (_methodLock.CreateUpgradeableReadLock()) + { + var row = method.GetMetadataTokenRowNumberSafe(); + if (_methodSymbols[row] == null) + { + using (_methodLock.CreateWriteLock()) + { + if (method is ConstructorInfo c) + { + if (method is ConstructorBuilder builder) + return _methodSymbols[row] ??= new ReflectionConstructorSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), builder); + else + return _methodSymbols[row] ??= new ReflectionConstructorSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), c); + } + else if (method is MethodInfo m) + { + if (method is MethodBuilder builder) + return _methodSymbols[row] ??= new ReflectionMethodSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), builder); + else + return _methodSymbols[row] ??= new ReflectionMethodSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), m); + } + else + { + throw new InvalidOperationException(); + } + } + } + else + { + return _methodSymbols[row] ?? throw new InvalidOperationException(); + } + } + } + + /// + /// Gets or creates the cached for the type by ctor. + /// + /// + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return (IReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by ctor. + /// + /// + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return (IReflectionConstructorSymbolBuilder)GetOrCreateConstructorSymbol((ConstructorInfo)ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return (IReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return (IReflectionMethodSymbolBuilder)GetOrCreateMethodBaseSymbol((MethodInfo)method); + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + if (field.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(field)); + + // create lock on demand + if (_fieldLock == null) + Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); + + using (_fieldLock.CreateUpgradeableReadLock()) + { + var row = field.GetMetadataTokenRowNumberSafe(); + if (_fieldSymbols[row] == null) + using (_fieldLock.CreateWriteLock()) + if (field is FieldBuilder builder) + return _fieldSymbols[row] ??= new ReflectionFieldSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), builder); + else + return _fieldSymbols[row] ??= new ReflectionFieldSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), field); + else + return _fieldSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return (IReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field); + } + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + if (property.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(property)); + + // create lock on demand + if (_propertyLock == null) + Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); + + using (_propertyLock.CreateUpgradeableReadLock()) + { + var row = property.GetMetadataTokenRowNumberSafe(); + if (_propertySymbols[row] == null) + using (_propertyLock.CreateWriteLock()) + if (property is PropertyBuilder builder) + return _propertySymbols[row] ??= new ReflectionPropertySymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), builder); + else + return _propertySymbols[row] ??= new ReflectionPropertySymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), property); + else + return _propertySymbols[row] ?? throw new InvalidOperationException(); + } + } + + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return (IReflectionPropertySymbolBuilder)GetOrCreatePropertySymbol((PropertyInfo)property); + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_eventLock == null) + Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); + + using (_eventLock.CreateUpgradeableReadLock()) + { + var row = @event.GetMetadataTokenRowNumberSafe(); + if (_eventSymbols[row] == null) + using (_eventLock.CreateWriteLock()) + return _eventSymbols[row] ??= new ReflectionEventSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.DeclaringType!), @event); + else + return _eventSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.GetModuleBuilder().GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_eventLock == null) + Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); + + using (_eventLock.CreateUpgradeableReadLock()) + { + var row = @event.GetMetadataTokenRowNumberSafe(); + if (_eventSymbols[row] == null) + using (_eventLock.CreateWriteLock()) + return (IReflectionEventSymbolBuilder)(_eventSymbols[row] ??= new ReflectionEventSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.GetTypeBuilder()), @event)); + else + return (IReflectionEventSymbolBuilder?)_eventSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.Member.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_parameterLock == null) + Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); + + using (_parameterLock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_parameterSymbols[position] == null) + using (_parameterLock.CreateWriteLock()) + return _parameterSymbols[position] ??= new ReflectionParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); + else + return _parameterSymbols[position] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.GetModuleBuilder().GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_parameterLock == null) + Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); + + using (_parameterLock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_parameterSymbols[position] == null) + using (_parameterLock.CreateWriteLock()) + return (IReflectionParameterSymbolBuilder)(_parameterSymbols[position] ??= new ReflectionParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveMethodSymbol(parameter.GetMethodBuilder()), parameter)); + else + return (IReflectionParameterSymbolBuilder?)_parameterSymbols[position] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericParameterType) + { + if (genericParameterType is null) + throw new ArgumentNullException(nameof(genericParameterType)); + if (genericParameterType.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) + throw new ArgumentException(nameof(genericParameterType)); + + // create lock on demand + if (_genericParameterLock == null) + Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); + + using (_genericParameterLock.CreateUpgradeableReadLock()) + { + var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.GetMetadataTokenSafe()); + var row = MetadataTokens.GetRowNumber(hnd); + if (_genericParameterSymbols[row] == null) + using (_genericParameterLock.CreateWriteLock()) + if (genericParameterType is GenericTypeParameterBuilder builder) + return _genericParameterSymbols[row] ??= new ReflectionGenericTypeParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), builder); + else + return _genericParameterSymbols[row] ??= new ReflectionGenericTypeParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), genericParameterType); + else + { + return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); + } + } + } + + /// + /// Gets or creates the cached for the module. + /// + /// + /// + IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) + { + return (IReflectionGenericTypeParameterSymbolBuilder)GetOrCreateGenericTypeParameterSymbol((Type)genericParameterType); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 57717f7bc5..bd247f2e7f 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -1,13 +1,9 @@ using System; -using System.Diagnostics; using System.Linq; using System.Reflection; using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; -using System.Threading; -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Threading; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -15,525 +11,211 @@ namespace IKVM.CoreLib.Symbols.Reflection /// /// Implementation of derived from System.Reflection. /// - class ReflectionModuleSymbol : ReflectionSymbol, IModuleSymbol + class ReflectionModuleSymbol : ReflectionSymbol, IReflectionModuleSymbol { - /// - /// Returns true if the given is a TypeDef. That is, not a modified or substituted or generic parameter type. - /// - /// - /// - static bool IsTypeDefinition(Type type) - { -#if NET - return type.IsTypeDefinition; -#else - return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; -#endif - } - - const int MAX_CAPACITY = 65536 * 2; - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - readonly ReflectionAssemblySymbol _containingAssembly; - Module _module; - - IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _typeLock; - - IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _methodLock; - - IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _fieldLock; - - IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _propertyLock; - - IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _eventLock; - - IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _parameterLock; - - IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _genericParameterLock; + readonly IReflectionAssemblySymbol _resolvingAssembly; + readonly Module _module; + ReflectionModuleMetadata _impl; /// /// Initializes a new instance. /// /// - /// + /// /// /// - public ReflectionModuleSymbol(ReflectionSymbolContext context, ReflectionAssemblySymbol containingAssembly, Module module) : + public ReflectionModuleSymbol(ReflectionSymbolContext context, IReflectionAssemblySymbol resolvingAssembly, Module module) : base(context) { - _containingAssembly = containingAssembly ?? throw new ArgumentNullException(nameof(containingAssembly)); + _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); _module = module ?? throw new ArgumentNullException(nameof(module)); + _impl = new ReflectionModuleMetadata(this); } - /// - /// Gets the which contains the metadata of this member. - /// - internal ReflectionAssemblySymbol ContainingAssembly => _containingAssembly; - - /// - /// Gets the wrapped . - /// - internal Module ReflectionObject => _module; - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - /// - internal ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - - Debug.Assert(type.Module == _module); - - // type is a generic parameter (GenericParam) - if (type.IsGenericParameter) - return GetOrCreateGenericParameterSymbol(type); - - // type is not a type definition (TypeDef) - if (IsTypeDefinition(type) == false) - return GetOrCreateTypeSymbolForSpecification(type); - - // create lock on demand - if (_typeLock == null) - Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); - - using (_typeLock.CreateUpgradeableReadLock()) - { - var row = type.GetMetadataTokenRowNumberSafe(); - if (_typeSymbols[row] == null) - using (_typeLock.CreateWriteLock()) - return _typeSymbols[row] ??= new ReflectionTypeSymbol(Context, this, type); - else - return _typeSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates a for the specification type: array, pointer, etc. - /// - /// - /// - /// - /// - ReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - - Debug.Assert(type.Module == _module); - - if (type.GetElementType() is { } elementType) - { - var elementTypeSymbol = ResolveTypeSymbol(elementType); - - // handles both SZ arrays and normal arrays - if (type.IsArray) - return (ReflectionTypeSymbol)elementTypeSymbol.MakeArrayType(type.GetArrayRank()); - - if (type.IsPointer) - return (ReflectionTypeSymbol)elementTypeSymbol.MakePointerType(); - - if (type.IsByRef) - return (ReflectionTypeSymbol)elementTypeSymbol.MakeByRefType(); - - throw new InvalidOperationException(); - } - - if (type.IsGenericType) - { - var definitionTypeSymbol = ResolveTypeSymbol(type.GetGenericTypeDefinition()); - return definitionTypeSymbol.GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); - } - - throw new InvalidOperationException(); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - Debug.Assert(method.Module.GetMetadataTokenSafe() == _module.GetMetadataTokenSafe()); - - // they are methods, but they are associated differently - if (method is DynamicMethod) - throw new ArgumentException("Dynamic methods cannot be attached to context."); - - // create lock on demand - if (_methodLock == null) - Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); - - using (_methodLock.CreateUpgradeableReadLock()) - { - var row = method.GetMetadataTokenRowNumberSafe(); - if (_methodSymbols[row] == null) - using (_methodLock.CreateWriteLock()) - if (method is ConstructorInfo c) - return _methodSymbols[row] ??= new ReflectionConstructorSymbol(Context, ResolveTypeSymbol(c.DeclaringType ?? throw new InvalidOperationException()), c); - else if (method is MethodInfo m) - if (method.DeclaringType is { } dt) - return _methodSymbols[row] ??= new ReflectionMethodSymbol(Context, ResolveTypeSymbol(dt), m); - else - return _methodSymbols[row] ??= new ReflectionMethodSymbol(Context, this, m); - else - throw new InvalidOperationException(); - else - return _methodSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - internal ReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return (ReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal ReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return (ReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - /// - internal ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - Debug.Assert(field.Module == _module); - - // create lock on demand - if (_fieldLock == null) - Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); - - using (_fieldLock.CreateUpgradeableReadLock()) - { - var row = field.GetMetadataTokenRowNumberSafe(); - if (_fieldSymbols[row] == null) - using (_fieldLock.CreateWriteLock()) - if (field.DeclaringType is { } dt) - return _fieldSymbols[row] ??= new ReflectionFieldSymbol(Context, ResolveTypeSymbol(dt), field); - else - return _fieldSymbols[row] ??= new ReflectionFieldSymbol(Context, this, field); - else - return _fieldSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - /// - internal ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - Debug.Assert(property.Module == _module); - - // create lock on demand - if (_propertyLock == null) - Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); - - using (_propertyLock.CreateUpgradeableReadLock()) - { - var row = property.GetMetadataTokenRowNumberSafe(); - if (_propertySymbols[row] == null) - using (_propertyLock.CreateWriteLock()) - return _propertySymbols[row] ??= new ReflectionPropertySymbol(Context, ResolveTypeSymbol(property.DeclaringType!), property); - else - return _propertySymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - /// - internal ReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - Debug.Assert(@event.Module == _module); - - // create lock on demand - if (_eventLock == null) - Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); - - using (_eventLock.CreateUpgradeableReadLock()) - { - var row = @event.GetMetadataTokenRowNumberSafe(); - if (_eventSymbols[row] == null) - using (_eventLock.CreateWriteLock()) - return _eventSymbols[row] ??= new ReflectionEventSymbol(Context, ResolveTypeSymbol(@event.DeclaringType!), @event); - else - return _eventSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - internal ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - Debug.Assert(parameter.Member.Module == _module); - - // create lock on demand - if (_parameterLock == null) - Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); - - using (_parameterLock.CreateUpgradeableReadLock()) - { - var position = parameter.Position; - if (_parameterSymbols[position] == null) - using (_parameterLock.CreateWriteLock()) - return _parameterSymbols[position] ??= new ReflectionParameterSymbol(Context, ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); - else - return _parameterSymbols[position] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - /// - internal ReflectionTypeSymbol GetOrCreateGenericParameterSymbol(Type genericParameterType) - { - if (genericParameterType is null) - throw new ArgumentNullException(nameof(genericParameterType)); - - Debug.Assert(genericParameterType.Module == _module); + /// + public Module UnderlyingModule => _module; - // create lock on demand - if (_genericParameterLock == null) - Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); + /// + public IReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; - using (_genericParameterLock.CreateUpgradeableReadLock()) - { - var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.GetMetadataTokenSafe()); - var row = MetadataTokens.GetRowNumber(hnd); - if (_genericParameterSymbols[row] == null) - using (_genericParameterLock.CreateWriteLock()) - return _genericParameterSymbols[row] ??= new ReflectionTypeSymbol(Context, this, genericParameterType); - else - return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); - } - } + #region IModuleSymbol /// - public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_module.Assembly); + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingModule.Assembly); /// - public string FullyQualifiedName => _module.FullyQualifiedName; + public string FullyQualifiedName => UnderlyingModule.FullyQualifiedName; /// - public int MetadataToken => _module.MetadataToken; + public int MetadataToken => UnderlyingModule.MetadataToken; /// - public Guid ModuleVersionId => _module.ModuleVersionId; + public Guid ModuleVersionId => UnderlyingModule.ModuleVersionId; /// - public string Name => _module.Name; + public string Name => UnderlyingModule.Name; /// - public string ScopeName => _module.ScopeName; + public string ScopeName => UnderlyingModule.ScopeName; /// public IFieldSymbol? GetField(string name) { - return _module.GetField(name) is { } f ? ResolveFieldSymbol(f) : null; + return ResolveFieldSymbol(UnderlyingModule.GetField(name)); } /// public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) { - return _module.GetField(name, bindingAttr) is { } f ? ResolveFieldSymbol(f) : null; + return ResolveFieldSymbol(UnderlyingModule.GetField(name, bindingAttr)); } /// public IFieldSymbol[] GetFields(BindingFlags bindingFlags) { - return ResolveFieldSymbols(_module.GetFields(bindingFlags)); + return ResolveFieldSymbols(UnderlyingModule.GetFields(bindingFlags))!; } /// public IFieldSymbol[] GetFields() { - return ResolveFieldSymbols(_module.GetFields()); + return ResolveFieldSymbols(UnderlyingModule.GetFields())!; } /// public IMethodSymbol? GetMethod(string name) { - return _module.GetMethod(name) is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name)); } /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _module.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, types.Unpack())); } /// public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - return _module.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers)); } /// public IMethodSymbol[] GetMethods() { - return ResolveMethodSymbols(_module.GetMethods()); + return ResolveMethodSymbols(UnderlyingModule.GetMethods())!; } /// public IMethodSymbol[] GetMethods(BindingFlags bindingFlags) { - return ResolveMethodSymbols(_module.GetMethods(bindingFlags)); + return ResolveMethodSymbols(UnderlyingModule.GetMethods(bindingFlags))!; } /// public ITypeSymbol? GetType(string className) { - return _module.GetType(className) is { } t ? ResolveTypeSymbol(t) : null; + return ResolveTypeSymbol(UnderlyingModule.GetType(className)); } /// public ITypeSymbol? GetType(string className, bool ignoreCase) { - return _module.GetType(className, ignoreCase) is { } t ? ResolveTypeSymbol(t) : null; + return ResolveTypeSymbol(UnderlyingModule.GetType(className, ignoreCase)); } /// public ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase) { - return _module.GetType(className, throwOnError, ignoreCase) is { } t ? ResolveTypeSymbol(t) : null; + return ResolveTypeSymbol(UnderlyingModule.GetType(className, throwOnError, ignoreCase)); } /// public ITypeSymbol[] GetTypes() { - return ResolveTypeSymbols(_module.GetTypes()); + return ResolveTypeSymbols(UnderlyingModule.GetTypes())!; } /// public bool IsResource() { - return _module.IsResource(); + return UnderlyingModule.IsResource(); } /// public IFieldSymbol? ResolveField(int metadataToken) { - return _module.ResolveField(metadataToken) is { } f ? ResolveFieldSymbol(f) : null; + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken)); } /// public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - return _module.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } f ? ResolveFieldSymbol(f) : null; + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); } /// public IMemberSymbol? ResolveMember(int metadataToken) { - return _module.ResolveMember(metadataToken) is { } m ? ResolveMemberSymbol(m) : null; + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken)); } /// public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - return _module.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMemberSymbol(m) : null; + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); } /// public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - return _module.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack()) is { } m ? ResolveMethodBaseSymbol(m) : null; + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); } /// public IMethodBaseSymbol? ResolveMethod(int metadataToken) { - return _module.ResolveMethod(metadataToken) is { } m ? ResolveMethodBaseSymbol(m) : null; + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken)); } /// public byte[] ResolveSignature(int metadataToken) { - return _module.ResolveSignature(metadataToken); + return UnderlyingModule.ResolveSignature(metadataToken); } /// public string ResolveString(int metadataToken) { - return _module.ResolveString(metadataToken); + return UnderlyingModule.ResolveString(metadataToken); } /// public ITypeSymbol ResolveType(int metadataToken) { - return ResolveTypeSymbol(_module.ResolveType(metadataToken)); + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken)); } /// public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) { - return ResolveTypeSymbol(_module.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); } /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return ResolveCustomAttributes(_module.GetCustomAttributesData()); + return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData()); } /// public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_module.GetCustomAttributesData().Where(i => i.AttributeType == ((ReflectionTypeSymbol)attributeType).ReflectionObject)); + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); } /// @@ -545,17 +227,93 @@ public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inh /// public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _module.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, false); + return UnderlyingModule.IsDefined(attributeType.Unpack(), false); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(Module module) + #endregion + + /// + public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + return _impl.GetOrCreateTypeSymbol(type); + } + + /// + public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return _impl.GetOrCreateTypeSymbol(type); + } + + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _impl.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return _impl.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return _impl.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return _impl.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _impl.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return _impl.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _impl.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return _impl.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _impl.GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return _impl.GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _impl.GetOrCreateParameterSymbol(parameter); + } + + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) { - ResolveModuleSymbol(_module = module); - ContainingAssembly.Complete(_module.Assembly); + return _impl.GetOrCreateParameterSymbol(parameter); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index 931bb03ce5..22628fd9dc 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -2,16 +2,15 @@ using System.Linq; using System.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; - namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionParameterSymbol : ReflectionSymbol, IParameterSymbol + class ReflectionParameterSymbol : ReflectionSymbol, IReflectionParameterSymbol { - readonly ReflectionMethodBaseSymbol _containingMethod; - ParameterInfo _parameter; + readonly IReflectionModuleSymbol _resolvingModule; + readonly IReflectionMethodBaseSymbol _resolvingMethod; + readonly ParameterInfo _parameter; CustomAttribute[]? _customAttributes; @@ -19,60 +18,71 @@ class ReflectionParameterSymbol : ReflectionSymbol, IParameterSymbol /// Initializes a new instance. /// /// - /// + /// + /// /// - public ReflectionParameterSymbol(ReflectionSymbolContext context, ReflectionMethodBaseSymbol containingMethod, ParameterInfo parameter) : + public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMethodBaseSymbol resolvingMethod, ParameterInfo parameter) : base(context) { - _containingMethod = containingMethod ?? throw new ArgumentNullException(nameof(containingMethod)); + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); } - internal ReflectionMethodBaseSymbol ContainingMethod => _containingMethod; + /// + public IReflectionModuleSymbol ResolvingModule => _resolvingModule; + + /// + public IReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; + + /// + public ParameterInfo UnderlyingParameter => _parameter; + + #region IParameterSymbol /// - public ParameterAttributes Attributes => _parameter.Attributes; + public ParameterAttributes Attributes => UnderlyingParameter.Attributes; /// - public object? DefaultValue => _parameter.DefaultValue; + public object? DefaultValue => UnderlyingParameter.DefaultValue; /// - public bool HasDefaultValue => _parameter.HasDefaultValue; + public bool HasDefaultValue => UnderlyingParameter.HasDefaultValue; /// - public bool IsIn => _parameter.IsIn; + public bool IsIn => UnderlyingParameter.IsIn; /// - public bool IsLcid => _parameter.IsLcid; + public bool IsLcid => UnderlyingParameter.IsLcid; /// - public bool IsOptional => _parameter.IsOptional; + public bool IsOptional => UnderlyingParameter.IsOptional; /// - public bool IsOut => _parameter.IsOut; + public bool IsOut => UnderlyingParameter.IsOut; /// - public bool IsRetval => _parameter.IsRetval; + public bool IsRetval => UnderlyingParameter.IsRetval; /// - public IMemberSymbol Member => ResolveMemberSymbol(_parameter.Member); + public IMemberSymbol Member => ResolveMemberSymbol(UnderlyingParameter.Member); /// - public int MetadataToken => _parameter.MetadataToken; + public int MetadataToken => UnderlyingParameter.MetadataToken; /// - public string? Name => _parameter.Name; + public string? Name => UnderlyingParameter.Name; /// - public ITypeSymbol ParameterType => ResolveTypeSymbol(_parameter.ParameterType); + public ITypeSymbol ParameterType => ResolveTypeSymbol(UnderlyingParameter.ParameterType); /// - public int Position => _parameter.Position; + public int Position => UnderlyingParameter.Position; /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return _customAttributes ??= ResolveCustomAttributes(_parameter.GetCustomAttributesData()); + return _customAttributes ??= ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData()); } /// @@ -90,30 +100,22 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _parameter.IsDefined(((ReflectionTypeSymbol)attributeType).ReflectionObject, inherit); + return UnderlyingParameter.IsDefined(attributeType.Unpack(), inherit); } /// public ITypeSymbol[] GetOptionalCustomModifiers() { - return ResolveTypeSymbols(_parameter.GetOptionalCustomModifiers()); + return ResolveTypeSymbols(UnderlyingParameter.GetOptionalCustomModifiers()); } /// public ITypeSymbol[] GetRequiredCustomModifiers() { - return ResolveTypeSymbols(_parameter.GetRequiredCustomModifiers()); + return ResolveTypeSymbols(UnderlyingParameter.GetRequiredCustomModifiers()); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(ParameterInfo parameter) - { - ResolveParameterSymbol(_parameter = parameter); - _customAttributes = null; - } + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs index 8e39abaeb6..e0f0036743 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs @@ -4,95 +4,94 @@ namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionPropertySymbol : ReflectionMemberSymbol, IPropertySymbol + class ReflectionPropertySymbol : ReflectionMemberSymbol, IReflectionPropertySymbol { - PropertyInfo _property; + readonly PropertyInfo _property; /// /// Initializes a new instance. /// /// + /// /// /// - public ReflectionPropertySymbol(ReflectionSymbolContext context, ReflectionTypeSymbol type, PropertyInfo property) : - base(context, type, property) + public ReflectionPropertySymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol type, PropertyInfo property) : + base(context, module, type, property) { _property = property ?? throw new ArgumentNullException(nameof(property)); } - /// - /// Gets the underlying wrapped by this symbol. - /// - internal new PropertyInfo ReflectionObject => _property; + /// + public PropertyInfo UnderlyingProperty => _property; /// - public PropertyAttributes Attributes => _property.Attributes; + public PropertyAttributes Attributes => UnderlyingProperty.Attributes; /// - public bool CanRead => _property.CanRead; + public bool CanRead => UnderlyingProperty.CanRead; /// - public bool CanWrite => _property.CanWrite; + public bool CanWrite => UnderlyingProperty.CanWrite; /// - public bool IsSpecialName => _property.IsSpecialName; + public bool IsSpecialName => UnderlyingProperty.IsSpecialName; /// - public ITypeSymbol PropertyType => ResolveTypeSymbol(_property.PropertyType); + public ITypeSymbol PropertyType => ResolveTypeSymbol(UnderlyingProperty.PropertyType); /// - public IMethodSymbol? GetMethod => _property.GetMethod is { } m ? ResolveMethodSymbol(m) : null; + public IMethodSymbol? GetMethod => ResolveMethodSymbol(UnderlyingProperty.GetMethod); /// - public IMethodSymbol? SetMethod => _property.SetMethod is { } m ? ResolveMethodSymbol(m) : null; + public IMethodSymbol? SetMethod => ResolveMethodSymbol(UnderlyingProperty.SetMethod); /// public object? GetRawConstantValue() { - return _property.GetRawConstantValue(); + return UnderlyingProperty.GetRawConstantValue(); } /// public IMethodSymbol[] GetAccessors() { - return ResolveMethodSymbols(_property.GetAccessors()); + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors()); } /// public IMethodSymbol[] GetAccessors(bool nonPublic) { - return ResolveMethodSymbols(_property.GetAccessors(nonPublic)); + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors(nonPublic)); } /// public IParameterSymbol[] GetIndexParameters() { - return ResolveParameterSymbols(_property.GetIndexParameters()); + return ResolveParameterSymbols(UnderlyingProperty.GetIndexParameters()); } /// public IMethodSymbol? GetGetMethod() { - return _property.GetGetMethod() is MethodInfo m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod()); } /// public IMethodSymbol? GetGetMethod(bool nonPublic) { - return _property.GetGetMethod(nonPublic) is MethodInfo m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod(nonPublic)); } /// public IMethodSymbol? GetSetMethod() { - return _property.GetSetMethod() is MethodInfo m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod()); } /// public IMethodSymbol? GetSetMethod(bool nonPublic) { - return _property.GetSetMethod(nonPublic) is MethodInfo m ? ResolveMethodSymbol(m) : null; + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod(nonPublic)); } /// @@ -104,23 +103,13 @@ public ITypeSymbol GetModifiedPropertyType() /// public ITypeSymbol[] GetOptionalCustomModifiers() { - return ResolveTypeSymbols(_property.GetOptionalCustomModifiers()); + return ResolveTypeSymbols(UnderlyingProperty.GetOptionalCustomModifiers()); } /// public ITypeSymbol[] GetRequiredCustomModifiers() { - return ResolveTypeSymbols(_property.GetRequiredCustomModifiers()); - } - - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(PropertyInfo property) - { - ResolvePropertySymbol(_property = property); - base.Complete(_property); + return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index 5ad5fe2ab0..bf9c87d3e4 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -1,7 +1,11 @@ using System; using System.Collections.Generic; using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -9,7 +13,7 @@ namespace IKVM.CoreLib.Symbols.Reflection /// /// Base class for managed symbols. /// - abstract class ReflectionSymbol : ISymbol + abstract class ReflectionSymbol : IReflectionSymbol { readonly ReflectionSymbolContext _context; @@ -26,301 +30,400 @@ public ReflectionSymbol(ReflectionSymbolContext context) /// /// Gets the associated . /// - protected ReflectionSymbolContext Context => _context; + public ReflectionSymbolContext Context => _context; /// - public bool IsMissing => false; + public virtual bool IsMissing => false; /// - public bool ContainsMissing => false; + public virtual bool ContainsMissing => false; - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected virtual internal ReflectionModuleSymbol ResolveModuleSymbol(Module module) + /// + public virtual bool IsComplete => true; + + /// + [return: NotNullIfNotNull(nameof(assembly))] + public virtual IReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly) + { + return assembly == null ? null : _context.GetOrCreateAssemblySymbol(assembly); + } + + /// + [return: NotNullIfNotNull(nameof(assembly))] + public virtual IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly) + { + if (assembly is null) + throw new ArgumentNullException(nameof(assembly)); + + return _context.GetOrCreateAssemblySymbol(assembly); + } + + /// + [return: NotNullIfNotNull(nameof(assemblies))] + public virtual IReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies) + { + if (assemblies == null) + return null; + if (assemblies.Length == 0) + return []; + + var a = new IReflectionAssemblySymbol[assemblies.Length]; + for (int i = 0; i < assemblies.Length; i++) + if (ResolveAssemblySymbol(assemblies[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(module))] + public virtual IReflectionModuleSymbol? ResolveModuleSymbol(Module? module) + { + return module == null ? null : _context.GetOrCreateModuleSymbol(module); + } + + /// + [return: NotNullIfNotNull(nameof(module))] + public virtual IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module) { + if (module is null) + throw new ArgumentNullException(nameof(module)); + return _context.GetOrCreateModuleSymbol(module); } - /// - /// Resolves the symbols for the specified modules. - /// - /// - /// - protected internal ReflectionModuleSymbol[] ResolveModuleSymbols(Module[] modules) + /// + [return: NotNullIfNotNull(nameof(modules))] + public virtual IReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules) { - var a = new ReflectionModuleSymbol[modules.Length]; + if (modules == null) + return null; + if (modules.Length == 0) + return []; + + var a = new IReflectionModuleSymbol[modules.Length]; for (int i = 0; i < modules.Length; i++) - a[i] = ResolveModuleSymbol(modules[i]); + if (ResolveModuleSymbol(modules[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbols for the specified modules. - /// - /// - /// - protected internal IEnumerable ResolveModuleSymbols(IEnumerable modules) + /// + public virtual IEnumerable ResolveModuleSymbols(IEnumerable modules) { foreach (var module in modules) - yield return ResolveModuleSymbol(module); + if (ResolveModuleSymbol(module) is { } symbol) + yield return symbol; } - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected virtual ReflectionMemberSymbol ResolveMemberSymbol(MemberInfo member) + /// + [return: NotNullIfNotNull(nameof(member))] + public virtual IReflectionMemberSymbol? ResolveMemberSymbol(MemberInfo? member) { - return member.MemberType switch + if (member == null) + return null; + + return member switch { - MemberTypes.Constructor => ResolveConstructorSymbol((ConstructorInfo)member), - MemberTypes.Event => ResolveEventSymbol((EventInfo)member), - MemberTypes.Field => ResolveFieldSymbol((FieldInfo)member), - MemberTypes.Method => ResolveMethodSymbol((MethodInfo)member), - MemberTypes.Property => ResolvePropertySymbol((PropertyInfo)member), - MemberTypes.TypeInfo => ResolveTypeSymbol((Type)member), - MemberTypes.NestedType => ResolveTypeSymbol((Type)member), - MemberTypes.Custom => throw new NotImplementedException(), - MemberTypes.All => throw new NotImplementedException(), + ConstructorInfo ctor => ResolveConstructorSymbol(ctor), + EventInfo @event => ResolveEventSymbol(@event), + FieldInfo field => ResolveFieldSymbol(field), + MethodInfo method => ResolveMethodSymbol(method), + PropertyInfo property => ResolvePropertySymbol(property), + Type type => ResolveTypeSymbol(type), _ => throw new InvalidOperationException(), }; } - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - protected internal ReflectionMemberSymbol[] ResolveMemberSymbols(MemberInfo[] types) + /// + [return: NotNullIfNotNull(nameof(members))] + public virtual IReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? members) { - var a = new ReflectionMemberSymbol[types.Length]; - for (int i = 0; i < types.Length; i++) - a[i] = ResolveMemberSymbol(types[i]); + if (members == null) + return null; + if (members.Length == 0) + return []; + + var a = new IReflectionMemberSymbol[members.Length]; + for (int i = 0; i < members.Length; i++) + if (ResolveMemberSymbol(members[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - protected virtual internal ReflectionTypeSymbol ResolveTypeSymbol(Type type) + /// + [return: NotNullIfNotNull(nameof(type))] + public virtual IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + return type == null ? null : _context.GetOrCreateTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull(nameof(type))] + public virtual IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) { + if (type is null) + throw new ArgumentNullException(nameof(type)); + return _context.GetOrCreateTypeSymbol(type); } - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - protected internal ReflectionTypeSymbol[] ResolveTypeSymbols(Type[] types) + /// + [return: NotNullIfNotNull(nameof(types))] + public virtual IReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types) { - var a = new ReflectionTypeSymbol[types.Length]; + if (types == null) + return null; + if (types.Length == 0) + return []; + + var a = new IReflectionTypeSymbol[types.Length]; for (int i = 0; i < types.Length; i++) - a[i] = ResolveTypeSymbol(types[i]); + if (ResolveTypeSymbol(types[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - protected internal IEnumerable ResolveTypeSymbols(IEnumerable types) + /// + public virtual IEnumerable ResolveTypeSymbols(IEnumerable types) { foreach (var type in types) - yield return ResolveTypeSymbol(type); + if (ResolveTypeSymbol(type) is { } symbol) + yield return symbol; } - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected virtual internal ReflectionMethodBaseSymbol ResolveMethodBaseSymbol(MethodBase method) + /// + [return: NotNullIfNotNull(nameof(method))] + public virtual IReflectionMethodBaseSymbol? ResolveMethodBaseSymbol(MethodBase? method) { - if (method.IsConstructor) - return ResolveConstructorSymbol((ConstructorInfo)method); - else - return ResolveMethodSymbol((MethodInfo)method); + return method switch + { + ConstructorInfo ctor => ResolveConstructorSymbol(ctor), + MethodInfo method_ => ResolveMethodSymbol(method_), + _ => null, + }; } - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - protected virtual internal ReflectionConstructorSymbol ResolveConstructorSymbol(ConstructorInfo ctor) + /// + [return: NotNullIfNotNull(nameof(ctor))] + public virtual IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) { + return ctor == null ? null : _context.GetOrCreateConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public virtual IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) + { + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + return _context.GetOrCreateConstructorSymbol(ctor); } - /// - /// Resolves the symbols for the specified constructors. - /// - /// - /// - protected internal ReflectionConstructorSymbol[] ResolveConstructorSymbols(ConstructorInfo[] ctors) + /// + [return: NotNullIfNotNull(nameof(ctors))] + public virtual IReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors) { - var a = new ReflectionConstructorSymbol[ctors.Length]; + if (ctors == null) + return null; + if (ctors.Length == 0) + return []; + + var a = new IReflectionConstructorSymbol[ctors.Length]; for (int i = 0; i < ctors.Length; i++) - a[i] = ResolveConstructorSymbol(ctors[i]); + if (ResolveConstructorSymbol(ctors[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - protected virtual internal ReflectionMethodSymbol ResolveMethodSymbol(MethodInfo method) + /// + [return: NotNullIfNotNull(nameof(method))] + public virtual IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) { + return method == null ? null : _context.GetOrCreateMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public virtual IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + return _context.GetOrCreateMethodSymbol(method); } - /// - /// Resolves the symbols for the specified methods. - /// - /// - /// - protected internal ReflectionMethodSymbol[] ResolveMethodSymbols(MethodInfo[] methods) + /// + [return: NotNullIfNotNull(nameof(methods))] + public virtual IReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods) { - var a = new ReflectionMethodSymbol[methods.Length]; + if (methods == null) + return null; + if (methods.Length == 0) + return []; + + var a = new IReflectionMethodSymbol[methods.Length]; for (int i = 0; i < methods.Length; i++) - a[i] = ResolveMethodSymbol(methods[i]); + if (ResolveMethodSymbol(methods[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected virtual internal ReflectionFieldSymbol ResolveFieldSymbol(FieldInfo field) + /// + [return: NotNullIfNotNull(nameof(field))] + public virtual IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) { + return field == null ? null : _context.GetOrCreateFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public virtual IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + return _context.GetOrCreateFieldSymbol(field); } - /// - /// Resolves the symbols for the specified fields. - /// - /// - /// - protected internal ReflectionFieldSymbol[] ResolveFieldSymbols(FieldInfo[] fields) + /// + [return: NotNullIfNotNull(nameof(fields))] + public virtual IReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields) { - var a = new ReflectionFieldSymbol[fields.Length]; + if (fields == null) + return null; + if (fields.Length == 0) + return []; + + var a = new IReflectionFieldSymbol[fields.Length]; for (int i = 0; i < fields.Length; i++) - a[i] = ResolveFieldSymbol(fields[i]); + if (ResolveFieldSymbol(fields[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - protected virtual internal ReflectionPropertySymbol ResolvePropertySymbol(PropertyInfo property) + /// + [return: NotNullIfNotNull(nameof(property))] + public virtual IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) { + return property == null ? null : _context.GetOrCreatePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public virtual IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + return _context.GetOrCreatePropertySymbol(property); } - /// - /// Resolves the symbols for the specified properties. - /// - /// - /// - protected internal ReflectionPropertySymbol[] ResolvePropertySymbols(PropertyInfo[] properties) + /// + [return: NotNullIfNotNull(nameof(properties))] + public virtual IReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties) { - var a = new ReflectionPropertySymbol[properties.Length]; + if (properties == null) + return null; + if (properties.Length == 0) + return []; + + var a = new IReflectionPropertySymbol[properties.Length]; for (int i = 0; i < properties.Length; i++) - a[i] = ResolvePropertySymbol(properties[i]); + if (ResolvePropertySymbol(properties[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - protected virtual internal ReflectionEventSymbol ResolveEventSymbol(EventInfo @event) + /// + [return: NotNullIfNotNull(nameof(@event))] + public virtual IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) + { + return @event == null ? null : _context.GetOrCreateEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public virtual IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + return _context.GetOrCreateEventSymbol(@event); } - /// - /// Resolves the symbols for the specified events. - /// - /// - /// - protected internal ReflectionEventSymbol[] ResolveEventSymbols(EventInfo[] events) + /// + [return: NotNullIfNotNull(nameof(events))] + public virtual IReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events) { - var a = new ReflectionEventSymbol[events.Length]; + if (@events == null) + return null; + if (@events.Length == 0) + return []; + + var a = new IReflectionEventSymbol[events.Length]; for (int i = 0; i < events.Length; i++) - a[i] = ResolveEventSymbol(events[i]); + if (ResolveEventSymbol(events[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - protected virtual internal ReflectionParameterSymbol ResolveParameterSymbol(ParameterInfo parameter) + /// + [return: NotNullIfNotNull(nameof(parameter))] + public virtual IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) { - return _context.GetOrCreateParameterSymbol(parameter); + return parameter == null ? null : _context.GetOrCreateParameterSymbol(parameter); } - /// - /// Resolves the symbols for the specified parameters. - /// - /// - /// - protected internal ReflectionParameterSymbol[] ResolveParameterSymbols(ParameterInfo[] parameters) + /// + [return: NotNullIfNotNull(nameof(parameter))] + public virtual IReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) { - var a = new ReflectionParameterSymbol[parameters.Length]; - for (int i = 0; i < parameters.Length; i++) - a[i] = ResolveParameterSymbol(parameters[i]); + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); - return a; + return _context.GetOrCreateParameterSymbol(parameter); } - /// - /// Resolves the symbols for the specified parameters. - /// - /// - /// - protected internal ReflectionParameterSymbol[] ResolveGenericParameterSymbols(ParameterInfo[] parameters) + /// + [return: NotNullIfNotNull(nameof(parameters))] + public virtual IReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters) { - var a = new ReflectionParameterSymbol[parameters.Length]; + if (parameters == null) + return null; + if (parameters.Length == 0) + return []; + + var a = new IReflectionParameterSymbol[parameters.Length]; for (int i = 0; i < parameters.Length; i++) - a[i] = ResolveParameterSymbol(parameters[i]); + if (ResolveParameterSymbol(parameters[i]) is { } symbol) + a[i] = symbol; return a; } - /// - /// Transforms a custom set of custom attribute data records to a symbol record. - /// - /// - /// - protected internal CustomAttribute[] ResolveCustomAttributes(IList attributes) + /// + [return: NotNullIfNotNull(nameof(attributes))] + public virtual CustomAttribute[]? ResolveCustomAttributes(IList? attributes) { + if (attributes == null) + return null; + if (attributes.Count == 0) + return []; + var a = new CustomAttribute[attributes.Count]; for (int i = 0; i < attributes.Count; i++) - a[i] = ResolveCustomAttribute(attributes[i]); + if (ResolveCustomAttribute(attributes[i]) is { } v) + a[i] = v; return a; } @@ -330,11 +433,15 @@ protected internal CustomAttribute[] ResolveCustomAttributes(IList /// /// - protected internal CustomAttribute[] ResolveCustomAttributes(IEnumerable attributes) + public virtual IEnumerable ResolveCustomAttributes(IEnumerable attributes) { + if (attributes is null) + throw new ArgumentNullException(nameof(attributes)); + var a = new List(); foreach (var i in attributes) - a.Add(ResolveCustomAttribute(i)); + if (ResolveCustomAttribute(i) is { } v) + a.Add(v); return a.ToArray(); } @@ -344,12 +451,15 @@ protected internal CustomAttribute[] ResolveCustomAttributes(IEnumerable /// /// - /// - protected internal CustomAttribute ResolveCustomAttribute(CustomAttributeData customAttributeData) + [return: NotNullIfNotNull(nameof(customAttributeData))] + public virtual CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) { + if (customAttributeData == null) + return null; + return new CustomAttribute( - ResolveTypeSymbol(customAttributeData.AttributeType), - ResolveConstructorSymbol(customAttributeData.Constructor), + ResolveTypeSymbol(customAttributeData.AttributeType)!, + ResolveConstructorSymbol(customAttributeData.Constructor)!, ResolveCustomAttributeTypedArguments(customAttributeData.ConstructorArguments), ResolveCustomAttributeNamedArguments(customAttributeData.NamedArguments)); } @@ -359,8 +469,13 @@ protected internal CustomAttribute ResolveCustomAttribute(CustomAttributeData cu /// /// /// - ImmutableArray ResolveCustomAttributeTypedArguments(IList args) + public ImmutableArray ResolveCustomAttributeTypedArguments(IList args) { + if (args is null) + throw new ArgumentNullException(nameof(args)); + if (args.Count == 0) + return []; + var a = new CustomAttributeTypedArgument[args.Count]; for (int i = 0; i < args.Count; i++) a[i] = ResolveCustomAttributeTypedArgument(args[i]); @@ -373,9 +488,11 @@ ImmutableArray ResolveCustomAttributeTypedArgument /// /// /// - CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg) + public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg) { - return new CustomAttributeTypedArgument(ResolveTypeSymbol(arg.ArgumentType), ResolveCustomAttributeTypedValue(arg.Value)); + return new CustomAttributeTypedArgument( + ResolveTypeSymbol(arg.ArgumentType)!, + ResolveCustomAttributeTypedValue(arg.Value)); } /// @@ -383,12 +500,13 @@ CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflecti /// /// /// - object? ResolveCustomAttributeTypedValue(object? value) + public object? ResolveCustomAttributeTypedValue(object? value) { - if (value is System.Type v) - return ResolveTypeSymbol(v); - - return value; + return value switch + { + Type v => ResolveTypeSymbol(v), + _ => value + }; } /// @@ -396,8 +514,13 @@ CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflecti /// /// /// - ImmutableArray ResolveCustomAttributeNamedArguments(IList args) + public ImmutableArray ResolveCustomAttributeNamedArguments(IList args) { + if (args is null) + throw new ArgumentNullException(nameof(args)); + if (args.Count == 0) + return []; + var a = new CustomAttributeNamedArgument[args.Count]; for (int i = 0; i < args.Count; i++) a[i] = ResolveCustomAttributeNamedArgument(args[i]); @@ -410,9 +533,13 @@ ImmutableArray ResolveCustomAttributeNamedArgument /// /// /// - CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg) + public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg) { - return new CustomAttributeNamedArgument(arg.IsField, ResolveMemberSymbol(arg.MemberInfo), arg.MemberName, ResolveCustomAttributeTypedArgument(arg.TypedValue)); + return new CustomAttributeNamedArgument( + arg.IsField, + ResolveMemberSymbol(arg.MemberInfo)!, + arg.MemberName, + ResolveCustomAttributeTypedArgument(arg.TypedValue)); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index f4e809e2f3..cbd65e7c93 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -5,6 +5,7 @@ using System.Runtime.CompilerServices; using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection @@ -13,11 +14,11 @@ namespace IKVM.CoreLib.Symbols.Reflection /// /// Holds references to symbols derived from System.Reflection. /// - class ReflectionSymbolContext + class ReflectionSymbolContext : ISymbolContext { - readonly ConcurrentDictionary> _symbolByName = new(AssemblyNameEqualityComparer.Instance); - readonly ConditionalWeakTable _symbolByAssembly = new(); + readonly ConcurrentDictionary> _symbolByName = new(AssemblyNameEqualityComparer.Instance); + readonly ConditionalWeakTable _symbolByAssembly = new(); /// /// Initializes a new instance. @@ -28,150 +29,267 @@ public ReflectionSymbolContext() } /// - /// Gets or creates a indexed based on the assembly's name. + /// Gets or creates a indexed based on the assembly's name. /// /// /// - ReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) + IReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) { - var r = _symbolByName.GetOrAdd(assembly.GetName(), _ => new WeakReference(new ReflectionAssemblySymbol(this, assembly))); + var r = _symbolByName.GetOrAdd(assembly.GetName(), _ => new(null)); - // reference has valid symbol - if (r.TryGetTarget(out var s)) - return s; - - // no valid symbol, must have been released, lock to restore lock (r) { - // still gone, recreate - if (r.TryGetTarget(out s) == false) - r.SetTarget(s = new ReflectionAssemblySymbol(this, assembly)); + // reference has no target, reset + if (r.TryGetTarget(out var s) == false) + { + if (assembly is AssemblyBuilder builder) + { + // we were passed in a builder, so generate a symbol builder and set it as the builder and symbol. + var a = builder.GetRuntimeAssembly(); + r.SetTarget(s = new ReflectionAssemblySymbolBuilder(this, builder)); + } + else + { + // we were passed a non builder, so generate a symbol and set it to the symbol + // TODO the weakness here is if we pass it the RuntimeAssembly from a non-associated builder + r.SetTarget(s = new ReflectionAssemblySymbol(this, assembly)); + } + } - return s; + return s ?? throw new InvalidOperationException(); } } /// - /// Gets or creates a for the specified . + /// Gets or creates a indexed based on the assembly's name. + /// + /// + /// + IReflectionAssemblySymbolBuilder GetOrCreateAssemblySymbolByName(AssemblyBuilder assembly) + { + return (IReflectionAssemblySymbolBuilder)GetOrCreateAssemblySymbolByName((Assembly)assembly); + } + + /// + /// Gets or creates a for the specified . /// /// /// - public ReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) + public IReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) { return _symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionAssemblySymbolBuilder GetOrCreateAssemblySymbol(AssemblyBuilder assembly) + { + return (IReflectionAssemblySymbolBuilder)_symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + if (module is ModuleBuilder builder) + return GetOrCreateModuleSymbol(builder); + else + return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); + } + + /// + /// Gets or creates a for the specified . /// /// /// - public ReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) { return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public ReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type is TypeBuilder builder) + return GetOrCreateTypeSymbol(builder); + else + return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) { return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - public ReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { - if (method is ConstructorInfo ctor) - return GetOrCreateConstructorSymbol(ctor); + if (ctor is ConstructorBuilder builder) + return GetOrCreateConstructorSymbol(builder); else - return GetOrCreateMethodSymbol((MethodInfo)method); + return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public ReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) { return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public ReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + if (method is MethodBuilder builder) + return GetOrCreateMethodSymbol(builder); + else + return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) { return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { return GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateParameterSymbol(parameter); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return GetOrCreateModuleSymbol(parameter.GetModuleBuilder()).GetOrCreateParameterSymbol(parameter); + } + + /// + /// Gets or creates a for the specified . /// /// /// - public ReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is FieldBuilder builder) + return GetOrCreateFieldSymbol(builder); + else + return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) { return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public ReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { - return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); + if (property is PropertyBuilder builder) + return GetOrCreatePropertySymbol(builder); + else + return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - public ReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) { - return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public ReflectionEventSymbol GetOrCreateEventSymbol(EventBuilder @event) + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { - return GetOrCreateEventSymbol(new ReflectionEventBuilderInfo(@event)); + return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public ReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterBuilder parameter) + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return GetOrCreateModuleSymbol(@event.GetModuleBuilder()).GetOrCreateEventSymbol(@event); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs) + { + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs)); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) + { + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedFields.Unpack(), fieldValues)); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) + { + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues)); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) { - return GetOrCreateParameterSymbol(new ReflectionParameterBuilderInfo(parameter)); + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues, namedFields.Unpack(), fieldValues)); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs new file mode 100644 index 0000000000..55b1fd5ef7 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Reflection +{ + + static class ReflectionSymbolExtensions + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs new file mode 100644 index 0000000000..e08a8a2c95 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs @@ -0,0 +1,633 @@ +using System; +using System.Collections.Concurrent; +using System.Reflection; +using System.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + /// + /// Provides common operations against a . + /// + struct ReflectionTypeImpl + { + + readonly IReflectionTypeSymbol _symbol; + + ReflectionTypeSymbol?[]? _asArray; + ReflectionTypeSymbol? _asSZArray; + ReflectionTypeSymbol? _asPointer; + ReflectionTypeSymbol? _asByRef; + ConcurrentDictionary? _genericTypeSymbols; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReflectionTypeImpl(IReflectionTypeSymbol symbol) + { + _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + } + + /// + /// Gets or creates the cached for the generic parameter type. + /// + /// + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) + { + if (genericTypeArguments is null) + throw new ArgumentNullException(nameof(genericTypeArguments)); + + if (_symbol.UnderlyingType.IsGenericTypeDefinition == false) + throw new InvalidOperationException(); + + if (_genericTypeSymbols == null) + Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); + + var __symbol = _symbol; + return _genericTypeSymbols.GetOrAdd(genericTypeArguments, _ => new ReflectionTypeSymbol(__symbol.Context, __symbol.ResolvingModule, __symbol.UnderlyingType.MakeGenericType(genericTypeArguments.Unpack()))); + } + + /// + public readonly IAssemblySymbol Assembly => _symbol.ResolveAssemblySymbol(_symbol.UnderlyingType.Assembly); + + /// + public readonly string? AssemblyQualifiedName => _symbol.UnderlyingType.AssemblyQualifiedName; + + /// + public readonly TypeAttributes Attributes => _symbol.UnderlyingType.Attributes; + + /// + public readonly ITypeSymbol? BaseType => _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.BaseType); + + /// + public readonly bool ContainsGenericParameters => _symbol.UnderlyingType.ContainsGenericParameters; + + /// + public readonly IMethodBaseSymbol? DeclaringMethod => _symbol.ResolveMethodBaseSymbol(_symbol.UnderlyingType.DeclaringMethod); + + /// + public readonly string? FullName => _symbol.UnderlyingType.FullName; + + /// + public readonly string? Namespace => _symbol.UnderlyingType.Namespace; + + /// + public readonly GenericParameterAttributes GenericParameterAttributes => _symbol.UnderlyingType.GenericParameterAttributes; + + /// + public readonly int GenericParameterPosition => _symbol.UnderlyingType.GenericParameterPosition; + + /// + public readonly ITypeSymbol[] GenericTypeArguments => _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GenericTypeArguments); + + /// + public readonly bool HasElementType => _symbol.UnderlyingType.HasElementType; + + /// + public readonly TypeCode TypeCode => Type.GetTypeCode(_symbol.UnderlyingType); + + /// + public readonly bool IsAbstract => _symbol.UnderlyingType.IsAbstract; + +#if NETFRAMEWORK + + /// + /// + /// There's no API to distinguish an array of rank 1 from a vector, + /// so we check if the type name ends in [], which indicates it's a vector + /// (non-vectors will have [*] or [,]). + /// + public readonly bool IsSZArray => _symbol.UnderlyingType.IsArray && _symbol.UnderlyingType.Name.EndsWith("[]"); + +#else + + /// + public readonly bool IsSZArray => _symbol.UnderlyingType.IsSZArray; + +#endif + + /// + public readonly bool IsArray => _symbol.UnderlyingType.IsArray; + + /// + public readonly bool IsAutoLayout => _symbol.UnderlyingType.IsAutoLayout; + + /// + public readonly bool IsExplicitLayout => _symbol.UnderlyingType.IsExplicitLayout; + + /// + public readonly bool IsByRef => _symbol.UnderlyingType.IsByRef; + + /// + public readonly bool IsClass => _symbol.UnderlyingType.IsClass; + + /// + public readonly bool IsEnum => _symbol.UnderlyingType.IsEnum; + + /// + public readonly bool IsInterface => _symbol.UnderlyingType.IsInterface; + + /// + public readonly bool IsConstructedGenericType => _symbol.UnderlyingType.IsConstructedGenericType; + + /// + public readonly bool IsGenericParameter => _symbol.UnderlyingType.IsGenericParameter; + + /// + public readonly bool IsGenericType => _symbol.UnderlyingType.IsGenericType; + + /// + public readonly bool IsGenericTypeDefinition => _symbol.UnderlyingType.IsGenericTypeDefinition; + + /// + public readonly bool IsLayoutSequential => _symbol.UnderlyingType.IsLayoutSequential; + + /// + public readonly bool IsNested => _symbol.UnderlyingType.IsNested; + + /// + public readonly bool IsNestedAssembly => _symbol.UnderlyingType.IsNestedAssembly; + + /// + public readonly bool IsNestedFamANDAssem => _symbol.UnderlyingType.IsNestedFamANDAssem; + + /// + public readonly bool IsNestedFamORAssem => _symbol.UnderlyingType.IsNestedFamORAssem; + + /// + public readonly bool IsNestedFamily => _symbol.UnderlyingType.IsNestedFamily; + + /// + public readonly bool IsNestedPrivate => _symbol.UnderlyingType.IsNestedPrivate; + + /// + public readonly bool IsNestedPublic => _symbol.UnderlyingType.IsNestedPublic; + + /// + public readonly bool IsNotPublic => _symbol.UnderlyingType.IsNotPublic; + + /// + public readonly bool IsPointer => _symbol.UnderlyingType.IsPointer; + +#if NET8_0_OR_GREATER + + /// + public readonly bool IsFunctionPointer => _symbol.UnderlyingType.IsFunctionPointer; + + /// + public readonly bool IsUnmanagedFunctionPointer => _symbol.UnderlyingType.IsUnmanagedFunctionPointer; + +#else + + /// + public readonly bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public readonly bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif + + /// + public readonly bool IsPrimitive => _symbol.UnderlyingType.IsPrimitive; + + /// + public readonly bool IsPublic => _symbol.UnderlyingType.IsPublic; + + /// + public readonly bool IsSealed => _symbol.UnderlyingType.IsSealed; + +#pragma warning disable SYSLIB0050 // Type or member is obsolete + /// + public readonly bool IsSerializable => _symbol.UnderlyingType.IsSerializable; +#pragma warning restore SYSLIB0050 // Type or member is obsolete + + /// + public readonly bool IsValueType => _symbol.UnderlyingType.IsValueType; + + /// + public readonly bool IsVisible => _symbol.UnderlyingType.IsVisible; + +#if NET6_0_OR_GREATER + + /// + public readonly bool IsSignatureType => _symbol.UnderlyingType.IsSignatureType; + +#else + + /// + public readonly bool IsSignatureType => throw new NotImplementedException(); + +#endif + + /// + public readonly bool IsSpecialName => _symbol.UnderlyingType.IsSpecialName; + + /// + public readonly IConstructorSymbol? TypeInitializer => _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.TypeInitializer); + + /// + public readonly int GetArrayRank() + { + return _symbol.UnderlyingType.GetArrayRank(); + } + + /// + public readonly IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null)); + } + + /// + public readonly IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor(types.Unpack())); + } + + /// + public readonly IConstructorSymbol[] GetConstructors() + { + return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors()); + } + + /// + public readonly IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + { + return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors(bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetDefaultMembers() + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetDefaultMembers()); + } + + /// + public readonly ITypeSymbol? GetElementType() + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetElementType()); + } + + /// + public readonly string? GetEnumName(object value) + { + return _symbol.UnderlyingType.GetEnumName(value); + } + + /// + public readonly string[] GetEnumNames() + { + return _symbol.UnderlyingType.GetEnumNames(); + } + + /// + public readonly ITypeSymbol GetEnumUnderlyingType() + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetEnumUnderlyingType()); + } + + /// + public readonly Array GetEnumValues() + { + return _symbol.UnderlyingType.GetEnumValues(); + } + + /// + public readonly IEventSymbol? GetEvent(string name) + { + return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name)); + } + + /// + public readonly IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + { + return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name, bindingAttr)); + } + + /// + public readonly IEventSymbol[] GetEvents() + { + return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents()); + } + + /// + public readonly IEventSymbol[] GetEvents(BindingFlags bindingAttr) + { + return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents(bindingAttr)); + } + + /// + public readonly IFieldSymbol? GetField(string name) + { + return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name)); + } + + /// + public readonly IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name, bindingAttr)); + } + + /// + public readonly IFieldSymbol[] GetFields() + { + return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields()); + } + + /// + public readonly IFieldSymbol[] GetFields(BindingFlags bindingAttr) + { + return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields(bindingAttr)); + } + + /// + public readonly ITypeSymbol[] GetGenericArguments() + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericArguments()); + } + + /// + public readonly ITypeSymbol[] GetGenericParameterConstraints() + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericParameterConstraints()); + } + + /// + public readonly ITypeSymbol GetGenericTypeDefinition() + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetGenericTypeDefinition()); + } + + /// + public readonly ITypeSymbol? GetInterface(string name) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name)); + } + + /// + public readonly ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name, ignoreCase)); + } + + /// + public readonly InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + throw new NotImplementedException(); + } + + /// + public readonly ITypeSymbol[] GetInterfaces(bool inherit = true) + { + if (inherit) + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); + } + + /// + public readonly IMemberSymbol[] GetMember(string name) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name)); + } + + /// + public readonly IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, type, bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers(bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetMembers() + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers()); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, types.Unpack())); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { +#if NETFRAMEWORK + throw new NotImplementedException(); +#else + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers)); +#endif + } + + /// + public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { +#if NETFRAMEWORK + throw new NotImplementedException(); +#else + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers)); +#endif + } + + /// + public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { +#if NETFRAMEWORK + throw new NotImplementedException(); +#else + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, genericParameterCount, types.Unpack(), modifiers)); +#endif + } + + /// + public readonly IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + { + return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods(bindingAttr)); + } + + /// + public readonly IMethodSymbol[] GetMethods() + { + return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods()); + } + + /// + public readonly ITypeSymbol? GetNestedType(string name) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name)); + } + + /// + public readonly ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name, bindingAttr)); + } + + /// + public readonly ITypeSymbol[] GetNestedTypes() + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes()); + } + + /// + public readonly ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes(bindingAttr)); + } + + /// + public readonly IPropertySymbol[] GetProperties() + { + return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties()); + } + + /// + public readonly IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + { + return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties(bindingAttr)); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, types.Unpack())); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, bindingAttr)); + } + + /// + public readonly IPropertySymbol? GetProperty(string name) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name)); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack())); + } + + /// + public readonly bool IsAssignableFrom(ITypeSymbol? c) + { + return _symbol.UnderlyingType.IsAssignableFrom(c?.Unpack()); + } + + /// + public readonly bool IsEnumDefined(object value) + { + return _symbol.UnderlyingType.IsEnumDefined(value); + } + + /// + public readonly bool IsSubclassOf(ITypeSymbol c) + { + return _symbol.UnderlyingType.IsSubclassOf(c.Unpack()); + } + + /// + public IReflectionTypeSymbol MakeArrayType() + { + if (_asSZArray == null) + Interlocked.CompareExchange(ref _asSZArray, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType()), null); + + return _asSZArray; + } + + /// + public IReflectionTypeSymbol MakeArrayType(int rank) + { + if (rank == 1) + return MakeArrayType(); + + if (_asArray == null) + Interlocked.CompareExchange(ref _asArray, new ReflectionTypeSymbol?[32], null); + + ref var asArray = ref _asArray[rank]; + if (asArray == null) + Interlocked.CompareExchange(ref asArray, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType(rank)), null); + + return asArray; + } + + /// + public IReflectionTypeSymbol MakeByRefType() + { + if (_asByRef == null) + Interlocked.CompareExchange(ref _asByRef, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeByRefType()), null); + + return _asByRef; + } + + /// + public IReflectionTypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return GetOrCreateGenericTypeSymbol(typeArguments); + } + + /// + public IReflectionTypeSymbol MakePointerType() + { + if (_asPointer == null) + Interlocked.CompareExchange(ref _asPointer, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakePointerType()), null); + + return _asPointer; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index d59075d06d..1ff52d6809 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -1,67 +1,39 @@ using System; -using System.Collections.Concurrent; -using System.Diagnostics; +using System.Diagnostics.CodeAnalysis; using System.Reflection; -using System.Threading; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionTypeSymbol : ReflectionMemberSymbol, ITypeSymbol + class ReflectionTypeSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol { - const int MAX_CAPACITY = 65536 * 2; - - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - - Type _type; - - ReflectionTypeSymbol?[]? _asArray; - ReflectionTypeSymbol? _asSZArray; - ReflectionTypeSymbol? _asPointer; - ReflectionTypeSymbol? _asByRef; - ConcurrentDictionary? _genericTypeSymbols; + readonly Type _type; + ReflectionTypeImpl _impl; /// /// Initializes a new instance. /// /// - /// + /// /// - public ReflectionTypeSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, Type type) : - base(context, module, type) + public ReflectionTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, Type type) : + base(context, resolvingModule, null, type) { - Debug.Assert(module.ReflectionObject == type.Module); _type = type ?? throw new ArgumentNullException(nameof(type)); + _impl = new ReflectionTypeImpl(this); } - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - internal ReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) - { - if (genericTypeArguments is null) - throw new ArgumentNullException(nameof(genericTypeArguments)); - - if (_type.IsGenericTypeDefinition == false) - throw new InvalidOperationException(); - - if (_genericTypeSymbols == null) - Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); - - return _genericTypeSymbols.GetOrAdd( - genericTypeArguments, - _ => new ReflectionTypeSymbol(Context, ContainingModule, _type.MakeGenericType(genericTypeArguments.Unpack()))); - } + /// + public Type UnderlyingType => _type; /// /// Resolves the symbol for the specified type. /// /// /// - protected internal override ReflectionTypeSymbol ResolveTypeSymbol(Type type) + [return: NotNullIfNotNull(nameof(type))] + public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) { if (type == _type) return this; @@ -69,616 +41,510 @@ protected internal override ReflectionTypeSymbol ResolveTypeSymbol(Type type) return base.ResolveTypeSymbol(type); } - /// - /// Gets the wrapped . - /// - internal new Type ReflectionObject => _type; + #region ITypeSymbol /// - public IAssemblySymbol Assembly => Context.GetOrCreateAssemblySymbol(_type.Assembly); + public TypeAttributes Attributes => _impl.Attributes; /// - public string? AssemblyQualifiedName => _type.AssemblyQualifiedName; + public IAssemblySymbol Assembly => _impl.Assembly; /// - public TypeAttributes Attributes => _type.Attributes; + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; /// - public ITypeSymbol? BaseType => _type.BaseType != null ? ResolveTypeSymbol(_type.BaseType) : null; + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; /// - public bool ContainsGenericParameters => _type.ContainsGenericParameters; + public string? FullName => _impl.FullName; /// - public IMethodBaseSymbol? DeclaringMethod => _type.DeclaringMethod is MethodInfo m ? ResolveMethodSymbol(m) : null; + public string? Namespace => _impl.Namespace; /// - public string? FullName => _type.FullName; + public TypeCode TypeCode => _impl.TypeCode; /// - public string? Namespace => _type.Namespace; + public ITypeSymbol? BaseType => _impl.BaseType; /// - public GenericParameterAttributes GenericParameterAttributes => _type.GenericParameterAttributes; + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; /// - public int GenericParameterPosition => _type.GenericParameterPosition; + public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; /// - public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(_type.GenericTypeArguments); + public int GenericParameterPosition => _impl.GenericParameterPosition; /// - public bool HasElementType => _type.HasElementType; + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; /// - public TypeCode TypeCode => Type.GetTypeCode(_type); + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; /// - public bool IsAbstract => _type.IsAbstract; - -#if NETFRAMEWORK + public bool IsGenericType => _impl.IsGenericType; /// - /// - /// There's no API to distinguish an array of rank 1 from a vector, - /// so we check if the type name ends in [], which indicates it's a vector - /// (non-vectors will have [*] or [,]). - /// - public bool IsSZArray => _type.IsArray && _type.Name.EndsWith("[]"); - -#else + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; /// - public bool IsSZArray => _type.IsSZArray; - -#endif + public bool IsGenericParameter => _impl.IsGenericParameter; /// - public bool IsArray => _type.IsArray; + public bool IsAutoLayout => _impl.IsAutoLayout; /// - public bool IsAutoLayout => _type.IsAutoLayout; + public bool IsExplicitLayout => _impl.IsExplicitLayout; /// - public bool IsExplicitLayout => _type.IsExplicitLayout; + public bool IsLayoutSequential => _impl.IsLayoutSequential; /// - public bool IsByRef => _type.IsByRef; + public bool HasElementType => _impl.HasElementType; /// - public bool IsClass => _type.IsClass; + public bool IsClass => _impl.IsClass; /// - public bool IsEnum => _type.IsEnum; + public bool IsValueType => _impl.IsValueType; /// - public bool IsInterface => _type.IsInterface; + public bool IsInterface => _impl.IsInterface; /// - public bool IsConstructedGenericType => _type.IsConstructedGenericType; + public bool IsPrimitive => _impl.IsPrimitive; /// - public bool IsGenericParameter => _type.IsGenericParameter; + public bool IsSZArray => _impl.IsSZArray; /// - public bool IsGenericType => _type.IsGenericType; + public bool IsArray => _impl.IsArray; /// - public bool IsGenericTypeDefinition => _type.IsGenericTypeDefinition; + public bool IsEnum => _impl.IsEnum; /// - public bool IsLayoutSequential => _type.IsLayoutSequential; + public bool IsPointer => _impl.IsPointer; /// - public bool IsNested => _type.IsNested; + public bool IsFunctionPointer => _impl.IsFunctionPointer; /// - public bool IsNestedAssembly => _type.IsNestedAssembly; + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; /// - public bool IsNestedFamANDAssem => _type.IsNestedFamANDAssem; + public bool IsByRef => _impl.IsByRef; /// - public bool IsNestedFamORAssem => _type.IsNestedFamORAssem; + public bool IsAbstract => _impl.IsAbstract; /// - public bool IsNestedFamily => _type.IsNestedFamily; + public bool IsSealed => _impl.IsSealed; /// - public bool IsNestedPrivate => _type.IsNestedPrivate; + public bool IsVisible => _impl.IsVisible; /// - public bool IsNestedPublic => _type.IsNestedPublic; + public bool IsPublic => _impl.IsPublic; /// - public bool IsNotPublic => _type.IsNotPublic; + public bool IsNotPublic => _impl.IsNotPublic; /// - public bool IsPointer => _type.IsPointer; - -#if NET8_0_OR_GREATER + public bool IsNested => _impl.IsNested; /// - public bool IsFunctionPointer => _type.IsFunctionPointer; + public bool IsNestedAssembly => _impl.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _type.IsUnmanagedFunctionPointer; - -#else + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; /// - public bool IsFunctionPointer => throw new NotImplementedException(); + public bool IsNestedFamily => _impl.IsNestedFamily; /// - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; /// - public bool IsPrimitive => _type.IsPrimitive; + public bool IsNestedPrivate => _impl.IsNestedPrivate; /// - public bool IsPublic => _type.IsPublic; + public bool IsNestedPublic => _impl.IsNestedPublic; /// - public bool IsSealed => _type.IsSealed; + public bool IsSerializable => _impl.IsSerializable; -#pragma warning disable SYSLIB0050 // Type or member is obsolete /// - public bool IsSerializable => _type.IsSerializable; -#pragma warning restore SYSLIB0050 // Type or member is obsolete + public bool IsSignatureType => _impl.IsSignatureType; /// - public bool IsValueType => _type.IsValueType; + public bool IsSpecialName => _impl.IsSpecialName; /// - public bool IsVisible => _type.IsVisible; - -#if NET6_0_OR_GREATER - - /// - public bool IsSignatureType => _type.IsSignatureType; - -#else - - /// - public bool IsSignatureType => throw new NotImplementedException(); - -#endif - - /// - public bool IsSpecialName => _type.IsSpecialName; - - /// - public IConstructorSymbol? TypeInitializer => _type.TypeInitializer is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; + public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); /// public int GetArrayRank() { - return _type.GetArrayRank(); - } - - /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) - { - return _type.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; - } - - /// - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return _type.GetConstructor(types.Unpack()) is ConstructorInfo ctor ? ResolveConstructorSymbol(ctor) : null; - } - - /// - public IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(_type.GetConstructors()); - } - - /// - public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(_type.GetConstructors(bindingAttr)); + return _impl.GetArrayRank(); } /// public IMemberSymbol[] GetDefaultMembers() { - return ResolveMemberSymbols(_type.GetDefaultMembers()); + return _impl.GetDefaultMembers(); } /// public ITypeSymbol? GetElementType() { - return _type.GetElementType() is Type t ? ResolveTypeSymbol(t) : null; + return _impl.GetElementType(); } /// public string? GetEnumName(object value) { - return _type.GetEnumName(value); + return _impl.GetEnumName(value); } /// public string[] GetEnumNames() { - return _type.GetEnumNames(); + return _impl.GetEnumNames(); } /// public ITypeSymbol GetEnumUnderlyingType() { - return ResolveTypeSymbol(_type.GetEnumUnderlyingType()); + return _impl.GetEnumUnderlyingType(); } /// - public Array GetEnumValues() - { - return _type.GetEnumValues(); - } - - /// - public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + public ITypeSymbol[] GetGenericArguments() { - throw new NotImplementedException(); + return _impl.GetGenericArguments(); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetGenericParameterConstraints() { - return _type.GetEvent(name) is { } f ? ResolveEventSymbol(f) : null; + return _impl.GetGenericParameterConstraints(); } /// - public IEventSymbol[] GetEvents() + public ITypeSymbol GetGenericTypeDefinition() { - return ResolveEventSymbols(_type.GetEvents()); + return _impl.GetGenericTypeDefinition(); } /// - public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name) { - return ResolveEventSymbols(_type.GetEvents(bindingAttr)); + return _impl.GetInterface(name); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _type.GetField(name) is FieldInfo f ? ResolveFieldSymbol(f) : null; + return _impl.GetInterface(name, ignoreCase); } /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _type.GetField(name, bindingAttr) is FieldInfo f ? ResolveFieldSymbol(f) : null; + return _impl.GetInterfaces(inherit); } /// - public IFieldSymbol[] GetFields() + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return ResolveFieldSymbols(_type.GetFields()); + return _impl.GetInterfaceMap(interfaceType); } /// - public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name) { - return ResolveFieldSymbols(_type.GetFields(bindingAttr)); + return _impl.GetMember(name); } /// - public ITypeSymbol[] GetGenericArguments() + public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) { - return ResolveTypeSymbols(_type.GetGenericArguments()); + return _impl.GetMember(name, bindingAttr); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) { - return ResolveTypeSymbols(_type.GetGenericParameterConstraints()); + return _impl.GetMember(name, type, bindingAttr); } /// - public ITypeSymbol GetGenericTypeDefinition() + public IMemberSymbol[] GetMembers() { - return ResolveTypeSymbol(_type.GetGenericTypeDefinition()); + return _impl.GetMembers(); } /// - public ITypeSymbol? GetInterface(string name) + public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) { - return _type.GetInterface(name) is { } i ? ResolveTypeSymbol(i) : null; + return _impl.GetMembers(bindingAttr); } - /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _type.GetInterface(name, ignoreCase) is { } i ? ResolveTypeSymbol(i) : null; + return _impl.GetConstructor(types); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) { - throw new NotImplementedException(); + return _impl.GetConstructor(bindingAttr, types); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IConstructorSymbol[] GetConstructors() { - if (inherit) - return ResolveTypeSymbols(_type.GetInterfaces()); - else - throw new NotImplementedException(); + return _impl.GetConstructors(); } /// - public IMemberSymbol[] GetMember(string name) + public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) { - return ResolveMemberSymbols(_type.GetMember(name)); + return _impl.GetConstructors(bindingAttr); } /// - public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return ResolveMemberSymbols(_type.GetMember(name, bindingAttr)); + return _impl.GetField(name); } /// - public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) { - return ResolveMemberSymbols(_type.GetMember(name, type, bindingAttr)); + return _impl.GetField(name, bindingAttr); } /// - public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + public IFieldSymbol[] GetFields() { - return ResolveMemberSymbols(_type.GetMembers(bindingAttr)); + return _impl.GetFields(); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol[] GetFields(BindingFlags bindingAttr) { - return ResolveMemberSymbols(_type.GetMembers()); + return _impl.GetFields(bindingAttr); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name) { - return _type.GetMethod(name, bindingAttr) is { } m ? ResolveMethodSymbol(m) : null; + return _impl.GetMethod(name); } /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _type.GetMethod(name, types.Unpack()) is { } m ? ResolveMethodSymbol(m) : null; + return _impl.GetMethod(name, types); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) { - return _type.GetMethod(name, bindingAttr, null, types.Unpack(), null) is { } m ? ResolveMethodSymbol(m) : null; + return _impl.GetMethod(name, bindingAttr); } /// - public IMethodSymbol? GetMethod(string name) + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) { - return _type.GetMethod(name) is { } m ? ResolveMethodSymbol(m) : null; + return _impl.GetMethod(name, bindingAttr, types); } /// public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - return _type.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); } /// public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { -#if NETFRAMEWORK - throw new NotImplementedException(); -#else - return _type.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; -#endif + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); } /// public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) { -#if NETFRAMEWORK - throw new NotImplementedException(); -#else - return _type.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; -#endif + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); } /// public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - return _type.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; + return _impl.GetMethod(name, bindingAttr, types, modifiers); } /// public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) { -#if NETFRAMEWORK - throw new NotImplementedException(); -#else - return _type.GetMethod(name, genericParameterCount, types.Unpack(), modifiers) is { } m ? ResolveMethodSymbol(m) : null; -#endif + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); } /// public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) { - return ResolveMethodSymbols(_type.GetMethods(bindingAttr)); + return _impl.GetMethods(bindingAttr); } /// - public IMethodSymbol[] GetMethods() + public IPropertySymbol? GetProperty(string name) { - return ResolveMethodSymbols(_type.GetMethods()); + return _impl.GetProperty(name); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) { - return _type.GetNestedType(name) is Type t ? ResolveTypeSymbol(t) : null; + return _impl.GetProperty(name, bindingAttr); } /// - public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _type.GetNestedType(name, bindingAttr) is Type t ? ResolveTypeSymbol(t) : null; + return _impl.GetProperty(name, types); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return ResolveTypeSymbols(_type.GetNestedTypes()); + return _impl.GetProperty(name, returnType, types); } /// - public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return ResolveTypeSymbols(_type.GetNestedTypes(bindingAttr)); + return _impl.GetProperty(name, returnType); } /// public IPropertySymbol[] GetProperties() { - return ResolvePropertySymbols(_type.GetProperties()); + return _impl.GetProperties(); } /// public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) { - return ResolvePropertySymbols(_type.GetProperties(bindingAttr)); + return _impl.GetProperties(bindingAttr); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IEventSymbol? GetEvent(string name) { - return _type.GetProperty(name, types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; + return _impl.GetEvent(name); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) { - return _type.GetProperty(name, returnType?.Unpack(), types.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; + return _impl.GetEvent(name, bindingAttr); } /// - public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + public IEventSymbol[] GetEvents() { - return _type.GetProperty(name, bindingAttr) is { } p ? ResolvePropertySymbol(p) : null; + return _impl.GetEvents(); } /// - public IPropertySymbol? GetProperty(string name) + public IEventSymbol[] GetEvents(BindingFlags bindingAttr) { - return _type.GetProperty(name) is { } p ? ResolvePropertySymbol(p) : null; + return _impl.GetEvents(bindingAttr); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public ITypeSymbol? GetNestedType(string name) { - return _type.GetProperty(name, returnType?.Unpack()) is { } p ? ResolvePropertySymbol(p) : null; + return _impl.GetNestedType(name); } /// - public bool IsAssignableFrom(ITypeSymbol? c) + public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) { - return _type.IsAssignableFrom(c?.Unpack()); + return _impl.GetNestedType(name, bindingAttr); } /// - public bool IsEnumDefined(object value) + public ITypeSymbol[] GetNestedTypes() { - return _type.IsEnumDefined(value); + return _impl.GetNestedTypes(); } /// - public bool IsSubclassOf(ITypeSymbol c) + public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) { - return _type.IsSubclassOf(c.Unpack()); + return _impl.GetNestedTypes(); } /// - public ITypeSymbol MakeArrayType() + public bool IsAssignableFrom(ITypeSymbol? c) { - if (_asSZArray == null) - Interlocked.CompareExchange(ref _asSZArray, new ReflectionTypeSymbol(Context, ContainingModule, _type.MakeArrayType()), null); - - return _asSZArray; + return _impl.IsAssignableFrom(c); } /// - public ITypeSymbol MakeArrayType(int rank) + public bool IsSubclassOf(ITypeSymbol c) { - if (rank == 1) - return MakeArrayType(); - - if (_asArray == null) - Interlocked.CompareExchange(ref _asArray, new ReflectionTypeSymbol?[32], null); - - ref var asArray = ref _asArray[rank]; - if (asArray == null) - Interlocked.CompareExchange(ref asArray, new ReflectionTypeSymbol(Context, ContainingModule, _type.MakeArrayType(rank)), null); + return _impl.IsSubclassOf(c); + } - return asArray; + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); } /// - public ITypeSymbol MakeByRefType() + public ITypeSymbol MakeArrayType() { - if (_asByRef == null) - Interlocked.CompareExchange(ref _asByRef, new ReflectionTypeSymbol(Context, ContainingModule, _type.MakeByRefType()), null); + return _impl.MakeArrayType(); + } - return _asByRef; + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); } /// public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return GetOrCreateGenericTypeSymbol(typeArguments); + return _impl.MakeGenericType(typeArguments); } /// public ITypeSymbol MakePointerType() { - if (_asPointer == null) - Interlocked.CompareExchange(ref _asPointer, new ReflectionTypeSymbol(Context, ContainingModule, _type.MakePointerType()), null); - - return _asPointer; + return _impl.MakePointerType(); } - /// - /// Sets the reflection type. Used by the builder infrastructure to complete a symbol. - /// - /// - internal void Complete(Type type) + /// + public ITypeSymbol MakeByRefType() { - ResolveTypeSymbol(_type = type); - base.Complete(_type); - - ContainingModule.Complete(_type.Module); - - foreach (var i in _type.GetConstructors(DefaultBindingFlags)) - ResolveConstructorSymbol(i).Complete(i); - - foreach (var i in _type.GetMethods(DefaultBindingFlags)) - ResolveMethodSymbol(i).Complete(i); - - foreach (var i in _type.GetFields(DefaultBindingFlags)) - ResolveFieldSymbol(i).Complete(i); - - foreach (var i in _type.GetProperties(DefaultBindingFlags)) - ResolvePropertySymbol(i).Complete(i); - - foreach (var i in _type.GetEvents(DefaultBindingFlags)) - ResolveEventSymbol(i).Complete(i); + return _impl.MakeByRefType(); } + #endregion + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index 30d9881679..fd823ad8ef 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -14,7 +14,10 @@ static class ReflectionUtil /// public static Module Unpack(this IModuleSymbol module) { - return ((ReflectionModuleSymbol)module).ReflectionObject; + if (module is IReflectionModuleSymbol symbol) + return symbol.UnderlyingModule; + + throw new InvalidOperationException(); } /// @@ -38,7 +41,10 @@ public static Module[] Unpack(this IModuleSymbol[] modules) /// public static Type Unpack(this ITypeSymbol type) { - return ((ReflectionTypeSymbol)type).ReflectionObject; + if (type is IReflectionTypeSymbol symbol) + return symbol.UnderlyingType; + + throw new InvalidOperationException(); } /// @@ -76,7 +82,10 @@ public static Type[][] Unpack(this ITypeSymbol[][] types) /// public static MemberInfo Unpack(this IMemberSymbol member) { - return ((ReflectionMemberSymbol)member).ReflectionObject; + if (member is IReflectionMemberSymbol symbol) + return symbol.UnderlyingMember; + + throw new InvalidOperationException(); } /// @@ -100,7 +109,10 @@ public static MemberInfo[] Unpack(this IMemberSymbol[] members) /// public static ConstructorInfo Unpack(this IConstructorSymbol ctor) { - return ((ReflectionConstructorSymbol)ctor).ReflectionObject; + if (ctor is IReflectionConstructorSymbol symbol) + return symbol.UnderlyingConstructor; + + throw new InvalidOperationException(); } /// @@ -124,7 +136,10 @@ public static ConstructorInfo[] Unpack(this IConstructorSymbol[] ctor) /// public static MethodInfo Unpack(this IMethodSymbol ctor) { - return ((ReflectionMethodSymbol)ctor).ReflectionObject; + if (ctor is IReflectionMethodSymbol symbol) + return symbol.UnderlyingMethod; + + throw new InvalidOperationException(); } /// @@ -141,6 +156,60 @@ public static MethodInfo[] Unpack(this IMethodSymbol[] ctor) return a; } + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static FieldInfo Unpack(this IFieldSymbol field) + { + if (field is IReflectionFieldSymbol symbol) + return symbol.UnderlyingField; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static FieldInfo[] Unpack(this IFieldSymbol[] fields) + { + var a = new FieldInfo[fields.Length]; + for (int i = 0; i < fields.Length; i++) + a[i] = fields[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static PropertyInfo Unpack(this IPropertySymbol property) + { + if (property is IReflectionPropertySymbol symbol) + return symbol.UnderlyingProperty; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static PropertyInfo[] Unpack(this IPropertySymbol[] properties) + { + var a = new PropertyInfo[properties.Length]; + for (int i = 0; i < properties.Length; i++) + a[i] = properties[i].Unpack(); + + return a; + } + } } diff --git a/src/IKVM.Runtime/Annotation.cs b/src/IKVM.Runtime/Annotation.cs index 9a53b8cb65..9e4d156f49 100644 --- a/src/IKVM.Runtime/Annotation.cs +++ b/src/IKVM.Runtime/Annotation.cs @@ -26,6 +26,7 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection.Emit; @@ -308,14 +309,14 @@ private static object[] ValueQualifyClassNames(RuntimeClassLoader loader, object } } - internal abstract void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation); - internal abstract void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation); - internal abstract void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation); - internal abstract void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation); - internal abstract void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation); - internal abstract void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation); + internal abstract void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation); + internal abstract void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation); + internal abstract void Apply(RuntimeClassLoader loader, IFieldSymbolBuilder fb, object annotation); + internal abstract void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder pb, object annotation); + internal abstract void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder ab, object annotation); + internal abstract void Apply(RuntimeClassLoader loader, IPropertySymbolBuilder pb, object annotation); - internal virtual void ApplyReturnValue(RuntimeClassLoader loader, MethodBuilder mb, ref ParameterBuilder pb, object annotation) + internal virtual void ApplyReturnValue(RuntimeClassLoader loader, IMethodSymbolBuilder mb, ref IParameterSymbolBuilder pb, object annotation) { } diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index 12e0e0bbc6..cea132a71e 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -33,15 +33,12 @@ Jeroen Frijters using IKVM.ByteCode.Decoding; using IKVM.ByteCode.Encoding; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.IkvmReflection; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; -using Type = IKVM.Reflection.Type; +#if IMPORTER || EXPORTER #else -using System.Reflection; -using System.Reflection.Emit; #endif #if IMPORTER @@ -61,10 +58,10 @@ class AttributeHelper #if IMPORTER - CustomAttributeBuilder compilerGeneratedAttribute; - CustomAttributeBuilder ghostInterfaceAttribute; - CustomAttributeBuilder deprecatedAttribute; - CustomAttributeBuilder editorBrowsableNever; + ICustomAttributeBuilder compilerGeneratedAttribute; + ICustomAttributeBuilder ghostInterfaceAttribute; + ICustomAttributeBuilder deprecatedAttribute; + ICustomAttributeBuilder editorBrowsableNever; IConstructorSymbol implementsAttribute; IConstructorSymbol throwsAttribute; IConstructorSymbol sourceFileAttribute; @@ -75,7 +72,7 @@ class AttributeHelper IConstructorSymbol methodParametersAttribute; IConstructorSymbol runtimeVisibleTypeAnnotationsAttribute; IConstructorSymbol constantPoolAttribute; - CustomAttributeBuilder paramArrayAttribute; + ICustomAttributeBuilder paramArrayAttribute; IConstructorSymbol nonNestedInnerClassAttribute; IConstructorSymbol nonNestedOuterClassAttribute; @@ -108,8 +105,8 @@ class AttributeHelper ITypeSymbol typeofRuntimeVisibleTypeAnnotationsAttribute; ITypeSymbol typeofConstantPoolAttribute; ITypeSymbol typeofDebuggableAttribute; - CustomAttributeBuilder hideFromJavaAttribute; - CustomAttributeBuilder hideFromReflection; + ICustomAttributeBuilder hideFromJavaAttribute; + ICustomAttributeBuilder hideFromReflection; IConstructorSymbol debuggableAttribute; #if IMPORTER @@ -168,9 +165,9 @@ class AttributeHelper ITypeSymbol TypeOfDebuggableAttribute => typeofDebuggableAttribute ??= context.Resolver.ResolveCoreType(typeof(DebuggableAttribute).FullName); - CustomAttributeBuilder HideFromJavaAttributeBuilder => hideFromJavaAttribute ??= new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor([]).AsReflection(), []); + ICustomAttributeBuilder HideFromJavaAttributeBuilder => hideFromJavaAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([]), []); - CustomAttributeBuilder HideFromReflectionBuilder => hideFromReflection ??= new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]).AsReflection(), [HideFromJavaFlags.Reflection | HideFromJavaFlags.StackTrace | HideFromJavaFlags.StackWalk]); + ICustomAttributeBuilder HideFromReflectionBuilder => hideFromReflection ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [HideFromJavaFlags.Reflection | HideFromJavaFlags.StackTrace | HideFromJavaFlags.StackWalk]); /// /// Loads the given managed type from the runtime assembly. @@ -253,32 +250,32 @@ object ParseValue(RuntimeClassLoader loader, RuntimeJavaType tw, string val) } } - internal void SetCustomAttribute(RuntimeClassLoader loader, TypeBuilder tb, IKVM.Tools.Importer.MapXml.Attribute attr) + internal void SetCustomAttribute(RuntimeClassLoader loader, ITypeSymbolBuilder tb, IKVM.Tools.Importer.MapXml.Attribute attr) { tb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); } - internal void SetCustomAttribute(RuntimeClassLoader loader, FieldBuilder fb, IKVM.Tools.Importer.MapXml.Attribute attr) + internal void SetCustomAttribute(RuntimeClassLoader loader, IFieldSymbolBuilder fb, IKVM.Tools.Importer.MapXml.Attribute attr) { fb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); } - internal void SetCustomAttribute(RuntimeClassLoader loader, ParameterBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) + internal void SetCustomAttribute(RuntimeClassLoader loader, IParameterSymbolBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) { pb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); } - internal void SetCustomAttribute(RuntimeClassLoader loader, MethodBuilder mb, IKVM.Tools.Importer.MapXml.Attribute attr) + internal void SetCustomAttribute(RuntimeClassLoader loader, IMethodSymbolBuilder mb, IKVM.Tools.Importer.MapXml.Attribute attr) { mb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); } - internal void SetCustomAttribute(RuntimeClassLoader loader, PropertyBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) + internal void SetCustomAttribute(RuntimeClassLoader loader, IPropertySymbolBuilder pb, IKVM.Tools.Importer.MapXml.Attribute attr) { pb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); } - internal void SetCustomAttribute(RuntimeClassLoader loader, AssemblyBuilder ab, IKVM.Tools.Importer.MapXml.Attribute attr) + internal void SetCustomAttribute(RuntimeClassLoader loader, IAssemblySymbolBuilder ab, IKVM.Tools.Importer.MapXml.Attribute attr) { ab.SetCustomAttribute(CreateCustomAttribute(loader, attr)); } @@ -312,7 +309,7 @@ void GetAttributeArgsAndTypes(RuntimeClassLoader loader, IKVM.Tools.Importer.Map } } - CustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr) + ICustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr) { // TODO add error handling GetAttributeArgsAndTypes(loader, attr, out var argTypes, out var args); @@ -351,7 +348,7 @@ CustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Too } } - return new CustomAttributeBuilder(ci.AsReflection(), args, namedProperties.AsReflection(), propertyValues, namedFields.AsReflection(), fieldValues); + return context.Resolver.Symbols.CreateCustomAttribute(ci, args, namedProperties, propertyValues, namedFields, fieldValues); } else { @@ -383,153 +380,142 @@ CustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Too mw.Link(); var ci = (mw.GetMethod() as IConstructorSymbol) ?? ((IConstructorSymbol)mw.GetMethod()); - return new CustomAttributeBuilder(ci.AsReflection(), args, namedFields.AsReflection(), fieldValues); + return context.Resolver.Symbols.CreateCustomAttribute(ci, args, namedFields, fieldValues); } } - CustomAttributeBuilder GetEditorBrowsableNever() + ICustomAttributeBuilder GetEditorBrowsableNever() { if (editorBrowsableNever == null) { - var typeofEditorBrowsableAttribute = context.Resolver.ResolveCoreType(typeof(EditorBrowsableAttribute).FullName).AsReflection(); - var typeofEditorBrowsableState = context.Resolver.ResolveCoreType(typeof(EditorBrowsableState).FullName).AsReflection(); - var ctor = (ConstructorInfo)typeofEditorBrowsableAttribute.__CreateMissingMethod(ConstructorInfo.ConstructorName, CallingConventions.Standard | CallingConventions.HasThis, null, default, new Type[] { typeofEditorBrowsableState }, null); - editorBrowsableNever = CustomAttributeBuilder.__FromBlob(ctor, new byte[] { 01, 00, 01, 00, 00, 00, 00, 00 }); + var typeofEditorBrowsableAttribute = context.Resolver.ResolveCoreType(typeof(EditorBrowsableAttribute).FullName); + var typeofEditorBrowsableState = context.Resolver.ResolveCoreType(typeof(EditorBrowsableState).FullName); + var ctor = typeofEditorBrowsableAttribute.GetConstructor([typeofEditorBrowsableState]); + editorBrowsableNever = context.Resolver.Symbols.CreateCustomAttribute(ctor, [EditorBrowsableState.Never]); } return editorBrowsableNever; } - internal void SetCompilerGenerated(TypeBuilder tb) + internal void SetCompilerGenerated(ITypeSymbolBuilder tb) { - compilerGeneratedAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).AsReflection().GetConstructor([]), Array.Empty()); + compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); tb.SetCustomAttribute(compilerGeneratedAttribute); } - internal void SetCompilerGenerated(MethodBuilder mb) + internal void SetCompilerGenerated(IMethodSymbolBuilder mb) { - compilerGeneratedAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).AsReflection().GetConstructor([]), Array.Empty()); + compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); mb.SetCustomAttribute(compilerGeneratedAttribute); } - internal void SetEditorBrowsableNever(TypeBuilder tb) + internal void SetEditorBrowsableNever(ITypeSymbolBuilder tb) { tb.SetCustomAttribute(GetEditorBrowsableNever()); } - internal void SetEditorBrowsableNever(MethodBuilder mb) + internal void SetEditorBrowsableNever(IMethodSymbolBuilder mb) { mb.SetCustomAttribute(GetEditorBrowsableNever()); } - internal void SetEditorBrowsableNever(PropertyBuilder pb) + internal void SetEditorBrowsableNever(IPropertySymbolBuilder pb) { pb.SetCustomAttribute(GetEditorBrowsableNever()); } - internal void SetDeprecatedAttribute(MethodBuilder mb) + internal void SetDeprecatedAttribute(IMethodSymbolBuilder mb) { - if (deprecatedAttribute == null) - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); - + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); mb.SetCustomAttribute(deprecatedAttribute); } - internal void SetDeprecatedAttribute(TypeBuilder tb) + internal void SetDeprecatedAttribute(ITypeSymbolBuilder tb) { - if (deprecatedAttribute == null) - { - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); - } - + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); tb.SetCustomAttribute(deprecatedAttribute); } - internal void SetDeprecatedAttribute(FieldBuilder fb) + internal void SetDeprecatedAttribute(IFieldSymbolBuilder fb) { - if (deprecatedAttribute == null) - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); - + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); fb.SetCustomAttribute(deprecatedAttribute); } - internal void SetDeprecatedAttribute(PropertyBuilder pb) + internal void SetDeprecatedAttribute(IPropertySymbolBuilder pb) { - if (deprecatedAttribute == null) - { - deprecatedAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]).AsReflection(), []); - } + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); pb.SetCustomAttribute(deprecatedAttribute); } - internal void SetThrowsAttribute(MethodBuilder mb, string[] exceptions) + internal void SetThrowsAttribute(IMethodSymbolBuilder mb, string[] exceptions) { if (exceptions != null && exceptions.Length != 0) { throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); exceptions = UnicodeUtil.EscapeInvalidSurrogates(exceptions); - mb.SetCustomAttribute(new CustomAttributeBuilder(throwsAttribute.AsReflection(), [exceptions])); + mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(throwsAttribute, [exceptions])); } } - internal void SetGhostInterface(TypeBuilder typeBuilder) + internal void SetGhostInterface(ITypeSymbolBuilder typeBuilder) { - ghostInterfaceAttribute ??= new CustomAttributeBuilder(TypeOfGhostInterfaceAttribute.GetConstructor([]).AsReflection(), []); + ghostInterfaceAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfGhostInterfaceAttribute.GetConstructor([]), []); typeBuilder.SetCustomAttribute(ghostInterfaceAttribute); } - internal void SetNonNestedInnerClass(TypeBuilder typeBuilder, string className) + internal void SetNonNestedInnerClass(ITypeSymbolBuilder typeBuilder, string className) { nonNestedInnerClassAttribute ??= TypeOfNonNestedInnerClassAttribute.GetConstructor([context.Types.String]); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(nonNestedInnerClassAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(className)])); + typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(nonNestedInnerClassAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className)])); } - internal void SetNonNestedOuterClass(TypeBuilder typeBuilder, string className) + internal void SetNonNestedOuterClass(ITypeSymbolBuilder typeBuilder, string className) { nonNestedOuterClassAttribute ??= TypeOfNonNestedOuterClassAttribute.GetConstructor([context.Types.String]); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(nonNestedOuterClassAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(className)])); + typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(nonNestedOuterClassAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className)])); } #endif // IMPORTER - internal void HideFromReflection(MethodBuilder mb) + internal void HideFromReflection(IMethodSymbolBuilder mb) { mb.SetCustomAttribute(HideFromReflectionBuilder); } - internal void HideFromReflection(FieldBuilder fb) + internal void HideFromReflection(IFieldSymbolBuilder fb) { fb.SetCustomAttribute(HideFromReflectionBuilder); } - internal void HideFromReflection(PropertyBuilder pb) + internal void HideFromReflection(IPropertySymbolBuilder pb) { pb.SetCustomAttribute(HideFromReflectionBuilder); } - internal void HideFromJava(TypeBuilder typeBuilder) + internal void HideFromJava(ITypeSymbolBuilder typeBuilder) { typeBuilder.SetCustomAttribute(HideFromJavaAttributeBuilder); } - internal void HideFromJava(MethodBuilder mb) + internal void HideFromJava(IMethodSymbolBuilder mb) { mb.SetCustomAttribute(HideFromJavaAttributeBuilder); } - internal void HideFromJava(MethodBuilder mb, HideFromJavaFlags flags) + internal void HideFromJava(IMethodSymbolBuilder mb, HideFromJavaFlags flags) { - mb.SetCustomAttribute(new CustomAttributeBuilder(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]).AsReflection(), [flags])); + mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [flags])); } - internal void HideFromJava(FieldBuilder fb) + internal void HideFromJava(IFieldSymbolBuilder fb) { fb.SetCustomAttribute(HideFromJavaAttributeBuilder); } #if IMPORTER - internal void HideFromJava(PropertyBuilder pb) + internal void HideFromJava(IPropertySymbolBuilder pb) { pb.SetCustomAttribute(HideFromJavaAttributeBuilder); } @@ -550,12 +536,12 @@ internal HideFromJavaFlags GetHideFromJavaFlags(IMemberSymbol mi) { // NOTE all privatescope fields and methods are "hideFromJava" // because Java cannot deal with the potential name clashes - var fi = mi as FieldInfo; - if (fi != null && (fi.Attributes & FieldAttributes.FieldAccessMask) == FieldAttributes.PrivateScope) + var fi = mi as IFieldSymbol; + if (fi != null && (fi.Attributes & System.Reflection.FieldAttributes.FieldAccessMask) == System.Reflection.FieldAttributes.PrivateScope) return HideFromJavaFlags.All; - var mb = mi as MethodBase; - if (mb != null && (mb.Attributes & MethodAttributes.MemberAccessMask) == MethodAttributes.PrivateScope) + var mb = mi as IMethodBaseSymbol; + if (mb != null && (mb.Attributes & System.Reflection.MethodAttributes.MemberAccessMask) == System.Reflection.MethodAttributes.PrivateScope) return HideFromJavaFlags.All; if (mi.Name.StartsWith("__<", StringComparison.Ordinal)) return HideFromJavaFlags.All; @@ -575,7 +561,7 @@ internal HideFromJavaFlags GetHideFromJavaFlags(IMemberSymbol mi) #if IMPORTER - internal void SetImplementsAttribute(TypeBuilder typeBuilder, RuntimeJavaType[] ifaceWrappers) + internal void SetImplementsAttribute(ITypeSymbolBuilder typeBuilder, RuntimeJavaType[] ifaceWrappers) { var interfaces = new string[ifaceWrappers.Length]; for (int i = 0; i < interfaces.Length; i++) @@ -584,7 +570,7 @@ internal void SetImplementsAttribute(TypeBuilder typeBuilder, RuntimeJavaType[] if (implementsAttribute == null) implementsAttribute = TypeOfImplementsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(implementsAttribute.AsReflection(), new object[] { interfaces })); + typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(implementsAttribute, [interfaces])); } #endif @@ -730,86 +716,86 @@ internal ExModifiers GetModifiers(IFieldSymbol fi, bool assemblyIsPrivate) return new ExModifiers(modifiers, false); } - internal void SetDebuggingModes(AssemblyBuilder assemblyBuilder, DebuggableAttribute.DebuggingModes modes) + internal void SetDebuggingModes(IAssemblySymbolBuilder assemblyBuilder, DebuggableAttribute.DebuggingModes modes) { debuggableAttribute ??= TypeOfDebuggableAttribute.GetConstructor([TypeOfDebuggableAttribute.GetNestedType(nameof(DebuggableAttribute.DebuggingModes))]); - assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(debuggableAttribute.AsReflection(), [modes])); + assemblyBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(debuggableAttribute, [modes])); } #if IMPORTER - internal void SetModifiers(MethodBuilder mb, Modifiers modifiers, bool isInternal) + internal void SetModifiers(IMethodSymbolBuilder mb, Modifiers modifiers, bool isInternal) { - CustomAttributeBuilder customAttributeBuilder; + ICustomAttributeBuilder customAttributeBuilder; if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); mb.SetCustomAttribute(customAttributeBuilder); } - internal void SetModifiers(FieldBuilder fb, Modifiers modifiers, bool isInternal) + internal void SetModifiers(IFieldSymbolBuilder fb, Modifiers modifiers, bool isInternal) { - CustomAttributeBuilder customAttributeBuilder; + ICustomAttributeBuilder customAttributeBuilder; if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); fb.SetCustomAttribute(customAttributeBuilder); } - internal void SetModifiers(PropertyBuilder pb, Modifiers modifiers, bool isInternal) + internal void SetModifiers(IPropertySymbolBuilder pb, Modifiers modifiers, bool isInternal) { - CustomAttributeBuilder customAttributeBuilder; + ICustomAttributeBuilder customAttributeBuilder; if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); pb.SetCustomAttribute(customAttributeBuilder); } - internal void SetModifiers(TypeBuilder tb, Modifiers modifiers, bool isInternal) + internal void SetModifiers(ITypeSymbolBuilder tb, Modifiers modifiers, bool isInternal) { - CustomAttributeBuilder customAttributeBuilder; + ICustomAttributeBuilder customAttributeBuilder; if (isInternal) - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]).AsReflection(), [modifiers, isInternal]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); else - customAttributeBuilder = new CustomAttributeBuilder(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]).AsReflection(), [modifiers]); + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); tb.SetCustomAttribute(customAttributeBuilder); } - internal void SetNameSig(MethodBuilder mb, string name, string sig) + internal void SetNameSig(IMethodSymbolBuilder mb, string name, string sig) { - var customAttributeBuilder = new CustomAttributeBuilder(TypeOfNameSigAttribute.GetConstructor([context.Types.String, context.Types.String]).AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(name), UnicodeUtil.EscapeInvalidSurrogates(sig)]); + var customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfNameSigAttribute.GetConstructor([context.Types.String, context.Types.String]), [UnicodeUtil.EscapeInvalidSurrogates(name), UnicodeUtil.EscapeInvalidSurrogates(sig)]); mb.SetCustomAttribute(customAttributeBuilder); } - internal void SetInnerClass(TypeBuilder typeBuilder, string innerClass, Modifiers modifiers) + internal void SetInnerClass(ITypeSymbolBuilder typeBuilder, string innerClass, Modifiers modifiers) { var argTypes = new ITypeSymbol[] { context.Types.String, TypeOfModifiers }; var args = new object[] { UnicodeUtil.EscapeInvalidSurrogates(innerClass), modifiers }; var ci = TypeOfInnerClassAttribute.GetConstructor(argTypes); - var customAttributeBuilder = new CustomAttributeBuilder(ci.AsReflection(), args); + var customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(ci, args); typeBuilder.SetCustomAttribute(customAttributeBuilder); } - internal void SetSourceFile(TypeBuilder typeBuilder, string filename) + internal void SetSourceFile(ITypeSymbolBuilder typeBuilder, string filename) { sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor([context.Types.String]); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(sourceFileAttribute.AsReflection(), [filename])); + typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(sourceFileAttribute, [filename])); } - internal void SetSourceFile(ModuleBuilder moduleBuilder, string filename) + internal void SetSourceFile(IMethodSymbolBuilder moduleBuilder, string filename) { sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor([context.Types.String]); - moduleBuilder.SetCustomAttribute(new CustomAttributeBuilder(sourceFileAttribute.AsReflection(), new object[] { filename })); + moduleBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(sourceFileAttribute, [filename])); } - internal void SetLineNumberTable(MethodBuilder mb, IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter writer) + internal void SetLineNumberTable(IMethodSymbolBuilder mb, IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter writer) { object arg; IConstructorSymbol con; @@ -825,81 +811,79 @@ internal void SetLineNumberTable(MethodBuilder mb, IKVM.Attributes.LineNumberTab con = lineNumberTableAttribute1; arg = writer.ToArray(); } - mb.SetCustomAttribute(new CustomAttributeBuilder(con.AsReflection(), [arg])); + + mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(con, [arg])); } - internal void SetEnclosingMethodAttribute(TypeBuilder tb, string className, string methodName, string methodSig) + internal void SetEnclosingMethodAttribute(ITypeSymbolBuilder tb, string className, string methodName, string methodSig) { - if (enclosingMethodAttribute == null) - { - enclosingMethodAttribute = TypeOfEnclosingMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String]); - } - tb.SetCustomAttribute(new CustomAttributeBuilder(enclosingMethodAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(className), UnicodeUtil.EscapeInvalidSurrogates(methodName), UnicodeUtil.EscapeInvalidSurrogates(methodSig)])); + enclosingMethodAttribute ??= TypeOfEnclosingMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String]); + tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(enclosingMethodAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className), UnicodeUtil.EscapeInvalidSurrogates(methodName), UnicodeUtil.EscapeInvalidSurrogates(methodSig)])); } - internal void SetSignatureAttribute(TypeBuilder tb, string signature) + internal void SetSignatureAttribute(ITypeSymbolBuilder tb, string signature) { signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); - tb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } - internal void SetSignatureAttribute(FieldBuilder fb, string signature) + internal void SetSignatureAttribute(IFieldSymbolBuilder fb, string signature) { signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); - fb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } - internal void SetSignatureAttribute(MethodBuilder mb, string signature) + internal void SetSignatureAttribute(IMethodSymbolBuilder mb, string signature) { signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); - mb.SetCustomAttribute(new CustomAttributeBuilder(signatureAttribute.AsReflection(), [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } - internal void SetMethodParametersAttribute(MethodBuilder mb, Modifiers[] modifiers) + internal void SetMethodParametersAttribute(IMethodSymbolBuilder mb, Modifiers[] modifiers) { methodParametersAttribute ??= TypeOfMethodParametersAttribute.GetConstructor([TypeOfModifiers.MakeArrayType()]); - mb.SetCustomAttribute(new CustomAttributeBuilder(methodParametersAttribute.AsReflection(), [modifiers])); + mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(methodParametersAttribute, [modifiers])); } - internal void SetRuntimeVisibleTypeAnnotationsAttribute(TypeBuilder tb, ref readonly TypeAnnotationTable table) + internal void SetRuntimeVisibleTypeAnnotationsAttribute(ITypeSymbolBuilder tb, ref readonly TypeAnnotationTable table) { var builder = new BlobBuilder(); var encoder = new TypeAnnotationTableEncoder(builder); table.WriteTo(ref encoder); runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - tb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute.AsReflection(), [builder.ToArray()])); + tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); } - internal void SetRuntimeVisibleTypeAnnotationsAttribute(FieldBuilder fb, ref readonly TypeAnnotationTable table) + internal void SetRuntimeVisibleTypeAnnotationsAttribute(IFieldSymbolBuilder fb, ref readonly TypeAnnotationTable table) { var builder = new BlobBuilder(); var encoder = new TypeAnnotationTableEncoder(builder); table.WriteTo(ref encoder); runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - fb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute.AsReflection(), [builder.ToArray()])); + fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); } - internal void SetRuntimeVisibleTypeAnnotationsAttribute(MethodBuilder mb, ref readonly TypeAnnotationTable table) + internal void SetRuntimeVisibleTypeAnnotationsAttribute(IMethodSymbolBuilder mb, ref readonly TypeAnnotationTable table) { var builder = new BlobBuilder(); var encoder = new TypeAnnotationTableEncoder(builder); table.WriteTo(ref encoder); runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - mb.SetCustomAttribute(new CustomAttributeBuilder(runtimeVisibleTypeAnnotationsAttribute.AsReflection(), [builder.ToArray()])); + mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); } - internal void SetConstantPoolAttribute(TypeBuilder tb, object[] constantPool) + internal void SetConstantPoolAttribute(ITypeSymbolBuilder tb, object[] constantPool) { constantPoolAttribute ??= TypeOfConstantPoolAttribute.GetConstructor([context.Types.Object.MakeArrayType()]); - tb.SetCustomAttribute(new CustomAttributeBuilder(constantPoolAttribute.AsReflection(), [constantPool])); + tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(constantPoolAttribute, [constantPool])); } - internal void SetParamArrayAttribute(ParameterBuilder pb) + internal void SetParamArrayAttribute(IParameterSymbolBuilder pb) { - paramArrayAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName).GetConstructor([]).AsReflection(), []); + paramArrayAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName).GetConstructor([]), []); pb.SetCustomAttribute(paramArrayAttribute); } @@ -916,19 +900,10 @@ internal NameSigAttribute GetNameSig(IMemberSymbol member) return null; } - internal T[] DecodeArray(CoreLib.Symbols.CustomAttributeTypedArgument arg) + internal T[] DecodeArray(IKVM.CoreLib.Symbols.CustomAttributeTypedArgument arg) { - -/* Unmerged change from project 'IKVM.Tools.Exporter (net8.0)' -Before: - var elems = (IList)arg.Value; - var arr = new T[elems.Count]; -After: - var elems = (IList)arg.Value; - var arr = new T[elems.Count]; -*/ - var elems = (IList)arg.Value; - var arr = new T[elems.Count]; + var elems = (CustomAttributeTypedArgument[])arg.Value; + var arr = new T[elems.Length]; for (int i = 0; i < arr.Length; i++) arr[i] = (T)elems[i].Value; @@ -957,11 +932,11 @@ internal ThrowsAttribute GetThrows(IMethodBaseSymbol mb) } else if (args[0].ArgumentType == context.Types.Type.MakeArrayType()) { - return new ThrowsAttribute(DecodeArray(args[0])); + return new ThrowsAttribute(DecodeArray(args[0]).Unpack()); } else { - return new ThrowsAttribute((Type)args[0].Value); + return new ThrowsAttribute(((ITypeSymbol)args[0].Value).AsReflection()); } } @@ -1125,49 +1100,49 @@ internal bool HasEnclosingMethodAttribute(ITypeSymbol type) internal IKVM.Attributes.EnclosingMethodAttribute GetEnclosingMethodAttribute(ITypeSymbol type) { foreach (var cad in type.GetCustomAttributes(TypeOfEnclosingMethodAttribute)) - return new IKVM.Attributes.EnclosingMethodAttribute((string)cad.ConstructorArguments[0].Value, (string)cad.ConstructorArguments[1].Value, (string)cad.ConstructorArguments[2].Value).SetClassName(context, type.AsReflection()); + return new IKVM.Attributes.EnclosingMethodAttribute((string)cad.ConstructorArguments[0].Value, (string)cad.ConstructorArguments[1].Value, (string)cad.ConstructorArguments[2].Value).SetClassName(context, type); return null; } #if IMPORTER - internal void SetRemappedClass(AssemblyBuilder assemblyBuilder, string name, ITypeSymbol shadowType) + internal void SetRemappedClass(IAssemblySymbolBuilder assemblyBuilder, string name, ITypeSymbol shadowType) { var remappedClassAttribute = TypeOfRemappedClassAttribute.GetConstructor([context.Types.String, context.Types.Type]); - assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(remappedClassAttribute.AsReflection(), [name, shadowType])); + assemblyBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(remappedClassAttribute, [name, shadowType])); } - internal void SetRemappedType(TypeBuilder typeBuilder, ITypeSymbol shadowType) + internal void SetRemappedType(ITypeSymbolBuilder typeBuilder, ITypeSymbol shadowType) { var remappedTypeAttribute = TypeOfRemappedTypeAttribute.GetConstructor([context.Types.Type]); - typeBuilder.SetCustomAttribute(new CustomAttributeBuilder(remappedTypeAttribute.AsReflection(), [shadowType])); + typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(remappedTypeAttribute, [shadowType])); } - internal void SetRemappedInterfaceMethod(TypeBuilder typeBuilder, string name, string mappedTo, string[] throws) + internal void SetRemappedInterfaceMethod(ITypeSymbolBuilder typeBuilder, string name, string mappedTo, string[] throws) { - var cab = new CustomAttributeBuilder(TypeOfRemappedInterfaceMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String.MakeArrayType()]).AsReflection(), [name, mappedTo, throws]); + var cab = context.Resolver.Symbols.CreateCustomAttribute(TypeOfRemappedInterfaceMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String.MakeArrayType()]), [name, mappedTo, throws]); typeBuilder.SetCustomAttribute(cab); } - internal void SetExceptionIsUnsafeForMapping(TypeBuilder typeBuilder) + internal void SetExceptionIsUnsafeForMapping(ITypeSymbolBuilder typeBuilder) { - var cab = new CustomAttributeBuilder(TypeOfExceptionIsUnsafeForMappingAttribute.GetConstructor([]).AsReflection(), Array.Empty()); + var cab = context.Resolver.Symbols.CreateCustomAttribute(TypeOfExceptionIsUnsafeForMappingAttribute.GetConstructor([]), []); typeBuilder.SetCustomAttribute(cab); } #endif - internal void SetRuntimeCompatibilityAttribute(AssemblyBuilder assemblyBuilder) + internal void SetRuntimeCompatibilityAttribute(IAssemblySymbolBuilder assemblyBuilder) { var runtimeCompatibilityAttribute = context.Resolver.ResolveCoreType(typeof(RuntimeCompatibilityAttribute).FullName); - assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(runtimeCompatibilityAttribute.GetConstructor([]).AsReflection(), [], [runtimeCompatibilityAttribute.GetProperty("WrapNonExceptionThrows").AsReflection()], [true], [], [])); + assemblyBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeCompatibilityAttribute.GetConstructor([]), [], [runtimeCompatibilityAttribute.GetProperty("WrapNonExceptionThrows")], [true], [], [])); } - internal void SetInternalsVisibleToAttribute(AssemblyBuilder assemblyBuilder, string assemblyName) + internal void SetInternalsVisibleToAttribute(IAssemblySymbolBuilder assemblyBuilder, string assemblyName) { var internalsVisibleToAttribute = context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName); - var cab = new CustomAttributeBuilder(internalsVisibleToAttribute.GetConstructor([context.Types.String]).AsReflection(), [assemblyName]); + var cab = context.Resolver.Symbols.CreateCustomAttribute(internalsVisibleToAttribute.GetConstructor([context.Types.String]), [assemblyName]); assemblyBuilder.SetCustomAttribute(cab); } diff --git a/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs b/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs index 3eb72debc7..39e1efa398 100644 --- a/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs +++ b/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs @@ -23,6 +23,7 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; #if IMPORTER || EXPORTER @@ -47,7 +48,7 @@ public EnclosingMethodAttribute(string className, string methodName, string meth this.methodSig = UnicodeUtil.UnescapeInvalidSurrogates(methodSig); } - internal EnclosingMethodAttribute SetClassName(RuntimeContext context, Type type) + internal EnclosingMethodAttribute SetClassName(RuntimeContext context, ITypeSymbol type) { className ??= context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).Name; return this; diff --git a/src/IKVM.Runtime/BootstrapClassLoader.cs b/src/IKVM.Runtime/BootstrapClassLoader.cs index c847939def..1e9d42aeb4 100644 --- a/src/IKVM.Runtime/BootstrapClassLoader.cs +++ b/src/IKVM.Runtime/BootstrapClassLoader.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using System.Collections.Generic; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -44,14 +46,14 @@ sealed class BootstrapClassLoader : RuntimeAssemblyClassLoader /// Initializes a new instance. /// internal BootstrapClassLoader(RuntimeContext context) : - base(context, context.Resolver.ResolveBaseAssembly().AsReflection(), [typeof(object).Assembly.FullName, typeof(Uri).Assembly.FullName]) + base(context, context.Resolver.ResolveBaseAssembly(), [typeof(object).Assembly.FullName, typeof(Uri).Assembly.FullName]) { #if FIRST_PASS == false && IMPORTER == false && EXPORTER == false RegisterNativeLibrary(LibJava.Instance.Handle); #endif } - internal override RuntimeJavaType GetJavaTypeFromAssemblyType(Type type) + internal override RuntimeJavaType GetJavaTypeFromAssemblyType(ITypeSymbol type) { // we have to special case the fake types here if (type.IsGenericType && !type.IsGenericTypeDefinition) diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index 0d17bb2132..ec6406b17b 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -28,6 +28,7 @@ Jeroen Frijters using System.Diagnostics; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER using IKVM.Reflection; @@ -77,9 +78,9 @@ public CodeEmitterFactory(RuntimeContext context) /// /// /// - public CodeEmitter Create(MethodBuilder mb) + public CodeEmitter Create(IMethodSymbolBuilder mb) { - return new CodeEmitter(context, mb.GetILGenerator(), context.Resolver.ResolveType(mb.DeclaringType)); + return new CodeEmitter(context, mb.GetILGenerator(), context.Resolver.ResolveType(mb.Symbol.DeclaringType)); } #if IMPORTER == false @@ -103,7 +104,7 @@ sealed class CodeEmitter readonly RuntimeContext context; - ILGenerator ilgen_real; + IILGenerator ilgen_real; bool inFinally; Stack exceptionStack = new Stack(); IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter linenums; @@ -148,7 +149,7 @@ struct OpCodeWrapper internal readonly CodeType pseudo; readonly CodeTypeFlags flags; - internal readonly OpCode opcode; + internal readonly System.Reflection.Emit.OpCode opcode; readonly object data; /// @@ -160,7 +161,7 @@ internal OpCodeWrapper(CodeType pseudo, object data) { this.pseudo = pseudo; this.flags = CodeTypeFlags.None; - this.opcode = OpCodes.Nop; + this.opcode = System.Reflection.Emit.OpCodes.Nop; this.data = data; } @@ -173,7 +174,7 @@ internal OpCodeWrapper(CodeType pseudo, CodeTypeFlags flags) { this.pseudo = pseudo; this.flags = flags; - this.opcode = OpCodes.Nop; + this.opcode = System.Reflection.Emit.OpCodes.Nop; this.data = null; } @@ -182,7 +183,7 @@ internal OpCodeWrapper(CodeType pseudo, CodeTypeFlags flags) /// /// /// - internal OpCodeWrapper(OpCode opcode, object data) + internal OpCodeWrapper(System.Reflection.Emit.OpCode opcode, object data) { this.pseudo = CodeType.OpCode; this.flags = CodeTypeFlags.None; @@ -290,7 +291,7 @@ internal ManagedCalliWrapper(CallingConventions callConv, ITypeSymbol returnType /// /// /// - public CodeEmitter(RuntimeContext context, ILGenerator ilgen, ITypeSymbol declaringType) + public CodeEmitter(RuntimeContext context, IILGenerator ilgen, ITypeSymbol declaringType) { this.context = context; this.ilgen_real = ilgen; @@ -307,7 +308,7 @@ private void EmitPseudoOpCode(CodeType type, object data) code.Add(new OpCodeWrapper(type, data)); } - private void EmitOpCode(OpCode opcode, object arg) + private void EmitOpCode(System.Reflection.Emit.OpCode opcode, object arg) { code.Add(new OpCodeWrapper(opcode, arg)); } @@ -336,7 +337,7 @@ private void RealEmitPseudoOpCode(int ilOffset, CodeType type, object data) ilgen_real.MarkSequencePoint(symbols, (int)data, 0, (int)data + 1, 0); #endif // we emit a nop to make sure we always have an instruction associated with the sequence point - ilgen_real.Emit(OpCodes.Nop); + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Nop); break; case CodeType.Label: ilgen_real.MarkLabel(((CodeEmitterLabel)data).Label); @@ -345,7 +346,7 @@ private void RealEmitPseudoOpCode(int ilOffset, CodeType type, object data) ilgen_real.BeginExceptionBlock(); break; case CodeType.BeginCatchBlock: - ilgen_real.BeginCatchBlock(((ITypeSymbol)data).AsReflection()); + ilgen_real.BeginCatchBlock(((ITypeSymbol)data)); break; case CodeType.BeginFaultBlock: ilgen_real.BeginFaultBlock(); @@ -355,23 +356,23 @@ private void RealEmitPseudoOpCode(int ilOffset, CodeType type, object data) break; case CodeType.EndExceptionBlock: ilgen_real.EndExceptionBlock(); - ilgen_real.Emit(OpCodes.Br_S, (sbyte)-2); // bogus target of implicit leave + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Br_S, (sbyte)-2); // bogus target of implicit leave break; case CodeType.MemoryBarrier: - ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MemoryBarrierMethod.AsReflection()); + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Call, context.CodeEmitterFactory.MemoryBarrierMethod); break; case CodeType.MonitorEnter: - ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MonitorEnterMethod.AsReflection()); + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Call, context.CodeEmitterFactory.MonitorEnterMethod); break; case CodeType.MonitorExit: - ilgen_real.Emit(OpCodes.Call, context.CodeEmitterFactory.MonitorExitMethod.AsReflection()); + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Call, context.CodeEmitterFactory.MonitorExitMethod); break; case CodeType.TailCallPrevention: - ilgen_real.Emit(OpCodes.Ldnull); - ilgen_real.Emit(OpCodes.Pop); + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Ldnull); + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Pop); break; case CodeType.ClearStack: - ilgen_real.Emit(OpCodes.Leave_S, (byte)0); + ilgen_real.Emit(System.Reflection.Emit.OpCodes.Leave_S, (byte)0); break; default: throw new InvalidOperationException(); @@ -379,12 +380,12 @@ private void RealEmitPseudoOpCode(int ilOffset, CodeType type, object data) } /// - /// Emits the real OpCode into the underlying IL generator. + /// Emits the real System.Reflection.Emit.OpCode into the underlying IL generator. /// /// /// /// - void RealEmitOpCode(OpCode opcode, object arg) + void RealEmitOpCode(System.Reflection.Emit.OpCode opcode, object arg) { if (arg == null) { @@ -400,15 +401,15 @@ void RealEmitOpCode(OpCode opcode, object arg) } else if (arg is IMethodSymbol mi) { - ilgen_real.Emit(opcode, mi.AsReflection()); + ilgen_real.Emit(opcode, mi); } else if (arg is IConstructorSymbol ci) { - ilgen_real.Emit(opcode, ci.AsReflection()); + ilgen_real.Emit(opcode, ci); } else if (arg is IFieldSymbol fi) { - ilgen_real.Emit(opcode, fi.AsReflection()); + ilgen_real.Emit(opcode, fi); } else if (arg is sbyte sby) { @@ -436,7 +437,7 @@ void RealEmitOpCode(OpCode opcode, object arg) } else if (arg is ITypeSymbol type) { - ilgen_real.Emit(opcode, type.AsReflection()); + ilgen_real.Emit(opcode, type); } else if (arg is CodeEmitterLocal local) { @@ -448,7 +449,7 @@ void RealEmitOpCode(OpCode opcode, object arg) } else if (arg is CodeEmitterLabel[] labels) { - var real = new Label[labels.Length]; + var real = new ILabel[labels.Length]; for (int i = 0; i < labels.Length; i++) real[i] = labels[i].Label; @@ -456,11 +457,11 @@ void RealEmitOpCode(OpCode opcode, object arg) } else if (arg is ManagedCalliWrapper margs) { - ilgen_real.EmitCalli(opcode, margs.callConv, margs.returnType.AsReflection(), margs.parameterTypes.AsReflection(), margs.optionalParameterTypes.AsReflection()); + ilgen_real.EmitCalli(opcode, margs.callConv, margs.returnType, margs.parameterTypes, margs.optionalParameterTypes); } else if (arg is CalliWrapper args) { - ilgen_real.EmitCalli(opcode, args.unmanagedCallConv, args.returnType.AsReflection(), args.parameterTypes.AsReflection()); + ilgen_real.EmitCalli(opcode, args.unmanagedCallConv, args.returnType, args.parameterTypes); } else { @@ -474,7 +475,7 @@ void RemoveJumpNext() { if (code[i].pseudo == CodeType.Label) { - if (code[i - 1].opcode == OpCodes.Br + if (code[i - 1].opcode == System.Reflection.Emit.OpCodes.Br && code[i - 1].MatchLabel(code[i])) { code.RemoveAt(i - 1); @@ -482,7 +483,7 @@ void RemoveJumpNext() } else if (i >= 2 && code[i - 1].pseudo == CodeType.LineNumber - && code[i - 2].opcode == OpCodes.Br + && code[i - 2].opcode == System.Reflection.Emit.OpCodes.Br && code[i - 2].MatchLabel(code[i])) { code.RemoveAt(i - 2); @@ -496,13 +497,13 @@ void AnnihilateStoreReleaseTempLocals() { for (int i = 1; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Stloc) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Stloc) { if (code[i + 1].pseudo == CodeType.ReleaseTempLocal && code[i].Local == code[i + 1].Local) { - code[i] = new OpCodeWrapper(OpCodes.Pop, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Pop, null); } - else if (code[i + 1].opcode == OpCodes.Ldloc && code[i + 1].Local == code[i].Local && code[i + 2].pseudo == CodeType.ReleaseTempLocal && code[i + 2].Local == code[i].Local) + else if (code[i + 1].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[i + 1].Local == code[i].Local && code[i + 2].pseudo == CodeType.ReleaseTempLocal && code[i + 2].Local == code[i].Local) { code.RemoveRange(i, 2); } @@ -514,7 +515,7 @@ void AnnihilatePops() { for (int i = 1; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Pop) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Pop) { // search backwards for a candidate push to annihilate int stack = 0; @@ -531,20 +532,20 @@ void AnnihilatePops() } stack++; } - else if (code[j].opcode == OpCodes.Stloc) + else if (code[j].opcode == System.Reflection.Emit.OpCodes.Stloc) { stack--; } - else if (code[j].opcode == OpCodes.Shl || code[j].opcode == OpCodes.And || code[j].opcode == OpCodes.Add || code[j].opcode == OpCodes.Sub) + else if (code[j].opcode == System.Reflection.Emit.OpCodes.Shl || code[j].opcode == System.Reflection.Emit.OpCodes.And || code[j].opcode == System.Reflection.Emit.OpCodes.Add || code[j].opcode == System.Reflection.Emit.OpCodes.Sub) { if (stack == 0) break; stack--; } - else if (code[j].opcode == OpCodes.Conv_Ovf_I4 - || code[j].opcode == OpCodes.Conv_I8 - || code[j].opcode == OpCodes.Ldlen) + else if (code[j].opcode == System.Reflection.Emit.OpCodes.Conv_Ovf_I4 + || code[j].opcode == System.Reflection.Emit.OpCodes.Conv_I8 + || code[j].opcode == System.Reflection.Emit.OpCodes.Ldlen) { if (stack == 0) { @@ -568,15 +569,15 @@ void AnnihilatePops() /// bool IsSideEffectFreePush(int index) { - if (code[index].opcode == OpCodes.Ldstr) + if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldstr) { return true; } - else if (code[index].opcode == OpCodes.Ldnull) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldnull) { return true; } - else if (code[index].opcode == OpCodes.Ldsfld) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldsfld) { var field = code[index].FieldInfo; if (field != null) @@ -598,47 +599,47 @@ bool IsSideEffectFreePush(int index) } return false; } - else if (code[index].opcode == OpCodes.Ldc_I4) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldc_I4) { return true; } - else if (code[index].opcode == OpCodes.Ldc_I8) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldc_I8) { return true; } - else if (code[index].opcode == OpCodes.Ldc_R4) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldc_R4) { return true; } - else if (code[index].opcode == OpCodes.Ldc_R8) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldc_R8) { return true; } - else if (code[index].opcode == OpCodes.Ldloc) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldloc) { return true; } - else if (code[index].opcode == OpCodes.Ldarg) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldarg) { return true; } - else if (code[index].opcode == OpCodes.Ldarg_S) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldarg_S) { return true; } - else if (code[index].opcode == OpCodes.Ldarg_0) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldarg_0) { return true; } - else if (code[index].opcode == OpCodes.Ldarg_1) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldarg_1) { return true; } - else if (code[index].opcode == OpCodes.Ldarg_2) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldarg_2) { return true; } - else if (code[index].opcode == OpCodes.Ldarg_3) + else if (code[index].opcode == System.Reflection.Emit.OpCodes.Ldarg_3) { return true; } @@ -653,59 +654,59 @@ void OptimizePatterns() SetLabelRefCounts(); for (int i = 1; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Isinst - && code[i + 1].opcode == OpCodes.Ldnull - && code[i + 2].opcode == OpCodes.Cgt_Un - && (code[i + 3].opcode == OpCodes.Brfalse || code[i + 3].opcode == OpCodes.Brtrue)) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Isinst + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Ldnull + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.Cgt_Un + && (code[i + 3].opcode == System.Reflection.Emit.OpCodes.Brfalse || code[i + 3].opcode == System.Reflection.Emit.OpCodes.Brtrue)) { code.RemoveRange(i + 1, 2); } - else if (code[i].opcode == OpCodes.Ldelem_I1 - && code[i + 1].opcode == OpCodes.Ldc_I4 && code[i + 1].ValueInt32 == 255 - && code[i + 2].opcode == OpCodes.And) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldelem_I1 + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Ldc_I4 && code[i + 1].ValueInt32 == 255 + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.And) { - code[i] = new OpCodeWrapper(OpCodes.Ldelem_U1, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldelem_U1, null); code.RemoveRange(i + 1, 2); } - else if (code[i].opcode == OpCodes.Ldelem_I1 - && code[i + 1].opcode == OpCodes.Conv_I8 - && code[i + 2].opcode == OpCodes.Ldc_I8 && code[i + 2].ValueInt64 == 255 - && code[i + 3].opcode == OpCodes.And) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldelem_I1 + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Conv_I8 + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.Ldc_I8 && code[i + 2].ValueInt64 == 255 + && code[i + 3].opcode == System.Reflection.Emit.OpCodes.And) { - code[i] = new OpCodeWrapper(OpCodes.Ldelem_U1, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldelem_U1, null); code.RemoveRange(i + 2, 2); } - else if (code[i].opcode == OpCodes.Ldc_I4 - && code[i + 1].opcode == OpCodes.Ldc_I4 - && code[i + 2].opcode == OpCodes.And) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldc_I4 + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Ldc_I4 + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.And) { - code[i] = new OpCodeWrapper(OpCodes.Ldc_I4, code[i].ValueInt32 & code[i + 1].ValueInt32); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4, code[i].ValueInt32 & code[i + 1].ValueInt32); code.RemoveRange(i + 1, 2); } - else if (MatchCompare(i, OpCodes.Cgt, OpCodes.Clt_Un, context.Types.Double) // dcmpl - || MatchCompare(i, OpCodes.Cgt, OpCodes.Clt_Un, context.Types.Single)) // fcmpl + else if (MatchCompare(i, System.Reflection.Emit.OpCodes.Cgt, System.Reflection.Emit.OpCodes.Clt_Un, context.Types.Double) // dcmpl + || MatchCompare(i, System.Reflection.Emit.OpCodes.Cgt, System.Reflection.Emit.OpCodes.Clt_Un, context.Types.Single)) // fcmpl { - PatchCompare(i, OpCodes.Ble_Un, OpCodes.Blt_Un, OpCodes.Bge, OpCodes.Bgt); + PatchCompare(i, System.Reflection.Emit.OpCodes.Ble_Un, System.Reflection.Emit.OpCodes.Blt_Un, System.Reflection.Emit.OpCodes.Bge, System.Reflection.Emit.OpCodes.Bgt); } - else if (MatchCompare(i, OpCodes.Cgt_Un, OpCodes.Clt, context.Types.Double) // dcmpg - || MatchCompare(i, OpCodes.Cgt_Un, OpCodes.Clt, context.Types.Single)) // fcmpg + else if (MatchCompare(i, System.Reflection.Emit.OpCodes.Cgt_Un, System.Reflection.Emit.OpCodes.Clt, context.Types.Double) // dcmpg + || MatchCompare(i, System.Reflection.Emit.OpCodes.Cgt_Un, System.Reflection.Emit.OpCodes.Clt, context.Types.Single)) // fcmpg { - PatchCompare(i, OpCodes.Ble, OpCodes.Blt, OpCodes.Bge_Un, OpCodes.Bgt_Un); + PatchCompare(i, System.Reflection.Emit.OpCodes.Ble, System.Reflection.Emit.OpCodes.Blt, System.Reflection.Emit.OpCodes.Bge_Un, System.Reflection.Emit.OpCodes.Bgt_Un); } - else if (MatchCompare(i, OpCodes.Cgt, OpCodes.Clt, context.Types.Int64)) // lcmp + else if (MatchCompare(i, System.Reflection.Emit.OpCodes.Cgt, System.Reflection.Emit.OpCodes.Clt, context.Types.Int64)) // lcmp { - PatchCompare(i, OpCodes.Ble, OpCodes.Blt, OpCodes.Bge, OpCodes.Bgt); + PatchCompare(i, System.Reflection.Emit.OpCodes.Ble, System.Reflection.Emit.OpCodes.Blt, System.Reflection.Emit.OpCodes.Bge, System.Reflection.Emit.OpCodes.Bgt); } else if (i < code.Count - 10 - && code[i].opcode == OpCodes.Ldc_I4 - && code[i + 1].opcode == OpCodes.Dup - && code[i + 2].opcode == OpCodes.Ldc_I4_M1 - && code[i + 3].opcode == OpCodes.Bne_Un - && code[i + 4].opcode == OpCodes.Pop - && code[i + 5].opcode == OpCodes.Neg - && code[i + 6].opcode == OpCodes.Br + && code[i].opcode == System.Reflection.Emit.OpCodes.Ldc_I4 + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Dup + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.Ldc_I4_M1 + && code[i + 3].opcode == System.Reflection.Emit.OpCodes.Bne_Un + && code[i + 4].opcode == System.Reflection.Emit.OpCodes.Pop + && code[i + 5].opcode == System.Reflection.Emit.OpCodes.Neg + && code[i + 6].opcode == System.Reflection.Emit.OpCodes.Br && code[i + 7].pseudo == CodeType.Label && code[i + 7].MatchLabel(code[i + 3]) && code[i + 7].Label.Temp == 1 - && code[i + 8].opcode == OpCodes.Div + && code[i + 8].opcode == System.Reflection.Emit.OpCodes.Div && code[i + 9].pseudo == CodeType.Label && code[i + 9].Label == code[i + 6].Label && code[i + 9].Label.Temp == 1) { int divisor = code[i].ValueInt32; @@ -721,16 +722,16 @@ void OptimizePatterns() } } else if (i < code.Count - 11 - && code[i].opcode == OpCodes.Ldc_I8 - && code[i + 1].opcode == OpCodes.Dup - && code[i + 2].opcode == OpCodes.Ldc_I4_M1 - && code[i + 3].opcode == OpCodes.Conv_I8 - && code[i + 4].opcode == OpCodes.Bne_Un - && code[i + 5].opcode == OpCodes.Pop - && code[i + 6].opcode == OpCodes.Neg - && code[i + 7].opcode == OpCodes.Br + && code[i].opcode == System.Reflection.Emit.OpCodes.Ldc_I8 + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Dup + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.Ldc_I4_M1 + && code[i + 3].opcode == System.Reflection.Emit.OpCodes.Conv_I8 + && code[i + 4].opcode == System.Reflection.Emit.OpCodes.Bne_Un + && code[i + 5].opcode == System.Reflection.Emit.OpCodes.Pop + && code[i + 6].opcode == System.Reflection.Emit.OpCodes.Neg + && code[i + 7].opcode == System.Reflection.Emit.OpCodes.Br && code[i + 8].pseudo == CodeType.Label && code[i + 8].MatchLabel(code[i + 4]) && code[i + 8].Label.Temp == 1 - && code[i + 9].opcode == OpCodes.Div + && code[i + 9].opcode == System.Reflection.Emit.OpCodes.Div && code[i + 10].pseudo == CodeType.Label && code[i + 10].MatchLabel(code[i + 7]) && code[i + 10].Label.Temp == 1) { long divisor = code[i].ValueInt64; @@ -745,26 +746,26 @@ void OptimizePatterns() code.RemoveRange(i + 2, 9); } } - else if (code[i].opcode == OpCodes.Box - && code[i + 1].opcode == OpCodes.Unbox && code[i + 1].Type == code[i].Type) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Box + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Unbox && code[i + 1].Type == code[i].Type) { CodeEmitterLocal local = new CodeEmitterLocal(code[i].Type); - code[i] = new OpCodeWrapper(OpCodes.Stloc, local); - code[i + 1] = new OpCodeWrapper(OpCodes.Ldloca, local); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Stloc, local); + code[i + 1] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldloca, local); } else if (i < code.Count - 13 - && code[i + 0].opcode == OpCodes.Box - && code[i + 1].opcode == OpCodes.Dup - && code[i + 2].opcode == OpCodes.Brtrue - && code[i + 3].opcode == OpCodes.Pop - && code[i + 4].opcode == OpCodes.Ldloca && code[i + 4].Local.LocalType == code[i + 0].Type - && code[i + 5].opcode == OpCodes.Initobj && code[i + 5].Type == code[i + 0].Type - && code[i + 6].opcode == OpCodes.Ldloc && code[i + 6].Local == code[i + 4].Local + && code[i + 0].opcode == System.Reflection.Emit.OpCodes.Box + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Dup + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.Brtrue + && code[i + 3].opcode == System.Reflection.Emit.OpCodes.Pop + && code[i + 4].opcode == System.Reflection.Emit.OpCodes.Ldloca && code[i + 4].Local.LocalType == code[i + 0].Type + && code[i + 5].opcode == System.Reflection.Emit.OpCodes.Initobj && code[i + 5].Type == code[i + 0].Type + && code[i + 6].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[i + 6].Local == code[i + 4].Local && code[i + 7].pseudo == CodeType.ReleaseTempLocal && code[i + 7].Local == code[i + 6].Local - && code[i + 8].opcode == OpCodes.Br + && code[i + 8].opcode == System.Reflection.Emit.OpCodes.Br && code[i + 9].pseudo == CodeType.Label && code[i + 9].MatchLabel(code[i + 2]) && code[i + 9].Label.Temp == 1 - && code[i + 10].opcode == OpCodes.Unbox && code[i + 10].Type == code[i + 0].Type - && code[i + 11].opcode == OpCodes.Ldobj && code[i + 11].Type == code[i + 0].Type + && code[i + 10].opcode == System.Reflection.Emit.OpCodes.Unbox && code[i + 10].Type == code[i + 0].Type + && code[i + 11].opcode == System.Reflection.Emit.OpCodes.Ldobj && code[i + 11].Type == code[i + 0].Type && code[i + 12].pseudo == CodeType.Label && code[i + 12].MatchLabel(code[i + 8]) && code[i + 12].Label.Temp == 1) { code.RemoveRange(i, 13); @@ -773,114 +774,114 @@ void OptimizePatterns() // NOTE intentionally not an else, because we want to optimize the code generated by the earlier compare optimization if (i < code.Count - 6 && code[i].opcode.FlowControl == FlowControl.Cond_Branch - && code[i + 1].opcode == OpCodes.Ldc_I4 && code[i + 1].ValueInt32 == 1 - && code[i + 2].opcode == OpCodes.Br + && code[i + 1].opcode == System.Reflection.Emit.OpCodes.Ldc_I4 && code[i + 1].ValueInt32 == 1 + && code[i + 2].opcode == System.Reflection.Emit.OpCodes.Br && code[i + 3].pseudo == CodeType.Label && code[i + 3].MatchLabel(code[i]) && code[i + 3].Label.Temp == 1 - && code[i + 4].opcode == OpCodes.Ldc_I4 && code[i + 4].ValueInt32 == 0 + && code[i + 4].opcode == System.Reflection.Emit.OpCodes.Ldc_I4 && code[i + 4].ValueInt32 == 0 && code[i + 5].pseudo == CodeType.Label && code[i + 5].MatchLabel(code[i + 2]) && code[i + 5].Label.Temp == 1) { - if (code[i].opcode == OpCodes.Bne_Un) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Bne_Un) { - code[i] = new OpCodeWrapper(OpCodes.Ceq, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ceq, null); code.RemoveRange(i + 1, 5); } - else if (code[i].opcode == OpCodes.Beq) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Beq) { - code[i + 0] = new OpCodeWrapper(OpCodes.Ceq, null); - code[i + 1] = new OpCodeWrapper(OpCodes.Ldc_I4, 0); - code[i + 2] = new OpCodeWrapper(OpCodes.Ceq, null); + code[i + 0] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ceq, null); + code[i + 1] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4, 0); + code[i + 2] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ceq, null); code.RemoveRange(i + 3, 3); } - else if (code[i].opcode == OpCodes.Ble || code[i].opcode == OpCodes.Ble_Un) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ble || code[i].opcode == System.Reflection.Emit.OpCodes.Ble_Un) { - code[i] = new OpCodeWrapper(OpCodes.Cgt, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Cgt, null); code.RemoveRange(i + 1, 5); } - else if (code[i].opcode == OpCodes.Blt) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Blt) { - code[i] = new OpCodeWrapper(OpCodes.Clt, null); - code[i + 1] = new OpCodeWrapper(OpCodes.Ldc_I4, 0); - code[i + 2] = new OpCodeWrapper(OpCodes.Ceq, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Clt, null); + code[i + 1] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4, 0); + code[i + 2] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ceq, null); code.RemoveRange(i + 3, 3); } - else if (code[i].opcode == OpCodes.Blt_Un) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Blt_Un) { - code[i] = new OpCodeWrapper(OpCodes.Clt_Un, null); - code[i + 1] = new OpCodeWrapper(OpCodes.Ldc_I4, 0); - code[i + 2] = new OpCodeWrapper(OpCodes.Ceq, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Clt_Un, null); + code[i + 1] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4, 0); + code[i + 2] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ceq, null); code.RemoveRange(i + 3, 3); } - else if (code[i].opcode == OpCodes.Bge || code[i].opcode == OpCodes.Bge_Un) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Bge || code[i].opcode == System.Reflection.Emit.OpCodes.Bge_Un) { - code[i] = new OpCodeWrapper(OpCodes.Clt, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Clt, null); code.RemoveRange(i + 1, 5); } - else if (code[i].opcode == OpCodes.Bgt) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Bgt) { - code[i] = new OpCodeWrapper(OpCodes.Cgt, null); - code[i + 1] = new OpCodeWrapper(OpCodes.Ldc_I4, 0); - code[i + 2] = new OpCodeWrapper(OpCodes.Ceq, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Cgt, null); + code[i + 1] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4, 0); + code[i + 2] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ceq, null); code.RemoveRange(i + 3, 3); } - else if (code[i].opcode == OpCodes.Bgt_Un) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Bgt_Un) { - code[i] = new OpCodeWrapper(OpCodes.Cgt_Un, null); - code[i + 1] = new OpCodeWrapper(OpCodes.Ldc_I4, 0); - code[i + 2] = new OpCodeWrapper(OpCodes.Ceq, null); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Cgt_Un, null); + code[i + 1] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4, 0); + code[i + 2] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ceq, null); code.RemoveRange(i + 3, 3); } } } } - bool MatchCompare(int index, OpCode cmp1, OpCode cmp2, ITypeSymbol type) + bool MatchCompare(int index, System.Reflection.Emit.OpCode cmp1, System.Reflection.Emit.OpCode cmp2, ITypeSymbol type) { - return code[index].opcode == OpCodes.Stloc && code[index].Local.LocalType == type - && code[index + 1].opcode == OpCodes.Stloc && code[index + 1].Local.LocalType == type - && code[index + 2].opcode == OpCodes.Ldloc && code[index + 2].MatchLocal(code[index + 1]) - && code[index + 3].opcode == OpCodes.Ldloc && code[index + 3].MatchLocal(code[index]) + return code[index].opcode == System.Reflection.Emit.OpCodes.Stloc && code[index].Local.LocalType == type + && code[index + 1].opcode == System.Reflection.Emit.OpCodes.Stloc && code[index + 1].Local.LocalType == type + && code[index + 2].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[index + 2].MatchLocal(code[index + 1]) + && code[index + 3].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[index + 3].MatchLocal(code[index]) && code[index + 4].opcode == cmp1 - && code[index + 5].opcode == OpCodes.Ldloc && code[index + 5].MatchLocal(code[index + 1]) - && code[index + 6].opcode == OpCodes.Ldloc && code[index + 6].MatchLocal(code[index]) + && code[index + 5].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[index + 5].MatchLocal(code[index + 1]) + && code[index + 6].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[index + 6].MatchLocal(code[index]) && code[index + 7].opcode == cmp2 - && code[index + 8].opcode == OpCodes.Sub + && code[index + 8].opcode == System.Reflection.Emit.OpCodes.Sub && code[index + 9].pseudo == CodeType.ReleaseTempLocal && code[index + 9].Local == code[index].Local && code[index + 10].pseudo == CodeType.ReleaseTempLocal && code[index + 10].Local == code[index + 1].Local && ((code[index + 11].opcode.FlowControl == FlowControl.Cond_Branch && code[index + 11].HasLabel) || - (code[index + 11].opcode == OpCodes.Ldc_I4_0 + (code[index + 11].opcode == System.Reflection.Emit.OpCodes.Ldc_I4_0 && (code[index + 12].opcode.FlowControl == FlowControl.Cond_Branch && code[index + 12].HasLabel))); } - void PatchCompare(int index, OpCode ble, OpCode blt, OpCode bge, OpCode bgt) + void PatchCompare(int index, System.Reflection.Emit.OpCode ble, System.Reflection.Emit.OpCode blt, System.Reflection.Emit.OpCode bge, System.Reflection.Emit.OpCode bgt) { - if (code[index + 11].opcode == OpCodes.Brtrue) + if (code[index + 11].opcode == System.Reflection.Emit.OpCodes.Brtrue) { - code[index] = new OpCodeWrapper(OpCodes.Bne_Un, code[index + 11].Label); + code[index] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Bne_Un, code[index + 11].Label); code.RemoveRange(index + 1, 11); } - else if (code[index + 11].opcode == OpCodes.Brfalse) + else if (code[index + 11].opcode == System.Reflection.Emit.OpCodes.Brfalse) { - code[index] = new OpCodeWrapper(OpCodes.Beq, code[index + 11].Label); + code[index] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Beq, code[index + 11].Label); code.RemoveRange(index + 1, 11); } - else if (code[index + 11].opcode == OpCodes.Ldc_I4_0) + else if (code[index + 11].opcode == System.Reflection.Emit.OpCodes.Ldc_I4_0) { - if (code[index + 12].opcode == OpCodes.Ble) + if (code[index + 12].opcode == System.Reflection.Emit.OpCodes.Ble) { code[index] = new OpCodeWrapper(ble, code[index + 12].Label); code.RemoveRange(index + 1, 12); } - else if (code[index + 12].opcode == OpCodes.Blt) + else if (code[index + 12].opcode == System.Reflection.Emit.OpCodes.Blt) { code[index] = new OpCodeWrapper(blt, code[index + 12].Label); code.RemoveRange(index + 1, 12); } - else if (code[index + 12].opcode == OpCodes.Bge) + else if (code[index + 12].opcode == System.Reflection.Emit.OpCodes.Bge) { code[index] = new OpCodeWrapper(bge, code[index + 12].Label); code.RemoveRange(index + 1, 12); } - else if (code[index + 12].opcode == OpCodes.Bgt) + else if (code[index + 12].opcode == System.Reflection.Emit.OpCodes.Bgt) { code[index] = new OpCodeWrapper(bgt, code[index + 12].Label); code.RemoveRange(index + 1, 12); @@ -895,9 +896,9 @@ void OptimizeEncodings() { for (int i = 0; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Ldc_I4) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldc_I4) code[i] = OptimizeLdcI4(code[i].ValueInt32); - else if (code[i].opcode == OpCodes.Ldc_I8) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldc_I8) OptimizeLdcI8(i); } } @@ -912,30 +913,30 @@ OpCodeWrapper OptimizeLdcI4(int value) switch (value) { case -1: - return new OpCodeWrapper(OpCodes.Ldc_I4_M1, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_M1, null); case 0: - return new OpCodeWrapper(OpCodes.Ldc_I4_0, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_0, null); case 1: - return new OpCodeWrapper(OpCodes.Ldc_I4_1, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_1, null); case 2: - return new OpCodeWrapper(OpCodes.Ldc_I4_2, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_2, null); case 3: - return new OpCodeWrapper(OpCodes.Ldc_I4_3, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_3, null); case 4: - return new OpCodeWrapper(OpCodes.Ldc_I4_4, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_4, null); case 5: - return new OpCodeWrapper(OpCodes.Ldc_I4_5, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_5, null); case 6: - return new OpCodeWrapper(OpCodes.Ldc_I4_6, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_6, null); case 7: - return new OpCodeWrapper(OpCodes.Ldc_I4_7, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_7, null); case 8: - return new OpCodeWrapper(OpCodes.Ldc_I4_8, null); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_8, null); default: if (value >= -128 && value <= 127) - return new OpCodeWrapper(OpCodes.Ldc_I4_S, (sbyte)value); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4_S, (sbyte)value); else - return new OpCodeWrapper(OpCodes.Ldc_I4, value); + return new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldc_I4, value); } } @@ -949,7 +950,7 @@ void OptimizeLdcI8(int index) if (value >= int.MinValue && value <= uint.MaxValue) { code[index] = OptimizeLdcI4((int)value); - code.Insert(index + 1, new OpCodeWrapper(value < 0 ? OpCodes.Conv_I8 : OpCodes.Conv_U8, null)); + code.Insert(index + 1, new OpCodeWrapper(value < 0 ? System.Reflection.Emit.OpCodes.Conv_I8 : System.Reflection.Emit.OpCodes.Conv_U8, null)); } } @@ -965,7 +966,7 @@ private void ChaseBranches() SetLabelIndexes(); for (int i = 0; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Br) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Br) { int target = code[i].Label.Temp + 1; if (code[target].pseudo == CodeType.LineNumber) @@ -973,36 +974,36 @@ private void ChaseBranches() // line number info on endfinally or ret is probably useless anyway target++; } - if (code[target].opcode == OpCodes.Endfinally || code[target].opcode == OpCodes.Ret) + if (code[target].opcode == System.Reflection.Emit.OpCodes.Endfinally || code[target].opcode == System.Reflection.Emit.OpCodes.Ret) { code[i] = code[target]; } else { CodeEmitterLabel label = null; - while (code[target].opcode == OpCodes.Br && target != i) + while (code[target].opcode == System.Reflection.Emit.OpCodes.Br && target != i) { label = code[target].Label; target = code[target].Label.Temp + 1; } if (label != null) { - code[i] = new OpCodeWrapper(OpCodes.Br, label); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Br, label); } } } - else if (code[i].opcode == OpCodes.Leave) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Leave) { int target = code[i].Label.Temp + 1; CodeEmitterLabel label = null; - while ((code[target].opcode == OpCodes.Br || code[target].opcode == OpCodes.Leave) && target != i) + while ((code[target].opcode == System.Reflection.Emit.OpCodes.Br || code[target].opcode == System.Reflection.Emit.OpCodes.Leave) && target != i) { label = code[target].Label; target = code[target].Label.Temp + 1; } if (label != null) { - code[i] = new OpCodeWrapper(OpCodes.Leave, label); + code[i] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Leave, label); } } } @@ -1034,9 +1035,9 @@ private void RemoveSingletonBranches() case CodeType.OpCode: switch (code[i].opcode.FlowControl) { - case FlowControl.Branch: - case FlowControl.Return: - case FlowControl.Throw: + case System.Reflection.Emit.FlowControl.Branch: + case System.Reflection.Emit.FlowControl.Return: + case System.Reflection.Emit.FlowControl.Throw: reachable = false; break; } @@ -1062,7 +1063,7 @@ private void RemoveSingletonBranches() // now remove the unconditional branches to labels with a refcount of one for (int i = 0; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Br && code[i].Label.Temp == 1) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Br && code[i].Label.Temp == 1) { int target = FindLabel(code[i].Label) + 1; for (int j = target; j < code.Count; j++) @@ -1077,9 +1078,9 @@ private void RemoveSingletonBranches() } switch (code[j].opcode.FlowControl) { - case FlowControl.Branch: - case FlowControl.Return: - case FlowControl.Throw: + case System.Reflection.Emit.FlowControl.Branch: + case System.Reflection.Emit.FlowControl.Return: + case System.Reflection.Emit.FlowControl.Throw: // we've found a viable sequence of opcode to move to the branch location List range = code.GetRange(target, j - target + 1); if (target < i) @@ -1214,7 +1215,7 @@ private void SetLabelRefCounts() { code[i].Label.Temp++; } - else if (code[i].opcode == OpCodes.Switch) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Switch) { foreach (CodeEmitterLabel label in code[i].Labels) { @@ -1269,9 +1270,9 @@ private void RemoveDeadCode() } code[i].Label.Temp |= ReachableFlag; } - else if (code[i].opcode == OpCodes.Switch) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Switch) { - foreach (CodeEmitterLabel label in code[i].Labels) + foreach (var label in code[i].Labels) { if (label.Temp == ProcessedFlag) { @@ -1282,15 +1283,15 @@ private void RemoveDeadCode() } switch (code[i].opcode.FlowControl) { - case FlowControl.Cond_Branch: - if (!code[i].HasLabel && code[i].opcode != OpCodes.Switch) + case System.Reflection.Emit.FlowControl.Cond_Branch: + if (!code[i].HasLabel && code[i].opcode != System.Reflection.Emit.OpCodes.Switch) { throw new NotSupportedException(); } break; - case FlowControl.Branch: - case FlowControl.Return: - case FlowControl.Throw: + case System.Reflection.Emit.FlowControl.Branch: + case System.Reflection.Emit.FlowControl.Return: + case System.Reflection.Emit.FlowControl.Throw: reachable = false; break; } @@ -1328,9 +1329,9 @@ private void RemoveDeadCode() { switch (code[i].opcode.FlowControl) { - case FlowControl.Branch: - case FlowControl.Return: - case FlowControl.Throw: + case System.Reflection.Emit.FlowControl.Branch: + case System.Reflection.Emit.FlowControl.Return: + case System.Reflection.Emit.FlowControl.Throw: reachable = false; firstUnreachable = i + 1; break; @@ -1417,7 +1418,7 @@ private void DeduplicateBranchSourceTargetCode() SetLabelIndexes(); for (int i = 0; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Br && code[i].HasLabel) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Br && code[i].HasLabel) { int source = i - 1; int target = code[i].Label.Temp - 1; @@ -1437,8 +1438,8 @@ private void DeduplicateBranchSourceTargetCode() } switch (code[source].opcode.FlowControl) { - case FlowControl.Branch: - case FlowControl.Cond_Branch: + case System.Reflection.Emit.FlowControl.Branch: + case System.Reflection.Emit.FlowControl.Cond_Branch: goto break_while; } source--; @@ -1452,7 +1453,7 @@ private void DeduplicateBranchSourceTargetCode() // TODO for now we only do this optimization if there happens to be an appriopriate label if (code[target - 1].pseudo == CodeType.Label) { - code[source] = new OpCodeWrapper(OpCodes.Br, code[target - 1].Label); + code[source] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Br, code[target - 1].Label); for (int j = source + 1; j <= i; j++) { // We can't depend on DCE for code correctness (we have to maintain all MSIL invariants at all times), @@ -1469,10 +1470,10 @@ private void OptimizeStackTransfer() { for (int i = 0; i < code.Count; i++) { - if (code[i].opcode == OpCodes.Ldloc && - code[i + 1].opcode == OpCodes.Stloc && + if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldloc && + code[i + 1].opcode == System.Reflection.Emit.OpCodes.Stloc && code[i + 2].pseudo == CodeType.BeginExceptionBlock && - code[i + 3].opcode == OpCodes.Ldloc && + code[i + 3].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[i + 3].MatchLocal(code[i + 1]) && code[i + 4].pseudo == CodeType.ReleaseTempLocal && code[i + 4].MatchLocal(code[i + 3])) @@ -1559,7 +1560,7 @@ private void MergeExceptionBlocks() // the BeginExceptionBlock of the second block. for (int j = beginFault1; j < i + 2; j++) { - code[j] = new OpCodeWrapper(OpCodes.Nop, null); + code[j] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Nop, null); } // Repair the linking structure. extra[extra[i]] = beginFault2; @@ -1587,7 +1588,7 @@ bool HasBranchTo(int start, int end, CodeEmitterLabel label) if (code[i].Label == label) return true; } - else if (code[i].opcode == OpCodes.Switch) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Switch) { foreach (CodeEmitterLabel swlbl in code[i].Labels) if (swlbl == label) @@ -1660,9 +1661,9 @@ private void ConvertSynchronizedFaultToFinally() i++; } // check if the fault handler is the synchronized block exit pattern - if (code[i + 1].opcode == OpCodes.Ldloc + if (code[i + 1].opcode == System.Reflection.Emit.OpCodes.Ldloc && code[i + 2].pseudo == CodeType.MonitorExit - && code[i + 3].opcode == OpCodes.Endfinally) + && code[i + 3].opcode == System.Reflection.Emit.OpCodes.Endfinally) { if (!labelIndexSet) { @@ -1676,13 +1677,13 @@ private void ConvertSynchronizedFaultToFinally() { for (int j = start; j < i; j++) { - if (code[j].opcode == OpCodes.Leave) + if (code[j].opcode == System.Reflection.Emit.OpCodes.Leave) { int target = code[j].Label.Temp; if (target < start || target > i) { // check if the code preceding the leave matches the fault block - if ((code[j - 1].opcode == OpCodes.Pop || code[j - 1].opcode == OpCodes.Stloc) + if ((code[j - 1].opcode == System.Reflection.Emit.OpCodes.Pop || code[j - 1].opcode == System.Reflection.Emit.OpCodes.Stloc) && code[j - 2].pseudo == CodeType.MonitorExit && code[j - 3].Match(code[i + 1])) { @@ -1745,14 +1746,14 @@ private void RemoveRedundantMemoryBarriers() lastMemoryBarrier = i; break; case CodeType.OpCode: - if (code[i].opcode == OpCodes.Volatile) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Volatile) { - if (code[i + 1].opcode != OpCodes.Stfld && code[i + 1].opcode != OpCodes.Stsfld) + if (code[i + 1].opcode != System.Reflection.Emit.OpCodes.Stfld && code[i + 1].opcode != System.Reflection.Emit.OpCodes.Stsfld) { lastMemoryBarrier = -1; } } - else if (code[i].opcode.FlowControl != FlowControl.Next) + else if (code[i].opcode.FlowControl != System.Reflection.Emit.FlowControl.Next) { lastMemoryBarrier = -1; } @@ -1763,32 +1764,32 @@ private void RemoveRedundantMemoryBarriers() private static bool MatchLdarg(OpCodeWrapper opc, out short arg) { - if (opc.opcode == OpCodes.Ldarg) + if (opc.opcode == System.Reflection.Emit.OpCodes.Ldarg) { arg = opc.ValueInt16; return true; } - else if (opc.opcode == OpCodes.Ldarg_S) + else if (opc.opcode == System.Reflection.Emit.OpCodes.Ldarg_S) { arg = opc.ValueByte; return true; } - else if (opc.opcode == OpCodes.Ldarg_0) + else if (opc.opcode == System.Reflection.Emit.OpCodes.Ldarg_0) { arg = 0; return true; } - else if (opc.opcode == OpCodes.Ldarg_1) + else if (opc.opcode == System.Reflection.Emit.OpCodes.Ldarg_1) { arg = 1; return true; } - else if (opc.opcode == OpCodes.Ldarg_2) + else if (opc.opcode == System.Reflection.Emit.OpCodes.Ldarg_2) { arg = 2; return true; } - else if (opc.opcode == OpCodes.Ldarg_3) + else if (opc.opcode == System.Reflection.Emit.OpCodes.Ldarg_3) { arg = 3; return true; @@ -1800,10 +1801,10 @@ private static bool MatchLdarg(OpCodeWrapper opc, out short arg) } } - private bool IsBranchEqNe(OpCode opcode) + private bool IsBranchEqNe(System.Reflection.Emit.OpCode opcode) { - return opcode == OpCodes.Beq - || opcode == OpCodes.Bne_Un; + return opcode == System.Reflection.Emit.OpCodes.Beq + || opcode == System.Reflection.Emit.OpCodes.Bne_Un; } private void CLRv4_x64_JIT_Workaround() @@ -1824,7 +1825,7 @@ private void CLRv4_x64_JIT_Workaround() // // The workaround is to replace ldarg with ldarga/ldind.i8. Looking at the generated code by the x86 and x64 JITs // this appears to be as efficient as the ldarg and it avoids the x64 bug. - if (code[i].opcode == OpCodes.Ldc_I8 && code[i].ValueInt64 == 0) + if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldc_I8 && code[i].ValueInt64 == 0) { short arg; int m; @@ -1840,8 +1841,8 @@ private void CLRv4_x64_JIT_Workaround() { continue; } - code[m] = new OpCodeWrapper(OpCodes.Ldarga, arg); - code.Insert(m + 1, new OpCodeWrapper(OpCodes.Ldind_I8, null)); + code[m] = new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldarga, arg); + code.Insert(m + 1, new OpCodeWrapper(System.Reflection.Emit.OpCodes.Ldind_I8, null)); } } } @@ -1913,7 +1914,7 @@ void CheckInvariantBranchInOrOutOfBlocks() { case CodeType.OpCode: if (code[i].HasLabel - && code[i].opcode != OpCodes.Leave + && code[i].opcode != System.Reflection.Emit.OpCodes.Leave && code[i].Label.Temp != blockId) { DumpMethod(); @@ -1941,9 +1942,9 @@ private void CheckInvariantOpCodeUsage() { switch (code[i].opcode.FlowControl) { - case FlowControl.Branch: - case FlowControl.Cond_Branch: - if (!code[i].HasLabel && code[i].opcode != OpCodes.Switch) + case System.Reflection.Emit.FlowControl.Branch: + case System.Reflection.Emit.FlowControl.Cond_Branch: + if (!code[i].HasLabel && code[i].opcode != System.Reflection.Emit.OpCodes.Switch) { throw new InvalidOperationException(); } @@ -2063,31 +2064,31 @@ internal void DumpMethod() { Console.Write(" label" + labelIndexes[code[i].Label]); } - else if (code[i].opcode == OpCodes.Ldarg_S || code[i].opcode == OpCodes.Ldarga_S) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldarg_S || code[i].opcode == System.Reflection.Emit.OpCodes.Ldarga_S) { Console.Write(" " + code[i].ValueByte); } - else if (code[i].opcode == OpCodes.Ldarg || code[i].opcode == OpCodes.Ldarga) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldarg || code[i].opcode == System.Reflection.Emit.OpCodes.Ldarga) { Console.Write(" " + code[i].ValueInt16); } - else if (code[i].opcode == OpCodes.Isinst || code[i].opcode == OpCodes.Castclass || code[i].opcode == OpCodes.Box || code[i].opcode == OpCodes.Unbox || code[i].opcode == OpCodes.Ldobj || code[i].opcode == OpCodes.Newarr) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Isinst || code[i].opcode == System.Reflection.Emit.OpCodes.Castclass || code[i].opcode == System.Reflection.Emit.OpCodes.Box || code[i].opcode == System.Reflection.Emit.OpCodes.Unbox || code[i].opcode == System.Reflection.Emit.OpCodes.Ldobj || code[i].opcode == System.Reflection.Emit.OpCodes.Newarr) { Console.Write(" " + code[i].Type); } - else if (code[i].opcode == OpCodes.Call || code[i].opcode == OpCodes.Callvirt) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Call || code[i].opcode == System.Reflection.Emit.OpCodes.Callvirt) { Console.Write(" " + code[i].MethodBase); } - else if (code[i].opcode == OpCodes.Ldfld || code[i].opcode == OpCodes.Ldsfld || code[i].opcode == OpCodes.Stfld || code[i].opcode == OpCodes.Stsfld) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldfld || code[i].opcode == System.Reflection.Emit.OpCodes.Ldsfld || code[i].opcode == System.Reflection.Emit.OpCodes.Stfld || code[i].opcode == System.Reflection.Emit.OpCodes.Stsfld) { Console.Write(" " + code[i].FieldInfo); } - else if (code[i].opcode == OpCodes.Ldc_I4) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldc_I4) { Console.Write(" " + code[i].ValueInt32); } - else if (code[i].opcode == OpCodes.Ldloc || code[i].opcode == OpCodes.Stloc) + else if (code[i].opcode == System.Reflection.Emit.OpCodes.Ldloc || code[i].opcode == System.Reflection.Emit.OpCodes.Stloc) { Console.Write(" " + code[i].Local.__LocalIndex); } @@ -2209,27 +2210,27 @@ internal CodeEmitterLabel DefineLabel() return new CodeEmitterLabel(ilgen_real.DefineLabel()); } - internal void Emit(OpCode opcode) + internal void Emit(System.Reflection.Emit.OpCode opcode) { EmitOpCode(opcode, null); } internal void EmitUnaligned(byte alignment) { - EmitOpCode(OpCodes.Unaligned, alignment); + EmitOpCode(System.Reflection.Emit.OpCodes.Unaligned, alignment); } - internal void Emit(OpCode opcode, IMethodBaseSymbol mb) + internal void Emit(System.Reflection.Emit.OpCode opcode, IMethodBaseSymbol mb) { EmitOpCode(opcode, mb); } internal void EmitLdc_R8(double arg) { - EmitOpCode(OpCodes.Ldc_R8, arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldc_R8, arg); } - internal void Emit(OpCode opcode, IFieldSymbol field) + internal void Emit(System.Reflection.Emit.OpCode opcode, IFieldSymbol field) { EmitOpCode(opcode, field); } @@ -2241,22 +2242,22 @@ internal void EmitLdarg(int arg) switch (arg) { case 0: - EmitOpCode(OpCodes.Ldarg_0, null); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarg_0, null); break; case 1: - EmitOpCode(OpCodes.Ldarg_1, null); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarg_1, null); break; case 2: - EmitOpCode(OpCodes.Ldarg_2, null); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarg_2, null); break; case 3: - EmitOpCode(OpCodes.Ldarg_3, null); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarg_3, null); break; default: if ((uint)arg <= byte.MaxValue) - EmitOpCode(OpCodes.Ldarg_S, (byte)arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarg_S, (byte)arg); else - EmitOpCode(OpCodes.Ldarg, (short)arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarg, (short)arg); break; } @@ -2267,9 +2268,9 @@ internal void EmitLdarga(int arg) Debug.Assert(0 <= arg && arg < 65536); if (arg < 256) - EmitOpCode(OpCodes.Ldarga_S, (byte)arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarga_S, (byte)arg); else - EmitOpCode(OpCodes.Ldarga, (short)arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldarga, (short)arg); } internal void EmitStarg(int arg) @@ -2277,112 +2278,112 @@ internal void EmitStarg(int arg) Debug.Assert(0 <= arg && arg < 65536); if (arg < 256) - EmitOpCode(OpCodes.Starg_S, (byte)arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Starg_S, (byte)arg); else - EmitOpCode(OpCodes.Starg, (short)arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Starg, (short)arg); } internal void EmitLdc_I8(long arg) { - EmitOpCode(OpCodes.Ldc_I8, arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldc_I8, arg); } internal void EmitBr(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Br, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Br, label); } internal void EmitBeq(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Beq, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Beq, label); } internal void EmitBne_Un(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Bne_Un, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Bne_Un, label); } internal void EmitBle_Un(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Ble_Un, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Ble_Un, label); } internal void EmitBlt_Un(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Blt_Un, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Blt_Un, label); } internal void EmitBge_Un(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Bge_Un, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Bge_Un, label); } internal void EmitBle(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Ble, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Ble, label); } internal void EmitBlt(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Blt, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Blt, label); } internal void EmitBge(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Bge, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Bge, label); } internal void EmitBgt(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Bgt, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Bgt, label); } internal void EmitBrtrue(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Brtrue, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Brtrue, label); } internal void EmitBrfalse(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Brfalse, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Brfalse, label); } internal void EmitLeave(CodeEmitterLabel label) { - EmitOpCode(OpCodes.Leave, label); + EmitOpCode(System.Reflection.Emit.OpCodes.Leave, label); } internal void EmitSwitch(CodeEmitterLabel[] labels) { - EmitOpCode(OpCodes.Switch, labels); + EmitOpCode(System.Reflection.Emit.OpCodes.Switch, labels); } - internal void Emit(OpCode opcode, CodeEmitterLocal local) + internal void Emit(System.Reflection.Emit.OpCode opcode, CodeEmitterLocal local) { EmitOpCode(opcode, local); } internal void EmitLdc_R4(float arg) { - EmitOpCode(OpCodes.Ldc_R4, arg); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldc_R4, arg); } - internal void Emit(OpCode opcode, string arg) + internal void Emit(System.Reflection.Emit.OpCode opcode, string arg) { EmitOpCode(opcode, arg); } - internal void Emit(OpCode opcode, ITypeSymbol cls) + internal void Emit(System.Reflection.Emit.OpCode opcode, ITypeSymbol cls) { EmitOpCode(opcode, cls); } - internal void EmitCalli(OpCode opcode, CallingConvention unmanagedCallConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + internal void EmitCalli(System.Reflection.Emit.OpCode opcode, CallingConvention unmanagedCallConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) { EmitOpCode(opcode, new CalliWrapper(unmanagedCallConv, returnType, parameterTypes)); } - internal void EmitCalli(OpCode opcode, CallingConventions unmanagedCallConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes, ITypeSymbol[] optionalParameterTypes) + internal void EmitCalli(System.Reflection.Emit.OpCode opcode, CallingConventions unmanagedCallConv, ITypeSymbol returnType, ITypeSymbol[] parameterTypes, ITypeSymbol[] optionalParameterTypes) { EmitOpCode(opcode, new ManagedCalliWrapper(unmanagedCallConv, returnType, parameterTypes, optionalParameterTypes)); } @@ -2405,8 +2406,8 @@ internal void MarkLabel(CodeEmitterLabel loc) internal void ThrowException(ITypeSymbol excType) { - Emit(OpCodes.Newobj, excType.GetConstructor([])); - Emit(OpCodes.Throw); + Emit(System.Reflection.Emit.OpCodes.Newobj, excType.GetConstructor([])); + Emit(System.Reflection.Emit.OpCodes.Throw); } internal void SetLineNumber(ushort line) @@ -2440,24 +2441,24 @@ internal void EmitThrow(string dottedClassName) var mw = exception.GetMethodWrapper("", "()V", false); mw.Link(); mw.EmitNewobj(this); - Emit(OpCodes.Throw); + Emit(System.Reflection.Emit.OpCodes.Throw); } internal void EmitThrow(string dottedClassName, string message) { var exception = context.ClassLoaderFactory.GetBootstrapClassLoader().LoadClassByName(dottedClassName); - Emit(OpCodes.Ldstr, message); + Emit(System.Reflection.Emit.OpCodes.Ldstr, message); var mw = exception.GetMethodWrapper("", "(Ljava.lang.String;)V", false); mw.Link(); mw.EmitNewobj(this); - Emit(OpCodes.Throw); + Emit(System.Reflection.Emit.OpCodes.Throw); } internal void EmitNullCheck() { // I think this is the most efficient way to generate a NullReferenceException if the reference is null - Emit(OpCodes.Ldvirtftn, context.CodeEmitterFactory.ObjectToStringMethod); - Emit(OpCodes.Pop); + Emit(System.Reflection.Emit.OpCodes.Ldvirtftn, context.CodeEmitterFactory.ObjectToStringMethod); + Emit(System.Reflection.Emit.OpCodes.Pop); } internal void EmitCastclass(ITypeSymbol type) @@ -2465,22 +2466,22 @@ internal void EmitCastclass(ITypeSymbol type) if (context.CodeEmitterFactory.VerboseCastFailureMethod != null) { var lb = DeclareLocal(context.Types.Object); - Emit(OpCodes.Stloc, lb); - Emit(OpCodes.Ldloc, lb); - Emit(OpCodes.Isinst, type); - Emit(OpCodes.Dup); + Emit(System.Reflection.Emit.OpCodes.Stloc, lb); + Emit(System.Reflection.Emit.OpCodes.Ldloc, lb); + Emit(System.Reflection.Emit.OpCodes.Isinst, type); + Emit(System.Reflection.Emit.OpCodes.Dup); var ok = DefineLabel(); EmitBrtrue(ok); - Emit(OpCodes.Ldloc, lb); + Emit(System.Reflection.Emit.OpCodes.Ldloc, lb); EmitBrfalse(ok); // handle null - Emit(OpCodes.Ldtoken, type); - Emit(OpCodes.Ldloc, lb); - Emit(OpCodes.Call, context.CodeEmitterFactory.VerboseCastFailureMethod); + Emit(System.Reflection.Emit.OpCodes.Ldtoken, type); + Emit(System.Reflection.Emit.OpCodes.Ldloc, lb); + Emit(System.Reflection.Emit.OpCodes.Call, context.CodeEmitterFactory.VerboseCastFailureMethod); MarkLabel(ok); } else { - Emit(OpCodes.Castclass, type); + Emit(System.Reflection.Emit.OpCodes.Castclass, type); } } @@ -2489,16 +2490,16 @@ internal void EmitCastclass(ITypeSymbol type) internal void EmitAssertType(ITypeSymbol type) { var isnull = DefineLabel(); - Emit(OpCodes.Dup); + Emit(System.Reflection.Emit.OpCodes.Dup); EmitBrfalse(isnull); - Emit(OpCodes.Isinst, type); - Emit(OpCodes.Dup); + Emit(System.Reflection.Emit.OpCodes.Isinst, type); + Emit(System.Reflection.Emit.OpCodes.Dup); var ok = DefineLabel(); EmitBrtrue(ok); EmitThrow("java.lang.IncompatibleClassChangeError"); MarkLabel(isnull); - Emit(OpCodes.Pop); - Emit(OpCodes.Ldnull); + Emit(System.Reflection.Emit.OpCodes.Pop); + Emit(System.Reflection.Emit.OpCodes.Ldnull); MarkLabel(ok); } @@ -2508,24 +2509,24 @@ internal void EmitUnboxSpecial(ITypeSymbol type) var label1 = DefineLabel(); var label2 = DefineLabel(); - Emit(OpCodes.Dup); + Emit(System.Reflection.Emit.OpCodes.Dup); EmitBrtrue(label1); - Emit(OpCodes.Pop); + Emit(System.Reflection.Emit.OpCodes.Pop); var local = AllocTempLocal(type); - Emit(OpCodes.Ldloca, local); - Emit(OpCodes.Initobj, type); - Emit(OpCodes.Ldloc, local); + Emit(System.Reflection.Emit.OpCodes.Ldloca, local); + Emit(System.Reflection.Emit.OpCodes.Initobj, type); + Emit(System.Reflection.Emit.OpCodes.Ldloc, local); ReleaseTempLocal(local); EmitBr(label2); MarkLabel(label1); - Emit(OpCodes.Unbox, type); - Emit(OpCodes.Ldobj, type); + Emit(System.Reflection.Emit.OpCodes.Unbox, type); + Emit(System.Reflection.Emit.OpCodes.Ldobj, type); MarkLabel(label2); } internal void EmitLdc_I4(int i) { - EmitOpCode(OpCodes.Ldc_I4, i); + EmitOpCode(System.Reflection.Emit.OpCodes.Ldc_I4, i); } internal void Emit_idiv() @@ -2536,14 +2537,14 @@ internal void Emit_idiv() var label1 = DefineLabel(); var label2 = DefineLabel(); - Emit(OpCodes.Dup); - Emit(OpCodes.Ldc_I4_M1); + Emit(System.Reflection.Emit.OpCodes.Dup); + Emit(System.Reflection.Emit.OpCodes.Ldc_I4_M1); EmitBne_Un(label1); - Emit(OpCodes.Pop); - Emit(OpCodes.Neg); + Emit(System.Reflection.Emit.OpCodes.Pop); + Emit(System.Reflection.Emit.OpCodes.Neg); EmitBr(label2); MarkLabel(label1); - Emit(OpCodes.Div); + Emit(System.Reflection.Emit.OpCodes.Div); MarkLabel(label2); } @@ -2555,23 +2556,23 @@ internal void Emit_ldiv() var label1 = DefineLabel(); var label2 = DefineLabel(); - Emit(OpCodes.Dup); - Emit(OpCodes.Ldc_I4_M1); - Emit(OpCodes.Conv_I8); + Emit(System.Reflection.Emit.OpCodes.Dup); + Emit(System.Reflection.Emit.OpCodes.Ldc_I4_M1); + Emit(System.Reflection.Emit.OpCodes.Conv_I8); EmitBne_Un(label1); - Emit(OpCodes.Pop); - Emit(OpCodes.Neg); + Emit(System.Reflection.Emit.OpCodes.Pop); + Emit(System.Reflection.Emit.OpCodes.Neg); EmitBr(label2); MarkLabel(label1); - Emit(OpCodes.Div); + Emit(System.Reflection.Emit.OpCodes.Div); MarkLabel(label2); } internal void Emit_instanceof(ITypeSymbol type) { - Emit(OpCodes.Isinst, type); - Emit(OpCodes.Ldnull); - Emit(OpCodes.Cgt_Un); + Emit(System.Reflection.Emit.OpCodes.Isinst, type); + Emit(System.Reflection.Emit.OpCodes.Ldnull); + Emit(System.Reflection.Emit.OpCodes.Cgt_Un); } internal enum Comparison @@ -2585,7 +2586,7 @@ internal enum Comparison internal void Emit_if_le_lt_ge_gt(Comparison comp, CodeEmitterLabel label) { // don't change this Ldc_I4_0 to Ldc_I4(0) because the optimizer recognizes only this specific pattern - Emit(OpCodes.Ldc_I4_0); + Emit(System.Reflection.Emit.OpCodes.Ldc_I4_0); switch (comp) { case Comparison.LessOrEqual: @@ -2603,52 +2604,52 @@ internal void Emit_if_le_lt_ge_gt(Comparison comp, CodeEmitterLabel label) } } - private void EmitCmp(ITypeSymbol type, OpCode cmp1, OpCode cmp2) + private void EmitCmp(ITypeSymbol type, System.Reflection.Emit.OpCode cmp1, System.Reflection.Emit.OpCode cmp2) { var value1 = AllocTempLocal(type); var value2 = AllocTempLocal(type); - Emit(OpCodes.Stloc, value2); - Emit(OpCodes.Stloc, value1); - Emit(OpCodes.Ldloc, value1); - Emit(OpCodes.Ldloc, value2); + Emit(System.Reflection.Emit.OpCodes.Stloc, value2); + Emit(System.Reflection.Emit.OpCodes.Stloc, value1); + Emit(System.Reflection.Emit.OpCodes.Ldloc, value1); + Emit(System.Reflection.Emit.OpCodes.Ldloc, value2); Emit(cmp1); - Emit(OpCodes.Ldloc, value1); - Emit(OpCodes.Ldloc, value2); + Emit(System.Reflection.Emit.OpCodes.Ldloc, value1); + Emit(System.Reflection.Emit.OpCodes.Ldloc, value2); Emit(cmp2); - Emit(OpCodes.Sub); + Emit(System.Reflection.Emit.OpCodes.Sub); ReleaseTempLocal(value2); ReleaseTempLocal(value1); } internal void Emit_lcmp() { - EmitCmp(context.Types.Int64, OpCodes.Cgt, OpCodes.Clt); + EmitCmp(context.Types.Int64, System.Reflection.Emit.OpCodes.Cgt, System.Reflection.Emit.OpCodes.Clt); } internal void Emit_fcmpl() { - EmitCmp(context.Types.Single, OpCodes.Cgt, OpCodes.Clt_Un); + EmitCmp(context.Types.Single, System.Reflection.Emit.OpCodes.Cgt, System.Reflection.Emit.OpCodes.Clt_Un); } internal void Emit_fcmpg() { - EmitCmp(context.Types.Single, OpCodes.Cgt_Un, OpCodes.Clt); + EmitCmp(context.Types.Single, System.Reflection.Emit.OpCodes.Cgt_Un, System.Reflection.Emit.OpCodes.Clt); } internal void Emit_dcmpl() { - EmitCmp(context.Types.Double, OpCodes.Cgt, OpCodes.Clt_Un); + EmitCmp(context.Types.Double, System.Reflection.Emit.OpCodes.Cgt, System.Reflection.Emit.OpCodes.Clt_Un); } internal void Emit_dcmpg() { - EmitCmp(context.Types.Double, OpCodes.Cgt_Un, OpCodes.Clt); + EmitCmp(context.Types.Double, System.Reflection.Emit.OpCodes.Cgt_Un, System.Reflection.Emit.OpCodes.Clt); } internal void Emit_And_I4(int v) { EmitLdc_I4(v); - Emit(OpCodes.And); + Emit(System.Reflection.Emit.OpCodes.And); } internal void CheckLabels() diff --git a/src/IKVM.Runtime/CodeEmitterLabel.cs b/src/IKVM.Runtime/CodeEmitterLabel.cs index 465b660a2d..d7cae4d015 100644 --- a/src/IKVM.Runtime/CodeEmitterLabel.cs +++ b/src/IKVM.Runtime/CodeEmitterLabel.cs @@ -22,12 +22,7 @@ Jeroen Frijters */ -#if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.Runtime { @@ -35,14 +30,14 @@ namespace IKVM.Runtime sealed class CodeEmitterLabel { - internal readonly Label Label; + internal readonly ILabel Label; internal int Temp; /// /// Initializes a new instance. /// /// - internal CodeEmitterLabel(Label label) + internal CodeEmitterLabel(ILabel label) { this.Label = label; } diff --git a/src/IKVM.Runtime/DefineMethodHelper.cs b/src/IKVM.Runtime/DefineMethodHelper.cs index 5468da3375..d6e041c684 100644 --- a/src/IKVM.Runtime/DefineMethodHelper.cs +++ b/src/IKVM.Runtime/DefineMethodHelper.cs @@ -21,7 +21,8 @@ Jeroen Frijters jeroen@frijters.net */ -using System; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols; #if IMPORTER using IKVM.Reflection; @@ -54,23 +55,23 @@ internal int ParameterCount get { return mw.GetParameters().Length + (mw.HasCallerID ? 1 : 0); } } - internal MethodBuilder DefineMethod(RuntimeByteCodeJavaType context, TypeBuilder tb, string name, MethodAttributes attribs) + internal IMethodSymbolBuilder DefineMethod(RuntimeByteCodeJavaType context, ITypeSymbolBuilder tb, string name, System.Reflection.MethodAttributes attribs) { return DefineMethod(context.ClassLoader.GetTypeWrapperFactory(), tb, name, attribs, null, false); } - internal MethodBuilder DefineMethod(RuntimeJavaTypeFactory context, TypeBuilder tb, string name, MethodAttributes attribs) + internal IMethodSymbolBuilder DefineMethod(RuntimeJavaTypeFactory context, ITypeSymbolBuilder tb, string name, System.Reflection.MethodAttributes attribs) { return DefineMethod(context, tb, name, attribs, null, false); } - internal MethodBuilder DefineMethod(RuntimeJavaTypeFactory context, TypeBuilder tb, string name, MethodAttributes attribs, Type firstParameter, bool mustBePublic) + internal IMethodSymbolBuilder DefineMethod(RuntimeJavaTypeFactory context, ITypeSymbolBuilder tb, string name, System.Reflection.MethodAttributes attribs, ITypeSymbol firstParameter, bool mustBePublic) { // we add optional modifiers to make the signature unique int firstParam = firstParameter == null ? 0 : 1; - RuntimeJavaType[] parameters = mw.GetParameters(); - Type[] parameterTypes = new Type[parameters.Length + (mw.HasCallerID ? 1 : 0) + firstParam]; - Type[][] modopt = new Type[parameterTypes.Length][]; + var parameters = mw.GetParameters(); + var parameterTypes = new ITypeSymbol[parameters.Length + (mw.HasCallerID ? 1 : 0) + firstParam]; + var modopt = new ITypeSymbol[parameterTypes.Length][]; if (firstParameter != null) { parameterTypes[0] = firstParameter; @@ -87,21 +88,20 @@ internal MethodBuilder DefineMethod(RuntimeJavaTypeFactory context, TypeBuilder { parameterTypes[parameterTypes.Length - 1] = mw.DeclaringType.Context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType; } - Type returnType = mustBePublic - ? mw.ReturnType.TypeAsPublicSignatureType - : mw.ReturnType.TypeAsSignatureType; - Type[] modoptReturnType = RuntimeByteCodeJavaType.GetModOpt(context, mw.ReturnType, mustBePublic); - return tb.DefineMethod(name, attribs, CallingConventions.Standard, returnType, null, modoptReturnType, parameterTypes, null, modopt); + + var returnType = mustBePublic ? mw.ReturnType.TypeAsPublicSignatureType : mw.ReturnType.TypeAsSignatureType; + var modoptReturnType = RuntimeByteCodeJavaType.GetModOpt(context, mw.ReturnType, mustBePublic); + return tb.DefineMethod(name, attribs, System.Reflection.CallingConventions.Standard, returnType, null, modoptReturnType, parameterTypes, null, modopt); } - internal MethodBuilder DefineConstructor(RuntimeByteCodeJavaType context, TypeBuilder tb, MethodAttributes attribs) + internal IMethodSymbolBuilder DefineConstructor(RuntimeByteCodeJavaType context, ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs) { return DefineConstructor(context.ClassLoader.GetTypeWrapperFactory(), tb, attribs); } - internal MethodBuilder DefineConstructor(RuntimeJavaTypeFactory context, TypeBuilder tb, MethodAttributes attribs) + internal IMethodSymbolBuilder DefineConstructor(RuntimeJavaTypeFactory context, ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs) { - return DefineMethod(context, tb, ConstructorInfo.ConstructorName, attribs | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName); + return DefineMethod(context, tb, ConstructorInfo.ConstructorName, attribs | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName); } } diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index b8f86ec232..c22efbdfa3 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -29,6 +29,10 @@ Jeroen Frijters using static System.Diagnostics.DebuggableAttribute; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols; + + #if IMPORTER @@ -202,17 +206,17 @@ internal sealed class DynamicClassLoader : RuntimeJavaTypeFactory readonly RuntimeContext context; readonly IDiagnosticHandler diagnostics; - readonly ModuleBuilder moduleBuilder; + readonly IModuleSymbolBuilder moduleBuilder; readonly bool hasInternalAccess; #if IMPORTER - TypeBuilder proxiesContainer; - List proxies; + ITypeSymbolBuilder proxiesContainer; + List proxies; #endif - Dictionary unloadables; - TypeBuilder unloadableContainer; - Type[] delegates; + Dictionary unloadables; + ITypeSymbolBuilder unloadableContainer; + ITypeSymbol[] delegates; /// /// Initializes a new instance. @@ -221,7 +225,7 @@ internal sealed class DynamicClassLoader : RuntimeJavaTypeFactory /// /// /// - internal DynamicClassLoader(RuntimeContext context, IDiagnosticHandler diagnostics, ModuleBuilder moduleBuilder, bool hasInternalAccess) + internal DynamicClassLoader(RuntimeContext context, IDiagnosticHandler diagnostics, IModuleSymbolBuilder moduleBuilder, bool hasInternalAccess) { this.context = context ?? throw new ArgumentNullException(nameof(context)); this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); @@ -310,84 +314,82 @@ private static java.lang.Class TieClassAndWrapper(RuntimeJavaType type, Protecti #if IMPORTER - internal TypeBuilder DefineProxy(string name, TypeAttributes typeAttributes, Type parent, Type[] interfaces) + internal ITypeSymbolBuilder DefineProxy(string name, System.Reflection.TypeAttributes typeAttributes, ITypeSymbol parent, ITypeSymbol[] interfaces) { if (proxiesContainer == null) { - proxiesContainer = moduleBuilder.DefineType(TypeNameUtil.ProxiesContainer, TypeAttributes.Public | TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.Abstract); + proxiesContainer = moduleBuilder.DefineType(TypeNameUtil.ProxiesContainer, System.Reflection.TypeAttributes.Public | System.Reflection.TypeAttributes.Class | System.Reflection.TypeAttributes.Sealed | System.Reflection.TypeAttributes.Abstract); context.AttributeHelper.HideFromJava(proxiesContainer); context.AttributeHelper.SetEditorBrowsableNever(proxiesContainer); - proxies = new List(); + proxies = new List(); } - TypeBuilder tb = proxiesContainer.DefineNestedType(name, typeAttributes, parent, interfaces); + + var tb = proxiesContainer.DefineNestedType(name, typeAttributes, parent, interfaces); proxies.Add(tb); return tb; } #endif - internal override Type DefineUnloadable(string name) + internal override ITypeSymbol DefineUnloadable(string name) { lock (this) { if (unloadables == null) - { - unloadables = new Dictionary(); - } - TypeBuilder type; - if (unloadables.TryGetValue(name, out type)) - { + unloadables = new Dictionary(); + + if (unloadables.TryGetValue(name, out var type)) return type; - } + if (unloadableContainer == null) { - unloadableContainer = moduleBuilder.DefineType(RuntimeUnloadableJavaType.ContainerTypeName, TypeAttributes.Interface | TypeAttributes.Abstract); + unloadableContainer = moduleBuilder.DefineType(RuntimeUnloadableJavaType.ContainerTypeName, System.Reflection.TypeAttributes.Interface | System.Reflection.TypeAttributes.Abstract); context.AttributeHelper.HideFromJava(unloadableContainer); } - type = unloadableContainer.DefineNestedType(TypeNameUtil.MangleNestedTypeName(name), TypeAttributes.NestedPrivate | TypeAttributes.Interface | TypeAttributes.Abstract); + + type = unloadableContainer.DefineNestedType(TypeNameUtil.MangleNestedTypeName(name), System.Reflection.TypeAttributes.NestedPrivate | System.Reflection.TypeAttributes.Interface | System.Reflection.TypeAttributes.Abstract); unloadables.Add(name, type); - return type; + return type.Symbol; } } - internal override Type DefineDelegate(int parameterCount, bool returnVoid) + internal override ITypeSymbol DefineDelegate(int parameterCount, bool returnVoid) { lock (this) { if (delegates == null) - { - delegates = new Type[512]; - } + delegates = new ITypeSymbol[512]; + int index = parameterCount + (returnVoid ? 256 : 0); - Type type = delegates[index]; + var type = delegates[index]; if (type != null) - { return type; - } - TypeBuilder tb = moduleBuilder.DefineType(returnVoid ? "__<>NVIV`" + parameterCount : "__<>NVI`" + (parameterCount + 1), TypeAttributes.NotPublic | TypeAttributes.Sealed, context.Types.MulticastDelegate); - string[] names = new string[parameterCount + (returnVoid ? 0 : 1)]; + + var tb = moduleBuilder.DefineType(returnVoid ? "__<>NVIV`" + parameterCount : "__<>NVI`" + (parameterCount + 1), System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Sealed, context.Types.MulticastDelegate); + var names = new string[parameterCount + (returnVoid ? 0 : 1)]; for (int i = 0; i < names.Length; i++) - { names[i] = "P" + i; - } + if (!returnVoid) - { names[names.Length - 1] = "R"; - } - Type[] genericParameters = tb.DefineGenericParameters(names); - Type[] parameterTypes = genericParameters; + + var genericParameters = tb.DefineGenericParameters(names); + var parameterTypes = genericParameters; if (!returnVoid) { - parameterTypes = new Type[genericParameters.Length - 1]; + parameterTypes = new ITypeSymbol[genericParameters.Length - 1]; Array.Copy(genericParameters, parameterTypes, parameterTypes.Length); } - tb.DefineMethod(ConstructorInfo.ConstructorName, MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName, context.Types.Void, new Type[] { context.Types.Object, context.Types.IntPtr }) - .SetImplementationFlags(MethodImplAttributes.Runtime); - MethodBuilder mb = tb.DefineMethod("Invoke", MethodAttributes.Public | MethodAttributes.NewSlot | MethodAttributes.Virtual, returnVoid ? context.Types.Void : genericParameters[genericParameters.Length - 1], parameterTypes); - mb.SetImplementationFlags(MethodImplAttributes.Runtime); - type = tb.CreateType(); - delegates[index] = type; - return type; + + var ctor = tb.DefineMethod(ConstructorInfo.ConstructorName, System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName, context.Types.Void, [context.Types.Object, context.Types.IntPtr]); + ctor.SetImplementationFlags(System.Reflection.MethodImplAttributes.Runtime); + + var mb = tb.DefineMethod("Invoke", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.NewSlot | System.Reflection.MethodAttributes.Virtual, returnVoid ? context.Types.Void : genericParameters[genericParameters.Length - 1], parameterTypes); + mb.SetImplementationFlags(System.Reflection.MethodImplAttributes.Runtime); + + tb.Complete(); + delegates[index] = tb.Symbol; + return tb.Symbol; } } @@ -449,7 +451,7 @@ internal static ModuleBuilder CreateJniProxyModuleBuilder() #endif - internal sealed override ModuleBuilder ModuleBuilder => moduleBuilder; + internal sealed override IModuleSymbolBuilder ModuleBuilder => moduleBuilder; #if !IMPORTER diff --git a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs index 09b5a01401..9196c97d23 100644 --- a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs +++ b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs @@ -3,7 +3,11 @@ using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER +using IKVM.Reflection; + using Type = IKVM.Reflection.Type; +#else +using System.Reflection; #endif namespace IKVM.Runtime @@ -15,6 +19,25 @@ namespace IKVM.Runtime interface IRuntimeSymbolResolver : ISymbolResolver { + /// + /// Gets the that manages access to symbols. + /// + ISymbolContext Symbols { get; } + + /// + /// Gets the associated with the specified type. + /// + /// + /// + IAssemblySymbol ResolveAssembly(Assembly assembly); + + /// + /// Gets the associated with the specified type. + /// + /// + /// + IModuleSymbol ResolveModule(Module module); + /// /// Gets the associated with the specified type. /// diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index 31889ad730..44c812677a 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -24,7 +24,7 @@ Jeroen Frijters using System; using IKVM.CoreLib.Symbols; - +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -116,9 +116,9 @@ internal static bool IsDynamicMethod(IMethodSymbol method) } } - internal static MethodBuilder DefineTypeInitializer(TypeBuilder typeBuilder, RuntimeClassLoader loader) + internal static IMethodSymbolBuilder DefineTypeInitializer(ITypeSymbolBuilder typeBuilder, RuntimeClassLoader loader) { - var attr = MethodAttributes.Static | MethodAttributes.RTSpecialName | MethodAttributes.SpecialName | MethodAttributes.Private; + var attr = System.Reflection.MethodAttributes.Static | System.Reflection.MethodAttributes.RTSpecialName | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.Private; return typeBuilder.DefineMethod(ConstructorInfo.TypeConstructorName, attr, null, []); } @@ -146,9 +146,9 @@ internal static bool IsConstructor(IMethodBaseSymbol method) return method.IsSpecialName && method.Name == ConstructorInfo.ConstructorName; } - internal static MethodBuilder DefineConstructor(TypeBuilder tb, MethodAttributes attribs, Type[] parameterTypes) + internal static IMethodSymbolBuilder DefineConstructor(ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs, ITypeSymbol[] parameterTypes) { - return tb.DefineMethod(ConstructorInfo.ConstructorName, attribs | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName, null, parameterTypes); + return tb.DefineMethod(ConstructorInfo.ConstructorName, attribs | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName, null, parameterTypes); } /// diff --git a/src/IKVM.Runtime/RuntimeArrayJavaType.cs b/src/IKVM.Runtime/RuntimeArrayJavaType.cs index 1bcc4c1b8a..95cd1a6c5b 100644 --- a/src/IKVM.Runtime/RuntimeArrayJavaType.cs +++ b/src/IKVM.Runtime/RuntimeArrayJavaType.cs @@ -27,7 +27,6 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Symbols; - #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -45,7 +44,7 @@ sealed class RuntimeArrayJavaType : RuntimeJavaType volatile RuntimeJavaType[] interfaces; readonly RuntimeJavaType ultimateElementTypeWrapper; - Type arrayType; + ITypeSymbol arrayType; bool finished; /// @@ -68,9 +67,9 @@ internal override RuntimeJavaType BaseTypeWrapper internal override RuntimeClassLoader ClassLoader => ultimateElementTypeWrapper.ClassLoader; - internal static MethodInfo GetCloneMethod(RuntimeContext context) + internal static IMethodSymbol GetCloneMethod(RuntimeContext context) { - return context.Types.Array.GetMethod("Clone", BindingFlags.Public | BindingFlags.Instance, null, [], null); + return context.Types.Array.GetMethod("Clone", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance, []); } protected override void LazyPublishMembers() @@ -113,14 +112,14 @@ internal override RuntimeJavaType[] Interfaces } } - internal override Type TypeAsTBD + internal override ITypeSymbol TypeAsTBD { get { while (arrayType == null) { bool prevFinished = finished; - Type type = MakeArrayType(ultimateElementTypeWrapper.TypeAsArrayType, this.ArrayRank); + var type = MakeArrayType(ultimateElementTypeWrapper.TypeAsArrayType, this.ArrayRank); if (prevFinished) { // We were already finished prior to the call to MakeArrayType, so we can safely diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.DynamicImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.DynamicImpl.cs index 5349598430..7606d43349 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.DynamicImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.DynamicImpl.cs @@ -21,9 +21,8 @@ Jeroen Frijters jeroen@frijters.net */ -using System; - using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER using IKVM.Reflection; @@ -42,13 +41,13 @@ partial class RuntimeByteCodeJavaType private abstract class DynamicImpl { - internal abstract Type Type { get; } + internal abstract ITypeSymbol Type { get; } internal abstract RuntimeJavaType[] InnerClasses { get; } internal abstract RuntimeJavaType DeclaringTypeWrapper { get; } internal abstract Modifiers ReflectiveModifiers { get; } internal abstract DynamicImpl Finish(); - internal abstract MethodBase LinkMethod(RuntimeJavaMethod mw); - internal abstract FieldInfo LinkField(RuntimeJavaField fw); + internal abstract IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw); + internal abstract IFieldSymbol LinkField(RuntimeJavaField fw); internal abstract void EmitRunClassConstructor(CodeEmitter ilgen); internal abstract string GetGenericSignature(); internal abstract string[] GetEnclosingMethod(); @@ -60,7 +59,7 @@ private abstract class DynamicImpl internal abstract object[][] GetParameterAnnotations(int index); internal abstract MethodParametersEntry[] GetMethodParameters(int index); internal abstract object[] GetFieldAnnotations(int index); - internal abstract MethodInfo GetFinalizeMethod(); + internal abstract IMethodSymbol GetFinalizeMethod(); internal abstract object[] GetConstantPool(); internal abstract byte[] GetRawTypeAnnotations(); internal abstract byte[] GetMethodRawTypeAnnotations(int index); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishedTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishedTypeImpl.cs index f6b97af947..7488888bee 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishedTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishedTypeImpl.cs @@ -25,6 +25,7 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER using IKVM.Reflection; @@ -46,16 +47,16 @@ partial class RuntimeByteCodeJavaType sealed class FinishedTypeImpl : DynamicImpl { - readonly Type type; + readonly ITypeSymbol type; readonly RuntimeJavaType[] innerclasses; readonly RuntimeJavaType declaringTypeWrapper; readonly Modifiers reflectiveModifiers; - readonly MethodInfo clinitMethod; - readonly MethodInfo finalizeMethod; + readonly IMethodSymbol clinitMethod; + readonly IMethodSymbol finalizeMethod; readonly Metadata metadata; readonly RuntimeJavaType host; - internal FinishedTypeImpl(Type type, RuntimeJavaType[] innerclasses, RuntimeJavaType declaringTypeWrapper, Modifiers reflectiveModifiers, Metadata metadata, MethodInfo clinitMethod, MethodInfo finalizeMethod, RuntimeJavaType host) + internal FinishedTypeImpl(ITypeSymbol type, RuntimeJavaType[] innerclasses, RuntimeJavaType declaringTypeWrapper, Modifiers reflectiveModifiers, Metadata metadata, IMethodSymbol clinitMethod, IMethodSymbol finalizeMethod, RuntimeJavaType host) { this.type = type; this.innerclasses = innerclasses; @@ -93,7 +94,7 @@ internal override Modifiers ReflectiveModifiers } } - internal override Type Type + internal override ITypeSymbol Type { get { @@ -105,7 +106,7 @@ internal override void EmitRunClassConstructor(CodeEmitter ilgen) { if (clinitMethod != null) { - ilgen.Emit(OpCodes.Call, clinitMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, clinitMethod); } } @@ -114,14 +115,14 @@ internal override DynamicImpl Finish() return this; } - internal override MethodBase LinkMethod(RuntimeJavaMethod mw) + internal override IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) { // we should never be called, because all methods on a finished type are already linked Debug.Assert(false); return mw.GetMethod(); } - internal override FieldInfo LinkField(RuntimeJavaField fw) + internal override IFieldSymbol LinkField(RuntimeJavaField fw) { // we should never be called, because all fields on a finished type are already linked Debug.Assert(false); @@ -178,7 +179,7 @@ internal override object[] GetFieldAnnotations(int index) return Metadata.GetFieldAnnotations(metadata, index); } - internal override MethodInfo GetFinalizeMethod() + internal override IMethodSymbol GetFinalizeMethod() { return finalizeMethod; } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index 2964cf197d..ffa19a8589 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -27,6 +27,8 @@ Jeroen Frijters using System.Collections.Concurrent; using IKVM.Attributes; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols; #if IMPORTER using IKVM.Reflection; @@ -54,20 +56,20 @@ private sealed partial class JavaTypeImpl : DynamicImpl readonly RuntimeJavaType host; readonly ClassFile classFile; readonly RuntimeDynamicOrImportJavaType wrapper; - TypeBuilder typeBuilder; + ITypeSymbolBuilder typeBuilder; RuntimeJavaMethod[] methods; RuntimeJavaMethod[][] baseMethods; RuntimeJavaField[] fields; FinishedTypeImpl finishedType; bool finishInProgress; - MethodBuilder clinitMethod; - MethodBuilder finalizeMethod; + IMethodSymbolBuilder clinitMethod; + IMethodSymbolBuilder finalizeMethod; int recursionCount; #if IMPORTER RuntimeByteCodeJavaType enclosingClassWrapper; AnnotationBuilder annotationBuilder; - TypeBuilder enumBuilder; - TypeBuilder privateInterfaceMethods; + ITypeSymbolBuilder enumBuilder; + ITypeSymbolBuilder privateInterfaceMethods; ConcurrentDictionary nestedTypeNames; // only keys are used, values are always null #endif @@ -952,19 +954,16 @@ private static void CheckLoaderConstraints(RuntimeJavaMethod mw, RuntimeJavaMeth } } - private int GetFieldIndex(RuntimeJavaField fw) + int GetFieldIndex(RuntimeJavaField fw) { for (int i = 0; i < fields.Length; i++) - { if (fields[i] == fw) - { return i; - } - } + throw new InvalidOperationException(); } - internal override FieldInfo LinkField(RuntimeJavaField fw) + internal override IFieldSymbol LinkField(RuntimeJavaField fw) { if (fw is RuntimeByteCodePropertyJavaField) { @@ -990,15 +989,9 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) // order, we emit the fields in class declaration order in the .NET metadata (and then when we retrieve them // using .NET reflection, we sort on metadata token.) if (fieldIndex > 0) - { if (!fields[fieldIndex - 1].IsLinked) - { for (int i = 0; i < fieldIndex; i++) - { fields[i].Link(); - } - } - } if (fieldIndex >= classFile.Fields.Length) { @@ -1028,21 +1021,24 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) { fieldAttribs |= FieldAttributes.InitOnly; } + return DefineField(fw.Name, fw.FieldTypeWrapper, fieldAttribs, fw.IsVolatile); } #endif // IMPORTER - FieldBuilder field; - ClassFile.Field fld = classFile.Fields[fieldIndex]; + IFieldSymbolBuilder field; + var fld = classFile.Fields[fieldIndex]; FieldAttributes attribs = 0; - string realFieldName = UnicodeUtil.EscapeInvalidSurrogates(fld.Name); + var realFieldName = UnicodeUtil.EscapeInvalidSurrogates(fld.Name); if (!ReferenceEquals(realFieldName, fld.Name)) { attribs |= FieldAttributes.SpecialName; } - MethodAttributes methodAttribs = MethodAttributes.HideBySig; + + var methodAttribs = MethodAttributes.HideBySig; #if IMPORTER bool setModifiers = fld.IsInternal || (fld.Modifiers & (Modifiers.Synthetic | Modifiers.Enum)) != 0; #endif + if (fld.IsPrivate) { attribs |= FieldAttributes.Private; @@ -1068,6 +1064,7 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) attribs |= FieldAttributes.Static; methodAttribs |= MethodAttributes.Static; } + // NOTE "constant" static finals are converted into literals // TODO it would be possible for Java code to change the value of a non-blank static final, but I don't // know if we want to support this (since the Java JITs don't really support it either) @@ -1138,7 +1135,7 @@ internal override FieldInfo LinkField(RuntimeJavaField fw) return field; } - FieldBuilder DefineField(string name, RuntimeJavaType tw, FieldAttributes attribs, bool isVolatile) + IFieldSymbolBuilder DefineField(string name, RuntimeJavaType tw, FieldAttributes attribs, bool isVolatile) { var modreq = isVolatile ? [wrapper.Context.Types.IsVolatile] : []; return typeBuilder.DefineField(name, tw.TypeAsSignatureType, modreq, wrapper.GetModOpt(tw, false), attribs); @@ -1384,10 +1381,10 @@ sealed class AnnotationBuilder : Annotation readonly RuntimeContext context; JavaTypeImpl impl; - TypeBuilder outer; - TypeBuilder annotationTypeBuilder; - TypeBuilder attributeTypeBuilder; - MethodBuilder defineConstructor; + ITypeSymbolBuilder outer; + ITypeSymbolBuilder annotationTypeBuilder; + ITypeSymbolBuilder attributeTypeBuilder; + IMethodSymbolBuilder defineConstructor; /// /// Initializes a new instance. @@ -1395,7 +1392,7 @@ sealed class AnnotationBuilder : Annotation /// /// /// - internal AnnotationBuilder(RuntimeContext context, JavaTypeImpl o, TypeBuilder outer) + internal AnnotationBuilder(RuntimeContext context, JavaTypeImpl o, ITypeSymbolBuilder outer) { this.context = context; this.impl = o; @@ -1541,28 +1538,25 @@ internal void Link() { // apply any .NET custom attributes that are on the annotation to the custom attribute we synthesize // (for example, to allow AttributeUsageAttribute to be overridden) - Annotation annotation = Annotation.Load(o.wrapper, def); + var annotation = Annotation.Load(o.wrapper, def); if (annotation != null && annotation.IsCustomAttribute) - { annotation.Apply(o.wrapper.ClassLoader, attributeTypeBuilder, def); - } if (def[1].Equals("Lcli/System/AttributeUsageAttribute$Annotation;")) - { hasAttributeUsageAttribute = true; - } } } + if (attributeUsageAttribute != null && !hasAttributeUsageAttribute) { attributeTypeBuilder.SetCustomAttribute(attributeUsageAttribute); } } - defineConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, new Type[] { context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType().AsReflection() }); + defineConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, [context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType()]); context.AttributeHelper.SetEditorBrowsableNever(defineConstructor); } - private static Type TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) + static ITypeSymbol TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) { bool isArray = false; if (tw.IsArray) @@ -1570,6 +1564,7 @@ private static Type TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) isArray = true; tw = tw.ElementTypeWrapper; } + if (tw.Annotation != null) { // we don't support Annotation args @@ -1577,7 +1572,7 @@ private static Type TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) } else { - Type argType; + ITypeSymbol argType; if (tw == tw.Context.JavaBase.TypeOfJavaLangClass) { argType = tw.Context.Types.Type; @@ -1594,15 +1589,15 @@ private static Type TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) { argType = tw.TypeAsSignatureType; } + if (isArray) - { argType = RuntimeArrayJavaType.MakeArrayType(argType, 1); - } + return argType; } } - private static bool IsDotNetEnum(RuntimeJavaType tw) + static bool IsDotNetEnum(RuntimeJavaType tw) { return tw.IsFakeNestedType && (tw.Modifiers & Modifiers.Enum) != 0; } @@ -1612,15 +1607,15 @@ internal string AttributeTypeName get { Link(); + if (attributeTypeBuilder != null) - { - return attributeTypeBuilder.FullName; - } + return attributeTypeBuilder.Symbol.FullName; + return null; } } - private static void EmitSetValueCall(RuntimeJavaType annotationAttributeBaseType, CodeEmitter ilgen, string name, RuntimeJavaType tw, int argIndex) + static void EmitSetValueCall(RuntimeJavaType annotationAttributeBaseType, CodeEmitter ilgen, string name, RuntimeJavaType tw, int argIndex) { ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ldstr, name); @@ -1637,6 +1632,7 @@ private static void EmitSetValueCall(RuntimeJavaType annotationAttributeBaseType { ilgen.Emit(OpCodes.Box, tw.DeclaringTypeWrapper.TypeAsSignatureType); } + var setValueMethod = annotationAttributeBaseType.GetMethodWrapper("setValue", "(Ljava.lang.String;Ljava.lang.Object;)V", false); setValueMethod.Link(); setValueMethod.EmitCall(ilgen); @@ -1683,7 +1679,7 @@ internal void Finish(JavaTypeImpl o) { if (requiredArgCount > 0) { - var args = new Type[requiredArgCount]; + var args = new ITypeSymbol[requiredArgCount]; for (int i = 0, j = 0; i < o.methods.Length; i++) { if (!o.methods[i].IsStatic) @@ -1699,7 +1695,7 @@ internal void Finish(JavaTypeImpl o) context.AttributeHelper.HideFromJava(reqArgConstructor); ilgen = context.CodeEmitterFactory.Create(reqArgConstructor); ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Call, defaultConstructor); + ilgen.Emit(OpCodes.Call, defaultConstructor.Symbol); for (int i = 0, j = 0; i < o.methods.Length; i++) { @@ -1852,38 +1848,38 @@ internal void Finish(JavaTypeImpl o) private CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { Link(); - ConstructorInfo ctor = defineConstructor != null + var ctor = defineConstructor != null ? defineConstructor.__AsConstructorInfo() - : context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").AsReflection().GetConstructor(new Type[] { context.Types.Object.MakeArrayType() }); + : context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").GetConstructor(new [] { context.Types.Object.MakeArrayType() }); return new CustomAttributeBuilder(ctor, new object[] { AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation)) }); } - internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) + internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) { tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) { mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IFieldSymbolBuilder fb, object annotation) { fb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder pb, object annotation) { pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) + internal override void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder ab, object annotation) { ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IPropertySymbolBuilder pb, object annotation) { pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } @@ -2365,7 +2361,7 @@ MethodAttributes GetPropertyAccess(RuntimeJavaMethod mw) } } - internal override MethodBase LinkMethod(RuntimeJavaMethod mw) + internal override IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) { Debug.Assert(mw != null); @@ -2945,7 +2941,7 @@ private static bool IsAccessBridge(ClassFile classFile, ClassFile.Method m) } #endif // IMPORTER - internal override Type Type + internal override ITypeSymbol Type { get { @@ -3013,7 +3009,7 @@ internal override object[] GetFieldAnnotations(int index) return null; } - internal override MethodInfo GetFinalizeMethod() + internal override IMethodSymbol GetFinalizeMethod() { return finalizeMethod; } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index ad900b87fb..5eb072d7c3 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -27,7 +27,8 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Diagnostics; - +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER using IKVM.Reflection; @@ -54,12 +55,6 @@ sealed partial class RuntimeByteCodeJavaType : RuntimeJavaType #endif { -#if IMPORTER == false && NETCOREAPP - - static readonly PropertyInfo MetadataTokenInternalPropertyInfo = typeof(MethodBuilder).GetProperty("MetadataTokenInternal", BindingFlags.Instance | BindingFlags.NonPublic); - -#endif - #if IMPORTER protected readonly ImportClassLoader classLoader; #else @@ -72,7 +67,7 @@ sealed partial class RuntimeByteCodeJavaType : RuntimeJavaType #if !IMPORTER byte[][] lineNumberTables; #endif - MethodBase automagicSerializationCtor; + IMethodBaseSymbol automagicSerializationCtor; RuntimeJavaType LoadTypeWrapper(RuntimeClassLoader classLoader, ProtectionDomain pd, ClassFile.ConstantPoolItemClass clazz) { @@ -93,21 +88,19 @@ private static void CheckMissing(RuntimeJavaType prev, RuntimeJavaType tw) #if IMPORTER do { - RuntimeUnloadableJavaType missing = tw as RuntimeUnloadableJavaType; + var missing = tw as RuntimeUnloadableJavaType; if (missing != null) { - Type mt = ReflectUtil.GetMissingType(missing.MissingType); - if (mt.Assembly.__IsMissing) - { + var mt = ReflectUtil.GetMissingType(missing.MissingType); + if (mt.Assembly.IsMissing) throw new FatalCompilerErrorException(DiagnosticEvent.MissingBaseTypeReference(mt.FullName, mt.Assembly.FullName)); - } throw new FatalCompilerErrorException(DiagnosticEvent.MissingBaseType(mt.FullName, mt.Assembly.FullName, prev.TypeAsBaseType.FullName, prev.TypeAsBaseType.Module.Name)); } + foreach (RuntimeJavaType iface in tw.Interfaces) - { CheckMissing(tw, iface); - } + prev = tw; tw = tw.BaseTypeWrapper; } @@ -351,7 +344,7 @@ internal override RuntimeJavaType DeclaringTypeWrapper } } - internal override Type TypeAsTBD + internal override ITypeSymbol TypeAsTBD { get { @@ -408,7 +401,7 @@ static bool TypesMatchForOverride(RuntimeJavaType tw1, RuntimeJavaType tw2) return false; } - void GenerateOverrideStub(TypeBuilder typeBuilder, RuntimeJavaMethod baseMethod, MethodInfo target, RuntimeJavaMethod targetMethod) + void GenerateOverrideStub(ITypeSymbolBuilder typeBuilder, RuntimeJavaMethod baseMethod, IMethodSymbol target, RuntimeJavaMethod targetMethod) { Debug.Assert(!baseMethod.HasCallerID); @@ -587,9 +580,9 @@ protected static void GetParameterNamesFromSig(string sig, string[] parameterNam parameterNames[i] = names[i]; } - protected static ParameterBuilder[] GetParameterBuilders(MethodBuilder mb, int parameterCount, string[] parameterNames) + protected static IParameterSymbolBuilder[] GetParameterBuilders(IMethodSymbolBuilder mb, int parameterCount, string[] parameterNames) { - var parameterBuilders = new ParameterBuilder[parameterCount]; + var parameterBuilders = new IParameterSymbolBuilder[parameterCount]; Dictionary clashes = null; for (int i = 0; i < parameterBuilders.Length; i++) { @@ -609,8 +602,10 @@ protected static ParameterBuilder[] GetParameterBuilders(MethodBuilder mb, int p name += clash; } } - parameterBuilders[i] = mb.DefineParameter(i + 1, ParameterAttributes.None, name); + + parameterBuilders[i] = mb.DefineParameter(i + 1, System.Reflection.ParameterAttributes.None, name); } + return parameterBuilders; } @@ -641,67 +636,57 @@ private static string GetParameterName(string type) protected abstract bool EmitMapXmlMethodPrologueAndOrBody(CodeEmitter ilgen, ClassFile f, ClassFile.Method m); - protected abstract void EmitMapXmlMetadata(TypeBuilder typeBuilder, ClassFile classFile, RuntimeJavaField[] fields, RuntimeJavaMethod[] methods); + protected abstract void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, ClassFile classFile, RuntimeJavaField[] fields, RuntimeJavaMethod[] methods); - protected abstract MethodBuilder DefineGhostMethod(TypeBuilder typeBuilder, string name, MethodAttributes attribs, RuntimeJavaMethod mw); + protected abstract MethodBuilder DefineGhostMethod(ITypeSymbolBuilder typeBuilder, string name, System.Reflection.MethodAttributes attribs, RuntimeJavaMethod mw); - protected abstract void FinishGhost(TypeBuilder typeBuilder, RuntimeJavaMethod[] methods); + protected abstract void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaMethod[] methods); protected abstract void FinishGhostStep2(); - protected abstract TypeBuilder DefineGhostType(string mangledTypeName, TypeAttributes typeAttribs); + protected abstract TypeBuilder DefineGhostType(string mangledTypeName, System.Reflection.TypeAttributes typeAttribs); #endif // IMPORTER private bool IsPInvokeMethod(ClassFile.Method m) { #if IMPORTER - Dictionary mapxml = classLoader.GetMapXmlClasses(); + var mapxml = classLoader.GetMapXmlClasses(); if (mapxml != null) { - IKVM.Tools.Importer.MapXml.Class clazz; - if (mapxml.TryGetValue(this.Name, out clazz) && clazz.Methods != null) + if (mapxml.TryGetValue(this.Name, out var clazz) && clazz.Methods != null) { foreach (IKVM.Tools.Importer.MapXml.Method method in clazz.Methods) { if (method.Name == m.Name && method.Sig == m.Signature) { if (method.Attributes != null) - { foreach (IKVM.Tools.Importer.MapXml.Attribute attr in method.Attributes) - { if (Context.StaticCompiler.GetType(classLoader, attr.Type) == Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.DllImportAttribute).FullName).AsReflection()) - { return true; - } - } - } + break; } } } } #endif + if (m.Annotations != null) - { foreach (object[] annot in m.Annotations) - { if ("Lcli/System/Runtime/InteropServices/DllImportAttribute$Annotation;".Equals(annot[1])) - { return true; - } - } - } + return false; } - internal override MethodBase LinkMethod(RuntimeJavaMethod mw) + internal override IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) { mw.AssertLinked(); return impl.LinkMethod(mw); } - internal override FieldInfo LinkField(RuntimeJavaField fw) + internal override IFieldSymbol LinkField(RuntimeJavaField fw) { fw.AssertLinked(); return impl.LinkField(fw); @@ -719,42 +704,33 @@ internal override string GetGenericSignature() internal override string GetGenericMethodSignature(RuntimeJavaMethod mw) { - RuntimeJavaMethod[] methods = GetMethods(); + var methods = GetMethods(); for (int i = 0; i < methods.Length; i++) - { if (methods[i] == mw) - { return impl.GetGenericMethodSignature(i); - } - } + Debug.Fail("Unreachable code"); return null; } internal override string GetGenericFieldSignature(RuntimeJavaField fw) { - RuntimeJavaField[] fields = GetFields(); + var fields = GetFields(); for (int i = 0; i < fields.Length; i++) - { if (fields[i] == fw) - { return impl.GetGenericFieldSignature(i); - } - } + Debug.Fail("Unreachable code"); return null; } internal override MethodParametersEntry[] GetMethodParameters(RuntimeJavaMethod mw) { - RuntimeJavaMethod[] methods = GetMethods(); + var methods = GetMethods(); for (int i = 0; i < methods.Length; i++) - { if (methods[i] == mw) - { return impl.GetMethodParameters(i); - } - } + Debug.Fail("Unreachable code"); return null; } @@ -780,30 +756,9 @@ internal override string GetSourceFileName() /// /// /// - int GetMethodBaseToken(MethodBase mb) + int GetMethodBaseToken(IMethodBaseSymbol mb) { - if (mb is MethodBuilder mbld) - { -#if NETFRAMEWORK - return mbld.GetToken().Token; -#else - try - { - return mbld.GetMetadataToken(); - } - catch (InvalidOperationException) - { - if (MetadataTokenInternalPropertyInfo != null) - return (int)MetadataTokenInternalPropertyInfo.GetValue(mbld); - } -#endif - } - -#if NETFRAMEWORK return mb.MetadataToken; -#else - return mb.GetMetadataToken(); -#endif } /// @@ -812,7 +767,7 @@ int GetMethodBaseToken(MethodBase mb) /// /// /// - internal override int GetSourceLineNumber(MethodBase mb, int ilOffset) + internal override int GetSourceLineNumber(IMethodBaseSymbol mb, int ilOffset) { if (lineNumberTables != null) { @@ -858,76 +813,71 @@ internal override object[] GetDeclaredAnnotations() internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) { - RuntimeJavaMethod[] methods = GetMethods(); + var methods = GetMethods(); for (int i = 0; i < methods.Length; i++) - { if (methods[i] == mw) - { return DecodeAnnotations(impl.GetMethodAnnotations(i)); - } - } + Debug.Fail("Unreachable code"); return null; } internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) { - RuntimeJavaMethod[] methods = GetMethods(); + var methods = GetMethods(); for (int i = 0; i < methods.Length; i++) { if (methods[i] == mw) { - object[][] annotations = impl.GetParameterAnnotations(i); + var annotations = impl.GetParameterAnnotations(i); if (annotations != null) { object[][] objs = new object[annotations.Length][]; for (int j = 0; j < annotations.Length; j++) - { objs[j] = DecodeAnnotations(annotations[j]); - } + return objs; } + return null; } } + Debug.Fail("Unreachable code"); return null; } internal override object[] GetFieldAnnotations(RuntimeJavaField fw) { - RuntimeJavaField[] fields = GetFields(); + var fields = GetFields(); for (int i = 0; i < fields.Length; i++) - { if (fields[i] == fw) - { return DecodeAnnotations(impl.GetFieldAnnotations(i)); - } - } + Debug.Fail("Unreachable code"); return null; } internal override object GetAnnotationDefault(RuntimeJavaMethod mw) { - RuntimeJavaMethod[] methods = GetMethods(); + var methods = GetMethods(); for (int i = 0; i < methods.Length; i++) { if (methods[i] == mw) { - object defVal = impl.GetMethodDefaultValue(i); + var defVal = impl.GetMethodDefaultValue(i); if (defVal != null) - { return JVM.NewAnnotationElementValue(mw.DeclaringType.ClassLoader.GetJavaClassLoader(), mw.ReturnType.ClassObject, defVal); - } + return null; } } + Debug.Fail("Unreachable code"); return null; } - private Type GetBaseTypeForDefineType() + private ITypeSymbol GetBaseTypeForDefineType() { return BaseTypeWrapper.TypeAsBaseType; } @@ -936,7 +886,7 @@ private Type GetBaseTypeForDefineType() #if IMPORTER - protected virtual Type GetBaseTypeForDefineType() + protected virtual ITypeSymbol GetBaseTypeForDefineType() { return BaseTypeWrapper.TypeAsBaseType; } @@ -948,33 +898,31 @@ internal virtual RuntimeJavaMethod[] GetReplacedMethodsFor(RuntimeJavaMethod mw) #endif // IMPORTER - internal override MethodBase GetSerializationConstructor() + internal override IMethodBaseSymbol GetSerializationConstructor() { return automagicSerializationCtor; } - private Type[] GetModOpt(RuntimeJavaType tw, bool mustBePublic) + private ITypeSymbol[] GetModOpt(RuntimeJavaType tw, bool mustBePublic) { return GetModOpt(ClassLoader.GetTypeWrapperFactory(), tw, mustBePublic); } - internal static Type[] GetModOpt(RuntimeJavaTypeFactory context, RuntimeJavaType tw, bool mustBePublic) + internal static ITypeSymbol[] GetModOpt(RuntimeJavaTypeFactory context, RuntimeJavaType tw, bool mustBePublic) { - Type[] modopt = []; + ITypeSymbol[] modopt = []; if (tw.IsUnloadable) { if (((RuntimeUnloadableJavaType)tw).MissingType == null) - { - modopt = new Type[] { ((RuntimeUnloadableJavaType)tw).GetCustomModifier(context) }; - } + modopt = new ITypeSymbol[] { ((RuntimeUnloadableJavaType)tw).GetCustomModifier(context) }; } else { - RuntimeJavaType tw1 = tw.IsArray ? tw.GetUltimateElementTypeWrapper() : tw; + var tw1 = tw.IsArray ? tw.GetUltimateElementTypeWrapper() : tw; if (tw1.IsErasedOrBoxedPrimitiveOrRemapped || tw.IsGhostArray || (mustBePublic && !tw1.IsPublic)) { // FXBUG Ref.Emit refuses arrays in custom modifiers, so we add an array type for each dimension - modopt = new Type[tw.ArrayRank + 1]; + modopt = new ITypeSymbol[tw.ArrayRank + 1]; modopt[0] = GetModOptHelper(tw1); for (int i = 1; i < modopt.Length; i++) { @@ -985,9 +933,10 @@ internal static Type[] GetModOpt(RuntimeJavaTypeFactory context, RuntimeJavaType return modopt; } - private static Type GetModOptHelper(RuntimeJavaType tw) + static ITypeSymbol GetModOptHelper(RuntimeJavaType tw) { Debug.Assert(!tw.IsUnloadable); + if (tw.IsArray) { return RuntimeArrayJavaType.MakeArrayType(GetModOptHelper(tw.GetUltimateElementTypeWrapper()), tw.ArrayRank); @@ -1003,7 +952,8 @@ private static Type GetModOptHelper(RuntimeJavaType tw) } #if IMPORTER - private bool NeedsType2AccessStub(RuntimeJavaField fw) + + bool NeedsType2AccessStub(RuntimeJavaField fw) { Debug.Assert(this.IsPublic && fw.DeclaringType == this); return fw.IsType2FinalField @@ -1011,6 +961,7 @@ private bool NeedsType2AccessStub(RuntimeJavaField fw) && (fw.IsPublic || (fw.IsProtected && !this.IsFinal)) && (fw.FieldTypeWrapper.IsUnloadable || fw.FieldTypeWrapper.IsAccessibleFrom(this) || fw.FieldTypeWrapper.InternalsVisibleTo(this))); } + #endif internal static bool RequiresDynamicReflectionCallerClass(string classFile, string method, string signature) @@ -1074,6 +1025,7 @@ internal void EmitLevel4Warning(HardError error, string message) } #endif } + } } \ No newline at end of file diff --git a/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs b/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs index 00a6b1c0a3..877505558a 100644 --- a/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs +++ b/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs @@ -21,16 +21,13 @@ Jeroen Frijters jeroen@frijters.net */ -using System; - -using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; - #else using System.Reflection; using System.Reflection.Emit; @@ -53,7 +50,7 @@ sealed class RuntimeByteCodePropertyJavaField : RuntimeJavaField readonly RuntimeJavaMethod getter; readonly RuntimeJavaMethod setter; - PropertyBuilder pb; + IPropertySymbolBuilder pb; RuntimeJavaMethod GetMethod(string name, string sig, bool isstatic) { @@ -94,31 +91,25 @@ internal override void ResolveField() #endif - internal PropertyBuilder GetPropertyBuilder() + internal IPropertySymbolBuilder GetPropertyBuilder() { AssertLinked(); return pb; } - internal void DoLink(TypeBuilder tb) + internal void DoLink(ITypeSymbolBuilder tb) { if (getter != null) - { getter.Link(); - } if (setter != null) - { setter.Link(); - } - pb = tb.DefineProperty(this.Name, PropertyAttributes.None, this.FieldTypeWrapper.TypeAsSignatureType, []); + + pb = tb.DefineProperty(Name, PropertyAttributes.None, FieldTypeWrapper.TypeAsSignatureType, []); if (getter != null) - { - pb.SetGetMethod((MethodBuilder)getter.GetMethod()); - } + pb.SetGetMethod((IMethodSymbolBuilder)getter.GetMethod()); if (setter != null) - { - pb.SetSetMethod((MethodBuilder)setter.GetMethod()); - } + pb.SetSetMethod((IMethodSymbolBuilder)setter.GetMethod()); + #if IMPORTER DeclaringType.Context.AttributeHelper.SetModifiers(pb, this.Modifiers, this.IsInternal); #endif @@ -147,7 +138,7 @@ internal static void EmitThrowNoSuchMethodErrorForGetter(CodeEmitter ilgen, Runt type.ClassLoader.Diagnostics.EmittedNoSuchMethodError("", member.DeclaringType.Name + "." + member.Name + member.Signature); #endif // HACK the branch around the throw is to keep the verifier happy - CodeEmitterLabel label = ilgen.DefineLabel(); + var label = ilgen.DefineLabel(); ilgen.Emit(OpCodes.Ldc_I4_0); ilgen.EmitBrtrue(label); ilgen.EmitThrow("java.lang.NoSuchMethodError"); @@ -192,7 +183,7 @@ internal static void EmitThrowNoSuchMethodErrorForSetter(CodeEmitter ilgen, Runt member.DeclaringType.ClassLoader.Diagnostics.EmittedNoSuchMethodError("", member.DeclaringType.Name + "." + member.Name + member.Signature); #endif // HACK the branch around the throw is to keep the verifier happy - CodeEmitterLabel label = ilgen.DefineLabel(); + var label = ilgen.DefineLabel(); ilgen.Emit(OpCodes.Ldc_I4_0); ilgen.EmitBrtrue(label); ilgen.EmitThrow("java.lang.NoSuchMethodError"); @@ -206,23 +197,23 @@ internal static void EmitThrowNoSuchMethodErrorForSetter(CodeEmitter ilgen, Runt #endif #if !IMPORTER && !FIRST_PASS + internal override object GetValue(object obj) { if (getter == null) - { throw new java.lang.NoSuchMethodError(); - } + return getter.Invoke(obj, []); } internal override void SetValue(object obj, object value) { if (setter == null) - { throw new java.lang.NoSuchMethodError(); - } + setter.Invoke(obj, new object[] { value }); } + #endif } diff --git a/src/IKVM.Runtime/RuntimeClassLoader.cs b/src/IKVM.Runtime/RuntimeClassLoader.cs index 03a426852d..e2d095ec17 100644 --- a/src/IKVM.Runtime/RuntimeClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeClassLoader.cs @@ -27,6 +27,7 @@ Jeroen Frijters using System.Diagnostics; using System.Threading; +using IKVM.CoreLib.Symbols; using IKVM.Runtime.Accessors.Java.Lang; using IKVM.CoreLib.Diagnostics; @@ -99,7 +100,7 @@ internal RuntimeClassLoader(RuntimeContext context, CodeGenOptions codegenoption #if IMPORTER || EXPORTER - internal void SetRemappedType(Type type, RuntimeJavaType tw) + internal void SetRemappedType(ITypeSymbol type, RuntimeJavaType tw) { lock (types) types.Add(tw.Name, tw); @@ -541,7 +542,7 @@ internal RuntimeJavaType FindOrLoadGenericClass(string name, LoadMode mode) } } - var typeArguments = new Type[typeParamNames.Count]; + var typeArguments = new ITypeSymbol[typeParamNames.Count]; for (int i = 0; i < typeArguments.Length; i++) { var s = typeParamNames[i]; @@ -741,13 +742,13 @@ internal virtual java.lang.ClassLoader GetJavaClassLoader() /// . /// /// - internal Type[] ArgTypeListFromSig(string signature) + internal ITypeSymbol[] ArgTypeListFromSig(string signature) { if (signature[1] == ')') return []; var javaTypes = ArgJavaTypeListFromSig(signature, LoadMode.LoadOrThrow); - var types = new Type[javaTypes.Length]; + var types = new ITypeSymbol[javaTypes.Length]; for (int i = 0; i < javaTypes.Length; i++) types[i] = javaTypes[i].TypeAsSignatureType; diff --git a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs index c84a9c54cd..f47f336ec6 100644 --- a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs @@ -263,22 +263,23 @@ internal RuntimeJavaType GetJavaTypeFromType(ITypeSymbol type) internal RuntimeClassLoader GetGenericClassLoader(RuntimeJavaType wrapper) { - Type type = wrapper.TypeAsTBD; + var type = wrapper.TypeAsTBD; Debug.Assert(type.IsGenericType); Debug.Assert(!type.ContainsGenericParameters); - List list = new List(); + var list = new List(); list.Add(context.AssemblyClassLoaderFactory.FromAssembly(type.Assembly)); - foreach (Type arg in type.GetGenericArguments()) + foreach (var arg in type.GetGenericArguments()) { - RuntimeClassLoader loader = GetJavaTypeFromType(arg).ClassLoader; + var loader = GetJavaTypeFromType(arg).ClassLoader; if (!list.Contains(loader) && loader != bootstrapClassLoader) { list.Add(loader); } } - RuntimeClassLoader[] key = list.ToArray(); - RuntimeClassLoader matchingLoader = GetGenericClassLoaderByKey(key); + + var key = list.ToArray(); + var matchingLoader = GetGenericClassLoaderByKey(key); matchingLoader.RegisterInitiatingLoader(wrapper); return matchingLoader; } @@ -307,7 +308,7 @@ RuntimeClassLoader GetGenericClassLoaderByKey(RuntimeClassLoader[] key) { lock (wrapperLock) { - foreach (RuntimeGenericClassLoader loader in genericClassLoaders) + foreach (var loader in genericClassLoaders) if (loader.Matches(key)) return loader; @@ -389,9 +390,9 @@ internal RuntimeClassLoader GetAssemblyClassLoaderByName(string name) return GetGenericClassLoaderByName(name); #if NETFRAMEWORK - return context.AssemblyClassLoaderFactory.FromAssembly(Assembly.Load(name)); + return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveAssembly( Assembly.Load(name))); #else - return context.AssemblyClassLoaderFactory.FromAssembly(AssemblyLoadContext.GetLoadContext(typeof(RuntimeClassLoader).Assembly).LoadFromAssemblyName(new AssemblyName(name))); + return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveAssembly(AssemblyLoadContext.GetLoadContext(typeof(RuntimeClassLoader).Assembly).LoadFromAssemblyName(new AssemblyName(name)))); #endif } @@ -409,7 +410,7 @@ internal RuntimeClassLoader GetGenericClassLoaderById(int id) return genericClassLoaders[id]; } - internal void SetWrapperForType(Type type, RuntimeJavaType wrapper) + internal void SetWrapperForType(ITypeSymbol type, RuntimeJavaType wrapper) { #if !IMPORTER RuntimeJavaType.AssertFinished(type); diff --git a/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs b/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs index 894722bc20..e986d08224 100644 --- a/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs @@ -25,6 +25,7 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -67,12 +68,12 @@ internal RuntimeGhostJavaMethod(RuntimeJavaType declaringType, string name, stri protected override void CallImpl(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Call, defaultImpl); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, defaultImpl); } protected override void CallvirtImpl(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Call, ghostMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ghostMethod); } #endif @@ -99,14 +100,14 @@ internal IMethodSymbol GetDefaultImpl() #if IMPORTER - internal void SetGhostMethod(MethodBuilder mb) + internal void SetGhostMethod(IMethodSymbolBuilder mb) { - this.ghostMethod = mb; + this.ghostMethod = mb.Symbol; } - internal MethodBuilder GetGhostMethod() + internal IMethodSymbolBuilder GetGhostMethod() { - return (MethodBuilder)ghostMethod.AsReflection(); + return ghostMethod.Builder; } #endif diff --git a/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs b/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs index 1da4591ce1..9d65d51838 100644 --- a/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs +++ b/src/IKVM.Runtime/RuntimeJavaTypeFactory.cs @@ -24,6 +24,7 @@ Jeroen Frijters using System.Collections.Generic; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection.Emit; @@ -43,7 +44,7 @@ namespace IKVM.Runtime abstract class RuntimeJavaTypeFactory { - internal abstract ModuleBuilder ModuleBuilder { get; } + internal abstract IModuleSymbolBuilder ModuleBuilder { get; } internal abstract RuntimeJavaType DefineClassImpl(Dictionary types, RuntimeJavaType host, ClassFile f, RuntimeClassLoader classLoader, ProtectionDomain protectionDomain); diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs index 8e03fb3358..ed369d2fe2 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs @@ -27,7 +27,6 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Symbols; - #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -149,11 +148,11 @@ RuntimeJavaMethod CreateRemappedMethodWrapper(IMethodBaseSymbol mb, HideFromJava for (int i = 0; i < parameters.Length; i++) argTypes[i + 1] = parameters[i].ParameterType; - var helper = type.GetMethod("instancehelper_" + mb.Name, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static, null, argTypes, null); + var helper = type.GetMethod("instancehelper_" + mb.Name, System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, argTypes); if (helper != null) mbHelper = helper; - mbNonvirtualHelper = type.GetMethod("nonvirtualhelper/" + mb.Name, BindingFlags.NonPublic | BindingFlags.Static, null, argTypes, null); + mbNonvirtualHelper = type.GetMethod("nonvirtualhelper/" + mb.Name, System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static, argTypes); } return new RemappedJavaMethod(this, name, sig, mb, retType, paramTypes, modifiers, hideFromReflection, mbHelper, mbNonvirtualHelper); diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index a0a349676e..f3cdaf1c55 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -24,25 +24,20 @@ Jeroen Frijters using System; using System.Collections.Generic; using System.Diagnostics; +using System.Linq; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; using IKVM.Attributes; using IKVM.Runtime.Syntax; using IKVM.ByteCode; -using IKVM.CoreLib.Symbols; -using com.sun.org.apache.bcel.@internal.generic; -using System.Linq; - - - +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; -using System.Runtime.Serialization.Formatters; - #else using System.Reflection; using System.Reflection.Emit; @@ -1198,40 +1193,40 @@ internal sealed class CompiledAnnotation : Annotation internal CompiledAnnotation(RuntimeContext context, ITypeSymbol type) { this.context = context ?? throw new ArgumentNullException(nameof(context)); - constructor = type.GetConstructor(new ITypeSymbol[] { context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType() }); + constructor = type.GetConstructor([context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType()]); } - private CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) + private ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { - return new CustomAttributeBuilder(constructor, new object[] { AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation)) }); + return context.Resolver.Symbols.CreateCustomAttribute(constructor, [AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation))]); } - internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) + internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) { tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) { mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IFieldSymbolBuilder fb, object annotation) { fb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder pb, object annotation) { pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) + internal override void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder ab, object annotation) { ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IPropertySymbolBuilder pb, object annotation) { pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs index b96ed3f2d5..d5b164b58f 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs @@ -23,6 +23,9 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; + #if IMPORTER || EXPORTER using IKVM.Reflection.Emit; @@ -43,7 +46,7 @@ sealed partial class AttributeAnnotationJavaType sealed class MultipleAnnotationJavaType : AttributeAnnotationJavaTypeBase { - readonly Type annotationType; + readonly ITypeSymbol annotationType; readonly AttributeAnnotationJavaType declaringType; internal MultipleAnnotationJavaType(RuntimeContext context, AttributeAnnotationJavaType declaringType) : @@ -60,19 +63,21 @@ internal MultipleAnnotationJavaType(RuntimeContext context, AttributeAnnotationJ protected override void LazyPublishMembers() { RuntimeJavaType tw = declaringType.MakeArrayType(1); - SetMethods(new RuntimeJavaMethod[] { new DynamicOnlyJavaMethod(this, "value", "()" + tw.SigName, tw, Array.Empty(), MemberFlags.None) }); - SetFields(Array.Empty()); + SetMethods([new DynamicOnlyJavaMethod(this, "value", "()" + tw.SigName, tw, [], MemberFlags.None)]); + SetFields([]); } internal override RuntimeJavaType DeclaringTypeWrapper => declaringType; - internal override Type TypeAsTBD => annotationType; + internal override ITypeSymbol TypeAsTBD => annotationType; #if !IMPORTER && !EXPORTER + internal override object[] GetDeclaredAnnotations() { return declaringType.GetDeclaredAnnotations(); } + #endif sealed class MultipleAnnotation : Annotation @@ -107,7 +112,7 @@ static object[] UnwrapArray(object annotation) return []; } - internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) { Annotation annot = type.Annotation; foreach (object ann in UnwrapArray(annotation)) @@ -116,7 +121,7 @@ internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object } } - internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) + internal override void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder ab, object annotation) { Annotation annot = type.Annotation; foreach (object ann in UnwrapArray(annotation)) @@ -125,7 +130,7 @@ internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, obje } } - internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IFieldSymbolBuilder fb, object annotation) { Annotation annot = type.Annotation; foreach (object ann in UnwrapArray(annotation)) @@ -134,7 +139,7 @@ internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object } } - internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder pb, object annotation) { Annotation annot = type.Annotation; foreach (object ann in UnwrapArray(annotation)) @@ -143,7 +148,7 @@ internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, obj } } - internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) + internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) { Annotation annot = type.Annotation; foreach (object ann in UnwrapArray(annotation)) @@ -152,7 +157,7 @@ internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object a } } - internal override void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IPropertySymbolBuilder pb, object annotation) { Annotation annot = type.Annotation; foreach (object ann in UnwrapArray(annotation)) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs index d7044a9803..81e268fd76 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -51,7 +53,7 @@ sealed partial class AttributeAnnotationJavaType sealed class ReturnValueAnnotationJavaType : AttributeAnnotationJavaTypeBase { - readonly Type fakeType; + readonly ITypeSymbol fakeType; readonly AttributeAnnotationJavaType declaringType; /// @@ -81,7 +83,7 @@ protected override void LazyPublishMembers() internal override RuntimeJavaType DeclaringTypeWrapper => declaringType; - internal override Type TypeAsTBD => fakeType; + internal override ITypeSymbol TypeAsTBD => fakeType; #if !IMPORTER && !FIRST_PASS && !EXPORTER @@ -113,7 +115,7 @@ internal ReturnValueAnnotation(AttributeAnnotationJavaType type) this.type = type; } - internal override void ApplyReturnValue(RuntimeClassLoader loader, MethodBuilder mb, ref ParameterBuilder pb, object annotation) + internal override void ApplyReturnValue(RuntimeClassLoader loader, IMethodSymbolBuilder mb, ref IParameterSymbolBuilder pb, object annotation) { // TODO make sure the descriptor is correct var ann = type.Annotation; @@ -122,7 +124,7 @@ internal override void ApplyReturnValue(RuntimeClassLoader loader, MethodBuilder { if ("value".Equals(arr[i])) { - pb ??= mb.DefineParameter(0, ParameterAttributes.None, null); + pb ??= mb.DefineParameter(0, System.Reflection.ParameterAttributes.None, null); var value = (object[])arr[i + 1]; if (value[0].Equals(AnnotationDefaultAttribute.TAG_ANNOTATION)) @@ -136,32 +138,32 @@ internal override void ApplyReturnValue(RuntimeClassLoader loader, MethodBuilder } } - internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) { } - internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) + internal override void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder ab, object annotation) { } - internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IFieldSymbolBuilder fb, object annotation) { } - internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder pb, object annotation) { } - internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) + internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) { } - internal override void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IPropertySymbolBuilder pb, object annotation) { } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs index a4867ea4da..6b2a6272b6 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs @@ -26,7 +26,7 @@ Jeroen Frijters using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; - +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -491,7 +491,7 @@ internal AttributeAnnotation(ITypeSymbol type) this.type = type; } - CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) + ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { object[] arr = (object[])annotation; object ctorArg = null; @@ -534,25 +534,25 @@ CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, obj // TODO required argument is missing } - return new CustomAttributeBuilder( - ctorArg == null ? defCtor.AsReflection() : singleOneArgCtor.AsReflection(), + return loader.Context.Resolver.Symbols.CreateCustomAttribute( + ctorArg == null ? defCtor : singleOneArgCtor, ctorArg == null ? [] : new object[] { ctorArg }, - properties.ToArray().AsReflection(), + properties.ToArray(), propertyValues.ToArray(), - fields.ToArray().AsReflection(), + fields.ToArray(), fieldValues.ToArray()); } - internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object annotation) + internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) { - if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.StructLayoutAttribute).FullName) && loader.Context.Resolver.ResolveType(tb.BaseType) != loader.Context.Types.Object) + if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.StructLayoutAttribute).FullName) && tb.Symbol.BaseType != loader.Context.Types.Object) { // we have to handle this explicitly, because if we apply an illegal StructLayoutAttribute, // TypeBuilder.CreateType() will later on throw an exception. #if IMPORTER - loader.Diagnostics.IgnoredCustomAttribute(type.FullName, $"Type '{tb.FullName}' does not extend cli.System.Object"); + loader.Diagnostics.IgnoredCustomAttribute(type.FullName, $"Type '{tb.Symbol.FullName}' does not extend cli.System.Object"); #else - loader.Diagnostics.GenericRuntimeError($"StructLayoutAttribute cannot be applied to {tb.FullName}, because it does not directly extend cli.System.Object"); + loader.Diagnostics.GenericRuntimeError($"StructLayoutAttribute cannot be applied to {tb.Symbol.FullName}, because it does not directly extend cli.System.Object"); #endif return; } @@ -560,17 +560,17 @@ internal override void Apply(RuntimeClassLoader loader, TypeBuilder tb, object a tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, MethodBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) { mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, FieldBuilder fb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IFieldSymbolBuilder fb, object annotation) { fb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder pb, object annotation) { // TODO with the current custom attribute annotation restrictions it is impossible to use this CA, // but if we make it possible, we should also implement it here @@ -580,9 +580,11 @@ internal override void Apply(RuntimeClassLoader loader, ParameterBuilder pb, obj pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, object annotation) + internal override void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder assemblyBuilder, object annotation) { #if IMPORTER + var ab = assemblyBuilder.AsReflection(); + if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.CompilerServices.TypeForwardedToAttribute).FullName)) { ab.__AddTypeForwarder((Type)ConvertValue(loader, loader.Context.Types.Type, ((object[])annotation)[3])); @@ -627,14 +629,14 @@ internal override void Apply(RuntimeClassLoader loader, AssemblyBuilder ab, obje } else { - ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); + assemblyBuilder.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } #else - ab.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); + assemblyBuilder.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); #endif } - internal override void Apply(RuntimeClassLoader loader, PropertyBuilder pb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IPropertySymbolBuilder pb, object annotation) { pb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs index 8438b052b7..678bb8f5e3 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs @@ -25,6 +25,7 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -45,7 +46,7 @@ sealed partial class RuntimeManagedJavaType sealed class DelegateJavaMethod : RuntimeJavaMethod { - readonly ConstructorInfo delegateConstructor; + readonly IConstructorSymbol delegateConstructor; readonly DelegateInnerClassJavaType iface; /// @@ -54,9 +55,9 @@ sealed class DelegateJavaMethod : RuntimeJavaMethod /// /// internal DelegateJavaMethod(RuntimeJavaType declaringType, DelegateInnerClassJavaType iface) : - base(declaringType, "", "(" + iface.SigName + ")V", null, declaringType.Context.PrimitiveJavaTypeFactory.VOID, new RuntimeJavaType[] { iface }, Modifiers.Public, MemberFlags.Intrinsic) + base(declaringType, "", "(" + iface.SigName + ")V", null, declaringType.Context.PrimitiveJavaTypeFactory.VOID, [iface], Modifiers.Public, MemberFlags.Intrinsic) { - this.delegateConstructor = declaringType.TypeAsTBD.GetConstructor(new Type[] { DeclaringType.Context.Types.Object, DeclaringType.Context.Types.IntPtr }); + this.delegateConstructor = declaringType.TypeAsTBD.GetConstructor([DeclaringType.Context.Types.Object, DeclaringType.Context.Types.IntPtr]); this.iface = iface; } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs index 1d521fbe4d..de5ed4d6d6 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection.Emit; @@ -43,7 +45,7 @@ sealed partial class RuntimeManagedJavaType internal sealed class EnumValueJavaField : RuntimeJavaField { - readonly Type underlyingType; + readonly ITypeSymbol underlyingType; /// /// Initializes a new instance. @@ -53,7 +55,7 @@ internal sealed class EnumValueJavaField : RuntimeJavaField internal EnumValueJavaField(RuntimeManagedJavaType tw, RuntimeJavaType fieldType) : base(tw, fieldType, "Value", fieldType.SigName, new ExModifiers(Modifiers.Public | Modifiers.Final, false), null) { - underlyingType = EnumHelper.GetUnderlyingType(tw.type); + underlyingType = tw.type.GetEnumUnderlyingType(); } #if EMITTERS diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index 523b20f724..0eaac509bb 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -804,7 +804,7 @@ RuntimeJavaMethod CreateMethodWrapper(string name, string sig, RuntimeJavaType[] if (name == "Finalize" && sig == "()V" && !mb.IsStatic && IsRemappedImplDerived(Context, TypeAsBaseType)) { // TODO if the .NET also has a "finalize" method, we need to hide that one (or rename it, or whatever) - var mw = new RuntimeSimpleCallJavaMethod(this, "finalize", "()V", (MethodInfo)mb, Context.PrimitiveJavaTypeFactory.VOID, Array.Empty(), mods, MemberFlags.None, SimpleOpCode.Call, SimpleOpCode.Callvirt); + var mw = new RuntimeSimpleCallJavaMethod(this, "finalize", "()V", (IMethodSymbol)mb, Context.PrimitiveJavaTypeFactory.VOID, [], mods, MemberFlags.None, SimpleOpCode.Call, SimpleOpCode.Callvirt); mw.SetDeclaredExceptions(new string[] { "java.lang.Throwable" }); return mw; } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs b/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs index d6c1aace87..617ed9132d 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaTypeFactory.cs @@ -63,7 +63,7 @@ public RuntimeManagedJavaTypeFactory(RuntimeContext context) /// public RuntimeJavaType GetJavaTypeFromManagedType(ITypeSymbol type) { - return cache.GetValue(type, _ => context.AssemblyClassLoaderFactory.FromAssembly(_.Assembly.AsReflection()).GetJavaTypeFromAssemblyType(_.AsReflection())); + return cache.GetValue(type, _ => context.AssemblyClassLoaderFactory.FromAssembly(_.Assembly).GetJavaTypeFromAssemblyType(_)); } /// diff --git a/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs b/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs index 0e3bf8d3be..424a8ac14a 100644 --- a/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs @@ -22,6 +22,7 @@ Jeroen Frijters */ using IKVM.Attributes; +using IKVM.CoreLib.Symbols; #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -51,7 +52,7 @@ sealed class RuntimeSimpleCallJavaMethod : RuntimeJavaMethod /// /// /// - internal RuntimeSimpleCallJavaMethod(RuntimeJavaType declaringType, string name, string sig, MethodInfo method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags, SimpleOpCode call, SimpleOpCode callvirt) : + internal RuntimeSimpleCallJavaMethod(RuntimeJavaType declaringType, string name, string sig, IMethodSymbol method, RuntimeJavaType returnType, RuntimeJavaType[] parameterTypes, Modifiers modifiers, MemberFlags flags, SimpleOpCode call, SimpleOpCode callvirt) : base(declaringType, name, sig, method, returnType, parameterTypes, modifiers, flags) { this.call = call; diff --git a/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs b/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs index a0265537b4..7c4e3cf260 100644 --- a/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs +++ b/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs @@ -143,7 +143,7 @@ internal override void Finish() internal ITypeSymbol CustomModifier => customModifier; - internal void SetCustomModifier(Type type) + internal void SetCustomModifier(ITypeSymbol type) { this.customModifier = type; } diff --git a/src/IKVM.Runtime/RuntimeVerifierJavaType.cs b/src/IKVM.Runtime/RuntimeVerifierJavaType.cs index 998f9c82c4..b3961bffdc 100644 --- a/src/IKVM.Runtime/RuntimeVerifierJavaType.cs +++ b/src/IKVM.Runtime/RuntimeVerifierJavaType.cs @@ -23,6 +23,8 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; + #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -202,7 +204,7 @@ protected override void LazyPublishMembers() throw new InvalidOperationException("LazyPublishMembers called on " + this); } - internal override Type TypeAsTBD + internal override ITypeSymbol TypeAsTBD { get { diff --git a/src/IKVM.Runtime/StubGen/StubGenerator.cs b/src/IKVM.Runtime/StubGen/StubGenerator.cs index 6c8911eb05..f5a6b5fa86 100644 --- a/src/IKVM.Runtime/StubGen/StubGenerator.cs +++ b/src/IKVM.Runtime/StubGen/StubGenerator.cs @@ -1,21 +1,13 @@ using System; -using System.IO; using System.Collections.Generic; +using System.IO; -using IKVM.ByteCode.Encoding; using IKVM.Attributes; using IKVM.ByteCode; -using IKVM.ByteCode.Decoding; using IKVM.ByteCode.Buffers; - - -#if EXPORTER -using IKVM.Reflection; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -#endif +using IKVM.ByteCode.Decoding; +using IKVM.ByteCode.Encoding; +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime.StubGen { @@ -222,7 +214,7 @@ void AddRuntimeVisibleAnnotationsAttribute(ClassFileBuilder builder, RuntimeJava /// void AddDeprecatedAttribute(ClassFileBuilder builder, RuntimeJavaType type) { - if (type.TypeAsBaseType.IsDefined(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).AsReflection(), false)) + if (type.TypeAsBaseType.IsDefined(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName), false)) builder.Attributes.Deprecated(); } @@ -310,7 +302,7 @@ void AddAssemblyAttribute(ClassFileBuilder builder, RuntimeJavaType javaType) /// /// /// - void AddExceptionsAttribute(ClassFileBuilder builder, RuntimeJavaType type, RuntimeJavaMethod method, AttributeTableBuilder attributes, MethodBase methodBase) + void AddExceptionsAttribute(ClassFileBuilder builder, RuntimeJavaType type, RuntimeJavaMethod method, AttributeTableBuilder attributes, IMethodBaseSymbol methodBase) { var throws = context.AttributeHelper.GetThrows(methodBase); if (throws == null) @@ -336,8 +328,8 @@ void AddExceptionsAttribute(ClassFileBuilder builder, RuntimeJavaType type, Runt e.Class(builder.Constants.GetOrAddClass(ex.Replace('.', '/'))); if (throws.types != null) - foreach (Type ex in throws.types) - e.Class(builder.Constants.GetOrAddClass(context.ClassLoaderFactory.GetJavaTypeFromType(ex).Name.Replace('.', '/'))); + foreach (var ex in throws.types) + e.Class(builder.Constants.GetOrAddClass(context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveType(ex)).Name.Replace('.', '/'))); }); } } @@ -380,11 +372,11 @@ void AddMethodParameters(ClassFileBuilder builder, RuntimeJavaType type, Runtime /// /// /// - void AddAnnotationDefaultAttribute(ClassFileBuilder builder, RuntimeJavaType type, RuntimeJavaMethod method, AttributeTableBuilder attributes, MethodBase methodBase) + void AddAnnotationDefaultAttribute(ClassFileBuilder builder, RuntimeJavaType type, RuntimeJavaMethod method, AttributeTableBuilder attributes, IMethodBaseSymbol methodBase) { var attr = GetAnnotationDefault(methodBase); - if (attr != null) - attributes.AnnotationDefault(e => EncodeAnnotationDefault(builder, ref e, attr.ConstructorArguments[0])); + if (attr is CustomAttribute ca) + attributes.AnnotationDefault(e => EncodeAnnotationDefault(builder, ref e, ca.ConstructorArguments[0])); } /// @@ -409,12 +401,12 @@ void AddSignatureAttribute(ClassFileBuilder builder, RuntimeJavaType type, Runti /// /// /// - void AddDeprecatedAttribute(ClassFileBuilder builder, RuntimeJavaType type, RuntimeJavaMethod method, AttributeTableBuilder attributes, MethodBase methodBase) + void AddDeprecatedAttribute(ClassFileBuilder builder, RuntimeJavaType type, RuntimeJavaMethod method, AttributeTableBuilder attributes, IMethodBaseSymbol methodBase) { // HACK the instancehelper methods are marked as Obsolete (to direct people toward the ikvm.extensions methods instead) // but in the Java world most of them are not deprecated (and to keep the Japi results clean we need to reflect this) // the Java deprecated methods actually have two Obsolete attributes - if (methodBase.IsDefined(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).AsReflection(), false) && (!methodBase.Name.StartsWith("instancehelper_") || methodBase.DeclaringType.FullName != "java.lang.String" || GetObsoleteCount(methodBase) == 2)) + if (methodBase.IsDefined(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName), false) && (!methodBase.Name.StartsWith("instancehelper_") || methodBase.DeclaringType.FullName != "java.lang.String" || GetObsoleteCount(methodBase) == 2)) attributes.Deprecated(); } @@ -477,7 +469,7 @@ void AddConstantValueAttribute(ClassFileBuilder builder, RuntimeJavaType type, R { var constant = field.GetField().GetRawConstantValue(); if (field.GetField().FieldType.IsEnum) - constant = EnumHelper.GetPrimitiveValue(context, EnumHelper.GetUnderlyingType(field.GetField().FieldType), constant); + constant = EnumHelper.GetPrimitiveValue(context, field.GetField().FieldType.GetEnumUnderlyingType(), constant); if (constant != null) { @@ -541,7 +533,7 @@ void AddSignatureAttribute(ClassFileBuilder builder, RuntimeJavaType type, Runti void AddDeprecatedAttribute(ClassFileBuilder builder, RuntimeJavaType type, RuntimeJavaField field, AttributeTableBuilder attributes) { // .NET ObsoleteAttribute translates to Deprecated attribute - if (field.GetField() != null && field.GetField().IsDefined(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).AsReflection(), false)) + if (field.GetField() != null && field.GetField().IsDefined(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName), false)) attributes.Deprecated(); } @@ -581,7 +573,7 @@ void AddRuntimeVisibleAnnotationsAttribute(ClassFileBuilder builder, RuntimeJava /// /// /// - bool EncodeAnnotations(ClassFileBuilder builder, ref AnnotationTableEncoder encoder, MemberInfo source) + bool EncodeAnnotations(ClassFileBuilder builder, ref AnnotationTableEncoder encoder, IMemberSymbol source) { var any = false; @@ -609,7 +601,7 @@ bool EncodeAnnotations(ClassFileBuilder builder, ref AnnotationTableEncoder enco /// /// /// - bool EncodeParameterAnnotations(ClassFileBuilder builder, ref ParameterAnnotationTableEncoder encoder, MethodBase source) + bool EncodeParameterAnnotations(ClassFileBuilder builder, ref ParameterAnnotationTableEncoder encoder, IMethodBaseSymbol source) { var any = false; @@ -918,7 +910,7 @@ public PackageConstantHandle Map(PackageConstantHandle handle) /// /// /// - object[] GetAnnotation(CustomAttributeData cad) + object[] GetAnnotation(CustomAttribute cad) { // attribute is either a AnnotationAttributeBase or a DynamicAnnotationAttribute with a single object[] in our internal annotation format if (cad.ConstructorArguments.Count == 1 && cad.ConstructorArguments[0].ArgumentType == typeof(object[]) && (cad.Constructor.DeclaringType.BaseType == typeof(ikvm.@internal.AnnotationAttributeBase) || cad.Constructor.DeclaringType == typeof(DynamicAnnotationAttribute))) @@ -1164,27 +1156,14 @@ object[] UnpackArray(IList list) return arr; } - int GetObsoleteCount(MethodBase mb) + int GetObsoleteCount(IMethodBaseSymbol mb) { -#if EXPORTER - return mb.__GetCustomAttributes(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).AsReflection(), false).Count; -#else - return mb.GetCustomAttributes(typeof(ObsoleteAttribute), false).Length; -#endif + return mb.GetCustomAttributes(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName), false).Length; } - CustomAttributeData GetAnnotationDefault(MethodBase mb) + CustomAttribute? GetAnnotationDefault(IMethodBaseSymbol mb) { -#if EXPORTER - var attr = CustomAttributeData.__GetCustomAttributes(mb, context.Resolver.ResolveRuntimeType(typeof(Attributes.AnnotationDefaultAttribute).FullName).AsReflection(), false); - return attr.Count == 1 ? attr[0] : null; -#else - foreach (var cad in CustomAttributeData.GetCustomAttributes(mb)) - if (cad.Constructor.DeclaringType == typeof(Attributes.AnnotationDefaultAttribute)) - return cad; - - return null; -#endif + return mb.GetCustomAttribute(context.Resolver.ResolveRuntimeType(typeof(Attributes.AnnotationDefaultAttribute).FullName), false); } string GetAssemblyName(RuntimeJavaType tw) diff --git a/src/IKVM.Runtime/SymbolExtensions.cs b/src/IKVM.Runtime/SymbolExtensions.cs index 65a6c08dff..14e3948b01 100644 --- a/src/IKVM.Runtime/SymbolExtensions.cs +++ b/src/IKVM.Runtime/SymbolExtensions.cs @@ -3,13 +3,18 @@ using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Reflection; using IKVM.CoreLib.Symbols.IkvmReflection; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; +using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; #else using System.Reflection; +using System.Reflection.Emit; #endif namespace IKVM.Runtime @@ -150,6 +155,78 @@ public static PropertyInfo[] AsReflection(this IPropertySymbol[] symbols) return a; } + public static AssemblyBuilder AsReflection(this IAssemblySymbolBuilder builder) + { + if (builder == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionAssemblySymbolBuilder)builder).ReflectionBuilder; +#else + return ((ReflectionAssemblySymbolBuilder)builder).ReflectionBuilder; +#endif + } + + public static ModuleBuilder AsReflection(this IModuleSymbolBuilder builder) + { + if (builder == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionModuleSymbolBuilder)builder).ReflectionBuilder; +#else + return ((ReflectionModuleSymbolBuilder)builder).ReflectionBuilder; +#endif + } + + public static TypeBuilder AsReflection(this ITypeSymbolBuilder builder) + { + if (builder == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionTypeSymbolBuilder)builder).ReflectionBuilder; +#else + return ((ReflectionTypeSymbolBuilder)builder).ReflectionBuilder; +#endif + } + + public static ConstructorBuilder AsReflection(this IConstructorSymbolBuilder builder) + { + if (builder == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionConstructorSymbolBuilder)builder).ReflectionBuilder; +#else + return ((ReflectionConstructorSymbolBuilder)builder).ReflectionBuilder; +#endif + } + + public static MethodBuilder AsReflection(this IMethodSymbolBuilder builder) + { + if (builder == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionMethodSymbolBuilder)builder).ReflectionBuilder; +#else + return ((ReflectionMethodSymbolBuilder)builder).ReflectionBuilder; +#endif + } + + public static FieldBuilder AsReflection(this IFieldSymbolBuilder builder) + { + if (builder == null) + return null; + +#if IMPORTER || EXPORTER + return ((IkvmReflectionFieldSymbolBuilder)builder).ReflectionBuilder; +#else + return ((ReflectionFieldSymbolBuilder)builder).ReflectionBuilder; +#endif + } + } } diff --git a/src/IKVM.Tools.Exporter/ExportImpl.cs b/src/IKVM.Tools.Exporter/ExportImpl.cs index 29ad16827a..dc57fffe85 100644 --- a/src/IKVM.Tools.Exporter/ExportImpl.cs +++ b/src/IKVM.Tools.Exporter/ExportImpl.cs @@ -7,6 +7,7 @@ using System.Reflection.PortableExecutable; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; using IKVM.Reflection; using IKVM.Runtime; using IKVM.Tools.Importer; @@ -174,7 +175,7 @@ public int Execute() context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(compiler, baseAssembly), false, compiler); } - if (context.AttributeHelper.IsJavaModule(assembly.ManifestModule)) + if (context.AttributeHelper.IsJavaModule(context.Resolver.ResolveModule(assembly.ManifestModule))) { diagnostics.ExportingImportsNotSupported(); return 1; @@ -344,7 +345,7 @@ void WriteClass(RuntimeJavaType javaType) javaType.Context.StubGenerator.Write(stream, javaType, options.IncludeNonPublicTypes, options.IncludeNonPublicInterfaces, options.IncludeNonPublicMembers, options.IncludeParameterNames, options.SerialVersionUID); } - bool ExportNamespace(IList namespaces, Type type) + bool ExportNamespace(IList namespaces, ITypeSymbol type) { if (namespaces.Count == 0) return true; @@ -360,7 +361,7 @@ bool ExportNamespace(IList namespaces, Type type) int ProcessTypes(RuntimeContext context, Type[] types) { int rc = 0; - foreach (var t in types) + foreach (var t in types.Select(context.Resolver.ResolveType)) { if ((t.IsPublic || options.IncludeNonPublicTypes) && ExportNamespace(options.Namespaces, t) && !t.IsGenericTypeDefinition && !context.AttributeHelper.IsHideFromJava(t) && (!t.IsGenericType || !context.AttributeHelper.IsJavaModule(t.Module))) { diff --git a/src/IKVM.Tools.Exporter/FakeTypes.cs b/src/IKVM.Tools.Exporter/FakeTypes.cs index 1cd9d3de55..3720cd2dc6 100644 --- a/src/IKVM.Tools.Exporter/FakeTypes.cs +++ b/src/IKVM.Tools.Exporter/FakeTypes.cs @@ -23,6 +23,7 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; using Type = IKVM.Reflection.Type; @@ -34,7 +35,7 @@ class FakeTypes { readonly RuntimeContext context; - readonly Type genericType; + readonly ITypeSymbol genericType; /// /// Initializes a new instance. @@ -44,30 +45,30 @@ class FakeTypes public FakeTypes(RuntimeContext context) { this.context = context ?? throw new ArgumentNullException(nameof(context)); - genericType = context.Resolver.ResolveRuntimeType("IKVM.Runtime.ValueObject`1").AsReflection(); + genericType = context.Resolver.ResolveRuntimeType("IKVM.Runtime.ValueObject`1"); } - internal Type GetAttributeType(Type type) + internal ITypeSymbol GetAttributeType(ITypeSymbol type) { return genericType.MakeGenericType(type); } - internal Type GetAttributeReturnValueType(Type type) + internal ITypeSymbol GetAttributeReturnValueType(ITypeSymbol type) { return genericType.MakeGenericType(type); } - internal Type GetAttributeMultipleType(Type type) + internal ITypeSymbol GetAttributeMultipleType(ITypeSymbol type) { return genericType.MakeGenericType(type); } - internal Type GetDelegateType(Type type) + internal ITypeSymbol GetDelegateType(ITypeSymbol type) { return genericType.MakeGenericType(type); } - internal Type GetEnumType(Type type) + internal ITypeSymbol GetEnumType(ITypeSymbol type) { return genericType.MakeGenericType(type); } diff --git a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs index d1f2ac4699..3d99416287 100644 --- a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs +++ b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs @@ -3,37 +3,41 @@ using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.IkvmReflection; using IKVM.Reflection; +using IKVM.Runtime; using Type = IKVM.Reflection.Type; namespace IKVM.Tools.Exporter { - class ManagedTypeResolver : ISymbolResolver + class ManagedTypeResolver : IRuntimeSymbolResolver { readonly StaticCompiler compiler; readonly Assembly baseAssembly; - readonly IkvmReflectionSymbolContext context = new(); + readonly IkvmReflectionSymbolContext symbols = new(); - /// - /// Initializes a new instance. - /// - /// - /// - public ManagedTypeResolver(StaticCompiler compiler, Assembly baseAssembly) + /// + /// Initializes a new instance. + /// + /// + /// + public ManagedTypeResolver(StaticCompiler compiler, Assembly baseAssembly) { this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); this.baseAssembly = baseAssembly; - } + } - /// - /// Attempts to resolve the base Java assembly. - /// - /// - public IAssemblySymbol ResolveBaseAssembly() + /// + public ISymbolContext Symbols => symbols; + + /// + /// Attempts to resolve the base Java assembly. + /// + /// + public IAssemblySymbol ResolveBaseAssembly() { - return baseAssembly != null ? context.GetOrCreateAssemblySymbol(baseAssembly) : null; + return baseAssembly != null ? symbols.GetOrCreateAssemblySymbol(baseAssembly) : null; } /// @@ -43,7 +47,7 @@ public IAssemblySymbol ResolveBaseAssembly() /// public IAssemblySymbol ResolveAssembly(string assemblyName) { - return compiler.Load(assemblyName) is { } a ? context.GetOrCreateAssemblySymbol(a) : null; + return compiler.Load(assemblyName) is { } a ? symbols.GetOrCreateAssemblySymbol(a) : null; } /// @@ -55,7 +59,7 @@ public ITypeSymbol ResolveCoreType(string typeName) { foreach (var assembly in compiler.Universe.GetAssemblies()) if (assembly.GetType(typeName) is Type t) - return context.GetOrCreateTypeSymbol(t); + return ResolveType(t); return null; } @@ -67,9 +71,27 @@ public ITypeSymbol ResolveCoreType(string typeName) /// public ITypeSymbol ResolveRuntimeType(string typeName) { - return compiler.GetRuntimeType(typeName) is { } t ? context.GetOrCreateTypeSymbol(t) : null; - } + return compiler.GetRuntimeType(typeName) is { } t ? symbols.GetOrCreateTypeSymbol(t) : null; + } + + /// + public IAssemblySymbol ResolveAssembly(Assembly assembly) + { + return symbols.GetOrCreateAssemblySymbol(assembly); + } + + /// + public IModuleSymbol ResolveModule(Module module) + { + return symbols.GetOrCreateModuleSymbol(module); + } + + /// + public ITypeSymbol ResolveType(Type type) + { + return symbols.GetOrCreateTypeSymbol(type); + } - } + } } diff --git a/src/IKVM.Tools.Exporter/RuntimeBootstrapClassLoader.cs b/src/IKVM.Tools.Exporter/RuntimeBootstrapClassLoader.cs index 12948e0eea..1debbee0d0 100644 --- a/src/IKVM.Tools.Exporter/RuntimeBootstrapClassLoader.cs +++ b/src/IKVM.Tools.Exporter/RuntimeBootstrapClassLoader.cs @@ -39,14 +39,14 @@ internal RuntimeBootstrapClassLoader(RuntimeContext context) : base(context, CodeGenOptions.None, null) { var javaLangObject = new RuntimeStubJavaType(context, Modifiers.Public, "java.lang.Object", null, true); - SetRemappedType(Context.Resolver.ResolveCoreType(typeof(object).FullName).AsReflection(), javaLangObject); - SetRemappedType(Context.Resolver.ResolveCoreType(typeof(string).FullName).AsReflection(), new RuntimeStubJavaType(context, Modifiers.Public | Modifiers.Final, "java.lang.String", javaLangObject, true)); - SetRemappedType(Context.Resolver.ResolveCoreType(typeof(Exception).FullName).AsReflection(), new RuntimeStubJavaType(context, Modifiers.Public, "java.lang.Throwable", javaLangObject, true)); - SetRemappedType(Context.Resolver.ResolveCoreType(typeof(IComparable).FullName).AsReflection(), new RuntimeStubJavaType(context, Modifiers.Public | Modifiers.Abstract | Modifiers.Interface, "java.lang.Comparable", null, true)); + SetRemappedType(Context.Resolver.ResolveCoreType(typeof(object).FullName), javaLangObject); + SetRemappedType(Context.Resolver.ResolveCoreType(typeof(string).FullName), new RuntimeStubJavaType(context, Modifiers.Public | Modifiers.Final, "java.lang.String", javaLangObject, true)); + SetRemappedType(Context.Resolver.ResolveCoreType(typeof(Exception).FullName), new RuntimeStubJavaType(context, Modifiers.Public, "java.lang.Throwable", javaLangObject, true)); + SetRemappedType(Context.Resolver.ResolveCoreType(typeof(IComparable).FullName), new RuntimeStubJavaType(context, Modifiers.Public | Modifiers.Abstract | Modifiers.Interface, "java.lang.Comparable", null, true)); var autoCloseable = new RuntimeStubJavaType(context, Modifiers.Public | Modifiers.Abstract | Modifiers.Interface, "java.lang.AutoCloseable", null, true); - autoCloseable.SetMethods(new[] { new RuntimeSimpleCallJavaMethod(autoCloseable, "close", "()V", Context.Resolver.ResolveCoreType(typeof(IDisposable).FullName).GetMethod("Dispose").AsReflection(), context.PrimitiveJavaTypeFactory.VOID, Array.Empty(), Modifiers.Public | Modifiers.Abstract, MemberFlags.None, SimpleOpCode.Callvirt, SimpleOpCode.Callvirt) }); - SetRemappedType(Context.Resolver.ResolveCoreType(typeof(IDisposable).FullName).AsReflection(), autoCloseable); + autoCloseable.SetMethods(new[] { new RuntimeSimpleCallJavaMethod(autoCloseable, "close", "()V", Context.Resolver.ResolveCoreType(typeof(IDisposable).FullName).GetMethod("Dispose"), context.PrimitiveJavaTypeFactory.VOID, Array.Empty(), Modifiers.Public | Modifiers.Abstract, MemberFlags.None, SimpleOpCode.Callvirt, SimpleOpCode.Callvirt) }); + SetRemappedType(Context.Resolver.ResolveCoreType(typeof(IDisposable).FullName), autoCloseable); RegisterInitiatingLoader(new RuntimeStubJavaType(context, Modifiers.Public, "java.lang.Enum", javaLangObject, false)); RegisterInitiatingLoader(new RuntimeStubJavaType(context, Modifiers.Public | Modifiers.Abstract | Modifiers.Interface, "java.lang.annotation.Annotation", null, false)); diff --git a/src/IKVM.Tools.Exporter/RuntimeStubJavaType.cs b/src/IKVM.Tools.Exporter/RuntimeStubJavaType.cs index a1c8780731..6c51d47493 100644 --- a/src/IKVM.Tools.Exporter/RuntimeStubJavaType.cs +++ b/src/IKVM.Tools.Exporter/RuntimeStubJavaType.cs @@ -24,8 +24,7 @@ Jeroen Frijters using System; using IKVM.Attributes; - -using Type = IKVM.Reflection.Type; +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { @@ -60,7 +59,7 @@ internal override RuntimeJavaType BaseTypeWrapper internal override RuntimeClassLoader ClassLoader => Context.ClassLoaderFactory.GetBootstrapClassLoader(); - internal override Type TypeAsTBD + internal override ITypeSymbol TypeAsTBD { get { throw new NotSupportedException(); } } diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index 8bbc52ed53..a535a19578 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -35,6 +35,8 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.ByteCode; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Reflection; using IKVM.Reflection.Emit; using IKVM.Runtime; @@ -2115,7 +2117,7 @@ internal override RuntimeJavaType[] Interfaces } } - internal override Type TypeAsTBD + internal override ITypeSymbol TypeAsTBD { get { @@ -2123,7 +2125,7 @@ internal override Type TypeAsTBD } } - internal override Type TypeAsBaseType + internal override ITypeSymbol TypeAsBaseType { get { @@ -2146,7 +2148,7 @@ internal override bool IsFastClassLiteralSafe } } - internal static void AddDeclaredExceptions(RuntimeContext context, MethodBuilder mb, IKVM.Tools.Importer.MapXml.Throws[] throws) + internal static void AddDeclaredExceptions(RuntimeContext context, IMethodSymbolBuilder mb, IKVM.Tools.Importer.MapXml.Throws[] throws) { if (throws != null) { diff --git a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs index 37c22bb2a1..9712f24ac8 100644 --- a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs +++ b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs @@ -27,6 +27,8 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Reflection; using IKVM.Reflection.Emit; using IKVM.Runtime; @@ -43,14 +45,14 @@ namespace IKVM.Tools.Importer sealed class RuntimeImportByteCodeJavaType : RuntimeByteCodeJavaType { - FieldInfo ghostRefField; - MethodBuilder ghostIsInstanceMethod; - MethodBuilder ghostIsInstanceArrayMethod; - MethodBuilder ghostCastMethod; - MethodBuilder ghostCastArrayMethod; - TypeBuilder typeBuilderGhostInterface; + IFieldSymbol ghostRefField; + IMethodSymbolBuilder ghostIsInstanceMethod; + IMethodSymbolBuilder ghostIsInstanceArrayMethod; + IMethodSymbolBuilder ghostCastMethod; + IMethodSymbolBuilder ghostCastArrayMethod; + ITypeSymbolBuilder typeBuilderGhostInterface; Annotation annotation; - Type enumType; + ITypeSymbol enumType; RuntimeJavaMethod[] replacedMethods; /// @@ -73,9 +75,9 @@ sealed class ConstructorForwarder : RuntimeJavaMethod { readonly RuntimeJavaTypeFactory context; - readonly TypeBuilder typeBuilder; + readonly ITypeSymbolBuilder typeBuilder; readonly RuntimeJavaMethod ctor; - MethodBuilder constructorBuilder; + IMethodSymbolBuilder constructorBuilder; /// /// Initializes a new instance. @@ -83,7 +85,7 @@ sealed class ConstructorForwarder : RuntimeJavaMethod /// /// /// - internal ConstructorForwarder(RuntimeJavaTypeFactory context, TypeBuilder typeBuilder, RuntimeJavaMethod ctor) : + internal ConstructorForwarder(RuntimeJavaTypeFactory context, ITypeSymbolBuilder typeBuilder, RuntimeJavaMethod ctor) : base(ctor.DeclaringType, ctor.Name, ctor.Signature, null, null, null, ctor.Modifiers, MemberFlags.None) { this.context = context; @@ -94,23 +96,23 @@ internal ConstructorForwarder(RuntimeJavaTypeFactory context, TypeBuilder typeBu protected override void DoLinkMethod() { ctor.Link(); - DefineMethodHelper dmh = ctor.GetDefineMethodHelper(); - constructorBuilder = dmh.DefineConstructor(context, typeBuilder, MethodAttributes.PrivateScope); + var dmh = ctor.GetDefineMethodHelper(); + constructorBuilder = dmh.DefineConstructor(context, typeBuilder, System.Reflection.MethodAttributes.PrivateScope); ctor.DeclaringType.Context.AttributeHelper.HideFromJava(constructorBuilder); - CodeEmitter ilgen = ctor.DeclaringType.Context.CodeEmitterFactory.Create(constructorBuilder); - ilgen.Emit(OpCodes.Ldarg_0); + var ilgen = ctor.DeclaringType.Context.CodeEmitterFactory.Create(constructorBuilder); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); for (int i = 1; i <= dmh.ParameterCount; i++) { ilgen.EmitLdarg(i); } ctor.EmitCall(ilgen); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); } internal override void EmitCall(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Call, constructorBuilder); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, constructorBuilder); } } @@ -118,7 +120,7 @@ internal override void EmitCall(CodeEmitter ilgen) internal override bool IsMapUnsafeException => classLoader.IsMapUnsafeException(this); - internal override Type TypeAsBaseType => typeBuilderGhostInterface != null ? typeBuilderGhostInterface : base.TypeAsBaseType; + internal override ITypeSymbol TypeAsBaseType => typeBuilderGhostInterface != null ? typeBuilderGhostInterface : base.TypeAsBaseType; internal void GetParameterNamesFromXml(string methodName, string methodSig, string[] parameterNames) { @@ -129,7 +131,7 @@ internal void GetParameterNamesFromXml(string methodName, string methodSig, stri parameterNames[i] = parameters[i].Name; } - internal void AddXmlMapParameterAttributes(MethodBuilder method, string className, string methodName, string methodSig, ref ParameterBuilder[] parameterBuilders) + internal void AddXmlMapParameterAttributes(IMethodSymbolBuilder method, string className, string methodName, string methodSig, ref ParameterBuilder[] parameterBuilders) { var parameters = classLoader.GetXmlMapParameters(className, methodName, methodSig); if (parameters != null) @@ -145,7 +147,7 @@ internal void AddXmlMapParameterAttributes(MethodBuilder method, string classNam } } - private void AddParameterMetadata(MethodBuilder method, RuntimeJavaMethod mw) + private void AddParameterMetadata(IMethodSymbolBuilder method, RuntimeJavaMethod mw) { ParameterBuilder[] pbs; if ((mw.DeclaringType.IsPublic && (mw.IsPublic || mw.IsProtected)) || classLoader.EmitSymbols) @@ -210,7 +212,7 @@ protected override bool EmitMapXmlMethodPrologueAndOrBody(CodeEmitter ilgen, Cla return false; } - void PublishAttributes(TypeBuilder typeBuilder, Class clazz) + void PublishAttributes(ITypeSymbolBuilder typeBuilder, Class clazz) { foreach (var attr in clazz.Attributes) Context.AttributeHelper.SetCustomAttribute(classLoader, typeBuilder, attr); @@ -222,7 +224,7 @@ void PublishAttributes(TypeBuilder typeBuilder, Class clazz) /// /// /// - static bool CheckPropertyArgs(Type[] args1, Type[] args2) + static bool CheckPropertyArgs(ITypeSymbol[] args1, ITypeSymbol[] args2) { if (args1.Length == args2.Length) { @@ -236,12 +238,12 @@ static bool CheckPropertyArgs(Type[] args1, Type[] args2) return false; } - static MethodAttributes GetPropertyMethodAttributes(RuntimeJavaMethod mw, bool final) + static System.Reflection.MethodAttributes GetPropertyMethodAttributes(RuntimeJavaMethod mw, bool final) { - var attribs = MethodAttributes.HideBySig; + var attribs = System.Reflection.MethodAttributes.HideBySig; if (mw.IsStatic) { - attribs |= MethodAttributes.Static; + attribs |= System.Reflection.MethodAttributes.Static; } else { @@ -249,36 +251,36 @@ static MethodAttributes GetPropertyMethodAttributes(RuntimeJavaMethod mw, bool f // the getter and setter methods need to have substantially the same method attributes, // so we may need to look at our peer to determine whether we should be final // or not (and vice versa). - attribs |= MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.CheckAccessOnOverride; + attribs |= System.Reflection.MethodAttributes.Virtual | System.Reflection.MethodAttributes.NewSlot | System.Reflection.MethodAttributes.CheckAccessOnOverride; if (final) - attribs |= MethodAttributes.Final; + attribs |= System.Reflection.MethodAttributes.Final; } // TODO what happens if accessibility doesn't match our peer? if (mw.IsPublic) - attribs |= MethodAttributes.Public; + attribs |= System.Reflection.MethodAttributes.Public; else if (mw.IsProtected) - attribs |= MethodAttributes.FamORAssem; + attribs |= System.Reflection.MethodAttributes.FamORAssem; else if (mw.IsPrivate) - attribs |= MethodAttributes.Private; + attribs |= System.Reflection.MethodAttributes.Private; else - attribs |= MethodAttributes.Assembly; + attribs |= System.Reflection.MethodAttributes.Assembly; return attribs; } - private void PublishProperties(TypeBuilder typeBuilder, Class clazz) + private void PublishProperties(ITypeSymbolBuilder typeBuilder, Class clazz) { foreach (var prop in clazz.Properties) { var typeWrapper = ClassLoader.RetTypeWrapperFromSig(prop.Sig, LoadMode.Link); var propargs = ClassLoader.ArgJavaTypeListFromSig(prop.Sig, LoadMode.Link); - Type[] indexer = new Type[propargs.Length]; + var indexer = new ITypeSymbol[propargs.Length]; for (int i = 0; i < propargs.Length; i++) { indexer[i] = propargs[i].TypeAsSignatureType; } - PropertyBuilder propbuilder = typeBuilder.DefineProperty(prop.Name, PropertyAttributes.None, typeWrapper.TypeAsSignatureType, indexer); + var propbuilder = typeBuilder.DefineProperty(prop.Name, System.Reflection.PropertyAttributes.None, typeWrapper.TypeAsSignatureType, indexer); Context.AttributeHelper.HideFromJava(propbuilder); if (prop.Attributes != null) { @@ -317,10 +319,12 @@ private void PublishProperties(TypeBuilder typeBuilder, Class clazz) } else { - var mb = mw.GetMethod() as MethodBuilder; - if (mb == null || mb.DeclaringType != typeBuilder || (!mb.IsFinal && final)) + var m = mw.GetMethod() as IMethodSymbol; + if (m == null || m.DeclaringType != typeBuilder || (!m.IsFinal && final)) { - mb = typeBuilder.DefineMethod("get_" + prop.Name, GetPropertyMethodAttributes(mw, final), typeWrapper.TypeAsSignatureType, indexer); + var mb = typeBuilder.DefineMethod("get_" + prop.Name, GetPropertyMethodAttributes(mw, final), typeWrapper.TypeAsSignatureType, indexer); + m = mb.Symbol; + Context.AttributeHelper.HideFromJava(mb); var ilgen = Context.CodeEmitterFactory.Create(mb); if (mw.IsStatic) @@ -333,15 +337,16 @@ private void PublishProperties(TypeBuilder typeBuilder, Class clazz) } else { - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); for (int i = 0; i < indexer.Length; i++) ilgen.EmitLdarg(i + 1); mw.EmitCallvirt(ilgen); } - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); + + propbuilder.SetGetMethod(mb); } - propbuilder.SetGetMethod(mb); } } if (setter != null) @@ -354,10 +359,12 @@ private void PublishProperties(TypeBuilder typeBuilder, Class clazz) } else { - var mb = mw.GetMethod() as MethodBuilder; - if (mb == null || mb.DeclaringType != typeBuilder || (!mb.IsFinal && final)) + var m = mw.GetMethod() as IMethodSymbol; + if (m == null || m.DeclaringType != typeBuilder || (!m.IsFinal && final)) { - mb = typeBuilder.DefineMethod("set_" + prop.Name, GetPropertyMethodAttributes(mw, final), mw.ReturnTypeForDefineMethod, args); + var mb = typeBuilder.DefineMethod("set_" + prop.Name, GetPropertyMethodAttributes(mw, final), mw.ReturnTypeForDefineMethod, args); + m = mb.Symbol; + Context.AttributeHelper.HideFromJava(mb); var ilgen = Context.CodeEmitterFactory.Create(mb); if (mw.IsStatic) @@ -368,22 +375,23 @@ private void PublishProperties(TypeBuilder typeBuilder, Class clazz) } else { - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); for (int i = 0; i <= indexer.Length; i++) ilgen.EmitLdarg(i + 1); mw.EmitCallvirt(ilgen); } - ilgen.Emit(OpCodes.Ret); + + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); - } - propbuilder.SetSetMethod(mb); + propbuilder.SetSetMethod(mb); + } } } } } - private static void MapModifiers(MapModifiers mapmods, bool isConstructor, out bool setmodifiers, ref MethodAttributes attribs, bool isNewSlot) + private static void MapModifiers(MapModifiers mapmods, bool isConstructor, out bool setmodifiers, ref System.Reflection.MethodAttributes attribs, bool isNewSlot) { setmodifiers = false; var modifiers = (Modifiers)mapmods; @@ -447,18 +455,18 @@ private static void MapModifiers(MapModifiers mapmods, bool isConstructor, out b } } - private void MapSignature(string sig, out Type returnType, out Type[] parameterTypes) + private void MapSignature(string sig, out ITypeSymbol returnType, out ITypeSymbol[] parameterTypes) { returnType = ClassLoader.RetTypeWrapperFromSig(sig, LoadMode.Link).TypeAsSignatureType; var parameterTypeWrappers = ClassLoader.ArgJavaTypeListFromSig(sig, LoadMode.Link); - parameterTypes = new Type[parameterTypeWrappers.Length]; + parameterTypes = new ITypeSymbol[parameterTypeWrappers.Length]; for (int i = 0; i < parameterTypeWrappers.Length; i++) { parameterTypes[i] = parameterTypeWrappers[i].TypeAsSignatureType; } } - protected override void EmitMapXmlMetadata(TypeBuilder typeBuilder, ClassFile classFile, RuntimeJavaField[] fields, RuntimeJavaMethod[] methods) + protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, ClassFile classFile, RuntimeJavaField[] fields, RuntimeJavaMethod[] methods) { var mapxml = classLoader.GetMapXmlClasses(); if (mapxml != null) @@ -605,7 +613,7 @@ protected override void EmitMapXmlMetadata(TypeBuilder typeBuilder, ClassFile cl } if (clazz.Interfaces != null) { - foreach (Implements iface in clazz.Interfaces) + foreach (var iface in clazz.Interfaces) { var tw = ClassLoader.LoadClassByName(iface.Class); // NOTE since this interface won't be part of the list in the ImplementAttribute, @@ -613,16 +621,16 @@ protected override void EmitMapXmlMetadata(TypeBuilder typeBuilder, ClassFile cl typeBuilder.AddInterfaceImplementation(tw.TypeAsBaseType); if (iface.Methods != null) { - foreach (Method m in iface.Methods) + foreach (var m in iface.Methods) { var mw = tw.GetMethodWrapper(m.Name, m.Sig, false); if (mw == null) throw new InvalidOperationException("Method " + m.Name + m.Sig + " not found in interface " + tw.Name); mw.Link(); - MethodBuilder mb = mw.GetDefineMethodHelper().DefineMethod(this, typeBuilder, tw.Name + "/" + m.Name, MethodAttributes.Private | MethodAttributes.NewSlot | MethodAttributes.Virtual | MethodAttributes.Final | MethodAttributes.CheckAccessOnOverride); + var mb = mw.GetDefineMethodHelper().DefineMethod(this, typeBuilder, tw.Name + "/" + m.Name, System.Reflection.MethodAttributes.Private | System.Reflection.MethodAttributes.NewSlot | System.Reflection.MethodAttributes.Virtual | System.Reflection.MethodAttributes.Final | System.Reflection.MethodAttributes.CheckAccessOnOverride); Context.AttributeHelper.HideFromJava(mb); - typeBuilder.DefineMethodOverride(mb, (MethodInfo)mw.GetMethod()); + typeBuilder.DefineMethodOverride(mb, (IMethodSymbol)mw.GetMethod()); CodeEmitter ilgen = Context.CodeEmitterFactory.Create(mb); m.Emit(classLoader, ilgen); ilgen.DoEmit(); @@ -634,12 +642,12 @@ protected override void EmitMapXmlMetadata(TypeBuilder typeBuilder, ClassFile cl } } - protected override MethodBuilder DefineGhostMethod(TypeBuilder typeBuilder, string name, MethodAttributes attribs, RuntimeJavaMethod mw) + protected override MethodBuilder DefineGhostMethod(ITypeSymbolBuilder typeBuilder, string name, System.Reflection.MethodAttributes attribs, RuntimeJavaMethod mw) { if (typeBuilderGhostInterface != null && mw.IsVirtual) { var helper = mw.GetDefineMethodHelper(); - var stub = helper.DefineMethod(this, typeBuilder, name, MethodAttributes.Public); + var stub = helper.DefineMethod(this, typeBuilder, name, System.Reflection.MethodAttributes.Public); ((RuntimeGhostJavaMethod)mw).SetGhostMethod(stub); return helper.DefineMethod(this, typeBuilderGhostInterface, name, attribs); } @@ -647,7 +655,7 @@ protected override MethodBuilder DefineGhostMethod(TypeBuilder typeBuilder, stri return null; } - protected override void FinishGhost(TypeBuilder typeBuilder, RuntimeJavaMethod[] methods) + protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaMethod[] methods) { if (typeBuilderGhostInterface != null) { @@ -664,24 +672,24 @@ protected override void FinishGhost(TypeBuilder typeBuilder, RuntimeJavaMethod[] var ilgen = Context.CodeEmitterFactory.Create(stub); var end = ilgen.DefineLabel(); var implementers = classLoader.GetGhostImplementers(this); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldfld, ghostRefField); - ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, typeBuilderGhostInterface); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldfld, ghostRefField); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, typeBuilderGhostInterface); var label = ilgen.DefineLabel(); ilgen.EmitBrfalse(label); - ilgen.Emit(OpCodes.Castclass, typeBuilderGhostInterface); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, typeBuilderGhostInterface); for (int k = 0; k < args.Length; k++) { ilgen.EmitLdarg(k + 1); } - ilgen.Emit(OpCodes.Callvirt, (MethodInfo)methods[i].GetMethod()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, (IMethodSymbol)methods[i].GetMethod()); ilgen.EmitBr(end); ilgen.MarkLabel(label); for (int j = 0; j < implementers.Length; j++) { - ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, implementers[j].TypeAsTBD); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, implementers[j].TypeAsTBD); label = ilgen.DefineLabel(); ilgen.EmitBrfalse(label); var mw = implementers[j].GetMethodWrapper(methods[i].Name, methods[i].Signature, true); @@ -828,7 +836,7 @@ protected override void FinishGhost(TypeBuilder typeBuilder, RuntimeJavaMethod[] ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ldtoken, typeBuilder); ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Call, Context.Resolver.ResolveRuntimeType(typeof(IKVM.Runtime.GhostTag).FullName).AsReflection().GetMethod("IsGhostArrayInstance", BindingFlags.NonPublic | BindingFlags.Static)); + ilgen.Emit(OpCodes.Call, Context.Resolver.ResolveRuntimeType(typeof(IKVM.Runtime.GhostTag).FullName).GetMethod("IsGhostArrayInstance", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static)); ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); @@ -964,15 +972,15 @@ protected override TypeBuilder DefineGhostType(string mangledTypeName, TypeAttri return typeBuilder; } - internal override FieldInfo GhostRefField => ghostRefField; + internal override IFieldSymbol GhostRefField => ghostRefField; internal override void EmitCheckcast(CodeEmitter ilgen) { if (IsGhost) { - ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Call, ghostCastMethod); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ghostCastMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); } else if (IsGhostArray) { @@ -985,8 +993,8 @@ internal override void EmitCheckcast(CodeEmitter ilgen) tw = tw.ElementTypeWrapper; } ilgen.EmitLdc_I4(rank); - ilgen.Emit(OpCodes.Call, ghostCastArrayMethod); - ilgen.Emit(OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(Context.Types.Object, rank)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ghostCastArrayMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(Context.Types.Object, rank)); } else { @@ -998,11 +1006,11 @@ internal override void EmitInstanceOf(CodeEmitter ilgen) { if (IsGhost) { - ilgen.Emit(OpCodes.Call, ghostIsInstanceMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ghostIsInstanceMethod); } else if (IsGhostArray) { - ilgen.Emit(OpCodes.Call, ghostIsInstanceArrayMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ghostIsInstanceArrayMethod); } else { @@ -1017,12 +1025,12 @@ internal void SetAnnotation(Annotation annotation) internal override Annotation Annotation => annotation; - internal void SetEnumType(Type enumType) + internal void SetEnumType(ITypeSymbol enumType) { this.enumType = enumType; } - internal override Type EnumType => enumType; + internal override ITypeSymbol EnumType => enumType; sealed class ReplacedMethodWrapper : RuntimeJavaMethod { From 434f8b5b611ed46e8e91006ac95e4b512b2b06b0 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 18 Sep 2024 10:55:48 -0500 Subject: [PATCH 07/59] Use safe method. --- src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 7037880a35..496e7b58e0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -92,7 +92,7 @@ public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModule public virtual MemberTypes MemberType => UnderlyingMember.MemberType; /// - public virtual int MetadataToken => UnderlyingMember.MetadataToken; + public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); /// public virtual string Name => UnderlyingMember.Name; From 41fdc5f22d436e7272fb0dcba085226485a59b40 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 18 Sep 2024 16:46:59 -0500 Subject: [PATCH 08/59] Reintroduced IKVM Reflection. --- .../IIkvmReflectionAssemblySymbolBuilder.cs | 17 ++++++++++++ ...IIkvmReflectionConstructorSymbolBuilder.cs | 14 ++++++++++ .../Emit/IIkvmReflectionEventSymbolBuilder.cs | 14 ++++++++++ .../Emit/IIkvmReflectionFieldSymbolBuilder.cs | 14 ++++++++++ ...ectionGenericTypeParameterSymbolBuilder.cs | 22 ++++++++++++++++ .../IIkvmReflectionMemberSymbolBuilder.cs | 17 ++++++++++++ .../IIkvmReflectionMethodBaseSymbolBuilder.cs | 13 ++++++++++ .../IIkvmReflectionMethodSymbolBuilder.cs | 17 ++++++++++++ ...ectionGenericTypeParameterSymbolBuilder.cs | 5 ++-- .../ReflectionConstructorSymbolBuilder.cs | 2 +- src/IKVM.Reflection/Emit/MethodBuilder.cs | 2 +- src/IKVM.Reflection/Emit/ParameterBuilder.cs | 26 +++++++++++-------- src/IKVM.Reflection/EventInfo.cs | 8 +++--- 13 files changed, 151 insertions(+), 20 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs new file mode 100644 index 0000000000..c8f4ce03eb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs @@ -0,0 +1,17 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionAssemblySymbolBuilder : IIkvmReflectionSymbolBuilder, IAssemblySymbolBuilder, IIkvmReflectionAssemblySymbol + { + + /// + /// Gets the underlying . + /// + AssemblyBuilder UnderlyingAssemblyBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs new file mode 100644 index 0000000000..86b966f989 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs @@ -0,0 +1,14 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionConstructorSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder, IIkvmReflectionConstructorSymbol + { + + ConstructorBuilder UnderlyingConstructorBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs new file mode 100644 index 0000000000..f5e3f728dc --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs @@ -0,0 +1,14 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionEventSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IEventSymbolBuilder, IIkvmReflectionEventSymbol + { + + EventBuilder UnderlyingEventBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs new file mode 100644 index 0000000000..fe61f4f345 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs @@ -0,0 +1,14 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionFieldSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IFieldSymbolBuilder, IIkvmReflectionFieldSymbol + { + + FieldBuilder UnderlyingFieldBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs new file mode 100644 index 0000000000..889de61f28 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -0,0 +1,22 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionGenericTypeParameterSymbolBuilder : IIkvmReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IIkvmReflectionTypeSymbol + { + + /// + /// Gets the underlying . + /// + GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder { get; } + + /// + /// Invoked when the type containing this generic type parameter is completed. + /// + void OnComplete(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs new file mode 100644 index 0000000000..e6d8459ce3 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs @@ -0,0 +1,17 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionMemberSymbolBuilder : IIkvmReflectionSymbolBuilder, IMemberSymbolBuilder, IIkvmReflectionMemberSymbol + { + + /// + /// Invoked when the type responsible for this builder is completed. Implementations should update their + /// underlying type, and optionally dispatch the OnComplete invocation to downstream elements. + /// + void OnComplete(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs new file mode 100644 index 0000000000..b5e6fcd571 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs @@ -0,0 +1,13 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionMethodBaseSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IIkvmReflectionMethodBaseSymbol + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs new file mode 100644 index 0000000000..8de0478935 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs @@ -0,0 +1,17 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionMethodSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder, IIkvmReflectionMethodSymbol + { + + /// + /// Gets the underlying . + /// + MethodBuilder UnderlyingMethodBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs index 20917942a9..a9cc7500f8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs @@ -1,9 +1,8 @@ using System.Reflection.Emit; -using IKVM.CoreLib.Symbols.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Symbols.Emit; -namespace IKVM.CoreLib.Symbols.Emit +namespace IKVM.CoreLib.Symbols.Reflection.Emit { interface IReflectionGenericTypeParameterSymbolBuilder : IReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IReflectionTypeSymbol diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index 2dbde97d2e..e9692b2c95 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -48,7 +48,7 @@ public void SetImplementationFlags(MethodImplAttributes attributes) /// public IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) { - return new ReflectionParameterSymbolBuilder(Context, ResolvingModule, this, UnderlyingConstructorBuilder.DefineParameter(iSequence, attributes, strParamName)); + return ResolveParameterSymbol(UnderlyingConstructorBuilder.DefineParameter(iSequence, attributes, strParamName)); } /// diff --git a/src/IKVM.Reflection/Emit/MethodBuilder.cs b/src/IKVM.Reflection/Emit/MethodBuilder.cs index db75abaf6b..f0757a90d1 100644 --- a/src/IKVM.Reflection/Emit/MethodBuilder.cs +++ b/src/IKVM.Reflection/Emit/MethodBuilder.cs @@ -285,7 +285,7 @@ public ParameterBuilder DefineParameter(int position, ParameterAttributes attrib parameters ??= new List(); ModuleBuilder.ParamTable.AddVirtualRecord(); - var pb = new ParameterBuilder(ModuleBuilder, position, attributes, strParamName); + var pb = new ParameterBuilder(this, position, attributes, strParamName); if (parameters.Count == 0 || position >= parameters[parameters.Count - 1].Position) { parameters.Add(pb); diff --git a/src/IKVM.Reflection/Emit/ParameterBuilder.cs b/src/IKVM.Reflection/Emit/ParameterBuilder.cs index 153c18cd50..a745632894 100644 --- a/src/IKVM.Reflection/Emit/ParameterBuilder.cs +++ b/src/IKVM.Reflection/Emit/ParameterBuilder.cs @@ -29,7 +29,7 @@ namespace IKVM.Reflection.Emit public sealed class ParameterBuilder { - readonly ModuleBuilder module; + readonly MethodBuilder method; short flags; readonly short sequence; readonly StringHandle nameIndex; @@ -39,16 +39,16 @@ public sealed class ParameterBuilder /// /// Initializes a new instance. /// - /// + /// /// /// /// - internal ParameterBuilder(ModuleBuilder module, int sequence, ParameterAttributes attribs, string name) + internal ParameterBuilder(MethodBuilder method, int sequence, ParameterAttributes attribs, string name) { - this.module = module; + this.method = method; this.flags = (short)attribs; this.sequence = (short)sequence; - this.nameIndex = name == null ? default : module.GetOrAddString(name); + this.nameIndex = name == null ? default : method.ModuleBuilder.GetOrAddString(name); this.name = name; } @@ -57,12 +57,16 @@ internal int PseudoToken get { if (lazyPseudoToken == 0) - lazyPseudoToken = module.AllocPseudoToken(); + lazyPseudoToken = method.ModuleBuilder.AllocPseudoToken(); return lazyPseudoToken; } } + public MethodInfo Method => method; + + public Module Module => method.Module; + public string Name { get { return name; } @@ -115,11 +119,11 @@ public void SetCustomAttribute(CustomAttributeBuilder customAttributeBuilder) flags |= (short)ParameterAttributes.Optional; break; case KnownCA.MarshalAsAttribute: - FieldMarshal.SetMarshalAsAttribute(module, PseudoToken, customAttributeBuilder); + FieldMarshal.SetMarshalAsAttribute(method.ModuleBuilder, PseudoToken, customAttributeBuilder); flags |= (short)ParameterAttributes.HasFieldMarshal; break; default: - module.SetCustomAttribute(PseudoToken, customAttributeBuilder); + method.ModuleBuilder.SetCustomAttribute(PseudoToken, customAttributeBuilder); break; } } @@ -127,12 +131,12 @@ public void SetCustomAttribute(CustomAttributeBuilder customAttributeBuilder) public void SetConstant(object defaultValue) { flags |= (short)ParameterAttributes.HasDefault; - module.AddConstant(PseudoToken, defaultValue); + method.ModuleBuilder.AddConstant(PseudoToken, defaultValue); } internal void WriteMetadata() { - module.Metadata.AddParameter( + method.ModuleBuilder.Metadata.AddParameter( (System.Reflection.ParameterAttributes)flags, nameIndex, sequence); @@ -141,7 +145,7 @@ internal void WriteMetadata() internal void FixupToken(int parameterToken) { if (lazyPseudoToken != 0) - module.RegisterTokenFixup(lazyPseudoToken, parameterToken); + method.ModuleBuilder.RegisterTokenFixup(lazyPseudoToken, parameterToken); } } diff --git a/src/IKVM.Reflection/EventInfo.cs b/src/IKVM.Reflection/EventInfo.cs index 5d2d3ac1e9..00900534c6 100644 --- a/src/IKVM.Reflection/EventInfo.cs +++ b/src/IKVM.Reflection/EventInfo.cs @@ -29,10 +29,10 @@ namespace IKVM.Reflection public abstract class EventInfo : MemberInfo { - /// - /// Initializes a new instance. - /// - internal EventInfo() + /// + /// Initializes a new instance. + /// + protected EventInfo() { } From 149ddcdba7f8a4c9d620a7ab74b1abf461a76526 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 18 Sep 2024 19:19:38 -0500 Subject: [PATCH 09/59] More replacement. --- .../IkvmReflectionSymbolTests.cs | 665 ++++++++++----- .../IIkvmReflectionModuleSymbolBuilder.cs | 17 + .../IIkvmReflectionParameterSymbolBuilder.cs | 22 + .../IIkvmReflectionPropertySymbolBuilder.cs | 14 + .../Emit/IIkvmReflectionSymbolBuilder.cs | 19 + .../Emit/IIkvmReflectionTypeSymbolBuilder.cs | 17 + .../IkvmReflectionAssemblySymbolBuilder.cs | 202 +++++ .../IkvmReflectionConstructorSymbolBuilder.cs | 97 +++ .../IkvmReflectionCustomAttributeBuilder.cs | 29 + .../Emit/IkvmReflectionEventSymbolBuilder.cs | 163 ++++ .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 145 ++++ ...ectionGenericTypeParameterSymbolBuilder.cs | 584 +++++++++++++ .../Emit/IkvmReflectionMemberSymbolBuilder.cs | 313 +++++++ .../IkvmReflectionMethodBaseSymbolBuilder.cs | 122 +++ .../Emit/IkvmReflectionMethodSymbolBuilder.cs | 150 ++++ .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 382 +++++++++ .../IkvmReflectionParameterBuilderInfo.cs | 71 ++ .../IkvmReflectionParameterSymbolBuilder.cs | 164 ++++ .../IkvmReflectionPropertySymbolBuilder.cs | 184 ++++ .../Emit/IkvmReflectionSymbolBuilder.cs | 24 + .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 802 ++++++++++++++++++ .../IIkvmReflectionAssemblySymbol.cs | 32 + .../IIkvmReflectionConstructorSymbol.cs | 16 + .../IIkvmReflectionEventSymbol.cs | 16 + .../IIkvmReflectionFieldSymbol.cs | 16 + .../IIkvmReflectionMemberSymbol.cs | 26 + .../IIkvmReflectionMethodBaseSymbol.cs | 16 + .../IIkvmReflectionMethodSymbol.cs | 16 + .../IIkvmReflectionModuleSymbol.cs | 123 +++ .../IIkvmReflectionParameterSymbol.cs | 26 + .../IIkvmReflectionPropertySymbol.cs | 16 + .../IkvmReflection/IIkvmReflectionSymbol.cs | 336 ++++++++ .../IIkvmReflectionTypeSymbol.cs | 16 + .../IkvmReflectionAssemblyMetadata.cs | 63 ++ .../IkvmReflectionAssemblySymbol.cs | 162 ++++ .../IkvmReflectionConstructorSymbol.cs | 34 + .../IkvmReflectionEventSymbol.cs | 104 +++ .../IkvmReflectionFieldSymbol.cs | 98 +++ ...kvmReflectionGenericTypeParameterSymbol.cs | 566 ++++++++++++ .../IkvmReflectionMemberSymbol.cs | 286 +++++++ .../IkvmReflectionMethodBaseSymbol.cs | 108 +++ .../IkvmReflectionMethodSymbol.cs | 65 ++ .../IkvmReflectionModuleMetadata.cs | 480 +++++++++++ .../IkvmReflectionModuleSymbol.cs | 320 +++++++ .../IkvmReflectionParameterSymbol.cs | 121 +++ .../IkvmReflectionPropertySymbol.cs | 121 +++ .../IkvmReflection/IkvmReflectionSymbol.cs | 549 ++++++++++++ .../IkvmReflectionSymbolContext.cs | 297 +++++++ .../IkvmReflectionSymbolExtensions.cs | 11 + .../IkvmReflection/IkvmReflectionTypeImpl.cs | 587 +++++++++++++ .../IkvmReflectionTypeSymbol.cs | 554 ++++++++++++ .../IkvmReflection/IkvmReflectionUtil.cs | 315 +++++++ .../Emit/ReflectionParameterSymbolBuilder.cs | 4 +- src/IKVM.Reflection/Emit/PropertyBuilder.cs | 11 + src/IKVM.Runtime/AttributeHelper.cs | 6 +- src/IKVM.Runtime/ByteCodeHelper.cs | 2 +- src/IKVM.Runtime/CodeEmitter.cs | 2 +- .../Java/Externs/sun/misc/Unsafe.cs | 24 +- src/IKVM.Runtime/LambdaMetafactory.cs | 132 +-- src/IKVM.Runtime/ReflectUtil.cs | 11 +- src/IKVM.Runtime/RuntimeArrayJavaType.cs | 12 - .../RuntimeByteCodeJavaType.FinishContext.cs | 182 ++-- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 46 +- src/IKVM.Runtime/RuntimeJavaField.cs | 16 +- src/IKVM.Runtime/RuntimeJavaType.cs | 78 +- .../RuntimeManagedByteCodeJavaType.cs | 2 +- ...gedJavaType.AttributeAnnotationJavaType.cs | 6 +- ...ntimeManagedJavaType.DelegateJavaMethod.cs | 32 +- src/IKVM.Runtime/Serialization.cs | 40 +- src/IKVM.Runtime/SymbolExtensions.cs | 56 +- src/IKVM.Runtime/atomic.cs | 107 ++- src/IKVM.Runtime/compiler.cs | 86 +- 72 files changed, 9894 insertions(+), 643 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionConstructorSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionEventSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionFieldSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMemberSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblyMetadata.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolExtensions.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index 47eb9aed49..b33adef9ee 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -1,221 +1,444 @@ -//using System.IO; - -//using FluentAssertions; - -//using IKVM.CoreLib.Symbols.IkvmReflection; -//using IKVM.Reflection; - -//using Microsoft.VisualStudio.TestPlatform.PlatformAbstractions; -//using Microsoft.VisualStudio.TestTools.UnitTesting; - -//namespace IKVM.CoreLib.Tests.Symbols.IkvmReflection -//{ - -// [TestClass] -// public class IkvmReflectionSymbolTests -// { - -// class Foo -// { - -// T? field; - -// bool Method(int p1) => true; - -// } - -// Universe? universe; -// Assembly? coreAssembly; -// Assembly? thisAssembly; - -// [TestInitialize] -// public void Setup() -// { -// universe = new Universe(typeof(object).Assembly.GetName().Name); -// universe.AssemblyResolve += Universe_AssemblyResolve; -// coreAssembly = universe.LoadFile(typeof(object).Assembly.GetAssemblyLocation()); -// thisAssembly = universe.LoadFile(typeof(IkvmReflectionSymbolTests).Assembly.GetAssemblyLocation()); -// } - -// /// -// /// Attempt to load assembly from system. -// /// -// /// -// /// -// /// -// Assembly? Universe_AssemblyResolve(object sender, ResolveEventArgs args) -// { -// try -// { -// var asm = System.Reflection.Assembly.Load(args.Name); -// if (asm != null && File.Exists(asm.Location)) -// return universe!.LoadFile(asm.Location); -// } -// catch -// { - -// } - -// return null; -// } - -// [TestMethod] -// public void SameTypeShouldBeSame() -// { -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Object")); -// var s2 = c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Object")); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public void GenericTypeDefinitionShouldBeSame() -// { -// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1"); -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(t); -// var s2 = c.GetOrCreateTypeSymbol(t); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public void GenericTypeShouldBeSame() -// { -// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(universe!.GetBuiltInType("System", "Int32")); -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(t); -// var s2 = c.GetOrCreateTypeSymbol(t); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public void ArrayTypeShouldBeSame() -// { -// var t = universe!.GetBuiltInType("System", "Object").MakeArrayType(2); -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(t); -// var s2 = c.GetOrCreateTypeSymbol(t); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public void SZArrayTypeShouldBeSame() -// { -// var t = universe!.GetBuiltInType("System", "Object").MakeArrayType(); -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(t); -// var s2 = c.GetOrCreateTypeSymbol(t); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public unsafe void PointerTypeShouldBeSame() -// { -// var t = universe!.GetBuiltInType("System", "Int32").MakePointerType(); -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(t); -// var s2 = c.GetOrCreateTypeSymbol(t); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public unsafe void ByRefTypeShouldBeSame() -// { -// var t = universe!.GetBuiltInType("System", "Int32").MakeByRefType(); -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(t); -// var s2 = c.GetOrCreateTypeSymbol(t); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public void EnumTypeShouldBeSame() -// { -// var a = universe!.Load(typeof(System.AttributeTargets).Assembly.FullName); -// var t = a.GetType("System.AttributeTargets"); -// var c = new IkvmReflectionSymbolContext(); -// var s1 = c.GetOrCreateTypeSymbol(t); -// var s2 = c.GetOrCreateTypeSymbol(t); -// s1.Should().BeSameAs(s2); -// } - -// [TestMethod] -// public void CanGetType() -// { -// var t = universe!.GetBuiltInType("System", "Object"); -// var c = new IkvmReflectionSymbolContext(); -// var s = c.GetOrCreateTypeSymbol(t); -// s.Name.Should().Be("Object"); -// s.FullName.Should().Be("System.Object"); -// } - -// [TestMethod] -// public void CanGetFieldOfGenericTypeDefinition() -// { -// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1"); -// var c = new IkvmReflectionSymbolContext(); -// var s = c.GetOrCreateTypeSymbol(t); -// s.IsGenericType.Should().BeTrue(); -// s.IsGenericTypeDefinition.Should().BeTrue(); -// var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); -// f.Name.Should().Be("field"); -// f.FieldType.IsGenericType.Should().BeFalse(); -// f.FieldType.IsGenericParameter.Should().BeTrue(); -// } - -// [TestMethod] -// public void CanGetFieldOfGenericType() -// { -// var t = thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(universe!.GetBuiltInType("System", "Int32")); -// var c = new IkvmReflectionSymbolContext(); -// var s = c.GetOrCreateTypeSymbol(t); -// s.IsGenericType.Should().BeTrue(); -// s.IsGenericTypeDefinition.Should().BeFalse(); -// var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); -// f.Name.Should().Be("field"); -// f.FieldType.IsGenericType.Should().BeFalse(); -// f.FieldType.IsGenericParameter.Should().BeFalse(); -// f.FieldType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "Int32"))); -// } - -// [TestMethod] -// public void CanGetMethod() -// { -// var t = universe!.GetBuiltInType("System", "Object"); -// var c = new IkvmReflectionSymbolContext(); -// var s = c.GetOrCreateTypeSymbol(t); -// var m = s.GetMethod("ToString"); -// m.Name.Should().Be("ToString"); -// m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "String"))); -// m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(universe!.GetBuiltInType("System", "String"))); -// m.IsGenericMethod.Should().BeFalse(); -// m.IsGenericMethodDefinition.Should().BeFalse(); -// m.IsPublic.Should().BeTrue(); -// m.IsPrivate.Should().BeFalse(); -// } - -// [System.AttributeUsage(System.AttributeTargets.Class)] -// class AttributeWithType : System.Attribute -// { - -// public AttributeWithType(System.Type type) -// { -// Type = type; -// } - -// public System.Type Type { get; } - -// } -// [TestMethod] -// public void CanReadCustomAttributes() -// { -// var c = new IkvmReflectionSymbolContext(); -// var s = c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); -// var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly!.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); -// var v = a.Value.ConstructorArguments[0].Value; -// v.Should().BeOfType(); -// } - -// } - -//} +using System; +using System.IO; +using System.Linq; + +using FluentAssertions; + +using IKVM.CoreLib.Symbols.IkvmReflection; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Microsoft.VisualStudio.TestPlatform.PlatformAbstractions; +using Microsoft.VisualStudio.TestTools.UnitTesting; + +namespace IKVM.CoreLib.Tests.Symbols.IkvmReflection +{ + + [TestClass] + public class IkvmReflectionSymbolTests + { + + class Foo + { + + T? field; + + bool Method(int p1) => true; + + } + + Universe? universe; + Assembly? coreAssembly; + Assembly? thisAssembly; + + [TestInitialize] + public void Setup() + { + universe = new Universe(typeof(object).Assembly.GetName().Name); + universe.AssemblyResolve += Universe_AssemblyResolve; + coreAssembly = universe.LoadFile(typeof(object).Assembly.GetAssemblyLocation()); + thisAssembly = universe.LoadFile(typeof(IkvmReflectionSymbolTests).Assembly.GetAssemblyLocation()); + } + + /// + /// Attempt to load assembly from system. + /// + /// + /// + /// + Assembly? Universe_AssemblyResolve(object sender, IKVM.Reflection.ResolveEventArgs args) + { + try + { + var asm = System.Reflection.Assembly.Load(args.Name); + if (asm != null && File.Exists(asm.Location)) + return universe!.LoadFile(asm.Location); + } + catch + { + + } + + return null; + } + + [TestMethod] + public void SameTypeShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); + var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); + s1.Should().BeOfType(); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void GenericTypeDefinitionShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); + var s2 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void GenericTypeShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); + var s2 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void ArrayTypeShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); + var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void SZArrayTypeShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); + var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public unsafe void PointerTypeShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakePointerType()); + var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakePointerType()); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public unsafe void ByRefTypeShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeByRefType()); + var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeByRefType()); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void EnumTypeShouldBeSame() + { + var c = new IkvmReflectionSymbolContext(); + var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.AttributeTargets")); + var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.AttributeTargets")); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void CanResolveType() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); + s.Name.Should().Be("Object"); + s.FullName.Should().Be("System.Object"); + } + + [TestMethod] + public void CanResolveFieldOfGenericTypeDefinition() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); + s.IsGenericType.Should().BeTrue(); + s.IsGenericTypeDefinition.Should().BeTrue(); + var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); + f.Name.Should().Be("field"); + f.FieldType.IsGenericType.Should().BeFalse(); + f.FieldType.IsGenericParameter.Should().BeTrue(); + } + + [TestMethod] + public void CanResolveFieldOfGenericType() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); + s.IsGenericType.Should().BeTrue(); + s.IsGenericTypeDefinition.Should().BeFalse(); + var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); + f.Name.Should().Be("field"); + f.FieldType.IsGenericType.Should().BeFalse(); + f.FieldType.IsGenericParameter.Should().BeFalse(); + f.FieldType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32"))); + } + + [TestMethod] + public void CanResolveMethod() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); + var m = s.GetMethod("ToString"); + m.Name.Should().Be("ToString"); + m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.String"))); + m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.String"))); + m.IsGenericMethod.Should().BeFalse(); + m.IsGenericMethodDefinition.Should().BeFalse(); + m.IsPublic.Should().BeTrue(); + m.IsPrivate.Should().BeFalse(); + } + + [TestMethod] + public void CanResolveGenericMethod() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.ValueTuple")); + var m = s.GetMethods().FirstOrDefault(i => i.Name == "Create" && i.GetGenericArguments().Length == 1); + m.Name.Should().Be("Create"); + m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.ValueTuple`1")).MakeGenericType(m.GetGenericArguments()[0])); + m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.ValueTuple`1")).MakeGenericType(m.GetGenericArguments()[0])); + m.IsGenericMethod.Should().BeTrue(); + m.IsGenericMethodDefinition.Should().BeTrue(); + m.IsPublic.Should().BeTrue(); + m.IsPrivate.Should().BeFalse(); + } + + [TestMethod] + public void CanResolveParameters() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); + var m = s.GetMethod("ReferenceEquals"); + m.Name.Should().Be("ReferenceEquals"); + m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Boolean"))); + m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Boolean"))); + m.IsGenericMethod.Should().BeFalse(); + m.IsGenericMethodDefinition.Should().BeFalse(); + m.IsPublic.Should().BeTrue(); + m.IsPrivate.Should().BeFalse(); + var p = m.GetParameters(); + p.Length.Should().Be(2); + p[0].Name.Should().Be("objA"); + p[0].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object"))); + p[1].Name.Should().Be("objB"); + p[1].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object"))); + } + + [AttributeUsage(AttributeTargets.Class)] + class AttributeWithType : Attribute + { + + public AttributeWithType(System.Type type) + { + Type = type; + } + + public System.Type Type { get; } + + } + + [AttributeWithType(typeof(object))] + class ClassWithAttributeWithType + { + + + + } + + [TestMethod] + public void CanReadCustomAttributes() + { + var c = new IkvmReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); + var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); + var v = a.Value.ConstructorArguments[0].Value; + v.Should().BeOfType(); + } + + [TestMethod] + public void CanResolveAssemblyBuilder() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var assemblySymbol = c.GetOrCreateAssemblySymbol(a); + assemblySymbol.Should().BeOfType(); + assemblySymbol.Should().BeSameAs(c.GetOrCreateAssemblySymbol(a)); + } + + [TestMethod] + public void CanResolveModuleBuilder() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var moduleSymbol = c.GetOrCreateModuleSymbol(m); + moduleSymbol.Should().BeOfType(); + moduleSymbol.Should().BeSameAs(c.GetOrCreateModuleSymbol(m)); + } + + [TestMethod] + public void CanResolveTypeBuilder() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + + var type1 = m.DefineType("DynamicType1"); + var type1Symbol = c.GetOrCreateTypeSymbol(type1); + type1Symbol.Should().BeOfType(); + type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); + } + + [TestMethod] + public void CanResolveMultipleTypeBuilders() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + + var type1 = m.DefineType("DynamicType1"); + var type1Symbol = c.GetOrCreateTypeSymbol(type1); + type1Symbol.Should().BeOfType(); + type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); + type1.CreateType(); + + var type2 = m.DefineType("DynamicType2"); + var type2Symbol = c.GetOrCreateTypeSymbol(type2); + type2Symbol.Should().BeOfType(); + type2Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type2)); + } + + [TestMethod] + public void CanResolveMethodBuilder() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + } + + [TestMethod] + public void CanResolveMultipleMethodBuilders() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); + var method1Symbol = c.GetOrCreateMethodSymbol(method1); + method1Symbol.Should().BeOfType(); + method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); + + var method2 = t.DefineMethod("DynamicMethod2", MethodAttributes.Public | MethodAttributes.Static); + var method2Symbol = c.GetOrCreateMethodSymbol(method2); + method2Symbol.Should().BeOfType(); + method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); + } + + [TestMethod] + public void CanResolveFieldBuilder() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var field = t.DefineField("dynamicField", coreAssembly.GetType("System.Object"), FieldAttributes.Public); + var fieldSymbol = c.GetOrCreateFieldSymbol(field); + fieldSymbol.Should().BeOfType(); + fieldSymbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field)); + } + + [TestMethod] + public void CanResolveMultipleFieldBuilders() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var field1 = t.DefineField("dynamicField1", coreAssembly.GetType("System.Object"), FieldAttributes.Public); + var field1Symbol = c.GetOrCreateFieldSymbol(field1); + field1Symbol.Should().BeOfType(); + field1Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field1)); + + var field2 = t.DefineField("dynamicField2", coreAssembly.GetType("System.Object"), FieldAttributes.Public); + var field2Symbol = c.GetOrCreateFieldSymbol(field2); + field2Symbol.Should().BeOfType(); + field2Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field2)); + } + + [TestMethod] + public void CanResolvePropertyBuilder() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var property = t.DefineProperty("DynamicProperty", PropertyAttributes.None, coreAssembly.GetType("System.Object"), []); + var propertySymbol = c.GetOrCreatePropertySymbol(property); + propertySymbol.Should().BeOfType(); + propertySymbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property)); + } + + [TestMethod] + public void CanResolveMultiplePropertyBuilders() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var property1 = t.DefineProperty("DynamicProperty1", PropertyAttributes.None, coreAssembly.GetType("System.Object"), []); + var property1Symbol = c.GetOrCreatePropertySymbol(property1); + property1Symbol.Should().BeOfType(); + property1Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property1)); + + var property2 = t.DefineProperty("DynamicProperty2", PropertyAttributes.None, coreAssembly.GetType("System.Object"), []); + var property2Symbol = c.GetOrCreatePropertySymbol(property2); + property2Symbol.Should().BeOfType(); + property2Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property2)); + } + + [TestMethod] + public void CanResolveEventBuilder() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly.GetType("System.EventHandler")); + var event1Symbol = c.GetOrCreateEventSymbol(event1); + event1Symbol.Should().BeOfType(); + event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); + } + + [TestMethod] + public void CanResolveMultipleEventBuilders() + { + var c = new IkvmReflectionSymbolContext(); + var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); + var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); + var t = m.DefineType("DynamicType"); + + var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly.GetType("System.EventHandler")); + var event1Symbol = c.GetOrCreateEventSymbol(event1); + event1Symbol.Should().BeOfType(); + event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); + + var event2 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly.GetType("System.EventHandler")); + var event2Symbol = c.GetOrCreateEventSymbol(event2); + event2Symbol.Should().BeOfType(); + event2Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event2)); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs new file mode 100644 index 0000000000..564c9e551e --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs @@ -0,0 +1,17 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionModuleSymbolBuilder : IIkvmReflectionSymbolBuilder, IModuleSymbolBuilder, IIkvmReflectionModuleSymbol + { + + /// + /// Gets the underlying . + /// + ModuleBuilder UnderlyingModuleBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs new file mode 100644 index 0000000000..8d74fa945e --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs @@ -0,0 +1,22 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionParameterSymbolBuilder : IIkvmReflectionSymbolBuilder, IParameterSymbolBuilder, IIkvmReflectionParameterSymbol + { + + /// + /// Gets the underlying . + /// + ParameterBuilder UnderlyingParameterBuilder { get; } + + /// + /// Invoked when the owning method of this parameter is completed. + /// + void OnComplete(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs new file mode 100644 index 0000000000..a52039bdd6 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs @@ -0,0 +1,14 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionPropertySymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IPropertySymbolBuilder, IIkvmReflectionPropertySymbol + { + + PropertyBuilder UnderlyingPropertyBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs new file mode 100644 index 0000000000..ce5e76e98c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs @@ -0,0 +1,19 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionSymbolBuilder : ISymbolBuilder + { + + } + + interface IIkvmReflectionSymbolBuilder : IIkvmReflectionSymbolBuilder, ISymbolBuilder + where TSymbol : IIkvmReflectionSymbol + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs new file mode 100644 index 0000000000..c16eeb22cd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs @@ -0,0 +1,17 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionTypeSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, ITypeSymbolBuilder, IIkvmReflectionTypeSymbol + { + + /// + /// Gets the underlying . + /// + TypeBuilder UnderlyingTypeBuilder { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs new file mode 100644 index 0000000000..21a7d7b028 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -0,0 +1,202 @@ +using System; +using System.Collections.Generic; +using System.Linq; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionAssemblySymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmReflectionAssemblySymbolBuilder + { + + readonly AssemblyBuilder _builder; + IkvmReflectionAssemblyMetadata _metadata; + + /// + /// Initializes a new instance. + /// + /// + /// + public IkvmReflectionAssemblySymbolBuilder(IkvmReflectionSymbolContext context, AssemblyBuilder builder) : + base(context) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _metadata = new IkvmReflectionAssemblyMetadata(this); + } + + /// + public Assembly UnderlyingAssembly => UnderlyingAssemblyBuilder; + + /// + public AssemblyBuilder UnderlyingAssemblyBuilder => _builder; + + #region IAssemblySymbolBuilder + + /// + public IModuleSymbolBuilder DefineModule(string name) + { + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, name + ".dll")); + } + + /// + public IModuleSymbolBuilder DefineModule(string name, string fileName) + { + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName)); + } + + /// + public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo) + { + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName, emitSymbolInfo)); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IAssemblySymbol + + /// + public IEnumerable DefinedTypes => ResolveTypeSymbols(UnderlyingAssembly.DefinedTypes); + + /// + public IMethodSymbol? EntryPoint => ResolveMethodSymbol(UnderlyingAssembly.EntryPoint); + + /// + public IEnumerable ExportedTypes => ResolveTypeSymbols(UnderlyingAssembly.ExportedTypes); + + /// + public string? FullName => UnderlyingAssembly.FullName; + + /// + public string ImageRuntimeVersion => UnderlyingAssembly.ImageRuntimeVersion; + + /// + public IModuleSymbol ManifestModule => ResolveModuleSymbol(UnderlyingAssembly.ManifestModule); + + /// + public IEnumerable Modules => ResolveModuleSymbols(UnderlyingAssembly.Modules); + + /// + public override bool IsComplete => _builder == null; + + /// + public ITypeSymbol[] GetExportedTypes() + { + return ResolveTypeSymbols(UnderlyingAssembly.GetExportedTypes()); + } + + /// + public IModuleSymbol? GetModule(string name) + { + return ResolveModuleSymbol(UnderlyingAssembly.GetModule(name)); + } + + /// + public IModuleSymbol[] GetModules() + { + return ResolveModuleSymbols(UnderlyingAssembly.GetModules()); + } + + /// + public IModuleSymbol[] GetModules(bool getResourceModules) + { + return ResolveModuleSymbols(UnderlyingAssembly.GetModules(getResourceModules)); + } + + /// + public System.Reflection.AssemblyName GetName() + { + return UnderlyingAssembly.GetName().ToAssemblyName(); + } + + /// + public System.Reflection.AssemblyName GetName(bool copiedName) + { + return UnderlyingAssembly.GetName(copiedName).ToAssemblyName(); + } + + /// + public System.Reflection.AssemblyName[] GetReferencedAssemblies() + { + return UnderlyingAssembly.GetReferencedAssemblies().ToAssemblyNames(); + } + + /// + public ITypeSymbol? GetType(string name, bool throwOnError) + { + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError)); + } + + /// + public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError, ignoreCase)); + } + + /// + public ITypeSymbol? GetType(string name) + { + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name)); + } + + /// + public ITypeSymbol[] GetTypes() + { + return ResolveTypeSymbols(UnderlyingAssembly.GetTypes()); + } + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData()); + } + + /// + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingAssembly.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingAssembly.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + + /// + public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _metadata.GetOrCreateModuleSymbol(module); + } + + /// + public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return (IIkvmReflectionModuleSymbolBuilder)_metadata.GetOrCreateModuleSymbol(module); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs new file mode 100644 index 0000000000..962750a1a7 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs @@ -0,0 +1,97 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionConstructorSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, IIkvmReflectionConstructorSymbolBuilder + { + + ConstructorBuilder? _builder; + ConstructorInfo _ctor; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public IkvmReflectionConstructorSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, ConstructorBuilder builder) : + base(context, resolvingModule, resolvingType) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _ctor = _builder; + } + + /// + public ConstructorInfo UnderlyingConstructor => _ctor; + + /// + public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; + + /// + public ConstructorBuilder UnderlyingConstructorBuilder => _builder ?? throw new InvalidOperationException(); + + #region IConstructorSymbolBuilder + + /// + public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + { + UnderlyingConstructorBuilder.SetImplementationFlags((MethodImplAttributes)attributes); + } + + /// + public IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection.ParameterAttributes attributes, string? strParamName) + { + return ResolveParameterSymbol(UnderlyingConstructorBuilder.DefineParameter(iSequence, (ParameterAttributes)attributes, strParamName)); + } + + /// + public IILGenerator GetILGenerator() + { + throw new NotImplementedException(); + } + + /// + public IILGenerator GetILGenerator(int streamSize) + { + throw new NotImplementedException(); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingConstructorBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingConstructorBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + #endregion + + #region IConstructorSymbol + + /// + public override bool IsComplete => _builder == null; + + #endregion + + /// + public override void OnComplete() + { + _ctor = (ConstructorInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs new file mode 100644 index 0000000000..3e9abec0fb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs @@ -0,0 +1,29 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionCustomAttributeBuilder : ICustomAttributeBuilder + { + + readonly CustomAttributeBuilder _builder; + + /// + /// Initializes a new instance. + /// + public IkvmReflectionCustomAttributeBuilder(CustomAttributeBuilder builder) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the underlying reflection . + /// + internal CustomAttributeBuilder UnderlyingBuilder => _builder; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs new file mode 100644 index 0000000000..385d806554 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs @@ -0,0 +1,163 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionEventSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionEventSymbolBuilder + { + + EventBuilder? _builder; + EventInfo _event; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public IkvmReflectionEventSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, EventBuilder builder) : + base(context, resolvingModule, resolvingType) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _event = _builder; + } + + /// + public EventInfo UnderlyingEvent => _event; + + /// + public EventBuilder UnderlyingEventBuilder => _builder ?? throw new NotImplementedException(); + + /// + public override MemberInfo UnderlyingMember => UnderlyingEvent; + + #region IEventSymbolBuilder + + /// + public void SetAddOnMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingEventBuilder.SetAddOnMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void SetRemoveOnMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingEventBuilder.SetRemoveOnMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void SetRaiseMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingEventBuilder.SetRaiseMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingEventBuilder.AddOtherMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingEventBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingEventBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IEventSymbol + + /// + public System.Reflection.EventAttributes Attributes => (System.Reflection.EventAttributes)UnderlyingEvent.Attributes; + + /// + public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); + + /// + public bool IsSpecialName => UnderlyingEvent.IsSpecialName; + + /// + public IMethodSymbol? AddMethod => ResolveMethodSymbol(UnderlyingEvent.AddMethod); + + /// + public IMethodSymbol? RemoveMethod => ResolveMethodSymbol(UnderlyingEvent.RemoveMethod); + + /// + public IMethodSymbol? RaiseMethod => ResolveMethodSymbol(UnderlyingEvent.RaiseMethod); + + /// + public override bool IsComplete => _builder == null; + + /// + public IMethodSymbol? GetAddMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod()); + } + + /// + public IMethodSymbol? GetAddMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetRemoveMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod()); + } + + /// + public IMethodSymbol? GetRemoveMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetRaiseMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod()); + } + + /// + public IMethodSymbol? GetRaiseMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod(nonPublic)); + } + + /// + public IMethodSymbol[] GetOtherMethods() + { + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods()); + } + + /// + public IMethodSymbol[] GetOtherMethods(bool nonPublic) + { + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods(nonPublic)); + } + + #endregion + + /// + public override void OnComplete() + { + _event = (EventInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs new file mode 100644 index 0000000000..b485e6561b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs @@ -0,0 +1,145 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionFieldSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionFieldSymbolBuilder + { + + FieldBuilder? _builder; + FieldInfo _field; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, FieldBuilder builder) : + base(context, resolvingModule, resolvingType) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _field = _builder; + } + + /// + public FieldInfo UnderlyingField => _field; + + /// + public override MemberInfo UnderlyingMember => UnderlyingField; + + /// + public FieldBuilder UnderlyingFieldBuilder => _builder ?? throw new InvalidOperationException(); + + #region IFieldSymbolBuilder + + /// + public void SetConstant(object? defaultValue) + { + UnderlyingFieldBuilder.SetConstant(defaultValue); + } + + /// + public void SetOffset(int iOffset) + { + UnderlyingFieldBuilder.SetOffset(iOffset); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingFieldBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingFieldBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IFieldSymbol + + /// + public System.Reflection.FieldAttributes Attributes => (System.Reflection.FieldAttributes)UnderlyingField.Attributes; + + /// + public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); + + /// + public bool IsSpecialName => UnderlyingField.IsSpecialName; + + /// + public bool IsAssembly => UnderlyingField.IsAssembly; + + /// + public bool IsFamily => UnderlyingField.IsFamily; + + /// + public bool IsFamilyAndAssembly => UnderlyingField.IsFamilyAndAssembly; + + /// + public bool IsFamilyOrAssembly => UnderlyingField.IsFamilyOrAssembly; + + /// + public bool IsInitOnly => UnderlyingField.IsInitOnly; + + /// + public bool IsLiteral => UnderlyingField.IsLiteral; + + /// + public bool IsNotSerialized => UnderlyingField.IsNotSerialized; + + /// + public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; + + /// + public bool IsPrivate => UnderlyingField.IsPrivate; + + /// + public bool IsPublic => UnderlyingField.IsPublic; + + /// + public bool IsStatic => UnderlyingField.IsStatic; + + /// + public override bool IsComplete => _builder == null; + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); + } + + /// + public object? GetRawConstantValue() + { + return UnderlyingField.GetRawConstantValue(); + } + + #endregion + + /// + public override void OnComplete() + { + _field = ResolvingModule.UnderlyingModule.ResolveField(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs new file mode 100644 index 0000000000..011eb99850 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -0,0 +1,584 @@ +using System; + +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionGenericTypeParameterSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionGenericTypeParameterSymbolBuilder + { + + readonly IIkvmReflectionMethodSymbol? _resolvingMethod; + + GenericTypeParameterBuilder? _builder; + Type _type; + IkvmReflectionTypeImpl _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public IkvmReflectionGenericTypeParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, IIkvmReflectionMethodSymbol? resolvingMethod, GenericTypeParameterBuilder builder) : + base(context, resolvingModule, resolvingType) + { + _resolvingMethod = resolvingMethod; + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _type = _builder; + _impl = new IkvmReflectionTypeImpl(this); + } + + /// + public Type UnderlyingType => _type; + + /// + public override MemberInfo UnderlyingMember => UnderlyingType; + + /// + public GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder => _builder ?? throw new InvalidOperationException(); + + #region ITypeSymbolBuilder + + /// + public void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint) + { + UnderlyingGenericTypeParameterBuilder.SetBaseTypeConstraint(baseTypeConstraint?.Unpack()); + } + + /// + public void SetGenericParameterAttributes(System.Reflection.GenericParameterAttributes genericParameterAttributes) + { + UnderlyingGenericTypeParameterBuilder.SetGenericParameterAttributes((GenericParameterAttributes)genericParameterAttributes); + } + + /// + public void SetInterfaceConstraints(params ITypeSymbol[]? interfaceConstraints) + { + UnderlyingGenericTypeParameterBuilder.SetInterfaceConstraints(interfaceConstraints?.Unpack()); + } + + #endregion + + #region ITypeSymbol + + /// + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)_impl.Attributes; + + /// + public IAssemblySymbol Assembly => _impl.Assembly; + + /// + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + + /// + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + + /// + public string? FullName => _impl.FullName; + + /// + public string? Namespace => _impl.Namespace; + + /// + public TypeCode TypeCode => _impl.TypeCode; + + /// + public ITypeSymbol? BaseType => _impl.BaseType; + + /// + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + + /// + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)_impl.GenericParameterAttributes; + + /// + public int GenericParameterPosition => _impl.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + + /// + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + + /// + public bool IsGenericType => _impl.IsGenericType; + + /// + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + + /// + public bool IsGenericParameter => _impl.IsGenericParameter; + + /// + public bool IsAutoLayout => _impl.IsAutoLayout; + + /// + public bool IsExplicitLayout => _impl.IsExplicitLayout; + + /// + public bool IsLayoutSequential => _impl.IsLayoutSequential; + + /// + public bool HasElementType => _impl.HasElementType; + + /// + public bool IsClass => _impl.IsClass; + + /// + public bool IsValueType => _impl.IsValueType; + + /// + public bool IsInterface => _impl.IsInterface; + + /// + public bool IsPrimitive => _impl.IsPrimitive; + + /// + public bool IsSZArray => _impl.IsSZArray; + + /// + public bool IsArray => _impl.IsArray; + + /// + public bool IsEnum => _impl.IsEnum; + + /// + public bool IsPointer => _impl.IsPointer; + + /// + public bool IsFunctionPointer => _impl.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + + /// + public bool IsByRef => _impl.IsByRef; + + /// + public bool IsAbstract => _impl.IsAbstract; + + /// + public bool IsSealed => _impl.IsSealed; + + /// + public bool IsVisible => _impl.IsVisible; + + /// + public bool IsPublic => _impl.IsPublic; + + /// + public bool IsNotPublic => _impl.IsNotPublic; + + /// + public bool IsNested => _impl.IsNested; + + /// + public bool IsNestedAssembly => _impl.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + + /// + public bool IsNestedFamily => _impl.IsNestedFamily; + + /// + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + + /// + public bool IsNestedPrivate => _impl.IsNestedPrivate; + + /// + public bool IsNestedPublic => _impl.IsNestedPublic; + + /// + public bool IsSerializable => _impl.IsSerializable; + + /// + public bool IsSignatureType => _impl.IsSignatureType; + + /// + public bool IsSpecialName => _impl.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + + /// + public override bool IsComplete => _builder == null; + + /// + public int GetArrayRank() + { + return _impl.GetArrayRank(); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return _impl.GetDefaultMembers(); + } + + /// + public ITypeSymbol? GetElementType() + { + return _impl.GetElementType(); + } + + /// + public string? GetEnumName(object value) + { + return _impl.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return _impl.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return _impl.GetEnumUnderlyingType(); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return _impl.GetGenericArguments(); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return _impl.GetGenericParameterConstraints(); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return _impl.GetGenericTypeDefinition(); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return _impl.GetInterface(name); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _impl.GetInterface(name, ignoreCase); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + return _impl.GetInterfaces(inherit); + } + + /// + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return _impl.GetInterfaceMap(interfaceType); + } + + /// + public IMemberSymbol[] GetMember(string name) + { + return _impl.GetMember(name); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, bindingAttr); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, type, bindingAttr); + } + + /// + public IMemberSymbol[] GetMembers() + { + return _impl.GetMembers(); + } + + /// + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMembers(bindingAttr); + } + + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _impl.GetConstructor(types); + } + + /// + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetConstructor(bindingAttr, types); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return _impl.GetConstructors(); + } + + /// + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetConstructors(bindingAttr); + } + + /// + public IFieldSymbol? GetField(string name) + { + return _impl.GetField(name); + } + + /// + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetField(name, bindingAttr); + } + + /// + public IFieldSymbol[] GetFields() + { + return _impl.GetFields(); + } + + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetFields(bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return _impl.GetMethod(name); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _impl.GetMethod(name, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethod(name, bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetMethod(name, bindingAttr, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); + } + + /// + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethods(bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return _impl.GetProperty(name); + } + + /// + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperty(name, bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _impl.GetProperty(name, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _impl.GetProperty(name, returnType, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _impl.GetProperty(name, returnType); + } + + /// + public IPropertySymbol[] GetProperties() + { + return _impl.GetProperties(); + } + + /// + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperties(bindingAttr); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return _impl.GetEvent(name); + } + + /// + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvent(name, bindingAttr); + } + + /// + public IEventSymbol[] GetEvents() + { + return _impl.GetEvents(); + } + + /// + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvents(bindingAttr); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return _impl.GetNestedType(name); + } + + /// + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedType(name, bindingAttr); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return _impl.GetNestedTypes(); + } + + /// + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedTypes(); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return _impl.IsAssignableFrom(c); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return _impl.IsSubclassOf(c); + } + + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); + } + + /// + public ITypeSymbol MakeArrayType() + { + return _impl.MakeArrayType(); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return _impl.MakeGenericType(typeArguments); + } + + /// + public ITypeSymbol MakePointerType() + { + return _impl.MakePointerType(); + } + + /// + public ITypeSymbol MakeByRefType() + { + return _impl.MakeByRefType(); + } + + #endregion + + /// + public override void OnComplete() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs new file mode 100644 index 0000000000..1b643dfdae --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs @@ -0,0 +1,313 @@ +using System; +using System.Diagnostics.CodeAnalysis; +using System.Linq; + +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + abstract class IkvmReflectionMemberSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder + { + + readonly IIkvmReflectionModuleSymbol _resolvingModule; + readonly IIkvmReflectionTypeSymbol? _resolvingType; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionMemberSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : + base(context) + { + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingType = resolvingType; + } + + #region IMemberSymbol + + /// + public abstract MemberInfo UnderlyingMember { get; } + + /// + public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingModule; + + /// + public IIkvmReflectionTypeSymbol? ResolvingType => ResolvingType; + + /// + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + + /// + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + + /// + public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + + /// + public virtual int MetadataToken => UnderlyingMember.MetadataToken; + + /// + public virtual string Name => UnderlyingMember.Name; + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(null, inherit)); + } + + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + + /// + [return: NotNullIfNotNull(nameof(type))] + public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + if (type is null) + return null; + + if (UnderlyingMember == type) + return (IIkvmReflectionTypeSymbol)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return _resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull("type")] + public override IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + + if (UnderlyingMember == type) + return (IIkvmReflectionTypeSymbolBuilder)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return (IIkvmReflectionTypeSymbolBuilder)_resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IIkvmReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) + { + if (ctor is null) + return null; + + if (UnderlyingMember == ctor) + return (IIkvmReflectionConstructorSymbol)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) + { + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + + if (UnderlyingMember == ctor) + return (IIkvmReflectionConstructorSymbolBuilder)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IIkvmReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) + { + if (method is null) + return null; + + if (UnderlyingMember == method) + return (IIkvmReflectionMethodSymbol)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + if (UnderlyingMember == method) + return (IIkvmReflectionMethodSymbolBuilder)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IIkvmReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) + { + if (field is null) + return null; + + if (UnderlyingMember == field) + return (IIkvmReflectionFieldSymbol)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + + if (UnderlyingMember == field) + return (IIkvmReflectionFieldSymbolBuilder)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IIkvmReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) + { + if (property is null) + return null; + + if (UnderlyingMember == property) + return (IIkvmReflectionPropertySymbol)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (UnderlyingMember == property) + return (IIkvmReflectionPropertySymbolBuilder)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) + { + if (@event is null) + return null; + + if (UnderlyingMember == @event) + return (IIkvmReflectionEventSymbol)this; + + if (@event.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + if (@event.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); + } + + /// + public virtual void OnComplete() + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs new file mode 100644 index 0000000000..b6a2326dd6 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs @@ -0,0 +1,122 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + abstract class IkvmReflectionMethodBaseSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : + base(context, resolvingModule, resolvingType) + { + + } + + /// + public abstract MethodBase UnderlyingMethodBase { get; } + + /// + public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + + #region IMethodBaseSymbol + + /// + public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; + + /// + public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; + + /// + public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; + + /// + public bool IsAbstract => UnderlyingMethodBase.IsAbstract; + + /// + public bool IsAssembly => UnderlyingMethodBase.IsAssembly; + + /// + public bool IsConstructor => UnderlyingMethodBase.IsConstructor; + + /// + public bool IsFamily => UnderlyingMethodBase.IsFamily; + + /// + public bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; + + /// + public bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; + + /// + public bool IsFinal => UnderlyingMethodBase.IsFinal; + + /// + public bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; + + /// + public bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; + + /// + public bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; + + /// + public bool IsPrivate => UnderlyingMethodBase.IsPrivate; + + /// + public bool IsPublic => UnderlyingMethodBase.IsPublic; + + /// + public bool IsStatic => UnderlyingMethodBase.IsStatic; + + /// + public bool IsVirtual => UnderlyingMethodBase.IsVirtual; + + /// + public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; + + /// + public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; + + /// + public ITypeSymbol[] GetGenericArguments() + { + return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); + } + + /// + public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() + { + return (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.GetMethodImplementationFlags(); + } + + /// + public IParameterSymbol[] GetParameters() + { + return ResolveParameterSymbols(UnderlyingMethodBase.GetParameters()); + } + + #endregion + + /// + public override void OnComplete() + { + foreach (var i in GetGenericArguments()) + if (i is IIkvmReflectionGenericTypeParameterSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetParameters()) + if (i is IIkvmReflectionParameterSymbolBuilder b) + b.OnComplete(); + + base.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs new file mode 100644 index 0000000000..db3c96967b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs @@ -0,0 +1,150 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionMethodSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, IIkvmReflectionMethodSymbolBuilder + { + + MethodBuilder? _builder; + MethodInfo _method; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, MethodBuilder builder) : + base(context, resolvingModule, resolvingType) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _method = _builder; + } + + /// + public MethodInfo UnderlyingMethod => _method; + + /// + public override MethodBase UnderlyingMethodBase => UnderlyingMethod; + + /// + public MethodBuilder UnderlyingMethodBuilder => _builder ?? throw new InvalidOperationException(); + + #region IMethodSymbolBuilder + + /// + public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + { + UnderlyingMethodBuilder.SetImplementationFlags((MethodImplAttributes)attributes); + } + + /// + public void SetParameters(params ITypeSymbol[] parameterTypes) + { + UnderlyingMethodBuilder.SetParameters(parameterTypes.Unpack()); + } + + /// + public void SetReturnType(ITypeSymbol? returnType) + { + UnderlyingMethodBuilder.SetReturnType(returnType?.Unpack()); + } + + /// + public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + UnderlyingMethodBuilder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); + } + + public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) + { + var l = UnderlyingMethodBuilder.DefineGenericParameters(names); + var a = new IGenericTypeParameterSymbolBuilder[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = new IkvmReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, ResolvingType, this, l[i]); + + return a; + } + + /// + public IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) + { + return ResolveParameterSymbol(UnderlyingMethodBuilder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); + } + + public IILGenerator GetILGenerator() + { + throw new NotImplementedException(); + } + + public IILGenerator GetILGenerator(int size) + { + throw new NotImplementedException(); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingMethodBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IMethodSymbol + + /// + public IParameterSymbol ReturnParameter => ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); + + /// + public ITypeSymbol ReturnType => ResolveTypeSymbol(UnderlyingMethod.ReturnType); + + /// + public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + + /// + public override bool IsComplete => _builder == null; + + /// + public IMethodSymbol GetBaseDefinition() + { + return ResolveMethodSymbol(UnderlyingMethod.GetBaseDefinition()); + } + + /// + public IMethodSymbol GetGenericMethodDefinition() + { + return ResolveMethodSymbol(UnderlyingMethod.GetGenericMethodDefinition()); + } + + /// + public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) + { + return ResolveMethodSymbol(UnderlyingMethod.MakeGenericMethod(typeArguments.Unpack())); + } + + #endregion + + /// + public override void OnComplete() + { + _method = (MethodInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs new file mode 100644 index 0000000000..deb3feca4c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -0,0 +1,382 @@ +using System; +using System.Linq; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionModuleSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmReflectionModuleSymbolBuilder + { + + readonly IIkvmReflectionAssemblySymbol _resolvingAssembly; + + readonly ModuleBuilder _builder; + IkvmReflectionModuleMetadata _metadata; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionAssemblySymbol resolvingAssembly, ModuleBuilder builder) : + base(context) + { + _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _metadata = new IkvmReflectionModuleMetadata(this); + } + + /// + public Module UnderlyingModule => UnderlyingModuleBuilder; + + /// + public ModuleBuilder UnderlyingModuleBuilder => _builder; + + /// + public IIkvmReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; + + #region IModuleSymbolBuilder + + /// + public ITypeSymbolBuilder DefineType(string name) + { + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typesize) + { + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), typesize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent) + { + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr) + { + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packsize) + { + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packsize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packingSize, int typesize) + { + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packingSize, typesize)); + } + + /// + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) + { + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), interfaces?.Unpack())); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingModuleBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingModuleBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IModuleSymbol + + /// + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingModule.Assembly); + + /// + public string FullyQualifiedName => UnderlyingModule.FullyQualifiedName; + + /// + public int MetadataToken => UnderlyingModule.MetadataToken; + + /// + public Guid ModuleVersionId => UnderlyingModule.ModuleVersionId; + + /// + public string Name => UnderlyingModule.Name; + + /// + public string ScopeName => UnderlyingModule.ScopeName; + + /// + public override bool IsComplete => _builder == null; + + /// + public IFieldSymbol? GetField(string name) + { + return ResolveFieldSymbol(UnderlyingModule.GetField(name)); + } + + /// + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolveFieldSymbol(UnderlyingModule.GetField(name, (BindingFlags)bindingAttr)); + } + + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingFlags) + { + return ResolveFieldSymbols(UnderlyingModule.GetFields((BindingFlags)bindingFlags))!; + } + + /// + public IFieldSymbol[] GetFields() + { + return ResolveFieldSymbols(UnderlyingModule.GetFields())!; + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name)); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, types.Unpack())); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + } + + /// + public IMethodSymbol[] GetMethods() + { + return ResolveMethodSymbols(UnderlyingModule.GetMethods())!; + } + + /// + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingFlags) + { + return ResolveMethodSymbols(UnderlyingModule.GetMethods((BindingFlags)bindingFlags))!; + } + + /// + public ITypeSymbol? GetType(string className) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className)); + } + + /// + public ITypeSymbol? GetType(string className, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className, ignoreCase)); + } + + /// + public ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className, throwOnError, ignoreCase)); + } + + /// + public ITypeSymbol[] GetTypes() + { + return ResolveTypeSymbols(UnderlyingModule.GetTypes())!; + } + + /// + public bool IsResource() + { + return UnderlyingModule.IsResource(); + } + + /// + public IFieldSymbol? ResolveField(int metadataToken) + { + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken)); + } + + /// + public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMemberSymbol? ResolveMember(int metadataToken) + { + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken)); + } + + /// + public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMethodBaseSymbol? ResolveMethod(int metadataToken) + { + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken)); + } + + /// + public byte[] ResolveSignature(int metadataToken) + { + return UnderlyingModule.ResolveSignature(metadataToken); + } + + /// + public string ResolveString(int metadataToken) + { + return UnderlyingModule.ResolveString(metadataToken); + } + + /// + public ITypeSymbol ResolveType(int metadataToken) + { + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken)); + } + + /// + public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData()); + } + + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingModule.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingModule.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingModule.IsDefined(attributeType.Unpack(), false); + } + + #endregion + + /// + public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + return _metadata.GetOrCreateTypeSymbol(type); + } + + /// + public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return _metadata.GetOrCreateTypeSymbol(type); + } + + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _metadata.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return _metadata.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return _metadata.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return _metadata.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _metadata.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return _metadata.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _metadata.GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return _metadata.GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _metadata.GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return _metadata.GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _metadata.GetOrCreateParameterSymbol(parameter); + } + + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _metadata.GetOrCreateParameterSymbol(parameter); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs new file mode 100644 index 0000000000..ea7a2a744f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs @@ -0,0 +1,71 @@ +using System; + +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + /// + /// Fake implementation that wraps a , which does not extend . + /// + class IkvmReflectionParameterBuilderInfo : ParameterInfo + { + + readonly ParameterBuilder _builder; + readonly Func _getDefaultValue; + + /// + /// Initialies a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionParameterBuilderInfo(ParameterBuilder builder, Func getDefaultValue) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _getDefaultValue = getDefaultValue ?? throw new ArgumentNullException(nameof(getDefaultValue)); + } + + /// + public override ParameterAttributes Attributes => (ParameterAttributes)_builder.Attributes; + + /// + public override MemberInfo Member => throw new NotImplementedException(); + + /// + public override Type ParameterType => ((MethodBase)Member).GetParameters()[Position].ParameterType; + + /// + public override Module Module => _builder.Module; + + /// + public override string? Name => _builder.Name; + + /// + public override int Position => _builder.Position; + + /// + public override int MetadataToken => throw new NotImplementedException(); + + /// + public override object? RawDefaultValue => _getDefaultValue(); + + /// + public override CustomModifiers __GetCustomModifiers() + { + throw new NotImplementedException(); + } + + /// + public override bool __TryGetFieldMarshal(out FieldMarshal fieldMarshal) + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs new file mode 100644 index 0000000000..fa7506bd8c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs @@ -0,0 +1,164 @@ +using System; +using System.Linq; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionParameterSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmReflectionParameterSymbolBuilder + { + + readonly IIkvmReflectionModuleSymbol _resolvingModule; + readonly IIkvmReflectionMethodBaseSymbol _resolvingMethod; + + ParameterBuilder? _builder; + ParameterInfo _parameter; + + object? _constant; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMethodBaseSymbol resolvingMethod, ParameterBuilder builder) : + base(context) + { + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _parameter = new IkvmReflectionParameterBuilderInfo(_builder, () => _constant); + } + + /// + public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingMethod.ResolvingModule; + + /// + public IIkvmReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; + + /// + public ParameterInfo UnderlyingParameter => _parameter; + + /// + public ParameterBuilder UnderlyingParameterBuilder => _builder ?? throw new InvalidOperationException(); + + #region IParameterSymbolBuilder + + /// + public void SetConstant(object? defaultValue) + { + UnderlyingParameterBuilder.SetConstant(_constant = defaultValue); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingParameterBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingParameterBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IParameterSymbol + + /// + public System.Reflection.ParameterAttributes Attributes => (System.Reflection.ParameterAttributes)UnderlyingParameter.Attributes; + + /// + public object? DefaultValue => UnderlyingParameter.RawDefaultValue; + + /// + public bool HasDefaultValue => UnderlyingParameter.HasDefaultValue; + + /// + public bool IsIn => UnderlyingParameter.IsIn; + + /// + public bool IsLcid => UnderlyingParameter.IsLcid; + + /// + public bool IsOptional => UnderlyingParameter.IsOptional; + + /// + public bool IsOut => UnderlyingParameter.IsOut; + + /// + public bool IsRetval => UnderlyingParameter.IsRetval; + + /// + public IMemberSymbol Member => ResolveMemberSymbol(UnderlyingParameter.Member); + + /// + public int MetadataToken => UnderlyingParameter.MetadataToken; + + /// + public string? Name => UnderlyingParameter.Name; + + /// + public ITypeSymbol ParameterType => ResolveTypeSymbol(UnderlyingParameter.ParameterType); + + /// + public int Position => UnderlyingParameter.Position; + + /// + public override bool IsComplete => _builder == null; + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData()); + } + + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingParameter.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingParameter.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingParameter.IsDefined(attributeType.Unpack(), inherit); + } + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingParameter.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingParameter.GetRequiredCustomModifiers()); + } + + #endregion + + /// + public void OnComplete() + { + var p = ResolvingMethod.UnderlyingMethodBase.GetParameters(); + _parameter = p[Position]; + _builder = null; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs new file mode 100644 index 0000000000..8ec05eeff6 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs @@ -0,0 +1,184 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionPropertySymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionPropertySymbolBuilder + { + + PropertyBuilder? _builder; + PropertyInfo _property; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public IkvmReflectionPropertySymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, PropertyBuilder builder) : + base(context, resolvingModule, resolvingType) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _property = _builder; + } + + /// + public PropertyInfo UnderlyingProperty => _property; + + /// + public PropertyBuilder UnderlyingPropertyBuilder => _builder ?? throw new InvalidOperationException(); + + /// + public override MemberInfo UnderlyingMember => UnderlyingProperty; + + #region IPropertySymbol + + /// + public void SetConstant(object? defaultValue) + { + UnderlyingPropertyBuilder.SetConstant(defaultValue); + } + + /// + public void SetGetMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingPropertyBuilder.SetGetMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void SetSetMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingPropertyBuilder.SetSetMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) + { + UnderlyingPropertyBuilder.AddOtherMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); + } + + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingPropertyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingPropertyBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region IPropertySymbol + + /// + public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)UnderlyingProperty.Attributes; + + /// + public bool CanRead => UnderlyingProperty.CanRead; + + /// + public bool CanWrite => UnderlyingProperty.CanWrite; + + /// + public bool IsSpecialName => UnderlyingProperty.IsSpecialName; + + /// + public ITypeSymbol PropertyType => ResolveTypeSymbol(UnderlyingProperty.PropertyType); + + /// + public IMethodSymbol? GetMethod => ResolveMethodSymbol(UnderlyingProperty.GetMethod); + + /// + public IMethodSymbol? SetMethod => ResolveMethodSymbol(UnderlyingProperty.SetMethod); + + /// + public override bool IsComplete => _builder == null; + + /// + public object? GetRawConstantValue() + { + return UnderlyingProperty.GetRawConstantValue(); + } + + /// + public IMethodSymbol[] GetAccessors() + { + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors()); + } + + /// + public IMethodSymbol[] GetAccessors(bool nonPublic) + { + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors(nonPublic)); + } + + /// + public IParameterSymbol[] GetIndexParameters() + { + return ResolveParameterSymbols(UnderlyingProperty.GetIndexParameters()); + } + + /// + public IMethodSymbol? GetGetMethod() + { + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod()); + } + + /// + public IMethodSymbol? GetGetMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetSetMethod() + { + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod()); + } + + /// + public IMethodSymbol? GetSetMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod(nonPublic)); + } + + /// + public ITypeSymbol GetModifiedPropertyType() + { + throw new NotImplementedException(); + } + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingProperty.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); + } + +#endregion + + /// + public override void OnComplete() + { + _property = (PropertyInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); + _builder = null; + base.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs new file mode 100644 index 0000000000..f00d737267 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs @@ -0,0 +1,24 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + /// + /// Reflection-specific implementation of . + /// + abstract class IkvmReflectionSymbolBuilder : IkvmReflectionSymbol, IIkvmReflectionSymbolBuilder + { + + /// + /// Initializes a new instance. + /// + /// + protected IkvmReflectionSymbolBuilder(IkvmReflectionSymbolContext context) : + base(context) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs new file mode 100644 index 0000000000..323f309d13 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -0,0 +1,802 @@ +using System; +using System.Runtime.InteropServices; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionTypeSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionTypeSymbolBuilder + { + + TypeBuilder? _builder; + Type _type; + IkvmReflectionTypeImpl _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionTypeSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, TypeBuilder builder) : + base(context, resolvingModule, null) + { + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _type = _builder; + _impl = new IkvmReflectionTypeImpl(this); + } + + /// + public Type UnderlyingType => _type; + + /// + public override MemberInfo UnderlyingMember => UnderlyingType; + + /// + public TypeBuilder UnderlyingTypeBuilder => _builder ?? throw new InvalidOperationException(); + + #region ITypeSymbolBuilder + + /// + public void SetParent(ITypeSymbol? parent) + { + UnderlyingTypeBuilder.SetParent(parent?.Unpack()); + } + + /// + public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) + { + var l = UnderlyingTypeBuilder.DefineGenericParameters(names); + var a = new IGenericTypeParameterSymbolBuilder[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = new IkvmReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, this, null, l[i]); + + return a; + } + + /// + public void AddInterfaceImplementation(ITypeSymbol interfaceType) + { + UnderlyingTypeBuilder.AddInterfaceImplementation(interfaceType.Unpack()); + } + + /// + public IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol[]? parameterTypes) + { + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor((MethodAttributes)attributes, (CallingConventions)callingConvention, parameterTypes?.Unpack())); + } + + /// + public IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredCustomModifiers, ITypeSymbol[][]? optionalCustomModifiers) + { + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor((MethodAttributes)attributes, (CallingConventions)callingConvention, parameterTypes?.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack())); + } + + /// + public IConstructorSymbolBuilder DefineDefaultConstructor(System.Reflection.MethodAttributes attributes) + { + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineDefaultConstructor((MethodAttributes)attributes)); + } + + /// + public IEventSymbolBuilder DefineEvent(string name, System.Reflection.EventAttributes attributes, ITypeSymbol eventtype) + { + return ResolveEventSymbol(UnderlyingTypeBuilder.DefineEvent(name, (EventAttributes)attributes, eventtype.Unpack())); + } + + /// + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, System.Reflection.FieldAttributes attributes) + { + return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), (FieldAttributes)attributes)); + } + + /// + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, System.Reflection.FieldAttributes attributes) + { + return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), (FieldAttributes)attributes)); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + { + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention) + { + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention)); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes) + { + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes)); + } + + /// + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + { + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + } + + /// + public void DefineMethodOverride(IMethodSymbolBuilder methodInfoBody, IMethodSymbol methodInfoDeclaration) + { + UnderlyingTypeBuilder.DefineMethodOverride(methodInfoBody.Unpack(), methodInfoDeclaration.Unpack()); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) + { + return ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), interfaces?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize, int typeSize) + { + return ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packSize, typeSize)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize) + { + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packSize)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name) + { + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent) + { + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack())); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr) + { + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typeSize) + { + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), typeSize)); + } + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + } + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + } + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack(), nativeCallConv, nativeCharSet)); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) + { + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, returnType.Unpack(), parameterTypes?.Unpack())); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) + { + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), parameterTypes?.Unpack())); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + } + + /// + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + { + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + } + + /// + public IConstructorSymbolBuilder DefineTypeInitializer() + { + return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineTypeInitializer()); + } + /// + public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + { + UnderlyingTypeBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + } + + /// + public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + { + UnderlyingTypeBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + #endregion + + #region ITypeSymbol + + /// + public System.Reflection.TypeAttributes Attributes => _impl.Attributes; + + /// + public IAssemblySymbol Assembly => _impl.Assembly; + + /// + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + + /// + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + + /// + public string? FullName => _impl.FullName; + + /// + public string? Namespace => _impl.Namespace; + + /// + public TypeCode TypeCode => _impl.TypeCode; + + /// + public ITypeSymbol? BaseType => _impl.BaseType; + + /// + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + + /// + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + + /// + public int GenericParameterPosition => _impl.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + + /// + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + + /// + public bool IsGenericType => _impl.IsGenericType; + + /// + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + + /// + public bool IsGenericParameter => _impl.IsGenericParameter; + + /// + public bool IsAutoLayout => _impl.IsAutoLayout; + + /// + public bool IsExplicitLayout => _impl.IsExplicitLayout; + + /// + public bool IsLayoutSequential => _impl.IsLayoutSequential; + + /// + public bool HasElementType => _impl.HasElementType; + + /// + public bool IsClass => _impl.IsClass; + + /// + public bool IsValueType => _impl.IsValueType; + + /// + public bool IsInterface => _impl.IsInterface; + + /// + public bool IsPrimitive => _impl.IsPrimitive; + + /// + public bool IsSZArray => _impl.IsSZArray; + + /// + public bool IsArray => _impl.IsArray; + + /// + public bool IsEnum => _impl.IsEnum; + + /// + public bool IsPointer => _impl.IsPointer; + + /// + public bool IsFunctionPointer => _impl.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + + /// + public bool IsByRef => _impl.IsByRef; + + /// + public bool IsAbstract => _impl.IsAbstract; + + /// + public bool IsSealed => _impl.IsSealed; + + /// + public bool IsVisible => _impl.IsVisible; + + /// + public bool IsPublic => _impl.IsPublic; + + /// + public bool IsNotPublic => _impl.IsNotPublic; + + /// + public bool IsNested => _impl.IsNested; + + /// + public bool IsNestedAssembly => _impl.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + + /// + public bool IsNestedFamily => _impl.IsNestedFamily; + + /// + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + + /// + public bool IsNestedPrivate => _impl.IsNestedPrivate; + + /// + public bool IsNestedPublic => _impl.IsNestedPublic; + + /// + public bool IsSerializable => _impl.IsSerializable; + + /// + public bool IsSignatureType => _impl.IsSignatureType; + + /// + public bool IsSpecialName => _impl.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + + /// + public override bool IsComplete => _builder == null; + + /// + public int GetArrayRank() + { + return _impl.GetArrayRank(); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return _impl.GetDefaultMembers(); + } + + /// + public ITypeSymbol? GetElementType() + { + return _impl.GetElementType(); + } + + /// + public string? GetEnumName(object value) + { + return _impl.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return _impl.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return _impl.GetEnumUnderlyingType(); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return _impl.GetGenericArguments(); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return _impl.GetGenericParameterConstraints(); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return _impl.GetGenericTypeDefinition(); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return _impl.GetInterface(name); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _impl.GetInterface(name, ignoreCase); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + return _impl.GetInterfaces(inherit); + } + + /// + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return _impl.GetInterfaceMap(interfaceType); + } + + /// + public IMemberSymbol[] GetMember(string name) + { + return _impl.GetMember(name); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, bindingAttr); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, type, bindingAttr); + } + + /// + public IMemberSymbol[] GetMembers() + { + return _impl.GetMembers(); + } + + /// + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMembers(bindingAttr); + } + + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _impl.GetConstructor(types); + } + + /// + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetConstructor(bindingAttr, types); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return _impl.GetConstructors(); + } + + /// + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetConstructors(bindingAttr); + } + + /// + public IFieldSymbol? GetField(string name) + { + return _impl.GetField(name); + } + + /// + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetField(name, bindingAttr); + } + + /// + public IFieldSymbol[] GetFields() + { + return _impl.GetFields(); + } + + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetFields(bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return _impl.GetMethod(name); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _impl.GetMethod(name, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethod(name, bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetMethod(name, bindingAttr, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); + } + + /// + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethods(bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return _impl.GetProperty(name); + } + + /// + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperty(name, bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _impl.GetProperty(name, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _impl.GetProperty(name, returnType, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _impl.GetProperty(name, returnType); + } + + /// + public IPropertySymbol[] GetProperties() + { + return _impl.GetProperties(); + } + + /// + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperties(bindingAttr); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return _impl.GetEvent(name); + } + + /// + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvent(name, bindingAttr); + } + + /// + public IEventSymbol[] GetEvents() + { + return _impl.GetEvents(); + } + + /// + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvents(bindingAttr); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return _impl.GetNestedType(name); + } + + /// + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedType(name, bindingAttr); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return _impl.GetNestedTypes(); + } + + /// + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedTypes(); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return _impl.IsAssignableFrom(c); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return _impl.IsSubclassOf(c); + } + + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); + } + + /// + public ITypeSymbol MakeArrayType() + { + return _impl.MakeArrayType(); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return _impl.MakeGenericType(typeArguments); + } + + /// + public ITypeSymbol MakePointerType() + { + return _impl.MakePointerType(); + } + + /// + public ITypeSymbol MakeByRefType() + { + return _impl.MakeByRefType(); + } + + #endregion + + /// + public void Complete() + { + if (_builder != null) + { + // complete type + if (_builder.IsCreated() == false) + _builder.CreateType(); + + // force module to reresolve + Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); + OnComplete(); + } + } + + /// + public override void OnComplete() + { + const System.Reflection.BindingFlags DefaultBindingFlags = System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Static; + + _type = ResolvingModule.UnderlyingModule.ResolveType(MetadataToken); + _builder = null; + + foreach (var i in GetGenericArguments()) + if (i is IIkvmReflectionGenericTypeParameterSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetConstructors(DefaultBindingFlags)) + if (i is IIkvmReflectionConstructorSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetMethods(DefaultBindingFlags)) + if (i is IIkvmReflectionMethodSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetFields(DefaultBindingFlags)) + if (i is IIkvmReflectionFieldSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetProperties(DefaultBindingFlags)) + if (i is IIkvmReflectionPropertySymbolBuilder b) + b.OnComplete(); + + foreach (var m in GetEvents(DefaultBindingFlags)) + if (m is IIkvmReflectionPropertySymbolBuilder b) + b.OnComplete(); + + base.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs new file mode 100644 index 0000000000..73df3a3be2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs @@ -0,0 +1,32 @@ +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionAssemblySymbol : IIkvmReflectionSymbol, IAssemblySymbol + { + + /// + /// Gets a reference to the underlying . + /// + Assembly UnderlyingAssembly { get; } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionConstructorSymbol.cs new file mode 100644 index 0000000000..13a8431999 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionConstructorSymbol.cs @@ -0,0 +1,16 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionConstructorSymbol : IIkvmReflectionMethodBaseSymbol, IConstructorSymbol + { + + /// + /// Gets the underlying . + /// + ConstructorInfo UnderlyingConstructor { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionEventSymbol.cs new file mode 100644 index 0000000000..b4395531a0 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionEventSymbol.cs @@ -0,0 +1,16 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionEventSymbol : IIkvmReflectionMemberSymbol, IEventSymbol + { + + /// + /// Gets the underlying . + /// + EventInfo UnderlyingEvent { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionFieldSymbol.cs new file mode 100644 index 0000000000..a45d4aa007 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionFieldSymbol.cs @@ -0,0 +1,16 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionFieldSymbol : IIkvmReflectionMemberSymbol, IFieldSymbol + { + + /// + /// Gets the underlying . + /// + FieldInfo UnderlyingField { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMemberSymbol.cs new file mode 100644 index 0000000000..a0fa129436 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMemberSymbol.cs @@ -0,0 +1,26 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionMemberSymbol : IIkvmReflectionSymbol, IMemberSymbol + { + + /// + /// Gets the resolving module. + /// + IIkvmReflectionModuleSymbol ResolvingModule { get; } + + /// + /// Gets the resolving type. + /// + IIkvmReflectionTypeSymbol? ResolvingType { get; } + + /// + /// Gets the underlying . + /// + MemberInfo UnderlyingMember { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs new file mode 100644 index 0000000000..483704f37c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs @@ -0,0 +1,16 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionMethodBaseSymbol : IIkvmReflectionMemberSymbol, IMethodBaseSymbol + { + + /// + /// Gets the underlying . + /// + MethodBase UnderlyingMethodBase { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs new file mode 100644 index 0000000000..c91b72a6b2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs @@ -0,0 +1,16 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionMethodSymbol : IIkvmReflectionMethodBaseSymbol, IMethodSymbol + { + + /// + /// Gets the underlying . + /// + MethodInfo UnderlyingMethod { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs new file mode 100644 index 0000000000..9c5129c3de --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs @@ -0,0 +1,123 @@ +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol + { + + /// + /// Gets the which contains this . + /// + IIkvmReflectionAssemblySymbol ResolvingAssembly { get; } + + /// + /// Gets the underlying . + /// + Module UnderlyingModule { get; } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs new file mode 100644 index 0000000000..ddc2d8eb70 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs @@ -0,0 +1,26 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionParameterSymbol : IIkvmReflectionSymbol, IParameterSymbol + { + + /// + /// Gets the module that resolved the parameter. + /// + IIkvmReflectionModuleSymbol ResolvingModule { get; } + + /// + /// Gets the method that resolved the parameter. + /// + IIkvmReflectionMethodBaseSymbol ResolvingMethod { get; } + + /// + /// Gets the underlying . + /// + ParameterInfo UnderlyingParameter { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs new file mode 100644 index 0000000000..57e05528e4 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs @@ -0,0 +1,16 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionPropertySymbol : IIkvmReflectionMemberSymbol, IPropertySymbol + { + + /// + /// Gets the underlying . + /// + PropertyInfo UnderlyingProperty { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs new file mode 100644 index 0000000000..891dc53f80 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs @@ -0,0 +1,336 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; + +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionSymbol : ISymbol + { + + /// + /// Gets the that contains this symbol. + /// + IkvmReflectionSymbolContext Context { get; } + + /// + /// Resolves the symbol for the specified assembly. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assembly))] + IIkvmReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly); + + /// + /// Resolves the symbol for the specified assembly builder. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assembly))] + IIkvmReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); + + /// + /// Resolves the symbols for the specified assemblies. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assemblies))] + IIkvmReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies); + + /// + /// Resolves the symbol for the specified module. + /// + /// + /// + [return: NotNullIfNotNull(nameof(module))] + IIkvmReflectionModuleSymbol? ResolveModuleSymbol(Module? module); + + /// + /// Resolves the symbol for the specified module. + /// + /// + /// + [return: NotNullIfNotNull(nameof(module))] + IIkvmReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); + + /// + /// Resolves the symbols for the specified modules. + /// + /// + /// + [return: NotNullIfNotNull(nameof(modules))] + IIkvmReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules); + + /// + /// Resolves the symbols for the specified modules. + /// + /// + /// + IEnumerable ResolveModuleSymbols(IEnumerable modules); + + /// + /// Resolves the symbol for the specified member. + /// + /// + /// + [return: NotNullIfNotNull(nameof(member))] + IIkvmReflectionMemberSymbol? ResolveMemberSymbol(MemberInfo? member); + + /// + /// Resolves the symbols for the specified members. + /// + /// + /// + [return: NotNullIfNotNull(nameof(types))] + IIkvmReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? types); + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type); + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); + + /// + /// Resolves the symbols for the specified types. + /// + /// + /// + [return: NotNullIfNotNull(nameof(types))] + IIkvmReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types); + + /// + /// Resolves the symbols for the specified types. + /// + /// + /// + IEnumerable ResolveTypeSymbols(IEnumerable types); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IIkvmReflectionMethodBaseSymbol? ResolveMethodBaseSymbol(MethodBase? method); + + /// + /// Resolves the symbol for the specified constructor. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctor))] + IIkvmReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor); + + /// + /// Resolves the symbol for the specified constructor. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctor))] + IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Resolves the symbols for the specified constructors. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctors))] + IIkvmReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IIkvmReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); + + /// + /// Resolves the symbols for the specified methods. + /// + /// + /// + [return: NotNullIfNotNull(nameof(methods))] + IIkvmReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods); + + /// + /// Resolves the symbol for the specified field. + /// + /// + /// + [return: NotNullIfNotNull(nameof(field))] + IIkvmReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field); + + /// + /// Resolves the symbol for the specified field. + /// + /// + /// + [return: NotNullIfNotNull(nameof(field))] + IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); + + /// + /// Resolves the symbols for the specified fields. + /// + /// + /// + [return: NotNullIfNotNull(nameof(fields))] + IIkvmReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields); + + /// + /// Resolves the symbol for the specified property. + /// + /// + /// + [return: NotNullIfNotNull(nameof(property))] + IIkvmReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property); + + /// + /// Resolves the symbol for the specified property. + /// + /// + /// + [return: NotNullIfNotNull(nameof(property))] + IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); + + /// + /// Resolves the symbols for the specified properties. + /// + /// + /// + [return: NotNullIfNotNull(nameof(properties))] + IIkvmReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties); + + /// + /// Resolves the symbol for the specified event. + /// + /// + /// + [return: NotNullIfNotNull(nameof(@event))] + IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event); + + /// + /// Resolves the symbol for the specified event. + /// + /// + /// + [return: NotNullIfNotNull(nameof(@event))] + IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); + + /// + /// Resolves the symbols for the specified events. + /// + /// + /// + [return: NotNullIfNotNull(nameof(events))] + IIkvmReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events); + + /// + /// Resolves the symbol for the specified parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(parameter))] + IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter); + + /// + /// Resolves the symbol for the specified parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(parameter))] + IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(ParameterBuilder parameter); + + /// + /// Resolves the symbols for the specified parameters. + /// + /// + /// + [return: NotNullIfNotNull(nameof(parameters))] + IIkvmReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters); + + /// + /// Transforms a custom set of custom attribute data records to a symbol record. + /// + /// + /// + [return: NotNullIfNotNull(nameof(attributes))] + CustomAttribute[]? ResolveCustomAttributes(IList? attributes); + + /// + /// Transforms a custom set of custom attribute data records to a symbol record. + /// + /// + /// + IEnumerable ResolveCustomAttributes(IEnumerable attributes); + + /// + /// Transforms a custom attribute data record to a symbol record. + /// + /// + /// + [return: NotNullIfNotNull(nameof(customAttributeData))] + CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData); + + /// + /// Transforms a list of values into symbols. + /// + /// + /// + ImmutableArray ResolveCustomAttributeTypedArguments(IList args); + + /// + /// Transforms a values into a symbol. + /// + /// + /// + CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Reflection.CustomAttributeTypedArgument arg); + + /// + /// Transforms the type as appropriate. + /// + /// + /// + object? ResolveCustomAttributeTypedValue(object? value); + + /// + /// Transforms a list of values into symbols. + /// + /// + /// + ImmutableArray ResolveCustomAttributeNamedArguments(IList args); + + /// + /// Transforms a values into a symbol. + /// + /// + /// + CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(IKVM.Reflection.CustomAttributeNamedArgument arg); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs new file mode 100644 index 0000000000..fd6281149f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs @@ -0,0 +1,16 @@ +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + interface IIkvmReflectionTypeSymbol : IIkvmReflectionMemberSymbol, ITypeSymbol + { + + /// + /// Gets the underlying . + /// + Type UnderlyingType { get; } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblyMetadata.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblyMetadata.cs new file mode 100644 index 0000000000..11dfb71158 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblyMetadata.cs @@ -0,0 +1,63 @@ +using System; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionAssemblyMetadata + { + + readonly IIkvmReflectionAssemblySymbol _symbol; + + IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); + ReaderWriterLockSlim? _moduleLock; + + /// + /// Initializes a new instance. + /// + /// + /// + public IkvmReflectionAssemblyMetadata(IIkvmReflectionAssemblySymbol symbol) + { + _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + } + + /// + /// Gets or creates the cached for the module. + /// + /// + /// + /// + public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + if (module is null) + throw new ArgumentNullException(nameof(module)); + + // create lock on demand + if (_moduleLock == null) + Interlocked.CompareExchange(ref _moduleLock, new ReaderWriterLockSlim(), null); + + using (_moduleLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.ModuleReferenceHandle(module.MetadataToken)); + if (_moduleSymbols[row] == null) + using (_moduleLock.CreateWriteLock()) + if (module is ModuleBuilder builder) + return _moduleSymbols[row] = new IkvmReflectionModuleSymbolBuilder(_symbol.Context, _symbol, builder); + else + return _moduleSymbols[row] = new IkvmReflectionModuleSymbol(_symbol.Context, _symbol, module); + else + return _moduleSymbols[row] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs new file mode 100644 index 0000000000..eb728f5513 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -0,0 +1,162 @@ +using System; +using System.Collections.Generic; +using System.Linq; + +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionAssemblySymbol : IkvmReflectionSymbol, IIkvmReflectionAssemblySymbol + { + + readonly Assembly _assembly; + IkvmReflectionAssemblyMetadata _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + public IkvmReflectionAssemblySymbol(IkvmReflectionSymbolContext context, Assembly assembly) : + base(context) + { + _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); + _impl = new IkvmReflectionAssemblyMetadata(this); + } + + /// + /// Gets the underlying instance. + /// + public Assembly UnderlyingAssembly => _assembly; + + #region IAssemblySymbol + + /// + public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); + + /// + public IMethodSymbol? EntryPoint => ResolveMethodSymbol(_assembly.EntryPoint); + + /// + public IEnumerable ExportedTypes => ResolveTypeSymbols(_assembly.ExportedTypes); + + /// + public string? FullName => _assembly.FullName; + + /// + public string ImageRuntimeVersion => _assembly.ImageRuntimeVersion; + + /// + public IModuleSymbol ManifestModule => ResolveModuleSymbol(_assembly.ManifestModule); + + /// + public IEnumerable Modules => ResolveModuleSymbols(_assembly.Modules); + + /// + public ITypeSymbol[] GetExportedTypes() + { + return ResolveTypeSymbols(_assembly.GetExportedTypes()); + } + + /// + public IModuleSymbol? GetModule(string name) + { + return ResolveModuleSymbol(_assembly.GetModule(name)); + } + + /// + public IModuleSymbol[] GetModules() + { + return ResolveModuleSymbols(_assembly.GetModules()); + } + + /// + public IModuleSymbol[] GetModules(bool getResourceModules) + { + return ResolveModuleSymbols(_assembly.GetModules(getResourceModules)); + } + + /// + public System.Reflection.AssemblyName GetName() + { + return _assembly.GetName().ToAssemblyName(); + } + + /// + public System.Reflection.AssemblyName GetName(bool copiedName) + { + return _assembly.GetName().ToAssemblyName(); + } + + /// + public System.Reflection.AssemblyName[] GetReferencedAssemblies() + { + return _assembly.GetReferencedAssemblies().ToAssemblyNames(); + } + + /// + public ITypeSymbol? GetType(string name, bool throwOnError) + { + return ResolveTypeSymbol(_assembly.GetType(name, throwOnError)); + } + + /// + public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) + { + return ResolveTypeSymbol(_assembly.GetType(name, throwOnError, ignoreCase)); + } + + /// + public ITypeSymbol? GetType(string name) + { + return ResolveTypeSymbol(_assembly.GetType(name)); + } + + /// + public ITypeSymbol[] GetTypes() + { + return ResolveTypeSymbols(_assembly.GetTypes()); + } + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); + } + + /// + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(_assembly.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(_assembly.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return _assembly.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + + public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _impl.GetOrCreateModuleSymbol(module); + } + + public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return (IIkvmReflectionModuleSymbolBuilder)_impl.GetOrCreateModuleSymbol(module); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs new file mode 100644 index 0000000000..10d812f160 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs @@ -0,0 +1,34 @@ +using System; + +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionConstructorSymbol : IkvmReflectionMethodBaseSymbol, IIkvmReflectionConstructorSymbol + { + + readonly ConstructorInfo _ctor; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionConstructorSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, ConstructorInfo ctor) : + base(context, resolvingModule, resolvingType) + { + _ctor = ctor ?? throw new ArgumentNullException(nameof(ctor)); + } + + /// + public ConstructorInfo UnderlyingConstructor => _ctor; + + /// + public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs new file mode 100644 index 0000000000..ce1e1f4976 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventSymbol.cs @@ -0,0 +1,104 @@ +using System; + +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionEventSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionEventSymbol + { + + readonly EventInfo _event; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionEventSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, EventInfo @event) : + base(context, resolvingModule, resolvingType) + { + _event = @event ?? throw new ArgumentNullException(nameof(@event)); + } + + /// + public EventInfo UnderlyingEvent => _event; + + /// + public override MemberInfo UnderlyingMember => UnderlyingEvent; + + #region IEventSymbol + + /// + public System.Reflection.EventAttributes Attributes => (System.Reflection.EventAttributes)UnderlyingEvent.Attributes; + + /// + public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); + + /// + public bool IsSpecialName => UnderlyingEvent.IsSpecialName; + + /// + public IMethodSymbol? AddMethod => ResolveMethodSymbol(UnderlyingEvent.AddMethod); + + /// + public IMethodSymbol? RemoveMethod => ResolveMethodSymbol(UnderlyingEvent.RemoveMethod); + + /// + public IMethodSymbol? RaiseMethod => ResolveMethodSymbol(UnderlyingEvent.RaiseMethod); + + /// + public IMethodSymbol? GetAddMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod()); + } + + /// + public IMethodSymbol? GetAddMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetRemoveMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod()); + } + + /// + public IMethodSymbol? GetRemoveMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetRaiseMethod() + { + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod()); + } + + /// + public IMethodSymbol? GetRaiseMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod(nonPublic)); + } + + /// + public IMethodSymbol[] GetOtherMethods() + { + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods()); + } + + /// + public IMethodSymbol[] GetOtherMethods(bool nonPublic) + { + return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods(nonPublic)); + } + + #endregion + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs new file mode 100644 index 0000000000..bd7c505781 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldSymbol.cs @@ -0,0 +1,98 @@ +using System; + +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionFieldSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionFieldSymbol + { + + readonly FieldInfo _field; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionFieldSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, FieldInfo field) : + base(context, resolvingModule, resolvingType) + { + _field = field ?? throw new ArgumentNullException(nameof(field)); + } + + /// + public FieldInfo UnderlyingField => _field; + + /// + public override MemberInfo UnderlyingMember => UnderlyingField; + + #region IFieldSymbol + + /// + public System.Reflection.FieldAttributes Attributes => (System.Reflection.FieldAttributes)UnderlyingField.Attributes; + + /// + public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); + + /// + public bool IsSpecialName => UnderlyingField.IsSpecialName; + + /// + public bool IsAssembly => UnderlyingField.IsAssembly; + + /// + public bool IsFamily => UnderlyingField.IsFamily; + + /// + public bool IsFamilyAndAssembly => UnderlyingField.IsFamilyAndAssembly; + + /// + public bool IsFamilyOrAssembly => UnderlyingField.IsFamilyOrAssembly; + + /// + public bool IsInitOnly => UnderlyingField.IsInitOnly; + + /// + public bool IsLiteral => UnderlyingField.IsLiteral; + + /// + public bool IsNotSerialized => UnderlyingField.IsNotSerialized; + + /// + public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; + + /// + public bool IsPrivate => UnderlyingField.IsPrivate; + + /// + public bool IsPublic => UnderlyingField.IsPublic; + + /// + public bool IsStatic => UnderlyingField.IsStatic; + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); + } + + /// + public object? GetRawConstantValue() + { + return UnderlyingField.GetRawConstantValue(); + } + + #endregion + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs new file mode 100644 index 0000000000..a685c97dc8 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs @@ -0,0 +1,566 @@ +using System; +using System.Diagnostics.CodeAnalysis; + +using IKVM.Reflection; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionGenericTypeParameterSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionTypeSymbol + { + + readonly IIkvmReflectionMethodSymbol? _resolvingMethod; + readonly Type _type; + IkvmReflectionTypeImpl _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public IkvmReflectionGenericTypeParameterSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, IIkvmReflectionMethodSymbol? resolvingMethod, Type type) : + base(context, resolvingModule, resolvingType) + { + _resolvingMethod = resolvingMethod; + _type = type ?? throw new ArgumentNullException(nameof(type)); + _impl = new IkvmReflectionTypeImpl(this); + } + + /// + public Type UnderlyingType => _type; + + /// + public override MemberInfo UnderlyingMember => UnderlyingType; + + /// + /// Gets the method base that declares this type parameter. + /// + public IIkvmReflectionMethodBaseSymbol? ResolvingMethodBase => _resolvingMethod; + + #region ITypeSymbol + + /// + public System.Reflection.TypeAttributes Attributes => _impl.Attributes; + + /// + public IAssemblySymbol Assembly => _impl.Assembly; + + /// + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + + /// + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + + /// + public string? FullName => _impl.FullName; + + /// + public string? Namespace => _impl.Namespace; + + /// + public TypeCode TypeCode => _impl.TypeCode; + + /// + public ITypeSymbol? BaseType => _impl.BaseType; + + /// + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + + /// + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + + /// + public int GenericParameterPosition => _impl.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + + /// + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + + /// + public bool IsGenericType => _impl.IsGenericType; + + /// + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + + /// + public bool IsGenericParameter => _impl.IsGenericParameter; + + /// + public bool IsAutoLayout => _impl.IsAutoLayout; + + /// + public bool IsExplicitLayout => _impl.IsExplicitLayout; + + /// + public bool IsLayoutSequential => _impl.IsLayoutSequential; + + /// + public bool HasElementType => _impl.HasElementType; + + /// + public bool IsClass => _impl.IsClass; + + /// + public bool IsValueType => _impl.IsValueType; + + /// + public bool IsInterface => _impl.IsInterface; + + /// + public bool IsPrimitive => _impl.IsPrimitive; + + /// + public bool IsSZArray => _impl.IsSZArray; + + /// + public bool IsArray => _impl.IsArray; + + /// + public bool IsEnum => _impl.IsEnum; + + /// + public bool IsPointer => _impl.IsPointer; + + /// + public bool IsFunctionPointer => _impl.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + + /// + public bool IsByRef => _impl.IsByRef; + + /// + public bool IsAbstract => _impl.IsAbstract; + + /// + public bool IsSealed => _impl.IsSealed; + + /// + public bool IsVisible => _impl.IsVisible; + + /// + public bool IsPublic => _impl.IsPublic; + + /// + public bool IsNotPublic => _impl.IsNotPublic; + + /// + public bool IsNested => _impl.IsNested; + + /// + public bool IsNestedAssembly => _impl.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + + /// + public bool IsNestedFamily => _impl.IsNestedFamily; + + /// + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + + /// + public bool IsNestedPrivate => _impl.IsNestedPrivate; + + /// + public bool IsNestedPublic => _impl.IsNestedPublic; + + /// + public bool IsSerializable => _impl.IsSerializable; + + /// + public bool IsSignatureType => _impl.IsSignatureType; + + /// + public bool IsSpecialName => _impl.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + + /// + public int GetArrayRank() + { + return _impl.GetArrayRank(); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return _impl.GetDefaultMembers(); + } + + /// + public ITypeSymbol? GetElementType() + { + return _impl.GetElementType(); + } + + /// + public string? GetEnumName(object value) + { + return _impl.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return _impl.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return _impl.GetEnumUnderlyingType(); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return _impl.GetGenericArguments(); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return _impl.GetGenericParameterConstraints(); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return _impl.GetGenericTypeDefinition(); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return _impl.GetInterface(name); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _impl.GetInterface(name, ignoreCase); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + return _impl.GetInterfaces(inherit); + } + + /// + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return _impl.GetInterfaceMap(interfaceType); + } + + /// + public IMemberSymbol[] GetMember(string name) + { + return _impl.GetMember(name); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, bindingAttr); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, type, bindingAttr); + } + + /// + public IMemberSymbol[] GetMembers() + { + return _impl.GetMembers(); + } + + /// + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMembers(bindingAttr); + } + + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _impl.GetConstructor(types); + } + + /// + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetConstructor(bindingAttr, types); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return _impl.GetConstructors(); + } + + /// + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetConstructors(bindingAttr); + } + + /// + public IFieldSymbol? GetField(string name) + { + return _impl.GetField(name); + } + + /// + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetField(name, bindingAttr); + } + + /// + public IFieldSymbol[] GetFields() + { + return _impl.GetFields(); + } + + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetFields(bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return _impl.GetMethod(name); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _impl.GetMethod(name, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethod(name, bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetMethod(name, bindingAttr, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); + } + + /// + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethods(bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return _impl.GetProperty(name); + } + + /// + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperty(name, bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _impl.GetProperty(name, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _impl.GetProperty(name, returnType, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _impl.GetProperty(name, returnType); + } + + /// + public IPropertySymbol[] GetProperties() + { + return _impl.GetProperties(); + } + + /// + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperties(bindingAttr); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return _impl.GetEvent(name); + } + + /// + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvent(name, bindingAttr); + } + + /// + public IEventSymbol[] GetEvents() + { + return _impl.GetEvents(); + } + + /// + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvents(bindingAttr); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return _impl.GetNestedType(name); + } + + /// + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedType(name, bindingAttr); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return _impl.GetNestedTypes(); + } + + /// + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedTypes(); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return _impl.IsAssignableFrom(c); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return _impl.IsSubclassOf(c); + } + + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); + } + + /// + public ITypeSymbol MakeArrayType() + { + return _impl.MakeArrayType(); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return _impl.MakeGenericType(typeArguments); + } + + /// + public ITypeSymbol MakePointerType() + { + return _impl.MakePointerType(); + } + + /// + public ITypeSymbol MakeByRefType() + { + return _impl.MakeByRefType(); + } + + #endregion + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + if (type == _type) + return this; + else + return base.ResolveTypeSymbol(type); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs new file mode 100644 index 0000000000..22ed03a6c9 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -0,0 +1,286 @@ +using System; +using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; +using System.Linq; + +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + /// + /// Obtains information about the attributes of a member and provides access to member metadata. + /// + abstract class IkvmReflectionMemberSymbol : IkvmReflectionSymbol, IIkvmReflectionMemberSymbol + { + + readonly IIkvmReflectionModuleSymbol _resolvingModule; + readonly IIkvmReflectionTypeSymbol? _resolvingType; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : + base(context) + { + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingType = resolvingType; + } + + /// + public abstract MemberInfo UnderlyingMember { get; } + + /// + /// Gets the which contains the metadata of this member. + /// + public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingModule; + + /// + /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. + /// + public IIkvmReflectionTypeSymbol? ResolvingType => _resolvingType; + + #region IMemberSymbol + + /// + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + + /// + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + + /// + public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + + /// + public virtual int MetadataToken => UnderlyingMember.MetadataToken; + + /// + public virtual string Name => UnderlyingMember.Name; + + /// + public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(null, inherit))!; + } + + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + + /// + [return: NotNullIfNotNull(nameof(type))] + public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + if (type is null) + return null; + + if (type == UnderlyingMember) + return (IIkvmReflectionTypeSymbol)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return _resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IIkvmReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) + { + if (ctor is null) + return null; + + if (ctor == UnderlyingMember) + return (IIkvmReflectionConstructorSymbol)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public override IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) + { + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IIkvmReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) + { + if (method is null) + return null; + + if (method == UnderlyingMember) + return (IIkvmReflectionMethodSymbol)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public override IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IIkvmReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) + { + if (field is null) + return null; + + if (field == UnderlyingMember) + return (IIkvmReflectionFieldSymbol)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public override IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IIkvmReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) + { + if (property is null) + return null; + + if (property == UnderlyingMember) + return (IIkvmReflectionPropertySymbol)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public override IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) + { + if (@event is null) + return null; + + if (@event == UnderlyingMember) + return (IIkvmReflectionEventSymbol)this; + + if (@event.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + if (@event.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs new file mode 100644 index 0000000000..3e5a0a8365 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs @@ -0,0 +1,108 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + abstract class IkvmReflectionMethodBaseSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionMethodBaseSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionMethodBaseSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : + base(context, resolvingModule, resolvingType) + { + + } + + #region IMethodBaseSymbol + + /// + public abstract MethodBase UnderlyingMethodBase { get; } + + /// + public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + + /// + public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; + + /// + public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; + + /// + public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; + + /// + public bool IsAbstract => UnderlyingMethodBase.IsAbstract; + + /// + public bool IsAssembly => UnderlyingMethodBase.IsAssembly; + + /// + public bool IsConstructor => UnderlyingMethodBase.IsConstructor; + + /// + public bool IsFamily => UnderlyingMethodBase.IsFamily; + + /// + public bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; + + /// + public bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; + + /// + public bool IsFinal => UnderlyingMethodBase.IsFinal; + + /// + public bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; + + /// + public bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; + + /// + public bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; + + /// + public bool IsPrivate => UnderlyingMethodBase.IsPrivate; + + /// + public bool IsPublic => UnderlyingMethodBase.IsPublic; + + /// + public bool IsStatic => UnderlyingMethodBase.IsStatic; + + /// + public bool IsVirtual => UnderlyingMethodBase.IsVirtual; + + /// + public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; + + /// + public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; + + /// + public ITypeSymbol[] GetGenericArguments() + { + return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); + } + + /// + public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() + { + return (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.GetMethodImplementationFlags(); + } + + /// + public IParameterSymbol[] GetParameters() + { + return ResolveParameterSymbols(UnderlyingMethodBase.GetParameters()); + } + + #endregion + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs new file mode 100644 index 0000000000..54dc46ff75 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs @@ -0,0 +1,65 @@ +using System; + +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionMethodSymbol : IkvmReflectionMethodBaseSymbol, IIkvmReflectionMethodSymbol + { + + readonly MethodInfo _method; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type, MethodInfo method) : + base(context, module, type) + { + _method = method ?? throw new ArgumentNullException(nameof(method)); + } + + /// + public MethodInfo UnderlyingMethod => _method; + + /// + public override MethodBase UnderlyingMethodBase => UnderlyingMethod; + + #region IMethodSymbol + + /// + public IParameterSymbol ReturnParameter => ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); + + /// + public ITypeSymbol ReturnType => ResolveTypeSymbol(UnderlyingMethod.ReturnType); + + /// + public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + + /// + public IMethodSymbol GetBaseDefinition() + { + return ResolveMethodSymbol(UnderlyingMethod.GetBaseDefinition()); + } + + /// + public IMethodSymbol GetGenericMethodDefinition() + { + return ResolveMethodSymbol(UnderlyingMethod.GetGenericMethodDefinition()); + } + + /// + public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) + { + return ResolveMethodSymbol(UnderlyingMethod.MakeGenericMethod(typeArguments.Unpack())); + } + + #endregion + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs new file mode 100644 index 0000000000..1d9b0a3e23 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs @@ -0,0 +1,480 @@ +using System; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + /// + /// Provides the metadata resolution implementation for a module. + /// + struct IkvmReflectionModuleMetadata + { + + /// + /// Returns true if the given is a TypeDef. That is, not a modified or substituted or generic parameter type. + /// + /// + /// + static bool IsTypeDefinition(Type type) + { + return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; + } + + const int MAX_CAPACITY = 65536 * 2; + + readonly IIkvmReflectionModuleSymbol _symbol; + + IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _typeLock; + + IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _methodLock; + + IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _fieldLock; + + IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _propertyLock; + + IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _eventLock; + + IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _parameterLock; + + IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); + ReaderWriterLockSlim? _genericParameterLock; + + /// + /// Initializes a new instance. + /// + /// + /// + public IkvmReflectionModuleMetadata(IIkvmReflectionModuleSymbol symbol) + { + _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + if (type.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(type)); + + // type is a generic parameter (GenericParam) + if (type.IsGenericParameter) + return GetOrCreateGenericTypeParameterSymbol(type); + + // type is not a type definition (TypeDef) + if (IsTypeDefinition(type) == false) + return GetOrCreateTypeSymbolForSpecification(type); + + // create lock on demand + if (_typeLock == null) + Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); + + using (_typeLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.TypeDefinitionHandle(type.MetadataToken)); + if (_typeSymbols[row] == null) + using (_typeLock.CreateWriteLock()) + if (type is TypeBuilder builder) + return _typeSymbols[row] ??= new IkvmReflectionTypeSymbolBuilder(_symbol.Context, _symbol, builder); + else + return _typeSymbols[row] ??= new IkvmReflectionTypeSymbol(_symbol.Context, _symbol, type); + else + return _typeSymbols[row] ?? throw new InvalidOperationException(); + } + } + + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return (IIkvmReflectionTypeSymbolBuilder)GetOrCreateTypeSymbol((Type)type); + } + + /// + /// Gets or creates a for the specification type: array, pointer, generic, etc. + /// + /// + /// + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + if (type.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(type)); + + if (type.GetElementType() is { } elementType) + { + var elementTypeSymbol = _symbol.ResolveTypeSymbol(elementType)!; + + // handles both SZ arrays and normal arrays + if (type.IsArray) + return (IIkvmReflectionTypeSymbol)elementTypeSymbol.MakeArrayType(type.GetArrayRank()); + + if (type.IsPointer) + return (IIkvmReflectionTypeSymbol)elementTypeSymbol.MakePointerType(); + + if (type.IsByRef) + return (IIkvmReflectionTypeSymbol)elementTypeSymbol.MakeByRefType(); + + throw new InvalidOperationException(); + } + + if (type.IsGenericType) + { + var definitionTypeSymbol = _symbol.GetOrCreateTypeSymbol(type.GetGenericTypeDefinition()); + return (IIkvmReflectionTypeSymbol)definitionTypeSymbol.MakeGenericType(definitionTypeSymbol.ResolveTypeSymbols(type.GetGenericArguments())!); + } + + throw new InvalidOperationException(); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + if (method.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(method)); + + // create lock on demand + if (_methodLock == null) + Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); + + using (_methodLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(method.MetadataToken)); + if (_methodSymbols[row] == null) + { + using (_methodLock.CreateWriteLock()) + { + if (method is ConstructorInfo c) + { + if (method is ConstructorBuilder builder) + return _methodSymbols[row] ??= new IkvmReflectionConstructorSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), builder); + else + return _methodSymbols[row] ??= new IkvmReflectionConstructorSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), c); + } + else if (method is MethodInfo m) + { + if (method is MethodBuilder builder) + return _methodSymbols[row] ??= new IkvmReflectionMethodSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), builder); + else + return _methodSymbols[row] ??= new IkvmReflectionMethodSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), m); + } + else + { + throw new InvalidOperationException(); + } + } + } + else + { + return _methodSymbols[row] ?? throw new InvalidOperationException(); + } + } + } + + /// + /// Gets or creates the cached for the type by ctor. + /// + /// + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return (IIkvmReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by ctor. + /// + /// + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return (IIkvmReflectionConstructorSymbolBuilder)GetOrCreateConstructorSymbol((ConstructorInfo)ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return (IIkvmReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return (IIkvmReflectionMethodSymbolBuilder)GetOrCreateMethodBaseSymbol((MethodInfo)method); + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + if (field.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(field)); + + // create lock on demand + if (_fieldLock == null) + Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); + + using (_fieldLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(field.MetadataToken)); + if (_fieldSymbols[row] == null) + using (_fieldLock.CreateWriteLock()) + if (field is FieldBuilder builder) + return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), builder); + else + return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), field); + else + return _fieldSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return (IIkvmReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field); + } + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + if (property.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(property)); + + // create lock on demand + if (_propertyLock == null) + Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); + + using (_propertyLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(property.MetadataToken)); + if (_propertySymbols[row] == null) + using (_propertyLock.CreateWriteLock()) + if (property is PropertyBuilder builder) + return _propertySymbols[row] ??= new IkvmReflectionPropertySymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), builder); + else + return _propertySymbols[row] ??= new IkvmReflectionPropertySymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), property); + else + return _propertySymbols[row] ?? throw new InvalidOperationException(); + } + } + + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return (IIkvmReflectionPropertySymbolBuilder)GetOrCreatePropertySymbol((PropertyInfo)property); + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_eventLock == null) + Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); + + using (_eventLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.MetadataToken)); + if (_eventSymbols[row] == null) + using (_eventLock.CreateWriteLock()) + return _eventSymbols[row] ??= new IkvmReflectionEventSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.DeclaringType!), @event); + else + return _eventSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_eventLock == null) + Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); + + using (_eventLock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.GetEventToken().Token)); + if (_eventSymbols[row] == null) + using (_eventLock.CreateWriteLock()) + return (IIkvmReflectionEventSymbolBuilder)(_eventSymbols[row] ??= new IkvmReflectionEventSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.DeclaringType), @event)); + else + return (IIkvmReflectionEventSymbolBuilder?)_eventSymbols[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.Member.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_parameterLock == null) + Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); + + using (_parameterLock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_parameterSymbols[position] == null) + using (_parameterLock.CreateWriteLock()) + return _parameterSymbols[position] ??= new IkvmReflectionParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); + else + return _parameterSymbols[position] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_parameterLock == null) + Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); + + using (_parameterLock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_parameterSymbols[position] == null) + using (_parameterLock.CreateWriteLock()) + return (IIkvmReflectionParameterSymbolBuilder)(_parameterSymbols[position] ??= new IkvmReflectionParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveMethodSymbol(parameter.Method), parameter)); + else + return (IIkvmReflectionParameterSymbolBuilder?)_parameterSymbols[position] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericParameterType) + { + if (genericParameterType is null) + throw new ArgumentNullException(nameof(genericParameterType)); + if (genericParameterType.Module.MetadataToken != _symbol.MetadataToken) + throw new ArgumentException(nameof(genericParameterType)); + + // create lock on demand + if (_genericParameterLock == null) + Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); + + using (_genericParameterLock.CreateUpgradeableReadLock()) + { + var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.MetadataToken); + var row = MetadataTokens.GetRowNumber(hnd); + if (_genericParameterSymbols[row] == null) + using (_genericParameterLock.CreateWriteLock()) + if (genericParameterType is GenericTypeParameterBuilder builder) + return _genericParameterSymbols[row] ??= new IkvmReflectionGenericTypeParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), builder); + else + return _genericParameterSymbols[row] ??= new IkvmReflectionGenericTypeParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), genericParameterType); + else + { + return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); + } + } + } + + /// + /// Gets or creates the cached for the module. + /// + /// + /// + IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) + { + return (IIkvmReflectionGenericTypeParameterSymbolBuilder)GetOrCreateGenericTypeParameterSymbol((Type)genericParameterType); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs new file mode 100644 index 0000000000..94913c88f8 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -0,0 +1,320 @@ +using System; +using System.Linq; + +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + /// + /// Implementation of derived from System.Reflection. + /// + class IkvmReflectionModuleSymbol : IkvmReflectionSymbol, IIkvmReflectionModuleSymbol + { + + readonly IIkvmReflectionAssemblySymbol _resolvingAssembly; + readonly Module _module; + IkvmReflectionModuleMetadata _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionModuleSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionAssemblySymbol resolvingAssembly, Module module) : + base(context) + { + _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _impl = new IkvmReflectionModuleMetadata(this); + } + + /// + public Module UnderlyingModule => _module; + + /// + public IIkvmReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; + + #region IModuleSymbol + + /// + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingModule.Assembly); + + /// + public string FullyQualifiedName => UnderlyingModule.FullyQualifiedName; + + /// + public int MetadataToken => UnderlyingModule.MetadataToken; + + /// + public Guid ModuleVersionId => UnderlyingModule.ModuleVersionId; + + /// + public string Name => UnderlyingModule.Name; + + /// + public string ScopeName => UnderlyingModule.ScopeName; + + /// + public IFieldSymbol? GetField(string name) + { + return ResolveFieldSymbol(UnderlyingModule.GetField(name)); + } + + /// + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolveFieldSymbol(UnderlyingModule.GetField(name, (BindingFlags)bindingAttr)); + } + + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingFlags) + { + return ResolveFieldSymbols(UnderlyingModule.GetFields((BindingFlags)bindingFlags))!; + } + + /// + public IFieldSymbol[] GetFields() + { + return ResolveFieldSymbols(UnderlyingModule.GetFields())!; + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name)); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, types.Unpack())); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + } + + /// + public IMethodSymbol[] GetMethods() + { + return ResolveMethodSymbols(UnderlyingModule.GetMethods())!; + } + + /// + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingFlags) + { + return ResolveMethodSymbols(UnderlyingModule.GetMethods((BindingFlags)bindingFlags))!; + } + + /// + public ITypeSymbol? GetType(string className) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className)); + } + + /// + public ITypeSymbol? GetType(string className, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className, ignoreCase)); + } + + /// + public ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingModule.GetType(className, throwOnError, ignoreCase)); + } + + /// + public ITypeSymbol[] GetTypes() + { + return ResolveTypeSymbols(UnderlyingModule.GetTypes())!; + } + + /// + public bool IsResource() + { + return UnderlyingModule.IsResource(); + } + + /// + public IFieldSymbol? ResolveField(int metadataToken) + { + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken)); + } + + /// + public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMemberSymbol? ResolveMember(int metadataToken) + { + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken)); + } + + /// + public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public IMethodBaseSymbol? ResolveMethod(int metadataToken) + { + return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken)); + } + + /// + public byte[] ResolveSignature(int metadataToken) + { + return UnderlyingModule.ResolveSignature(metadataToken); + } + + /// + public string ResolveString(int metadataToken) + { + return UnderlyingModule.ResolveString(metadataToken); + } + + /// + public ITypeSymbol ResolveType(int metadataToken) + { + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken)); + } + + /// + public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) + { + return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); + } + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData()); + } + + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingModule.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingModule.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingModule.IsDefined(attributeType.Unpack(), false); + } + + #endregion + + /// + public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + return _impl.GetOrCreateTypeSymbol(type); + } + + /// + public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return _impl.GetOrCreateTypeSymbol(type); + } + + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _impl.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return _impl.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return _impl.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return _impl.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _impl.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return _impl.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _impl.GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return _impl.GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _impl.GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return _impl.GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _impl.GetOrCreateParameterSymbol(parameter); + } + + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _impl.GetOrCreateParameterSymbol(parameter); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs new file mode 100644 index 0000000000..58440f6c39 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs @@ -0,0 +1,121 @@ +using System; +using System.Linq; + +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionParameterSymbol : IkvmReflectionSymbol, IIkvmReflectionParameterSymbol + { + + readonly IIkvmReflectionModuleSymbol _resolvingModule; + readonly IIkvmReflectionMethodBaseSymbol _resolvingMethod; + readonly ParameterInfo _parameter; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMethodBaseSymbol resolvingMethod, ParameterInfo parameter) : + base(context) + { + _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); + _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); + } + + /// + public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingModule; + + /// + public IIkvmReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; + + /// + public ParameterInfo UnderlyingParameter => _parameter; + + #region IParameterSymbol + + /// + public System.Reflection.ParameterAttributes Attributes => (System.Reflection.ParameterAttributes)UnderlyingParameter.Attributes; + + /// + public object? DefaultValue => UnderlyingParameter.RawDefaultValue; + + /// + public bool HasDefaultValue => UnderlyingParameter.HasDefaultValue; + + /// + public bool IsIn => UnderlyingParameter.IsIn; + + /// + public bool IsLcid => UnderlyingParameter.IsLcid; + + /// + public bool IsOptional => UnderlyingParameter.IsOptional; + + /// + public bool IsOut => UnderlyingParameter.IsOut; + + /// + public bool IsRetval => UnderlyingParameter.IsRetval; + + /// + public IMemberSymbol Member => ResolveMemberSymbol(UnderlyingParameter.Member); + + /// + public int MetadataToken => UnderlyingParameter.MetadataToken; + + /// + public string? Name => UnderlyingParameter.Name; + + /// + public ITypeSymbol ParameterType => ResolveTypeSymbol(UnderlyingParameter.ParameterType); + + /// + public int Position => UnderlyingParameter.Position; + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData()); + } + + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingParameter.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } + + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingParameter.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + } + + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingParameter.IsDefined(attributeType.Unpack(), inherit); + } + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingParameter.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingParameter.GetRequiredCustomModifiers()); + } + + #endregion + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs new file mode 100644 index 0000000000..96b8eb3582 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs @@ -0,0 +1,121 @@ +using System; + +using IKVM.Reflection; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionPropertySymbol : IkvmReflectionMemberSymbol, IIkvmReflectionPropertySymbol + { + + readonly PropertyInfo _property; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionPropertySymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol type, PropertyInfo property) : + base(context, module, type) + { + _property = property ?? throw new ArgumentNullException(nameof(property)); + } + + /// + public PropertyInfo UnderlyingProperty => _property; + + /// + public override MemberInfo UnderlyingMember => UnderlyingProperty; + + /// + public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)UnderlyingProperty.Attributes; + + /// + public bool CanRead => UnderlyingProperty.CanRead; + + /// + public bool CanWrite => UnderlyingProperty.CanWrite; + + /// + public bool IsSpecialName => UnderlyingProperty.IsSpecialName; + + /// + public ITypeSymbol PropertyType => ResolveTypeSymbol(UnderlyingProperty.PropertyType); + + /// + public IMethodSymbol? GetMethod => ResolveMethodSymbol(UnderlyingProperty.GetMethod); + + /// + public IMethodSymbol? SetMethod => ResolveMethodSymbol(UnderlyingProperty.SetMethod); + + /// + public object? GetRawConstantValue() + { + return UnderlyingProperty.GetRawConstantValue(); + } + + /// + public IMethodSymbol[] GetAccessors() + { + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors()); + } + + /// + public IMethodSymbol[] GetAccessors(bool nonPublic) + { + return ResolveMethodSymbols(UnderlyingProperty.GetAccessors(nonPublic)); + } + + /// + public IParameterSymbol[] GetIndexParameters() + { + return ResolveParameterSymbols(UnderlyingProperty.GetIndexParameters()); + } + + /// + public IMethodSymbol? GetGetMethod() + { + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod()); + } + + /// + public IMethodSymbol? GetGetMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod(nonPublic)); + } + + /// + public IMethodSymbol? GetSetMethod() + { + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod()); + } + + /// + public IMethodSymbol? GetSetMethod(bool nonPublic) + { + return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod(nonPublic)); + } + + /// + public ITypeSymbol GetModifiedPropertyType() + { + throw new NotImplementedException(); + } + + /// + public ITypeSymbol[] GetOptionalCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingProperty.GetOptionalCustomModifiers()); + } + + /// + public ITypeSymbol[] GetRequiredCustomModifiers() + { + return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs new file mode 100644 index 0000000000..393b98db49 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -0,0 +1,549 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; + +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + /// + /// Base class for managed symbols. + /// + abstract class IkvmReflectionSymbol : IIkvmReflectionSymbol + { + + readonly IkvmReflectionSymbolContext _context; + + /// + /// Initializes a new instance. + /// + /// + public IkvmReflectionSymbol(IkvmReflectionSymbolContext context) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + } + + /// + /// Gets the associated . + /// + public IkvmReflectionSymbolContext Context => _context; + + /// + public virtual bool IsMissing => false; + + /// + public virtual bool ContainsMissing => false; + + /// + public virtual bool IsComplete => true; + + /// + [return: NotNullIfNotNull(nameof(assembly))] + public virtual IIkvmReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly) + { + return assembly == null ? null : _context.GetOrCreateAssemblySymbol(assembly); + } + + /// + [return: NotNullIfNotNull(nameof(assembly))] + public virtual IIkvmReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly) + { + if (assembly is null) + throw new ArgumentNullException(nameof(assembly)); + + return _context.GetOrCreateAssemblySymbol(assembly); + } + + /// + [return: NotNullIfNotNull(nameof(assemblies))] + public virtual IIkvmReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies) + { + if (assemblies == null) + return null; + if (assemblies.Length == 0) + return []; + + var a = new IIkvmReflectionAssemblySymbol[assemblies.Length]; + for (int i = 0; i < assemblies.Length; i++) + if (ResolveAssemblySymbol(assemblies[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(module))] + public virtual IIkvmReflectionModuleSymbol? ResolveModuleSymbol(Module? module) + { + return module == null ? null : _context.GetOrCreateModuleSymbol(module); + } + + /// + [return: NotNullIfNotNull(nameof(module))] + public virtual IIkvmReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module) + { + if (module is null) + throw new ArgumentNullException(nameof(module)); + + return _context.GetOrCreateModuleSymbol(module); + } + + /// + [return: NotNullIfNotNull(nameof(modules))] + public virtual IIkvmReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules) + { + if (modules == null) + return null; + if (modules.Length == 0) + return []; + + var a = new IIkvmReflectionModuleSymbol[modules.Length]; + for (int i = 0; i < modules.Length; i++) + if (ResolveModuleSymbol(modules[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + public virtual IEnumerable ResolveModuleSymbols(IEnumerable modules) + { + foreach (var module in modules) + if (ResolveModuleSymbol(module) is { } symbol) + yield return symbol; + } + + /// + [return: NotNullIfNotNull(nameof(member))] + public virtual IIkvmReflectionMemberSymbol? ResolveMemberSymbol(MemberInfo? member) + { + if (member == null) + return null; + + return member switch + { + ConstructorInfo ctor => ResolveConstructorSymbol(ctor), + EventInfo @event => ResolveEventSymbol(@event), + FieldInfo field => ResolveFieldSymbol(field), + MethodInfo method => ResolveMethodSymbol(method), + PropertyInfo property => ResolvePropertySymbol(property), + Type type => ResolveTypeSymbol(type), + _ => throw new InvalidOperationException(), + }; + } + + /// + [return: NotNullIfNotNull(nameof(members))] + public virtual IIkvmReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? members) + { + if (members == null) + return null; + if (members.Length == 0) + return []; + + var a = new IIkvmReflectionMemberSymbol[members.Length]; + for (int i = 0; i < members.Length; i++) + if (ResolveMemberSymbol(members[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(type))] + public virtual IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + return type == null ? null : _context.GetOrCreateTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull(nameof(type))] + public virtual IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + + return _context.GetOrCreateTypeSymbol(type); + } + + /// + [return: NotNullIfNotNull(nameof(types))] + public virtual IIkvmReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types) + { + if (types == null) + return null; + if (types.Length == 0) + return []; + + var a = new IIkvmReflectionTypeSymbol[types.Length]; + for (int i = 0; i < types.Length; i++) + if (ResolveTypeSymbol(types[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + public virtual IEnumerable ResolveTypeSymbols(IEnumerable types) + { + foreach (var type in types) + if (ResolveTypeSymbol(type) is { } symbol) + yield return symbol; + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public virtual IIkvmReflectionMethodBaseSymbol? ResolveMethodBaseSymbol(MethodBase? method) + { + return method switch + { + ConstructorInfo ctor => ResolveConstructorSymbol(ctor), + MethodInfo method_ => ResolveMethodSymbol(method_), + _ => null, + }; + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public virtual IIkvmReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) + { + return ctor == null ? null : _context.GetOrCreateConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(ctor))] + public virtual IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) + { + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + + return _context.GetOrCreateConstructorSymbol(ctor); + } + + /// + [return: NotNullIfNotNull(nameof(ctors))] + public virtual IIkvmReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors) + { + if (ctors == null) + return null; + if (ctors.Length == 0) + return []; + + var a = new IIkvmReflectionConstructorSymbol[ctors.Length]; + for (int i = 0; i < ctors.Length; i++) + if (ResolveConstructorSymbol(ctors[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public virtual IIkvmReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) + { + return method == null ? null : _context.GetOrCreateMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(method))] + public virtual IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + return _context.GetOrCreateMethodSymbol(method); + } + + /// + [return: NotNullIfNotNull(nameof(methods))] + public virtual IIkvmReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods) + { + if (methods == null) + return null; + if (methods.Length == 0) + return []; + + var a = new IIkvmReflectionMethodSymbol[methods.Length]; + for (int i = 0; i < methods.Length; i++) + if (ResolveMethodSymbol(methods[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public virtual IIkvmReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) + { + return field == null ? null : _context.GetOrCreateFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(field))] + public virtual IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + + return _context.GetOrCreateFieldSymbol(field); + } + + /// + [return: NotNullIfNotNull(nameof(fields))] + public virtual IIkvmReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields) + { + if (fields == null) + return null; + if (fields.Length == 0) + return []; + + var a = new IIkvmReflectionFieldSymbol[fields.Length]; + for (int i = 0; i < fields.Length; i++) + if (ResolveFieldSymbol(fields[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public virtual IIkvmReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) + { + return property == null ? null : _context.GetOrCreatePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(property))] + public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + return _context.GetOrCreatePropertySymbol(property); + } + + /// + [return: NotNullIfNotNull(nameof(properties))] + public virtual IIkvmReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties) + { + if (properties == null) + return null; + if (properties.Length == 0) + return []; + + var a = new IIkvmReflectionPropertySymbol[properties.Length]; + for (int i = 0; i < properties.Length; i++) + if (ResolvePropertySymbol(properties[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public virtual IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) + { + return @event == null ? null : _context.GetOrCreateEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(@event))] + public virtual IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + return _context.GetOrCreateEventSymbol(@event); + } + + /// + [return: NotNullIfNotNull(nameof(events))] + public virtual IIkvmReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events) + { + if (@events == null) + return null; + if (@events.Length == 0) + return []; + + var a = new IIkvmReflectionEventSymbol[events.Length]; + for (int i = 0; i < events.Length; i++) + if (ResolveEventSymbol(events[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public virtual IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) + { + return parameter == null ? null : _context.GetOrCreateParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public virtual IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + return _context.GetOrCreateParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameters))] + public virtual IIkvmReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters) + { + if (parameters == null) + return null; + if (parameters.Length == 0) + return []; + + var a = new IIkvmReflectionParameterSymbol[parameters.Length]; + for (int i = 0; i < parameters.Length; i++) + if (ResolveParameterSymbol(parameters[i]) is { } symbol) + a[i] = symbol; + + return a; + } + + /// + [return: NotNullIfNotNull(nameof(attributes))] + public virtual CustomAttribute[]? ResolveCustomAttributes(IList? attributes) + { + if (attributes == null) + return null; + if (attributes.Count == 0) + return []; + + var a = new CustomAttribute[attributes.Count]; + for (int i = 0; i < attributes.Count; i++) + if (ResolveCustomAttribute(attributes[i]) is { } v) + a[i] = v; + + return a; + } + + /// + /// Transforms a custom set of custom attribute data records to a symbol record. + /// + /// + /// + public virtual IEnumerable ResolveCustomAttributes(IEnumerable attributes) + { + if (attributes is null) + throw new ArgumentNullException(nameof(attributes)); + + var a = new List(); + foreach (var i in attributes) + if (ResolveCustomAttribute(i) is { } v) + a.Add(v); + + return a.ToArray(); + } + + /// + /// Transforms a custom attribute data record to a symbol record. + /// + /// + /// + [return: NotNullIfNotNull(nameof(customAttributeData))] + public virtual CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) + { + if (customAttributeData == null) + return null; + + return new CustomAttribute( + ResolveTypeSymbol(customAttributeData.AttributeType)!, + ResolveConstructorSymbol(customAttributeData.Constructor)!, + ResolveCustomAttributeTypedArguments(customAttributeData.ConstructorArguments), + ResolveCustomAttributeNamedArguments(customAttributeData.NamedArguments)); + } + + /// + /// Transforms a list of values into symbols. + /// + /// + /// + public ImmutableArray ResolveCustomAttributeTypedArguments(IList args) + { + if (args is null) + throw new ArgumentNullException(nameof(args)); + if (args.Count == 0) + return []; + + var a = new CustomAttributeTypedArgument[args.Count]; + for (int i = 0; i < args.Count; i++) + a[i] = ResolveCustomAttributeTypedArgument(args[i]); + + return a.ToImmutableArray(); + } + + /// + /// Transforms a values into a symbol. + /// + /// + /// + public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Reflection.CustomAttributeTypedArgument arg) + { + return new CustomAttributeTypedArgument( + ResolveTypeSymbol(arg.ArgumentType)!, + ResolveCustomAttributeTypedValue(arg.Value)); + } + + /// + /// Transforms the type as appropriate. + /// + /// + /// + public object? ResolveCustomAttributeTypedValue(object? value) + { + return value switch + { + Type v => ResolveTypeSymbol(v), + _ => value + }; + } + + /// + /// Transforms a list of values into symbols. + /// + /// + /// + public ImmutableArray ResolveCustomAttributeNamedArguments(IList args) + { + if (args is null) + throw new ArgumentNullException(nameof(args)); + if (args.Count == 0) + return []; + + var a = new CustomAttributeNamedArgument[args.Count]; + for (int i = 0; i < args.Count; i++) + a[i] = ResolveCustomAttributeNamedArgument(args[i]); + + return ImmutableArray.Create(a); + } + + /// + /// Transforms a values into a symbol. + /// + /// + /// + public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(IKVM.Reflection.CustomAttributeNamedArgument arg) + { + return new CustomAttributeNamedArgument( + arg.IsField, + ResolveMemberSymbol(arg.MemberInfo)!, + arg.MemberName, + ResolveCustomAttributeTypedArgument(arg.TypedValue)); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs new file mode 100644 index 0000000000..8268ab17bb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -0,0 +1,297 @@ +using System; +using System.Collections.Concurrent; +using System.Runtime.CompilerServices; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + /// + /// Holds references to symbols derived from System.Reflection. + /// + class IkvmReflectionSymbolContext : ISymbolContext + { + + readonly ConcurrentDictionary> _symbolByName = new(); + readonly ConditionalWeakTable _symbolByAssembly = new(); + + /// + /// Initializes a new instance. + /// + public IkvmReflectionSymbolContext() + { + + } + + /// + /// Gets or creates a indexed based on the assembly's name. + /// + /// + /// + IIkvmReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) + { + var r = _symbolByName.GetOrAdd(assembly.FullName, _ => new(null)); + + lock (r) + { + // reference has no target, reset + if (r.TryGetTarget(out var s) == false) + { + if (assembly is AssemblyBuilder builder) + { + // we were passed in a builder, so generate a symbol builder and set it as the builder and symbol. + r.SetTarget(s = new IkvmReflectionAssemblySymbolBuilder(this, builder)); + } + else + { + // we were passed a non builder, so generate a symbol and set it to the symbol + // TODO the weakness here is if we pass it the RuntimeAssembly from a non-associated builder + r.SetTarget(s = new IkvmReflectionAssemblySymbol(this, assembly)); + } + } + + return s ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates a indexed based on the assembly's name. + /// + /// + /// + IIkvmReflectionAssemblySymbolBuilder GetOrCreateAssemblySymbolByName(AssemblyBuilder assembly) + { + return (IIkvmReflectionAssemblySymbolBuilder)GetOrCreateAssemblySymbolByName((Assembly)assembly); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) + { + return _symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionAssemblySymbolBuilder GetOrCreateAssemblySymbol(AssemblyBuilder assembly) + { + return (IIkvmReflectionAssemblySymbolBuilder)_symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + if (module is ModuleBuilder builder) + return GetOrCreateModuleSymbol(builder); + else + return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type is TypeBuilder builder) + return GetOrCreateTypeSymbol(builder); + else + return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + if (ctor is ConstructorBuilder builder) + return GetOrCreateConstructorSymbol(builder); + else + return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + if (method is MethodBuilder builder) + return GetOrCreateMethodSymbol(builder); + else + return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return GetOrCreateModuleSymbol(parameter.Module).GetOrCreateParameterSymbol(parameter); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return GetOrCreateModuleSymbol(parameter.Module).GetOrCreateParameterSymbol(parameter); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is FieldBuilder builder) + return GetOrCreateFieldSymbol(builder); + else + return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + if (property is PropertyBuilder builder) + return GetOrCreatePropertySymbol(builder); + else + return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs) + { + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs)); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) + { + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedFields.Unpack(), fieldValues)); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) + { + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues)); + } + + /// + public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) + { + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues, namedFields.Unpack(), fieldValues)); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolExtensions.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolExtensions.cs new file mode 100644 index 0000000000..988078c421 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolExtensions.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + static class IkvmReflectionSymbolExtensions + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs new file mode 100644 index 0000000000..e3b7d7fa9a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs @@ -0,0 +1,587 @@ +using System; +using System.Collections.Concurrent; +using System.Threading; + +using IKVM.Reflection; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + /// + /// Provides common operations against a . + /// + struct IkvmReflectionTypeImpl + { + + readonly IIkvmReflectionTypeSymbol _symbol; + + IkvmReflectionTypeSymbol?[]? _asArray; + IkvmReflectionTypeSymbol? _asSZArray; + IkvmReflectionTypeSymbol? _asPointer; + IkvmReflectionTypeSymbol? _asByRef; + ConcurrentDictionary? _genericTypeSymbols; + + /// + /// Initializes a new instance. + /// + /// + /// + public IkvmReflectionTypeImpl(IIkvmReflectionTypeSymbol symbol) + { + _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + } + + /// + /// Gets or creates the cached for the generic parameter type. + /// + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) + { + if (genericTypeArguments is null) + throw new ArgumentNullException(nameof(genericTypeArguments)); + + if (_symbol.UnderlyingType.IsGenericTypeDefinition == false) + throw new InvalidOperationException(); + + if (_genericTypeSymbols == null) + Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); + + var __symbol = _symbol; + return _genericTypeSymbols.GetOrAdd(genericTypeArguments, _ => new IkvmReflectionTypeSymbol(__symbol.Context, __symbol.ResolvingModule, __symbol.UnderlyingType.MakeGenericType(genericTypeArguments.Unpack()))); + } + + /// + public readonly IAssemblySymbol Assembly => _symbol.ResolveAssemblySymbol(_symbol.UnderlyingType.Assembly); + + /// + public readonly string? AssemblyQualifiedName => _symbol.UnderlyingType.AssemblyQualifiedName; + + /// + public readonly System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)_symbol.UnderlyingType.Attributes; + + /// + public readonly ITypeSymbol? BaseType => _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.BaseType); + + /// + public readonly bool ContainsGenericParameters => _symbol.UnderlyingType.ContainsGenericParameters; + + /// + public readonly IMethodBaseSymbol? DeclaringMethod => _symbol.ResolveMethodBaseSymbol(_symbol.UnderlyingType.DeclaringMethod); + + /// + public readonly string? FullName => _symbol.UnderlyingType.FullName; + + /// + public readonly string? Namespace => _symbol.UnderlyingType.Namespace; + + /// + public readonly System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)_symbol.UnderlyingType.GenericParameterAttributes; + + /// + public readonly int GenericParameterPosition => _symbol.UnderlyingType.GenericParameterPosition; + + /// + public readonly ITypeSymbol[] GenericTypeArguments => _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GenericTypeArguments); + + /// + public readonly bool HasElementType => _symbol.UnderlyingType.HasElementType; + + /// + public readonly TypeCode TypeCode => Type.GetTypeCode(_symbol.UnderlyingType); + + /// + public readonly bool IsAbstract => _symbol.UnderlyingType.IsAbstract; + + /// + public readonly bool IsSZArray => _symbol.UnderlyingType.IsSZArray; + + /// + public readonly bool IsArray => _symbol.UnderlyingType.IsArray; + + /// + public readonly bool IsAutoLayout => _symbol.UnderlyingType.IsAutoLayout; + + /// + public readonly bool IsExplicitLayout => _symbol.UnderlyingType.IsExplicitLayout; + + /// + public readonly bool IsByRef => _symbol.UnderlyingType.IsByRef; + + /// + public readonly bool IsClass => _symbol.UnderlyingType.IsClass; + + /// + public readonly bool IsEnum => _symbol.UnderlyingType.IsEnum; + + /// + public readonly bool IsInterface => _symbol.UnderlyingType.IsInterface; + + /// + public readonly bool IsConstructedGenericType => _symbol.UnderlyingType.IsConstructedGenericType; + + /// + public readonly bool IsGenericParameter => _symbol.UnderlyingType.IsGenericParameter; + + /// + public readonly bool IsGenericType => _symbol.UnderlyingType.IsGenericType; + + /// + public readonly bool IsGenericTypeDefinition => _symbol.UnderlyingType.IsGenericTypeDefinition; + + /// + public readonly bool IsLayoutSequential => _symbol.UnderlyingType.IsLayoutSequential; + + /// + public readonly bool IsNested => _symbol.UnderlyingType.IsNested; + + /// + public readonly bool IsNestedAssembly => _symbol.UnderlyingType.IsNestedAssembly; + + /// + public readonly bool IsNestedFamANDAssem => _symbol.UnderlyingType.IsNestedFamANDAssem; + + /// + public readonly bool IsNestedFamORAssem => _symbol.UnderlyingType.IsNestedFamORAssem; + + /// + public readonly bool IsNestedFamily => _symbol.UnderlyingType.IsNestedFamily; + + /// + public readonly bool IsNestedPrivate => _symbol.UnderlyingType.IsNestedPrivate; + + /// + public readonly bool IsNestedPublic => _symbol.UnderlyingType.IsNestedPublic; + + /// + public readonly bool IsNotPublic => _symbol.UnderlyingType.IsNotPublic; + + /// + public readonly bool IsPointer => _symbol.UnderlyingType.IsPointer; + + /// + public readonly bool IsFunctionPointer => _symbol.UnderlyingType.IsFunctionPointer; + + /// + public readonly bool IsUnmanagedFunctionPointer => _symbol.UnderlyingType.IsUnmanagedFunctionPointer; + + /// + public readonly bool IsPrimitive => _symbol.UnderlyingType.IsPrimitive; + + /// + public readonly bool IsPublic => _symbol.UnderlyingType.IsPublic; + + /// + public readonly bool IsSealed => _symbol.UnderlyingType.IsSealed; + + /// + public readonly bool IsSerializable => _symbol.UnderlyingType.IsSerializable; + + /// + public readonly bool IsValueType => _symbol.UnderlyingType.IsValueType; + + /// + public readonly bool IsVisible => _symbol.UnderlyingType.IsVisible; + + /// + public readonly bool IsSignatureType => throw new NotImplementedException(); + + /// + public readonly bool IsSpecialName => _symbol.UnderlyingType.IsSpecialName; + + /// + public readonly IConstructorSymbol? TypeInitializer => _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.TypeInitializer); + + /// + public readonly int GetArrayRank() + { + return _symbol.UnderlyingType.GetArrayRank(); + } + + /// + public readonly IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); + } + + /// + public readonly IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor(types.Unpack())); + } + + /// + public readonly IConstructorSymbol[] GetConstructors() + { + return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors()); + } + + /// + public readonly IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetDefaultMembers() + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetDefaultMembers()); + } + + /// + public readonly ITypeSymbol? GetElementType() + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetElementType()); + } + + /// + public readonly string? GetEnumName(object value) + { + return _symbol.UnderlyingType.GetEnumName(value); + } + + /// + public readonly string[] GetEnumNames() + { + return _symbol.UnderlyingType.GetEnumNames(); + } + + /// + public readonly ITypeSymbol GetEnumUnderlyingType() + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetEnumUnderlyingType()); + } + + /// + public readonly Array GetEnumValues() + { + return _symbol.UnderlyingType.GetEnumValues(); + } + + /// + public readonly IEventSymbol? GetEvent(string name) + { + return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name)); + } + + /// + public readonly IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); + } + + /// + public readonly IEventSymbol[] GetEvents() + { + return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents()); + } + + /// + public readonly IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents((BindingFlags)bindingAttr)); + } + + /// + public readonly IFieldSymbol? GetField(string name) + { + return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name)); + } + + /// + public readonly IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); + } + + /// + public readonly IFieldSymbol[] GetFields() + { + return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields()); + } + + /// + public readonly IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields((BindingFlags)bindingAttr)); + } + + /// + public readonly ITypeSymbol[] GetGenericArguments() + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericArguments()); + } + + /// + public readonly ITypeSymbol[] GetGenericParameterConstraints() + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericParameterConstraints()); + } + + /// + public readonly ITypeSymbol GetGenericTypeDefinition() + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetGenericTypeDefinition()); + } + + /// + public readonly ITypeSymbol? GetInterface(string name) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name)); + } + + /// + public readonly ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name, ignoreCase)); + } + + /// + public readonly InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + throw new NotImplementedException(); + } + + /// + public readonly ITypeSymbol[] GetInterfaces(bool inherit = true) + { + if (inherit) + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); + } + + /// + public readonly IMemberSymbol[] GetMember(string name) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name)); + } + + /// + public readonly IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers((BindingFlags)bindingAttr)); + } + + /// + public readonly IMemberSymbol[] GetMembers() + { + return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers()); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, types.Unpack())); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name)); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + } + + /// + public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public readonly IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods((BindingFlags)bindingAttr)); + } + + /// + public readonly IMethodSymbol[] GetMethods() + { + return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods()); + } + + /// + public readonly ITypeSymbol? GetNestedType(string name) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name)); + } + + /// + public readonly ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); + } + + /// + public readonly ITypeSymbol[] GetNestedTypes() + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes()); + } + + /// + public readonly ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); + } + + /// + public readonly IPropertySymbol[] GetProperties() + { + return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties()); + } + + /// + public readonly IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties((BindingFlags)bindingAttr)); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, types.Unpack())); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); + } + + /// + public readonly IPropertySymbol? GetProperty(string name) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name)); + } + + /// + public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack())); + } + + /// + public readonly bool IsAssignableFrom(ITypeSymbol? c) + { + return _symbol.UnderlyingType.IsAssignableFrom(c?.Unpack()); + } + + /// + public readonly bool IsEnumDefined(object value) + { + return _symbol.UnderlyingType.IsEnumDefined(value); + } + + /// + public readonly bool IsSubclassOf(ITypeSymbol c) + { + return _symbol.UnderlyingType.IsSubclassOf(c.Unpack()); + } + + /// + public IIkvmReflectionTypeSymbol MakeArrayType() + { + if (_asSZArray == null) + Interlocked.CompareExchange(ref _asSZArray, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType()), null); + + return _asSZArray; + } + + /// + public IIkvmReflectionTypeSymbol MakeArrayType(int rank) + { + if (rank == 1) + return MakeArrayType(); + + if (_asArray == null) + Interlocked.CompareExchange(ref _asArray, new IkvmReflectionTypeSymbol?[32], null); + + ref var asArray = ref _asArray[rank]; + if (asArray == null) + Interlocked.CompareExchange(ref asArray, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType(rank)), null); + + return asArray; + } + + /// + public IIkvmReflectionTypeSymbol MakeByRefType() + { + if (_asByRef == null) + Interlocked.CompareExchange(ref _asByRef, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeByRefType()), null); + + return _asByRef; + } + + /// + public IIkvmReflectionTypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return GetOrCreateGenericTypeSymbol(typeArguments); + } + + /// + public IIkvmReflectionTypeSymbol MakePointerType() + { + if (_asPointer == null) + Interlocked.CompareExchange(ref _asPointer, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakePointerType()), null); + + return _asPointer; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs new file mode 100644 index 0000000000..99ef2c73c4 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -0,0 +1,554 @@ +using System; +using System.Diagnostics.CodeAnalysis; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + class IkvmReflectionTypeSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionTypeSymbol + { + + readonly Type _type; + IkvmReflectionTypeImpl _impl; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionTypeSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, Type type) : + base(context, resolvingModule, null) + { + _type = type ?? throw new ArgumentNullException(nameof(type)); + _impl = new IkvmReflectionTypeImpl(this); + } + + /// + public Type UnderlyingType => _type; + + /// + public override IKVM.Reflection.MemberInfo UnderlyingMember => UnderlyingType; + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + if (type == _type) + return this; + else + return base.ResolveTypeSymbol(type); + } + + #region ITypeSymbol + + /// + public System.Reflection.TypeAttributes Attributes => _impl.Attributes; + + /// + public IAssemblySymbol Assembly => _impl.Assembly; + + /// + public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + + /// + public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + + /// + public string? FullName => _impl.FullName; + + /// + public string? Namespace => _impl.Namespace; + + /// + public TypeCode TypeCode => _impl.TypeCode; + + /// + public ITypeSymbol? BaseType => _impl.BaseType; + + /// + public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + + /// + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + + /// + public int GenericParameterPosition => _impl.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + + /// + public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + + /// + public bool IsGenericType => _impl.IsGenericType; + + /// + public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + + /// + public bool IsGenericParameter => _impl.IsGenericParameter; + + /// + public bool IsAutoLayout => _impl.IsAutoLayout; + + /// + public bool IsExplicitLayout => _impl.IsExplicitLayout; + + /// + public bool IsLayoutSequential => _impl.IsLayoutSequential; + + /// + public bool HasElementType => _impl.HasElementType; + + /// + public bool IsClass => _impl.IsClass; + + /// + public bool IsValueType => _impl.IsValueType; + + /// + public bool IsInterface => _impl.IsInterface; + + /// + public bool IsPrimitive => _impl.IsPrimitive; + + /// + public bool IsSZArray => _impl.IsSZArray; + + /// + public bool IsArray => _impl.IsArray; + + /// + public bool IsEnum => _impl.IsEnum; + + /// + public bool IsPointer => _impl.IsPointer; + + /// + public bool IsFunctionPointer => _impl.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + + /// + public bool IsByRef => _impl.IsByRef; + + /// + public bool IsAbstract => _impl.IsAbstract; + + /// + public bool IsSealed => _impl.IsSealed; + + /// + public bool IsVisible => _impl.IsVisible; + + /// + public bool IsPublic => _impl.IsPublic; + + /// + public bool IsNotPublic => _impl.IsNotPublic; + + /// + public bool IsNested => _impl.IsNested; + + /// + public bool IsNestedAssembly => _impl.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + + /// + public bool IsNestedFamily => _impl.IsNestedFamily; + + /// + public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + + /// + public bool IsNestedPrivate => _impl.IsNestedPrivate; + + /// + public bool IsNestedPublic => _impl.IsNestedPublic; + + /// + public bool IsSerializable => _impl.IsSerializable; + + /// + public bool IsSignatureType => _impl.IsSignatureType; + + /// + public bool IsSpecialName => _impl.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + + /// + public int GetArrayRank() + { + return _impl.GetArrayRank(); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return _impl.GetDefaultMembers(); + } + + /// + public ITypeSymbol? GetElementType() + { + return _impl.GetElementType(); + } + + /// + public string? GetEnumName(object value) + { + return _impl.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return _impl.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return _impl.GetEnumUnderlyingType(); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return _impl.GetGenericArguments(); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return _impl.GetGenericParameterConstraints(); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return _impl.GetGenericTypeDefinition(); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return _impl.GetInterface(name); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _impl.GetInterface(name, ignoreCase); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + return _impl.GetInterfaces(inherit); + } + + /// + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return _impl.GetInterfaceMap(interfaceType); + } + + /// + public IMemberSymbol[] GetMember(string name) + { + return _impl.GetMember(name); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, bindingAttr); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMember(name, type, bindingAttr); + } + + /// + public IMemberSymbol[] GetMembers() + { + return _impl.GetMembers(); + } + + /// + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMembers(bindingAttr); + } + + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return _impl.GetConstructor(types); + } + + /// + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetConstructor(bindingAttr, types); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return _impl.GetConstructors(); + } + + /// + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetConstructors(bindingAttr); + } + + /// + public IFieldSymbol? GetField(string name) + { + return _impl.GetField(name); + } + + /// + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetField(name, bindingAttr); + } + + /// + public IFieldSymbol[] GetFields() + { + return _impl.GetFields(); + } + + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetFields(bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return _impl.GetMethod(name); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return _impl.GetMethod(name, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethod(name, bindingAttr); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return _impl.GetMethod(name, bindingAttr, types); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return _impl.GetMethod(name, genericParameterCount, types, modifiers); + } + + /// + public IMethodSymbol[] GetMethods() + { + return _impl.GetMethods(); + } + + /// + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetMethods(bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return _impl.GetProperty(name); + } + + /// + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperty(name, bindingAttr); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return _impl.GetProperty(name, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return _impl.GetProperty(name, returnType, types); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return _impl.GetProperty(name, returnType); + } + + /// + public IPropertySymbol[] GetProperties() + { + return _impl.GetProperties(); + } + + /// + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetProperties(bindingAttr); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return _impl.GetEvent(name); + } + + /// + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvent(name, bindingAttr); + } + + /// + public IEventSymbol[] GetEvents() + { + return _impl.GetEvents(); + } + + /// + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetEvents(bindingAttr); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return _impl.GetNestedType(name); + } + + /// + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedType(name, bindingAttr); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return _impl.GetNestedTypes(); + } + + /// + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + { + return _impl.GetNestedTypes(); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return _impl.IsAssignableFrom(c); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return _impl.IsSubclassOf(c); + } + + /// + public bool IsEnumDefined(object value) + { + return _impl.IsEnumDefined(value); + } + + /// + public ITypeSymbol MakeArrayType() + { + return _impl.MakeArrayType(); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return _impl.MakeArrayType(rank); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return _impl.MakeGenericType(typeArguments); + } + + /// + public ITypeSymbol MakePointerType() + { + return _impl.MakePointerType(); + } + + /// + public ITypeSymbol MakeByRefType() + { + return _impl.MakeByRefType(); + } + + #endregion + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs new file mode 100644 index 0000000000..0aa5322ab7 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -0,0 +1,315 @@ +using System; + +using IKVM.Reflection; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + static class IkvmReflectionUtil + { + +#pragma warning disable SYSLIB0017 // Type or member is obsolete +#pragma warning disable SYSLIB0037 // Type or member is obsolete + + /// + /// Converts a to a . + /// + /// + /// + public static System.Reflection.AssemblyName ToAssemblyName(this AssemblyName n) + { + return new System.Reflection.AssemblyName() + { + Name = n.Name, + Version = n.Version, + CultureInfo = n.CultureInfo, + CultureName = n.CultureName, + ProcessorArchitecture = (System.Reflection.ProcessorArchitecture)n.ProcessorArchitecture, + Flags = (System.Reflection.AssemblyNameFlags)n.Flags, + HashAlgorithm = (System.Configuration.Assemblies.AssemblyHashAlgorithm)n.HashAlgorithm, + ContentType = (System.Reflection.AssemblyContentType)n.ContentType, + VersionCompatibility = (System.Configuration.Assemblies.AssemblyVersionCompatibility)n.VersionCompatibility, + }; + } + +#pragma warning restore SYSLIB0037 // Type or member is obsolete +#pragma warning restore SYSLIB0017 // Type or member is obsolete + + /// + /// Converts a set of to a set of . + /// + /// + /// + public static System.Reflection.AssemblyName[] ToAssemblyNames(this AssemblyName[] n) + { + if (n.Length == 0) + return []; + + var a = new System.Reflection.AssemblyName[n.Length]; + for (int i = 0; i < n.Length; i++) + a[i] = n[i].ToAssemblyName(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static Module Unpack(this IModuleSymbol module) + { + if (module is IIkvmReflectionModuleSymbol symbol) + return symbol.UnderlyingModule; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Module[] Unpack(this IModuleSymbol[] modules) + { + if (modules.Length == 0) + return []; + + var a = new Module[modules.Length]; + for (int i = 0; i < modules.Length; i++) + a[i] = modules[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static Type Unpack(this ITypeSymbol type) + { + if (type is IIkvmReflectionTypeSymbol symbol) + return symbol.UnderlyingType; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Type[] Unpack(this ITypeSymbol[] types) + { + if (types.Length == 0) + return []; + + var a = new Type[types.Length]; + for (int i = 0; i < types.Length; i++) + a[i] = types[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static Type[][] Unpack(this ITypeSymbol[][] types) + { + if (types.Length == 0) + return []; + + var a = new Type[types.Length][]; + for (int i = 0; i < types.Length; i++) + a[i] = types[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static MemberInfo Unpack(this IMemberSymbol member) + { + if (member is IIkvmReflectionMemberSymbol symbol) + return symbol.UnderlyingMember; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static MemberInfo[] Unpack(this IMemberSymbol[] members) + { + if (members.Length == 0) + return []; + + var a = new MemberInfo[members.Length]; + for (int i = 0; i < members.Length; i++) + a[i] = members[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static ConstructorInfo Unpack(this IConstructorSymbol ctor) + { + if (ctor is IIkvmReflectionConstructorSymbol symbol) + return symbol.UnderlyingConstructor; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static ConstructorInfo[] Unpack(this IConstructorSymbol[] ctor) + { + if (ctor.Length == 0) + return []; + + var a = new ConstructorInfo[ctor.Length]; + for (int i = 0; i < ctor.Length; i++) + a[i] = ctor[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static MethodInfo Unpack(this IMethodSymbol ctor) + { + if (ctor is IIkvmReflectionMethodSymbol symbol) + return symbol.UnderlyingMethod; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static MethodInfo[] Unpack(this IMethodSymbol[] ctor) + { + if (ctor.Length == 0) + return []; + + var a = new MethodInfo[ctor.Length]; + for (int i = 0; i < ctor.Length; i++) + a[i] = ctor[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static FieldInfo Unpack(this IFieldSymbol field) + { + if (field is IIkvmReflectionFieldSymbol symbol) + return symbol.UnderlyingField; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static FieldInfo[] Unpack(this IFieldSymbol[] fields) + { + if (fields.Length == 0) + return []; + + var a = new FieldInfo[fields.Length]; + for (int i = 0; i < fields.Length; i++) + a[i] = fields[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original type. + /// + /// + /// + public static PropertyInfo Unpack(this IPropertySymbol property) + { + if (property is IIkvmReflectionPropertySymbol symbol) + return symbol.UnderlyingProperty; + + throw new InvalidOperationException(); + } + + /// + /// Unpacks the symbols into their original type. + /// + /// + /// + public static PropertyInfo[] Unpack(this IPropertySymbol[] properties) + { + if (properties.Length == 0) + return []; + + var a = new PropertyInfo[properties.Length]; + for (int i = 0; i < properties.Length; i++) + a[i] = properties[i].Unpack(); + + return a; + } + + /// + /// Unpacks the parameter modifier. + /// + /// + /// + /// + public static ParameterModifier Unpack(this System.Reflection.ParameterModifier modifier) + { + throw new NotSupportedException(); + } + + /// + /// Unpacks the parameter modifier. + /// + /// + /// + /// + public static ParameterModifier[] Unpack(this System.Reflection.ParameterModifier[] modifiers) + { + if (modifiers.Length == 0) + return []; + + var a = new ParameterModifier[modifiers.Length]; + for (int i = 0; i < modifiers.Length; i++) + a[i] = modifiers[i].Unpack(); + + return a; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs index 5495e484bc..879a74a62a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs @@ -122,13 +122,13 @@ public CustomAttribute[] GetCustomAttributes(bool inherit = false) /// public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData().Where(i => attributeType.IsAssignableFrom(attributeType)).ToArray()); } /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + return ResolveCustomAttribute(UnderlyingParameter.GetCustomAttributesData().Where(i => attributeType.IsAssignableFrom(attributeType)).FirstOrDefault()); } /// diff --git a/src/IKVM.Reflection/Emit/PropertyBuilder.cs b/src/IKVM.Reflection/Emit/PropertyBuilder.cs index 0a906ce609..a114f26c23 100644 --- a/src/IKVM.Reflection/Emit/PropertyBuilder.cs +++ b/src/IKVM.Reflection/Emit/PropertyBuilder.cs @@ -269,6 +269,17 @@ internal override int GetCurrentToken() return lazyPseudoToken; } + public override int MetadataToken + { + get + { + if (lazyPseudoToken == 0) + lazyPseudoToken = typeBuilder.ModuleBuilder.AllocPseudoToken(); + + return GetCurrentToken(); + } + } + } } diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index cea132a71e..cf883ce9ae 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -38,7 +38,9 @@ Jeroen Frijters #if IMPORTER || EXPORTER +using IKVM.Reflection; #else +using System.Reflection; #endif #if IMPORTER @@ -902,7 +904,7 @@ internal NameSigAttribute GetNameSig(IMemberSymbol member) internal T[] DecodeArray(IKVM.CoreLib.Symbols.CustomAttributeTypedArgument arg) { - var elems = (CustomAttributeTypedArgument[])arg.Value; + var elems = (IKVM.CoreLib.Symbols.CustomAttributeTypedArgument[])arg.Value; var arr = new T[elems.Length]; for (int i = 0; i < arr.Length; i++) arr[i] = (T)elems[i].Value; @@ -932,7 +934,7 @@ internal ThrowsAttribute GetThrows(IMethodBaseSymbol mb) } else if (args[0].ArgumentType == context.Types.Type.MakeArrayType()) { - return new ThrowsAttribute(DecodeArray(args[0]).Unpack()); + return new ThrowsAttribute(DecodeArray(args[0]).AsReflection()); } else { diff --git a/src/IKVM.Runtime/ByteCodeHelper.cs b/src/IKVM.Runtime/ByteCodeHelper.cs index df39527faf..43f3be833b 100644 --- a/src/IKVM.Runtime/ByteCodeHelper.cs +++ b/src/IKVM.Runtime/ByteCodeHelper.cs @@ -105,7 +105,7 @@ public static object multianewarray_ghost(RuntimeTypeHandle typeHandle, int[] le type = type.GetElementType(); } - var obj = multianewarray(RuntimeArrayJavaType.MakeArrayType(typeof(object), rank).TypeHandle, lengths); + var obj = multianewarray(typeof(object).MakeArrayType(rank).TypeHandle, lengths); GhostTag.SetTag(obj, typeHandle); return obj; } diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index ec6406b17b..cf4cb20cb2 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -80,7 +80,7 @@ public CodeEmitterFactory(RuntimeContext context) /// public CodeEmitter Create(IMethodSymbolBuilder mb) { - return new CodeEmitter(context, mb.GetILGenerator(), context.Resolver.ResolveType(mb.Symbol.DeclaringType)); + return new CodeEmitter(context, mb.GetILGenerator(), context.Resolver.ResolveType(mb.DeclaringType)); } #if IMPORTER == false diff --git a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs index 20a8de6f9a..229822b1dc 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs @@ -1734,9 +1734,9 @@ public static object allocateInstance(object self, global::java.lang.Class cls) } #if NETFRAMEWORK - return FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType); + return FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection()); #else - return RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType); + return RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection()); #endif } @@ -1854,8 +1854,8 @@ static void PutFieldVolatile(object o, long offset, T value) /// static Delegate CreateGetArrayVolatileDelegate(RuntimeJavaType tw) { - var et = tw.IsPrimitive ? tw.TypeAsTBD : typeof(object); - var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD, true, et, new[] { typeof(object[]), typeof(long) }); + var et = tw.IsPrimitive ? tw.TypeAsTBD.AsReflection() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.AsReflection(), true, et, new[] { typeof(object[]), typeof(long) }); var il = dm.GetILGenerator(); // load reference to element @@ -1865,17 +1865,17 @@ static Delegate CreateGetArrayVolatileDelegate(RuntimeJavaType tw) il.Emit(OpCodes.Ldc_I4, ArrayIndexScale(tw.MakeArrayType(1))); il.Emit(OpCodes.Div); il.Emit(OpCodes.Conv_Ovf_I); - il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType); + il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.AsReflection()); if (tw.IsWidePrimitive == false) { il.Emit(OpCodes.Volatile); - EmitLdind(il, tw.TypeAsLocalOrStackType); + EmitLdind(il, tw.TypeAsLocalOrStackType.AsReflection()); } else { // Java volatile semantics require atomicity, CLR volatile semantics do not - var mi = typeof(Unsafe).GetMethod(nameof(InterlockedRead), BindingFlags.NonPublic | BindingFlags.Static, null, new[] { tw.TypeAsTBD.MakeByRefType() }, null); + var mi = typeof(Unsafe).GetMethod(nameof(InterlockedRead), BindingFlags.NonPublic | BindingFlags.Static, null, new[] { tw.TypeAsTBD.MakeByRefType().AsReflection() }, null); il.Emit(OpCodes.Call, mi); } @@ -1912,8 +1912,8 @@ static object GetArrayObjectVolatile(object[] array, long offset) /// static Delegate CreatePutArrayVolatileDelegate(RuntimeJavaType tw) { - var et = tw.IsPrimitive ? tw.TypeAsTBD : typeof(object); - var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD, true, typeof(void), new[] { typeof(object[]), typeof(long), et }); + var et = tw.IsPrimitive ? tw.TypeAsTBD.AsReflection() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.AsReflection(), true, typeof(void), new[] { typeof(object[]), typeof(long), et }); var il = dm.GetILGenerator(); // load reference to element @@ -1923,19 +1923,19 @@ static Delegate CreatePutArrayVolatileDelegate(RuntimeJavaType tw) il.Emit(OpCodes.Ldc_I4, ArrayIndexScale(tw.MakeArrayType(1))); il.Emit(OpCodes.Div); il.Emit(OpCodes.Conv_Ovf_I); - il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType); + il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.AsReflection()); il.Emit(OpCodes.Ldarg_2); if (tw.IsWidePrimitive == false) { il.Emit(OpCodes.Volatile); - EmitStind(il, tw.TypeAsLocalOrStackType); + EmitStind(il, tw.TypeAsLocalOrStackType.AsReflection()); } else { // Java volatile semantics require atomicity, CLR volatile semantics do not - var mi = typeof(Interlocked).GetMethod(nameof(Interlocked.Exchange), new[] { tw.TypeAsTBD.MakeByRefType() }); + var mi = typeof(Interlocked).GetMethod(nameof(Interlocked.Exchange), new[] { tw.TypeAsTBD.MakeByRefType().AsReflection() }); il.Emit(OpCodes.Call, mi); } diff --git a/src/IKVM.Runtime/LambdaMetafactory.cs b/src/IKVM.Runtime/LambdaMetafactory.cs index ea553973bc..50877f45be 100644 --- a/src/IKVM.Runtime/LambdaMetafactory.cs +++ b/src/IKVM.Runtime/LambdaMetafactory.cs @@ -27,17 +27,16 @@ Jeroen Frijters using IKVM.ByteCode; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; using Type = IKVM.Reflection.Type; #else using System.Reflection; using System.Reflection.Emit; - #endif namespace IKVM.Runtime @@ -46,16 +45,17 @@ namespace IKVM.Runtime sealed class LambdaMetafactory { - private MethodBuilder getInstance; + private IMethodSymbolBuilder getInstance; internal static bool Emit(RuntimeByteCodeJavaType.FinishContext context, ClassFile classFile, int constantPoolIndex, ClassFile.ConstantPoolItemInvokeDynamic cpi, CodeEmitter ilgen) { - ClassFile.BootstrapMethod bsm = classFile.GetBootstrapMethod(cpi.BootstrapMethod); + var bsm = classFile.GetBootstrapMethod(cpi.BootstrapMethod); if (!IsLambdaMetafactory(classFile, bsm) && !IsLambdaAltMetafactory(classFile, bsm)) { return false; } - LambdaMetafactory lmf = context.GetValue(constantPoolIndex); + + var lmf = context.GetValue(constantPoolIndex); if (lmf.getInstance == null && !lmf.EmitImpl(context, classFile, cpi, bsm, ilgen)) { #if IMPORTER @@ -64,6 +64,7 @@ internal static bool Emit(RuntimeByteCodeJavaType.FinishContext context, ClassFi #endif return false; } + ilgen.Emit(OpCodes.Call, lmf.getInstance); return true; } @@ -166,6 +167,7 @@ private bool EmitImpl(RuntimeByteCodeJavaType.FinishContext context, ClassFile c return false; } } + RuntimeJavaMethod interfaceMethod = null; List methods = new List(); foreach (RuntimeJavaMethod mw in methodList) @@ -186,7 +188,7 @@ private bool EmitImpl(RuntimeByteCodeJavaType.FinishContext context, ClassFile c return false; } - TypeBuilder tb = context.DefineAnonymousClass(); + var tb = context.DefineAnonymousClass(); // we're not implementing the interfaces recursively (because we don't care about .NET Compact anymore), // but should we decide to do that, we'd need to somehow communicate to AnonymousTypeWrapper what the 'real' interface is tb.AddInterfaceImplementation(interfaceType.TypeAsBaseType); @@ -194,10 +196,10 @@ private bool EmitImpl(RuntimeByteCodeJavaType.FinishContext context, ClassFile c { tb.AddInterfaceImplementation(context.Context.JavaBase.TypeOfJavaIoSerializable.TypeAsBaseType); } - foreach (RuntimeJavaType marker in markers) - { + + foreach (var marker in markers) tb.AddInterfaceImplementation(marker.TypeAsBaseType); - } + getInstance = CreateConstructorAndDispatch(context, cpi, tb, methods, implParameters, samMethodType, implMethod, instantiatedMethodType, serializable); AddDefaultInterfaceMethods(context, methodList, tb); return true; @@ -216,11 +218,13 @@ private static bool CheckConstraints(ClassFile.ConstantPoolItemMethodType instan Fail("instantiatedMethodType <= methodType"); return false; } + if (args.Length + methodType.GetArgTypes().Length != implParameters.Length) { Fail("K + N = M"); return false; } + for (int i = 0, K = args.Length; i < K; i++) { if (args[i] == implParameters[i]) @@ -233,6 +237,7 @@ private static bool CheckConstraints(ClassFile.ConstantPoolItemMethodType instan return false; } } + for (int i = 0, N = methodType.GetArgTypes().Length, k = args.Length; i < N; i++) { if (!IsAdaptable(instantiatedMethodType.GetArgTypes()[i], implParameters[i + k], false)) @@ -241,17 +246,17 @@ private static bool CheckConstraints(ClassFile.ConstantPoolItemMethodType instan return false; } } + return true; } private static RuntimeJavaType[] GetImplParameters(ClassFile.ConstantPoolItemMethodHandle implMethod) { - RuntimeJavaMethod mw = (RuntimeJavaMethod)implMethod.Member; - RuntimeJavaType[] parameters = mw.GetParameters(); + var mw = (RuntimeJavaMethod)implMethod.Member; + var parameters = mw.GetParameters(); if (mw.IsStatic || mw.IsConstructor) - { return parameters; - } + return ArrayUtil.Concat(mw.DeclaringType, parameters); } @@ -313,7 +318,7 @@ private static bool IsAdaptable(RuntimeJavaType Q, RuntimeJavaType S, bool isRet if (S.IsPrimitive) { // If Q is a primitive wrapper, check that Primitive(Q) can be widened to S - RuntimeJavaType primitive = GetPrimitiveFromWrapper(Q); + var primitive = GetPrimitiveFromWrapper(Q); return primitive != null && IsAdaptable(primitive, S, isReturn); } else @@ -377,8 +382,9 @@ private static RuntimeJavaType GetPrimitiveFromWrapper(RuntimeJavaType wrapper) private static bool IsSubTypeOf(ClassFile.ConstantPoolItemMethodType instantiatedMethodType, ClassFile.ConstantPoolItemMethodType samMethodType) { - RuntimeJavaType[] T = instantiatedMethodType.GetArgTypes(); - RuntimeJavaType[] U = samMethodType.GetArgTypes(); + var T = instantiatedMethodType.GetArgTypes(); + var U = samMethodType.GetArgTypes(); + if (T.Length != U.Length) { return false; @@ -390,34 +396,34 @@ private static bool IsSubTypeOf(ClassFile.ConstantPoolItemMethodType instantiate return false; } } - RuntimeJavaType Rt = instantiatedMethodType.GetRetType(); - RuntimeJavaType Ru = samMethodType.GetRetType(); + + var Rt = instantiatedMethodType.GetRetType(); + var Ru = samMethodType.GetRetType(); return Rt.IsAssignableTo(Ru); } - private static MethodBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaType.FinishContext context, ClassFile.ConstantPoolItemInvokeDynamic cpi, TypeBuilder tb, + private static IMethodSymbolBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaType.FinishContext context, ClassFile.ConstantPoolItemInvokeDynamic cpi, ITypeSymbolBuilder tb, List methods, RuntimeJavaType[] implParameters, ClassFile.ConstantPoolItemMethodType samMethodType, ClassFile.ConstantPoolItemMethodHandle implMethod, ClassFile.ConstantPoolItemMethodType instantiatedMethodType, bool serializable) { - RuntimeJavaType[] args = cpi.GetArgTypes(); + var args = cpi.GetArgTypes(); // captured values - Type[] capturedTypes = new Type[args.Length]; - FieldBuilder[] capturedFields = new FieldBuilder[capturedTypes.Length]; + var capturedTypes = new ITypeSymbol[args.Length]; + var capturedFields = new IFieldSymbolBuilder[capturedTypes.Length]; for (int i = 0; i < capturedTypes.Length; i++) { capturedTypes[i] = args[i].TypeAsSignatureType; - FieldAttributes attr = FieldAttributes.Private; + var attr = FieldAttributes.Private; if (i > 0 || !args[0].IsGhost) - { attr |= FieldAttributes.InitOnly; - } + capturedFields[i] = tb.DefineField("arg$" + (i + 1), capturedTypes[i], attr); } // constructor - MethodBuilder ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, capturedTypes); - CodeEmitter ilgen = context.Context.CodeEmitterFactory.Create(ctor); + var ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, capturedTypes); + var ilgen = context.Context.CodeEmitterFactory.Create(ctor); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Call, context.Context.Types.Object.GetConstructor([])); for (int i = 0; i < capturedTypes.Length; i++) @@ -430,17 +436,17 @@ private static MethodBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaTyp ilgen.DoEmit(); // instance getter - MethodBuilder getInstance = tb.DefineMethod("__", MethodAttributes.Assembly | MethodAttributes.Static, cpi.GetRetType().TypeAsBaseType, capturedTypes); - CodeEmitter ilgenGet = context.Context.CodeEmitterFactory.Create(getInstance); + var getInstance = tb.DefineMethod("__", MethodAttributes.Assembly | MethodAttributes.Static, cpi.GetRetType().TypeAsBaseType, capturedTypes); + var ilgenGet = context.Context.CodeEmitterFactory.Create(getInstance); if (capturedTypes.Length == 0) { // use singleton for lambdas with no captures - FieldBuilder instField = tb.DefineField("inst", tb, FieldAttributes.Private | FieldAttributes.Static); + var instField = tb.DefineField("inst", tb, FieldAttributes.Private | FieldAttributes.Static); // static constructor - MethodBuilder cctor = ReflectUtil.DefineTypeInitializer(tb, context.TypeWrapper.ClassLoader); - CodeEmitter ilgenCCtor = context.Context.CodeEmitterFactory.Create(cctor); + var cctor = ReflectUtil.DefineTypeInitializer(tb, context.TypeWrapper.ClassLoader); + var ilgenCCtor = context.Context.CodeEmitterFactory.Create(cctor); ilgenCCtor.Emit(OpCodes.Newobj, ctor); ilgenCCtor.Emit(OpCodes.Stsfld, instField); ilgenCCtor.Emit(OpCodes.Ret); @@ -471,7 +477,7 @@ private static MethodBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaTyp // writeReplace method if (serializable) { - MethodBuilder writeReplace = tb.DefineMethod("writeReplace", MethodAttributes.Private, context.Context.Types.Object, []); + var writeReplace = tb.DefineMethod("writeReplace", MethodAttributes.Private, context.Context.Types.Object, []); ilgen = context.Context.CodeEmitterFactory.Create(writeReplace); context.TypeWrapper.EmitClassLiteral(ilgen); ilgen.Emit(OpCodes.Ldstr, cpi.GetRetType().Name.Replace('.', '/')); @@ -500,8 +506,7 @@ private static MethodBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaTyp } ilgen.Emit(OpCodes.Stelem, context.Context.Types.Object); } - RuntimeJavaMethod ctorSerializedLambda = context.Context.ClassLoaderFactory.LoadClassCritical("java.lang.invoke.SerializedLambda").GetMethodWrapper(StringConstants.INIT, - "(Ljava.lang.Class;Ljava.lang.String;Ljava.lang.String;Ljava.lang.String;ILjava.lang.String;Ljava.lang.String;Ljava.lang.String;Ljava.lang.String;[Ljava.lang.Object;)V", false); + var ctorSerializedLambda = context.Context.ClassLoaderFactory.LoadClassCritical("java.lang.invoke.SerializedLambda").GetMethodWrapper(StringConstants.INIT, "(Ljava.lang.Class;Ljava.lang.String;Ljava.lang.String;Ljava.lang.String;ILjava.lang.String;Ljava.lang.String;Ljava.lang.String;Ljava.lang.String;[Ljava.lang.Object;)V", false); ctorSerializedLambda.Link(); ctorSerializedLambda.EmitNewobj(ilgen); ilgen.Emit(OpCodes.Ret); @@ -518,10 +523,10 @@ private static MethodBuilder CreateConstructorAndDispatch(RuntimeByteCodeJavaTyp return getInstance; } - private static void EmitDispatch(RuntimeByteCodeJavaType.FinishContext context, RuntimeJavaType[] args, TypeBuilder tb, RuntimeJavaMethod interfaceMethod, RuntimeJavaType[] implParameters, - ClassFile.ConstantPoolItemMethodHandle implMethod, ClassFile.ConstantPoolItemMethodType instantiatedMethodType, FieldBuilder[] capturedFields) + private static void EmitDispatch(RuntimeByteCodeJavaType.FinishContext context, RuntimeJavaType[] args, ITypeSymbolBuilder tb, RuntimeJavaMethod interfaceMethod, RuntimeJavaType[] implParameters, + ClassFile.ConstantPoolItemMethodHandle implMethod, ClassFile.ConstantPoolItemMethodType instantiatedMethodType, IFieldSymbolBuilder[] capturedFields) { - MethodBuilder mb = interfaceMethod.GetDefineMethodHelper().DefineMethod(context.TypeWrapper, tb, interfaceMethod.Name, MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final); + var mb = interfaceMethod.GetDefineMethodHelper().DefineMethod(context.TypeWrapper, tb, interfaceMethod.Name, MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final); if (interfaceMethod.Name != interfaceMethod.RealName) { tb.DefineMethodOverride(mb, (MethodInfo)interfaceMethod.GetMethod()); @@ -529,7 +534,7 @@ private static void EmitDispatch(RuntimeByteCodeJavaType.FinishContext context, context.Context.AttributeHelper.HideFromJava(mb); - CodeEmitter ilgen = context.Context.CodeEmitterFactory.Create(mb); + var ilgen = context.Context.CodeEmitterFactory.Create(mb); for (int i = 0; i < capturedFields.Length; i++) { ilgen.EmitLdarg(0); @@ -732,34 +737,34 @@ private static void EmitUnboxNumber(RuntimeContext context, CodeEmitter ilgen, s mw.EmitCallvirt(ilgen); } - private static void AddDefaultInterfaceMethods(RuntimeByteCodeJavaType.FinishContext context, RuntimeJavaMethod[] methodList, TypeBuilder tb) + private static void AddDefaultInterfaceMethods(RuntimeByteCodeJavaType.FinishContext context, RuntimeJavaMethod[] methodList, ITypeSymbolBuilder tb) { // we use special name to hide these from Java reflection const MethodAttributes attr = MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final | MethodAttributes.SpecialName; - RuntimeJavaTypeFactory factory = context.TypeWrapper.ClassLoader.GetTypeWrapperFactory(); - foreach (RuntimeJavaMethod mw in methodList) + + var factory = context.TypeWrapper.ClassLoader.GetTypeWrapperFactory(); + foreach (var mw in methodList) { if (!mw.IsAbstract) { - MethodBuilder mb = mw.GetDefineMethodHelper().DefineMethod(factory, tb, mw.Name, attr); + var mb = mw.GetDefineMethodHelper().DefineMethod(factory, tb, mw.Name, attr); if (mw.Name != mw.RealName) - { - tb.DefineMethodOverride(mb, (MethodInfo)mw.GetMethod()); - } + tb.DefineMethodOverride(mb, (IMethodSymbol)mw.GetMethod()); + context.EmitCallDefaultInterfaceMethod(mb, mw); } else if (IsObjectMethod(mw)) { - MethodBuilder mb = mw.GetDefineMethodHelper().DefineMethod(factory, tb, mw.Name, attr); + var mb = mw.GetDefineMethodHelper().DefineMethod(factory, tb, mw.Name, attr); if (mw.Name != mw.RealName) - { - tb.DefineMethodOverride(mb, (MethodInfo)mw.GetMethod()); - } - CodeEmitter ilgen = context.Context.CodeEmitterFactory.Create(mb); + tb.DefineMethodOverride(mb, (IMethodSymbol)mw.GetMethod()); + + var ilgen = context.Context.CodeEmitterFactory.Create(mb); for (int i = 0, count = mw.GetParameters().Length; i <= count; i++) { ilgen.EmitLdarg(i); } + context.Context.JavaBase.TypeOfJavaLangObject.GetMethodWrapper(mw.Name, mw.Signature, false).EmitCallvirt(ilgen); ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); @@ -780,11 +785,11 @@ static bool IsSupportedImplMethod(ClassFile.ConstantPoolItemMethodHandle implMet default: return false; } - RuntimeJavaMethod mw = (RuntimeJavaMethod)implMethod.Member; + + var mw = (RuntimeJavaMethod)implMethod.Member; if (mw == null || mw.HasCallerID || RuntimeByteCodeJavaType.RequiresDynamicReflectionCallerClass(mw.DeclaringType.Name, mw.Name, mw.Signature)) - { return false; - } + RuntimeJavaType instance; if (mw.IsConstructor) { @@ -803,10 +808,12 @@ static bool IsSupportedImplMethod(ClassFile.ConstantPoolItemMethodHandle implMet return false; } } + if (!mw.IsAccessibleFrom(mw.DeclaringType, caller, instance)) { return false; } + mw.Link(); return true; } @@ -827,7 +834,7 @@ private static bool CheckSupportedInterfaces(RuntimeJavaType caller, RuntimeJava methodList = null; return false; } - Dictionary methods = new Dictionary(); + var methods = new Dictionary(); int abstractMethodCount = 0; int bridgeMethodCount = 0; if (GatherAllInterfaceMethods(tw, bridges, methods, ref abstractMethodCount, ref bridgeMethodCount) && abstractMethodCount == 1) @@ -860,11 +867,11 @@ private static bool CheckSupportedInterfaces(RuntimeJavaType caller, RuntimeJava private static bool GatherAllInterfaceMethods(RuntimeJavaType tw, ClassFile.ConstantPoolItemMethodType[] bridges, Dictionary methods, ref int abstractMethodCount, ref int bridgeMethodCount) { - foreach (RuntimeJavaMethod mw in tw.GetMethods()) + foreach (var mw in tw.GetMethods()) { if (mw.IsVirtual) { - RuntimeMirandaJavaMethod mmw = mw as RuntimeMirandaJavaMethod; + var mmw = mw as RuntimeMirandaJavaMethod; if (mmw != null) { if (mmw.Error != null) @@ -873,7 +880,8 @@ private static bool GatherAllInterfaceMethods(RuntimeJavaType tw, ClassFile.Cons } continue; } - MethodKey key = new MethodKey("", mw.Name, mw.Signature); + + var key = new MethodKey("", mw.Name, mw.Signature); RuntimeJavaMethod current; if (methods.TryGetValue(key, out current)) { @@ -898,6 +906,7 @@ private static bool GatherAllInterfaceMethods(RuntimeJavaType tw, ClassFile.Cons } } } + mw.Link(); if (mw.GetMethod() == null) { @@ -909,13 +918,15 @@ private static bool GatherAllInterfaceMethods(RuntimeJavaType tw, ClassFile.Cons } } } - foreach (RuntimeJavaType tw1 in tw.Interfaces) + + foreach (var tw1 in tw.Interfaces) { if (!GatherAllInterfaceMethods(tw1, bridges, methods, ref abstractMethodCount, ref bridgeMethodCount)) { return false; } } + return true; } @@ -928,6 +939,7 @@ private static bool IsBridge(RuntimeJavaMethod mw, ClassFile.ConstantPoolItemMet return true; } } + return false; } diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index 44c812677a..f684f71ef3 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -156,7 +156,7 @@ internal static IMethodSymbolBuilder DefineConstructor(ITypeSymbolBuilder tb, Sy /// /// /// - internal static bool CanOwnDynamicMethod(ITypeSymbol type) + internal static bool CanOwnDynamicMethod(Type type) { return type != null && !type.IsInterface && !type.HasElementType && !type.IsGenericTypeDefinition && !type.IsGenericParameter; } @@ -192,6 +192,15 @@ private static bool MatchTypes(ITypeSymbol[] t1, ITypeSymbol[] t2) return false; } + internal static bool IsVector(Type type) + { +#if NET + return type.IsSZArray; +#else + return type.IsArray && type.Name.EndsWith("[]"); +#endif + } + #if IMPORTER internal static ITypeSymbol GetMissingType(ITypeSymbol type) diff --git a/src/IKVM.Runtime/RuntimeArrayJavaType.cs b/src/IKVM.Runtime/RuntimeArrayJavaType.cs index 95cd1a6c5b..5295a96b6e 100644 --- a/src/IKVM.Runtime/RuntimeArrayJavaType.cs +++ b/src/IKVM.Runtime/RuntimeArrayJavaType.cs @@ -180,18 +180,6 @@ internal override RuntimeJavaType GetUltimateElementTypeWrapper() return ultimateElementTypeWrapper; } - internal static ITypeSymbol MakeArrayType(ITypeSymbol type, int dims) - { - // NOTE this is not just an optimization, but it is also required to - // make sure that ReflectionOnly types stay ReflectionOnly types - // (in particular instantiations of generic types from mscorlib that - // have ReflectionOnly type parameters). - for (int i = 0; i < dims; i++) - type = type.MakeArrayType(); - - return type; - } - } } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index 9443a3efa8..1001ff45ac 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -28,15 +28,12 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.ByteCode; using IKVM.ByteCode.Decoding; -using IKVM.CoreLib.Diagnostics; - +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; -using Type = IKVM.Reflection.Type; using DynamicOrAotTypeWrapper = IKVM.Tools.Importer.RuntimeImportByteCodeJavaType; #else using System.Reflection; @@ -58,15 +55,15 @@ internal sealed class FinishContext readonly RuntimeJavaType host; readonly ClassFile classFile; readonly DynamicOrAotTypeWrapper wrapper; - readonly TypeBuilder typeBuilder; - List nestedTypeBuilders; - MethodInfo callerIDMethod; + readonly ITypeSymbolBuilder typeBuilder; + List nestedTypeBuilders; + IMethodSymbol callerIDMethod; List items; - Dictionary arfuMap; - Dictionary invokespecialstubcache; - Dictionary dynamicClassLiteral; + Dictionary arfuMap; + Dictionary invokespecialstubcache; + Dictionary dynamicClassLiteral; #if IMPORTER - TypeBuilder interfaceHelperMethodsTypeBuilder; + ITypeSymbolBuilder interfaceHelperMethodsTypeBuilder; #else List liveObjects; #endif @@ -85,7 +82,7 @@ private struct Item /// /// /// - internal FinishContext(RuntimeContext context, RuntimeJavaType host, ClassFile classFile, DynamicOrAotTypeWrapper wrapper, TypeBuilder typeBuilder) + internal FinishContext(RuntimeContext context, RuntimeJavaType host, ClassFile classFile, DynamicOrAotTypeWrapper wrapper, ITypeSymbolBuilder typeBuilder) { this.context = context; this.host = host; @@ -124,7 +121,7 @@ internal void EmitDynamicClassLiteral(CodeEmitter ilgen, RuntimeJavaType tw, boo { Debug.Assert(tw.IsUnloadable); - dynamicClassLiteral ??= new Dictionary(); + dynamicClassLiteral ??= new Dictionary(); var cacheKey = tw.Name; if (dynamicCallerID) @@ -183,13 +180,13 @@ internal void EmitCallerID(CodeEmitter ilgen, bool dynamic) private void CreateGetCallerID() { - RuntimeJavaType tw = context.JavaBase.TypeOfIkvmInternalCallerID; - FieldBuilder callerIDField = typeBuilder.DefineField("__", tw.TypeAsSignatureType, FieldAttributes.Private | FieldAttributes.Static | FieldAttributes.SpecialName); - MethodBuilder mb = DefineHelperMethod("__", tw.TypeAsSignatureType, []); + var tw = context.JavaBase.TypeOfIkvmInternalCallerID; + var callerIDField = typeBuilder.DefineField("__", tw.TypeAsSignatureType, FieldAttributes.Private | FieldAttributes.Static | FieldAttributes.SpecialName); + var mb = DefineHelperMethod("__", tw.TypeAsSignatureType, []); callerIDMethod = mb; - CodeEmitter ilgen = context.CodeEmitterFactory.Create(mb); + var ilgen = context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldsfld, callerIDField); - CodeEmitterLabel done = ilgen.DefineLabel(); + var done = ilgen.DefineLabel(); ilgen.EmitBrtrue(done); EmitCallerIDInitialization(ilgen, callerIDField); ilgen.MarkLabel(done); @@ -232,7 +229,7 @@ internal Type FinishImpl() { foreach (RuntimeJavaMethod mw in parent.GetMethods()) { - var mi = mw.GetMethod() as MethodInfo; + var mi = mw.GetMethod() as IMethodSymbol; if (mi != null && mi.IsAbstract && !mi.DeclaringType.IsInterface) { bool needStub = false; @@ -268,13 +265,13 @@ internal Type FinishImpl() // NOTE in Sun's JRE 1.4.1 this method cannot be overridden by subclasses, // but I think this is a bug, so we'll support it anyway. string name = mi.Name; - MethodAttributes attr = mi.Attributes & ~(MethodAttributes.Abstract | MethodAttributes.NewSlot); + var attr = mi.Attributes & ~(MethodAttributes.Abstract | MethodAttributes.NewSlot); if (needRename) { name = "__<>" + name + "/" + mi.DeclaringType.FullName; attr = MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot; } - MethodBuilder mb = mw.GetDefineMethodHelper().DefineMethod(wrapper, typeBuilder, name, attr); + var mb = mw.GetDefineMethodHelper().DefineMethod(wrapper, typeBuilder, name, attr); if (needRename) { typeBuilder.DefineMethodOverride(mb, mi); @@ -300,7 +297,7 @@ internal Type FinishImpl() for (int i = 0; i < classFile.Methods.Length; i++) { var m = classFile.Methods[i]; - var mb = (MethodBuilder)methods[i].GetMethod(); + var mb = (IMethodSymbolBuilder)methods[i].GetMethod(); if (mb == null) { // method doesn't really exist (e.g. delegate constructor or that is optimized away) @@ -386,7 +383,7 @@ internal Type FinishImpl() } #endif - MethodInfo nativeMethod = null; + IMethodSymbol nativeMethod = null; var args = methods[i].GetParameters(); var nargs = args; @@ -512,7 +509,7 @@ internal Type FinishImpl() { if (m.IsVirtual && classFile.IsInterface) { - mb = (MethodBuilder)RuntimeDefaultInterfaceJavaMethod.GetImpl(methods[i]); + mb = (IMethodSymbolBuilder)RuntimeDefaultInterfaceJavaMethod.GetImpl(methods[i]); #if IMPORTER CreateDefaultMethodInterop(ref tbDefaultMethods, mb, methods[i]); #endif @@ -561,10 +558,10 @@ internal Type FinishImpl() if (clinitIndex != -1 || (basehasclinit && !classFile.IsInterface) || classFile.HasInitializedFields) { - MethodBuilder cb; + IMethodSymbolBuilder cb; if (clinitIndex != -1) { - cb = (MethodBuilder)methods[clinitIndex].GetMethod(); + cb = (IMethodSymbolBuilder)methods[clinitIndex].GetMethod(); } else { @@ -662,7 +659,7 @@ internal Type FinishImpl() for (int i = 0; i < classFile.Methods.Length; i++) { var m = classFile.Methods[i]; - var mb = (MethodBuilder)methods[i].GetMethod(); + var mb = (IMethodSymbolBuilder)methods[i].GetMethod(); if (mb == null) continue; @@ -708,7 +705,7 @@ internal Type FinishImpl() } else { - annotation.Apply(wrapper.ClassLoader, (FieldBuilder)fields[i].GetField(), def); + annotation.Apply(wrapper.ClassLoader, (IFieldSymbolBuilder)fields[i].GetField(), def); } } } @@ -730,22 +727,21 @@ internal Type FinishImpl() AddImplementsAttribute(); #endif - Type type; Profiler.Enter("TypeBuilder.CreateType"); try { - type = typeBuilder.CreateType(); + typeBuilder.Complete(); if (nestedTypeBuilders != null) { context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicAtomicReferenceFieldUpdater").Finish(); context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicThreadLocal").Finish(); - foreach (TypeBuilder tb in nestedTypeBuilders) - tb.CreateType(); + foreach (var tb in nestedTypeBuilders) + tb.Complete(); } #if !IMPORTER if (liveObjects != null) - typeof(IKVM.Runtime.LiveObjectHolder<>).MakeGenericType(type).GetField("values", BindingFlags.Static | BindingFlags.Public).SetValue(null, liveObjects.ToArray()); + context.Resolver.ResolveRuntimeType("IKVM.Runtime.LiveObjectHolder`1").GetField("values", BindingFlags.Static | BindingFlags.Public).AsReflection().SetValue(liveObjects.ToArray()); #endif } finally @@ -754,14 +750,14 @@ internal Type FinishImpl() } #if !IMPORTER // When we're statically compiling we don't need to set the wrapper here, because we've already done so for the typeBuilder earlier. - context.ClassLoaderFactory.SetWrapperForType(type, wrapper); + context.ClassLoaderFactory.SetWrapperForType(typeBuilder, wrapper); #endif #if IMPORTER wrapper.FinishGhostStep2(); #endif - return type; + return typeBuilder; } #if IMPORTER @@ -1006,7 +1002,7 @@ private bool EmitInterlockedCompareAndSet(RuntimeJavaMethod method, string field } #endif - private void AddMethodParameterInfo(ClassFile.Method m, RuntimeJavaMethod mw, MethodBuilder mb, out string[] parameterNames) + private void AddMethodParameterInfo(ClassFile.Method m, RuntimeJavaMethod mw, IMethodSymbolBuilder mb, out string[] parameterNames) { parameterNames = null; ParameterBuilder[] parameterBuilders = null; @@ -1116,7 +1112,7 @@ void AddInterfaceMethodsInterop(RuntimeJavaMethod[] methods) } - private void CreateDefaultMethodInterop(ref TypeBuilder tbDefaultMethods, MethodBuilder defaultMethod, RuntimeJavaMethod mw) + private void CreateDefaultMethodInterop(ref TypeBuilder tbDefaultMethods, IMethodSymbolBuilder defaultMethod, RuntimeJavaMethod mw) { if (!ParametersAreAccessible(mw)) { @@ -1169,7 +1165,7 @@ private void AddInheritedDefaultInterfaceMethods(RuntimeJavaMethod[] methods) if (mmw.Error == null && !mmw.BaseMethod.IsAbstract) { // we inherited a default interface method, so we need to forward the miranda method to the default method - MethodBuilder mb = (MethodBuilder)mmw.GetMethod(); + var mb = (IMethodSymbolBuilder)mmw.GetMethod(); if (classFile.IsInterface) { // if we're an interface with a default miranda method, we need to create a new default method that forwards to the original @@ -1182,7 +1178,7 @@ private void AddInheritedDefaultInterfaceMethods(RuntimeJavaMethod[] methods) } } - internal void EmitCallDefaultInterfaceMethod(MethodBuilder mb, RuntimeJavaMethod defaultMethod) + internal void EmitCallDefaultInterfaceMethod(IMethodSymbolBuilder mb, RuntimeJavaMethod defaultMethod) { CodeEmitter ilgen = context.CodeEmitterFactory.Create(mb); if (defaultMethod.DeclaringType.IsGhost) @@ -1287,7 +1283,7 @@ void GenerateAccessStub(RuntimeJavaField fw, bool type1) // we attach the AccessStub custom modifier because the C# compiler prefers fields without custom modifiers // so if this class defines a field with the same name, that will be preferred over this one by the C# compiler - var fb = typeBuilder.DefineField(fw.Name, fw.FieldTypeWrapper.TypeAsSignatureType, null, new Type[] { context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName).AsReflection() }, attribs); + var fb = typeBuilder.DefineField(fw.Name, fw.FieldTypeWrapper.TypeAsSignatureType, null, new ITypeSymbol[] { context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName) }, attribs); context.AttributeHelper.HideFromReflection(fb); fb.SetConstant(cjf.GetConstantValue()); } @@ -1327,7 +1323,7 @@ void GenerateAccessStub(RuntimeJavaField fw, bool type1) attribs |= MethodAttributes.Private; } - var setter = typeBuilder.DefineMethod("set_" + fw.Name, attribs, CallingConventions.Standard, null, null, null, new Type[] { propType }, null, new Type[][] { modopt2 }); + var setter = typeBuilder.DefineMethod("set_" + fw.Name, attribs, CallingConventions.Standard, null, null, null, new ITypeSymbol[] { propType }, null, new ITypeSymbol[][] { modopt2 }); context.AttributeHelper.HideFromJava(setter); pb.SetSetMethod(setter); ilgen = context.CodeEmitterFactory.Create(setter); @@ -1393,9 +1389,9 @@ void GenerateAccessStub(int id, RuntimeJavaMethod mw, bool virt, bool type1) stubattribs |= MethodAttributes.Static; var parameters = mw.GetParameters(); - var realParameterTypes = new Type[parameters.Length]; - var parameterTypes = new Type[parameters.Length]; - var modopt = new Type[parameters.Length][]; + var realParameterTypes = new ITypeSymbol[parameters.Length]; + var parameterTypes = new ITypeSymbol[parameters.Length]; + var modopt = new ITypeSymbol[parameters.Length][]; for (int i = 0; i < parameters.Length; i++) { realParameterTypes[i] = parameters[i].TypeAsSignatureType; @@ -1538,7 +1534,7 @@ void ImplementInterfaceMethodStubImpl(RuntimeJavaMethod ifmethod, bool baseClass var ilgen = context.CodeEmitterFactory.Create(mb); ilgen.EmitThrow("java.lang.LinkageError", wrapper.Name + "." + ifmethod.Name + ifmethod.Signature); ilgen.DoEmit(); - typeBuilder.DefineMethodOverride(mb, (MethodInfo)ifmethod.GetMethod()); + typeBuilder.DefineMethodOverride(mb, (IMethodSymbol)ifmethod.GetMethod()); return; } } @@ -1555,7 +1551,7 @@ void ImplementInterfaceMethodStubImpl(RuntimeJavaMethod ifmethod, bool baseClass var ilgen = context.CodeEmitterFactory.Create(mb); ilgen.EmitThrow("java.lang.IllegalAccessError", wrapper.Name + "." + ifmethod.Name + ifmethod.Signature); ilgen.DoEmit(); - typeBuilder.DefineMethodOverride(mb, (MethodInfo)ifmethod.GetMethod()); + typeBuilder.DefineMethodOverride(mb, (IMethodSymbol)ifmethod.GetMethod()); wrapper.SetHasIncompleteInterfaceImplementation(); } else if (mce.GetMethod() == null || mce.RealName != ifmethod.RealName || mce.IsInternal || !ReflectUtil.IsSameAssembly(mce.DeclaringType.TypeAsTBD, typeBuilder) || CheckRequireOverrideStub(mce, ifmethod)) @@ -1567,7 +1563,7 @@ void ImplementInterfaceMethodStubImpl(RuntimeJavaMethod ifmethod, bool baseClass } else if (baseClassInterface && mce.DeclaringType == wrapper) { - typeBuilder.DefineMethodOverride((MethodInfo)mce.GetMethod(), (MethodInfo)ifmethod.GetMethod()); + typeBuilder.DefineMethodOverride((IMethodSymbol)mce.GetMethod(), (IMethodSymbol)ifmethod.GetMethod()); } } else @@ -1581,14 +1577,14 @@ void ImplementInterfaceMethodStubImpl(RuntimeJavaMethod ifmethod, bool baseClass var ilgen = context.CodeEmitterFactory.Create(mb); ilgen.EmitThrow("java.lang.AbstractMethodError", wrapper.Name + "." + ifmethod.Name + ifmethod.Signature); ilgen.DoEmit(); - typeBuilder.DefineMethodOverride(mb, (MethodInfo)ifmethod.GetMethod()); + typeBuilder.DefineMethodOverride(mb, (IMethodSymbol)ifmethod.GetMethod()); wrapper.SetHasIncompleteInterfaceImplementation(); wrapper.EmitLevel4Warning(HardError.AbstractMethodError, wrapper.Name + "." + ifmethod.Name + ifmethod.Signature); } } } - MethodBuilder DefineInterfaceStubMethod(string name, RuntimeJavaMethod mw) + IMethodSymbolBuilder DefineInterfaceStubMethod(string name, RuntimeJavaMethod mw) { return mw.GetDefineMethodHelper().DefineMethod(wrapper, typeBuilder, name, MethodAttributes.HideBySig | MethodAttributes.NewSlot | MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.Final); } @@ -1613,9 +1609,9 @@ static JniProxyBuilder() internal static void Generate(RuntimeByteCodeJavaType.FinishContext context, CodeEmitter ilGenerator, RuntimeByteCodeJavaType wrapper, RuntimeJavaMethod mw, TypeBuilder typeBuilder, ClassFile classFile, ClassFile.Method m, RuntimeJavaType[] args) { - TypeBuilder tb = mod.DefineType("__" + System.Threading.Interlocked.Increment(ref count), TypeAttributes.Public | TypeAttributes.Class); + var tb = mod.DefineType("__" + System.Threading.Interlocked.Increment(ref count), TypeAttributes.Public | TypeAttributes.Class); int instance = m.IsStatic ? 0 : 1; - Type[] argTypes = new Type[args.Length + instance + 1]; + var argTypes = new ITypeSymbolvvvvvvvvvvvvvvvv[args.Length + instance + 1]; if (instance != 0) { argTypes[0] = typeof(object); @@ -1626,9 +1622,10 @@ internal static void Generate(RuntimeByteCodeJavaType.FinishContext context, Cod // are public and so we can get away with replacing all other types with object. argTypes[i + instance] = !args[i].IsUnloadable && (args[i].IsPrimitive || args[i].IsGhost || args[i].IsNonPrimitiveValueType) ? args[i].TypeAsSignatureType : typeof(object); } + argTypes[argTypes.Length - 1] = context.context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType; - Type retType = !mw.ReturnType.IsUnloadable && (mw.ReturnType.IsPrimitive || mw.ReturnType.IsGhost || mw.ReturnType.IsNonPrimitiveValueType) ? mw.ReturnType.TypeAsSignatureType : typeof(object); - MethodBuilder mb = tb.DefineMethod("method", MethodAttributes.Public | MethodAttributes.Static, retType, argTypes); + var retType = !mw.ReturnType.IsUnloadable && (mw.ReturnType.IsPrimitive || mw.ReturnType.IsGhost || mw.ReturnType.IsNonPrimitiveValueType) ? mw.ReturnType.TypeAsSignatureType : typeof(object); + var mb = tb.DefineMethod("method", MethodAttributes.Public | MethodAttributes.Static, retType, argTypes); context.context.AttributeHelper.HideFromJava(mb); CodeEmitter ilgen = context.context.CodeEmitterFactory.Create(mb); new JniBuilder(context.context).Generate(context, ilgen, wrapper, mw, tb, classFile, m, args, true); @@ -1665,23 +1662,23 @@ public JniBuilder(RuntimeContext context) Type LocalRefStructType => context.Resolver.ResolveRuntimeType("IKVM.Runtime.JNI.JNIFrame").AsReflection(); - MethodInfo JniFuncPtrMethod => LocalRefStructType.GetMethod("GetFuncPtr"); + IMethodSymbol JniFuncPtrMethod => LocalRefStructType.GetMethod("GetFuncPtr"); - MethodInfo EnterLocalRefStructMethod => LocalRefStructType.GetMethod("Enter"); + IMethodSymbol EnterLocalRefStructMethod => LocalRefStructType.GetMethod("Enter"); - MethodInfo LeaveLocalRefStructMethod => LocalRefStructType.GetMethod("Leave"); + IMethodSymbol LeaveLocalRefStructMethod => LocalRefStructType.GetMethod("Leave"); - MethodInfo MakeLocalRefMethod => LocalRefStructType.GetMethod("MakeLocalRef"); + IMethodSymbol MakeLocalRefMethod => LocalRefStructType.GetMethod("MakeLocalRef"); - MethodInfo UnwrapLocalRefMethod => LocalRefStructType.GetMethod("UnwrapLocalRef"); + IMethodSymbol UnwrapLocalRefMethod => LocalRefStructType.GetMethod("UnwrapLocalRef"); - MethodInfo WriteLineMethod => context.Resolver.ResolveCoreType(typeof(Console).FullName).AsReflection().GetMethod("WriteLine", [context.Types.Object]); + IMethodSymbol WriteLineMethod => context.Resolver.ResolveCoreType(typeof(Console).FullName).GetMethod("WriteLine", [context.Types.Object]); - MethodInfo MonitorEnterMethod => context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).AsReflection().GetMethod("Enter", [context.Types.Object]); + IMethodSymbol MonitorEnterMethod => context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", [context.Types.Object]); - MethodInfo MonitorExitMethod => context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).AsReflection().GetMethod("Exit", [context.Types.Object]); + IMethodSymbol MonitorExitMethod => context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", [context.Types.Object]); - internal void Generate(RuntimeByteCodeJavaType.FinishContext context, CodeEmitter ilGenerator, RuntimeByteCodeJavaType wrapper, RuntimeJavaMethod mw, TypeBuilder typeBuilder, ClassFile classFile, ClassFile.Method m, RuntimeJavaType[] args, bool thruProxy) + internal void Generate(RuntimeByteCodeJavaType.FinishContext context, CodeEmitter ilGenerator, RuntimeByteCodeJavaType wrapper, RuntimeJavaMethod mw, ITypeSymbolBuilder typeBuilder, ClassFile classFile, ClassFile.Method m, RuntimeJavaType[] args, bool thruProxy) { CodeEmitterLocal syncObject = null; if (m.IsSynchronized && m.IsStatic) @@ -1734,7 +1731,7 @@ internal void Generate(RuntimeByteCodeJavaType.FinishContext context, CodeEmitte ilGenerator.Emit(OpCodes.Ldloc, jnienv); - var modargs = new Type[args.Length + 2]; + var modargs = new ITypeSymbol[args.Length + 2]; modargs[0] = context.context.Types.IntPtr; modargs[1] = context.context.Types.IntPtr; for (int i = 0; i < args.Length; i++) @@ -1861,7 +1858,7 @@ void EmitCallerIDStub(RuntimeJavaMethod mw, string[] parameterNames) { // we don't need to support custom modifiers, because there aren't any callerid methods that have parameter types that require a custom modifier var parameters = mw.GetParameters(); - var parameterTypes = new Type[parameters.Length]; + var parameterTypes = new ITypeSymbol[parameters.Length]; for (int i = 0; i < parameterTypes.Length; i++) parameterTypes[i] = parameters[i].TypeAsSignatureType; @@ -1910,7 +1907,7 @@ void EmitCallerIDStub(RuntimeJavaMethod mw, string[] parameterNames) } ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.Emit(OpCodes.Ldc_I4_0); - ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveCoreType(typeof(StackFrame).FullName).AsReflection().GetConstructor(new Type[] { context.Types.Int32, context.Types.Boolean })); + ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveCoreType(typeof(StackFrame).FullName).AsReflection().GetConstructor(new ITypeSymbol[] { context.Types.Int32, context.Types.Boolean })); var callerID = context.JavaBase.TypeOfIkvmInternalCallerID.GetMethodWrapper("create", "(Lcli.System.Diagnostics.StackFrame;)Likvm.internal.CallerID;", false); callerID.Link(); callerID.EmitCall(ilgen); @@ -1966,7 +1963,7 @@ void ImplementInterfaces(RuntimeJavaType[] interfaces, List int // if we implement a ghost interface, add an implicit conversion to the ghost reference value type if (iface.IsGhost && wrapper.IsPublic) { - var mb = typeBuilder.DefineMethod("op_Implicit", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, iface.TypeAsSignatureType, new Type[] { wrapper.TypeAsSignatureType }); + var mb = typeBuilder.DefineMethod("op_Implicit", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, iface.TypeAsSignatureType, new ITypeSymbol[] { wrapper.TypeAsSignatureType }); context.AttributeHelper.HideFromJava(mb); var ilgen = context.CodeEmitterFactory.Create(mb); var local = ilgen.DeclareLocal(iface.TypeAsSignatureType); @@ -2014,25 +2011,25 @@ void AddUnsupportedAbstractMethods() } } - void GenerateUnsupportedAbstractMethodStub(MethodBase mb) + void GenerateUnsupportedAbstractMethodStub(IMethodBaseSymbol mb) { var parameters = mb.GetParameters(); - var parameterTypes = new Type[parameters.Length]; + var parameterTypes = new ITypeSymbol[parameters.Length]; for (int i = 0; i < parameters.Length; i++) parameterTypes[i] = parameters[i].ParameterType; var attr = MethodAttributes.NewSlot | MethodAttributes.Virtual | MethodAttributes.Private; - var m = typeBuilder.DefineMethod("__" + mb.DeclaringType.FullName + "/" + mb.Name, attr, ((MethodInfo)mb).ReturnType, parameterTypes); + var m = typeBuilder.DefineMethod("__" + mb.DeclaringType.FullName + "/" + mb.Name, attr, ((IMethodSymbol)mb).ReturnType, parameterTypes); if (mb.IsGenericMethodDefinition) CopyGenericArguments(mb, m); var ilgen = context.CodeEmitterFactory.Create(m); ilgen.EmitThrow("java.lang.AbstractMethodError", "Method " + mb.DeclaringType.FullName + "." + mb.Name + " is unsupported by IKVM."); ilgen.DoEmit(); - typeBuilder.DefineMethodOverride(m, (MethodInfo)mb); + typeBuilder.DefineMethodOverride(m, (IMethodSymbol)mb); } - void CopyGenericArguments(MethodBase mi, MethodBuilder mb) + void CopyGenericArguments(IMethodBaseSymbol mi, IMethodSymbolBuilder mb) { var genericParameters = mi.GetGenericArguments(); var genParamNames = new string[genericParameters.Length]; @@ -2068,7 +2065,7 @@ void CompileConstructorBody(FinishContext context, CodeEmitter ilGenerator, int Compiler.Compile(context, host, wrapper, methods[methodIndex], classFile, m, ilGenerator, ref nonLeaf); ilGenerator.DoEmit(); #if IMPORTER - ilGenerator.EmitLineNumberTable((MethodBuilder)methods[methodIndex].GetMethod()); + ilGenerator.EmitLineNumberTable((IMethodSymbolBuilder)methods[methodIndex].GetMethod()); #else // IMPORTER var linenumbers = ilGenerator.GetLineNumberTable(); if (linenumbers != null) @@ -2117,7 +2114,7 @@ void EmitCallerIDInitialization(CodeEmitter ilGenerator, FieldInfo callerIDField ilGenerator.Emit(OpCodes.Stsfld, callerIDField); } - internal static TypeBuilder EmitCreateCallerID(RuntimeContext context, TypeBuilder typeBuilder, CodeEmitter ilGenerator) + internal static ITypeSymbolBuilder EmitCreateCallerID(RuntimeContext context, ITypeSymbolBuilder typeBuilder, CodeEmitter ilGenerator) { var tw = context.JavaBase.TypeOfIkvmInternalCallerID; var typeCallerID = typeBuilder.DefineNestedType(NestedTypeName.CallerID, TypeAttributes.Sealed | TypeAttributes.NestedPrivate, tw.TypeAsBaseType); @@ -2190,7 +2187,7 @@ void EmitConstantValueInitialization(RuntimeJavaField[] fields, CodeEmitter ilGe } } - internal MethodBuilder DefineThreadLocalType() + internal IMethodSymbolBuilder DefineThreadLocalType() { var threadLocal = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicThreadLocal"); int id = nestedTypeBuilders == null ? 0 : nestedTypeBuilders.Count; @@ -2222,14 +2219,14 @@ internal MethodBuilder DefineThreadLocalType() return cb; } - internal MethodBuilder GetAtomicReferenceFieldUpdater(RuntimeJavaField field) + internal IMethodSymbolBuilder GetAtomicReferenceFieldUpdater(RuntimeJavaField field) { - arfuMap ??= new Dictionary(); + arfuMap ??= new Dictionary(); if (!arfuMap.TryGetValue(field, out var cb)) { - RuntimeJavaType arfuTypeWrapper = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicAtomicReferenceFieldUpdater"); - TypeBuilder tb = typeBuilder.DefineNestedType(NestedTypeName.AtomicReferenceFieldUpdater + arfuMap.Count, TypeAttributes.NestedPrivate | TypeAttributes.Sealed, arfuTypeWrapper.TypeAsBaseType); + var arfuTypeWrapper = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicAtomicReferenceFieldUpdater"); + var tb = typeBuilder.DefineNestedType(NestedTypeName.AtomicReferenceFieldUpdater + arfuMap.Count, TypeAttributes.NestedPrivate | TypeAttributes.Sealed, arfuTypeWrapper.TypeAsBaseType); AtomicReferenceFieldUpdaterEmitter.EmitImpl(context, tb, field.GetField()); cb = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, []); arfuMap.Add(field, cb); @@ -2245,7 +2242,7 @@ internal MethodBuilder GetAtomicReferenceFieldUpdater(RuntimeJavaField field) return cb; } - internal TypeBuilder DefineIndyCallSiteType() + internal ITypeSymbolBuilder DefineIndyCallSiteType() { int id = nestedTypeBuilders == null ? 0 : nestedTypeBuilders.Count; var tb = typeBuilder.DefineNestedType(NestedTypeName.IndyCallSite + id, TypeAttributes.NestedPrivate | TypeAttributes.Abstract | TypeAttributes.Sealed | TypeAttributes.BeforeFieldInit); @@ -2253,14 +2250,14 @@ internal TypeBuilder DefineIndyCallSiteType() return tb; } - internal TypeBuilder DefineMethodHandleConstantType(MethodHandleConstantHandle handle) + internal ITypeSymbolBuilder DefineMethodHandleConstantType(MethodHandleConstantHandle handle) { var tb = typeBuilder.DefineNestedType(NestedTypeName.MethodHandleConstant + handle.Slot, TypeAttributes.NestedPrivate | TypeAttributes.Sealed | TypeAttributes.Abstract | TypeAttributes.BeforeFieldInit); ; RegisterNestedTypeBuilder(tb); return tb; } - internal TypeBuilder DefineMethodTypeConstantType(MethodTypeConstantHandle handle) + internal ITypeSymbolBuilder DefineMethodTypeConstantType(MethodTypeConstantHandle handle) { var tb = typeBuilder.DefineNestedType(NestedTypeName.MethodTypeConstant + handle.Slot, TypeAttributes.NestedPrivate | TypeAttributes.Sealed | TypeAttributes.Abstract | TypeAttributes.BeforeFieldInit); RegisterNestedTypeBuilder(tb); @@ -2268,7 +2265,7 @@ internal TypeBuilder DefineMethodTypeConstantType(MethodTypeConstantHandle handl } // this is used to define intrinsified anonymous classes (in the Unsafe.defineAnonymousClass() sense) - internal TypeBuilder DefineAnonymousClass() + internal ITypeSymbolBuilder DefineAnonymousClass() { int id = nestedTypeBuilders == null ? 0 : nestedTypeBuilders.Count; var tb = typeBuilder.DefineNestedType(NestedTypeName.IntrinsifiedAnonymousClass + id, TypeAttributes.NestedPrivate | TypeAttributes.Sealed | TypeAttributes.SpecialName | TypeAttributes.BeforeFieldInit); @@ -2276,39 +2273,39 @@ internal TypeBuilder DefineAnonymousClass() return tb; } - MethodBuilder DefineHelperMethod(string name, Type returnType, Type[] parameterTypes) + IMethodSymbolBuilder DefineHelperMethod(string name, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) { return typeBuilder.DefineMethod(name, MethodAttributes.PrivateScope | MethodAttributes.Static, returnType, parameterTypes); } - internal MethodBuilder DefineMethodHandleDispatchStub(Type returnType, Type[] parameterTypes) + internal IMethodSymbolBuilder DefineMethodHandleDispatchStub(ITypeSymbol returnType, ITypeSymbol[] parameterTypes) { return DefineHelperMethod("__<>MHC", returnType, parameterTypes); } - internal FieldBuilder DefineMethodHandleInvokeCacheField(Type fieldType) + internal IFieldSymbolBuilder DefineMethodHandleInvokeCacheField(ITypeSymbol fieldType) { return typeBuilder.DefineField("__<>invokeCache", fieldType, FieldAttributes.Static | FieldAttributes.PrivateScope); } - internal FieldBuilder DefineDynamicMethodHandleCacheField() + internal IFieldSymbolBuilder DefineDynamicMethodHandleCacheField() { return typeBuilder.DefineField("__<>dynamicMethodHandleCache", context.JavaBase.TypeOfJavaLangInvokeMethodHandle.TypeAsSignatureType, FieldAttributes.Static | FieldAttributes.PrivateScope); } - internal FieldBuilder DefineDynamicMethodTypeCacheField() + internal IFieldSymbolBuilder DefineDynamicMethodTypeCacheField() { return typeBuilder.DefineField("__<>dynamicMethodTypeCache", context.JavaBase.TypeOfJavaLangInvokeMethodType.TypeAsSignatureType, FieldAttributes.Static | FieldAttributes.PrivateScope); } - internal MethodBuilder DefineDelegateInvokeErrorStub(Type returnType, Type[] parameterTypes) + internal IMethodSymbolBuilder DefineDelegateInvokeErrorStub(ITypeSymbol returnType, ITypeSymbol[] parameterTypes) { return DefineHelperMethod("__<>", returnType, parameterTypes); } - internal MethodInfo GetInvokeSpecialStub(RuntimeJavaMethod method) + internal IMethodSymbol GetInvokeSpecialStub(RuntimeJavaMethod method) { - invokespecialstubcache ??= new Dictionary(); + invokespecialstubcache ??= new Dictionary(); var key = new MethodKey(method.DeclaringType.Name, method.Name, method.Signature); @@ -2335,8 +2332,7 @@ internal MethodInfo GetInvokeSpecialStub(RuntimeJavaMethod method) internal void EmitLiveObjectLoad(CodeEmitter ilgen, object value) { liveObjects ??= new List(); - var fi = TypeBuilder.GetField(typeof(IKVM.Runtime.LiveObjectHolder<>).MakeGenericType(typeBuilder), typeof(IKVM.Runtime.LiveObjectHolder<>).GetField("values", BindingFlags.Static | BindingFlags.Public)); - ilgen.Emit(OpCodes.Ldsfld, fi); + ilgen.Emit(OpCodes.Ldsfld, context.Resolver.ResolveRuntimeType("IKVM.Runtime.LiveObjectHolder`1").MakeGenericType(typeBuilder).GetField("values", BindingFlags.Static | BindingFlags.Public)); ilgen.EmitLdc_I4(liveObjects.Count); ilgen.Emit(OpCodes.Ldelem_Ref); liveObjects.Add(value); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index ffa19a8589..5f50536199 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -1812,7 +1812,7 @@ internal void Finish(JavaTypeImpl o) getValueMethod.EmitCall(ilgen); o.methods[i].ReturnType.EmitCheckcast(ilgen); } - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); if (o.classFile.Methods[i].AnnotationDefault != null @@ -1822,16 +1822,16 @@ internal void Finish(JavaTypeImpl o) Type argType = TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType); if (argType != null) { - PropertyBuilder pb = attributeTypeBuilder.DefineProperty(o.methods[i].Name, PropertyAttributes.None, argType, []); + var pb = attributeTypeBuilder.DefineProperty(o.methods[i].Name, PropertyAttributes.None, argType, []); context.AttributeHelper.HideFromJava(pb); - MethodBuilder setter = attributeTypeBuilder.DefineMethod("set_" + o.methods[i].Name, MethodAttributes.Public, context.Types.Void, new Type[] { argType }); + var setter = attributeTypeBuilder.DefineMethod("set_" + o.methods[i].Name, MethodAttributes.Public, context.Types.Void, new ITypeSymbol[] { argType }); context.AttributeHelper.HideFromJava(setter); pb.SetSetMethod(setter); ilgen = context.CodeEmitterFactory.Create(setter); EmitSetValueCall(annotationAttributeBaseType, ilgen, o.methods[i].Name, o.methods[i].ReturnType, 1); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); - MethodBuilder getter = attributeTypeBuilder.DefineMethod("get_" + o.methods[i].Name, MethodAttributes.Public, argType, []); + var getter = attributeTypeBuilder.DefineMethod("get_" + o.methods[i].Name, MethodAttributes.Public, argType, []); context.AttributeHelper.HideFromJava(getter); pb.SetGetMethod(getter); // TODO implement the getter method @@ -2129,7 +2129,7 @@ bool IsAccessibleInternal(RuntimeJavaMethod mw) return mw.IsInternal && mw.DeclaringType.InternalsVisibleTo(wrapper); } - static MethodBase LinkAndGetMethod(RuntimeJavaMethod mw) + static IMethodSymbol LinkAndGetMethod(RuntimeJavaMethod mw) { mw.Link(); return mw.GetMethod(); @@ -2260,7 +2260,7 @@ RuntimeJavaMethod[] FindBaseMethodsLegacy(string name, string sig, out bool expl return null; } - static MethodInfo GetBaseFinalizeMethod(RuntimeJavaType wrapper) + static IMethodSymbol GetBaseFinalizeMethod(RuntimeJavaType wrapper) { for (; ; ) { @@ -2294,7 +2294,7 @@ static MethodInfo GetBaseFinalizeMethod(RuntimeJavaType wrapper) while (type != null) { - foreach (MethodInfo m in type.GetMethods(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance | BindingFlags.DeclaredOnly)) + foreach (var m in type.GetMethods(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance | BindingFlags.DeclaredOnly)) { if (m.Name == "Finalize" && m.ReturnType == wrapper.Context.Types.Void @@ -2467,7 +2467,7 @@ internal override IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) } var m = classFile.Methods[index]; - MethodBuilder method; + IMethodSymbolBuilder method; bool setModifiers = false; if (methods[index].HasCallerID && (m.Modifiers & Modifiers.VarArgs) != 0) @@ -2573,12 +2573,12 @@ private bool HasSerialVersionUID } } - MethodBuilder GenerateConstructor(RuntimeJavaMethod mw) + IMethodSymbolBuilder GenerateConstructor(RuntimeJavaMethod mw) { return mw.GetDefineMethodHelper().DefineConstructor(wrapper, typeBuilder, GetMethodAccess(mw) | MethodAttributes.HideBySig); } - MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifiers) + IMethodSymbolBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifiers) { var attribs = MethodAttributes.HideBySig; if (m.IsNative) @@ -2630,6 +2630,7 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier setModifiers = true; } } + if (m.IsFinal) { if (m.IsVirtual) @@ -2641,6 +2642,7 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier setModifiers = true; } } + if (m.IsStatic) { attribs |= MethodAttributes.Static; @@ -2653,7 +2655,8 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier { attribs |= MethodAttributes.Virtual | MethodAttributes.CheckAccessOnOverride; } - string name = UnicodeUtil.EscapeInvalidSurrogates(m.Name); + + var name = UnicodeUtil.EscapeInvalidSurrogates(m.Name); if (!ReferenceEquals(name, m.Name)) { // mark as specialname to remind us to unescape the name @@ -2689,9 +2692,9 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier // if we have a method overriding a more accessible method (the JVM allows this), we need to make the // method more accessible, because otherwise the CLR will complain that we're reducing access bool hasPublicBaseMethod = false; - foreach (RuntimeJavaMethod baseMethodWrapper in baseMethods[index]) + foreach (var baseMethodWrapper in baseMethods[index]) { - MethodBase baseMethod = baseMethodWrapper.GetMethod(); + var baseMethod = baseMethodWrapper.GetMethod(); if ((baseMethod.IsPublic && !m.IsPublic) || ((baseMethod.IsFamily || baseMethod.IsFamilyOrAssembly) && !m.IsPublic && !m.IsProtected) || (!m.IsPublic && !m.IsProtected && !baseMethodWrapper.DeclaringType.IsPackageAccessibleFrom(wrapper))) @@ -2704,7 +2707,8 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier } } } - MethodBuilder mb = null; + + IMethodSymbolBuilder mb = null; #if IMPORTER mb = wrapper.DefineGhostMethod(typeBuilder, name, attribs, methods[index]); #endif @@ -2830,15 +2834,15 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier var ilgen = wrapper.Context.CodeEmitterFactory.Create(finalizeMethod); ilgen.EmitLdarg(0); - ilgen.Emit(OpCodes.Call, wrapper.Context.ByteCodeHelperMethods.SkipFinalizerOf); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, wrapper.Context.ByteCodeHelperMethods.SkipFinalizerOf); var skip = ilgen.DefineLabel(); ilgen.EmitBrtrue(skip); if (needDispatch) { ilgen.BeginExceptionBlock(); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Callvirt, mb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, mb); ilgen.EmitLeave(skip); ilgen.BeginCatchBlock(wrapper.Context.Types.Object); ilgen.EmitLeave(skip); @@ -2846,12 +2850,12 @@ MethodBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setModifier } else { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Call, baseFinalize); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, baseFinalize); } ilgen.MarkLabel(skip); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); } #if IMPORTER diff --git a/src/IKVM.Runtime/RuntimeJavaField.cs b/src/IKVM.Runtime/RuntimeJavaField.cs index c4cd21c80e..f36a6325c3 100644 --- a/src/IKVM.Runtime/RuntimeJavaField.cs +++ b/src/IKVM.Runtime/RuntimeJavaField.cs @@ -27,6 +27,8 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; + #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -438,20 +440,10 @@ internal static RuntimeJavaField Create(RuntimeJavaType declaringType, RuntimeJa } #if !IMPORTER && !EXPORTER + internal virtual void ResolveField() { - var fb = field.AsReflection() as FieldBuilder; - if (fb != null) - { -#if NETFRAMEWORK - field = fb.DeclaringType.Module.ResolveField(fb.GetToken().Token); -#else - BindingFlags flags = BindingFlags.DeclaredOnly; - flags |= fb.IsPublic ? BindingFlags.Public : BindingFlags.NonPublic; - flags |= fb.IsStatic ? BindingFlags.Static : BindingFlags.Instance; - field = DeclaringType.TypeAsTBD.GetField(fb.Name, flags); -#endif - } + } #if !FIRST_PASS diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index ff32a16733..319b7455a1 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -1231,7 +1231,7 @@ internal void EmitBox(CodeEmitter ilgen) { Debug.Assert(this.IsNonPrimitiveValueType); - ilgen.Emit(OpCodes.Box, this.TypeAsTBD); + ilgen.Emit(System.Reflection.Emit.OpCodes.Box, this.TypeAsTBD); } internal void EmitConvSignatureTypeToStackType(CodeEmitter ilgen) @@ -1242,7 +1242,7 @@ internal void EmitConvSignatureTypeToStackType(CodeEmitter ilgen) } else if (this == context.PrimitiveJavaTypeFactory.BYTE) { - ilgen.Emit(OpCodes.Conv_I1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Conv_I1); } else if (IsNonPrimitiveValueType) { @@ -1251,9 +1251,9 @@ internal void EmitConvSignatureTypeToStackType(CodeEmitter ilgen) else if (IsGhost) { var local = ilgen.DeclareLocal(TypeAsSignatureType); - ilgen.Emit(OpCodes.Stloc, local); - ilgen.Emit(OpCodes.Ldloca, local); - ilgen.Emit(OpCodes.Ldfld, GhostRefField); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, local); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloca, local); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldfld, GhostRefField); } } @@ -1266,13 +1266,13 @@ internal void EmitConvStackTypeToSignatureType(CodeEmitter ilgen, RuntimeJavaTyp if (IsGhost) { CodeEmitterLocal local1 = ilgen.DeclareLocal(TypeAsLocalOrStackType); - ilgen.Emit(OpCodes.Stloc, local1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, local1); CodeEmitterLocal local2 = ilgen.DeclareLocal(TypeAsSignatureType); - ilgen.Emit(OpCodes.Ldloca, local2); - ilgen.Emit(OpCodes.Ldloc, local1); - ilgen.Emit(OpCodes.Stfld, GhostRefField); - ilgen.Emit(OpCodes.Ldloca, local2); - ilgen.Emit(OpCodes.Ldobj, TypeAsSignatureType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloca, local2); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, local1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stfld, GhostRefField); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloca, local2); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldobj, TypeAsSignatureType); } // because of the way interface merging works, any reference is valid // for any interface reference @@ -1287,7 +1287,7 @@ internal void EmitConvStackTypeToSignatureType(CodeEmitter ilgen, RuntimeJavaTyp } else if (sourceType != null && sourceType.IsUnloadable) { - ilgen.Emit(OpCodes.Castclass, TypeAsSignatureType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, TypeAsSignatureType); } } } @@ -1296,16 +1296,16 @@ internal virtual void EmitCheckcast(CodeEmitter ilgen) { if (IsGhost) { - ilgen.Emit(OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); // TODO make sure we get the right "Cast" method and cache it // NOTE for dynamic ghosts we don't end up here because AotTypeWrapper overrides this method, // so we're safe to call GetMethod on TypeAsTBD (because it has to be a compiled type, if we're here) - ilgen.Emit(OpCodes.Call, TypeAsTBD.GetMethod("Cast")); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, TypeAsTBD.GetMethod("Cast")); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); } else if (IsGhostArray) { - ilgen.Emit(OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); // TODO make sure we get the right "CastArray" method and cache it // NOTE for dynamic ghosts we don't end up here because AotTypeWrapper overrides this method, // so we're safe to call GetMethod on TypeAsTBD (because it has to be a compiled type, if we're here) @@ -1317,8 +1317,8 @@ internal virtual void EmitCheckcast(CodeEmitter ilgen) tw = tw.ElementTypeWrapper; } ilgen.EmitLdc_I4(rank); - ilgen.Emit(OpCodes.Call, tw.TypeAsTBD.GetMethod("CastArray")); - ilgen.Emit(OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(context.Types.Object, rank)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, tw.TypeAsTBD.GetMethod("CastArray")); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(context.Types.Object, rank)); } else { @@ -1333,7 +1333,7 @@ internal virtual void EmitInstanceOf(CodeEmitter ilgen) // TODO make sure we get the right "IsInstance" method and cache it // NOTE for dynamic ghosts we don't end up here because DynamicTypeWrapper overrides this method, // so we're safe to call GetMethod on TypeAsTBD (because it has to be a compiled type, if we're here) - ilgen.Emit(OpCodes.Call, TypeAsTBD.GetMethod("IsInstance")); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, TypeAsTBD.GetMethod("IsInstance")); } else if (IsGhostArray) { @@ -1348,7 +1348,7 @@ internal virtual void EmitInstanceOf(CodeEmitter ilgen) tw = tw.ElementTypeWrapper; } ilgen.EmitLdc_I4(rank); - ilgen.Emit(OpCodes.Call, tw.TypeAsTBD.GetMethod("IsInstanceArray")); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, tw.TypeAsTBD.GetMethod("IsInstanceArray")); } else { @@ -1363,23 +1363,23 @@ internal virtual void EmitInstanceOf(CodeEmitter ilgen) internal virtual void EmitLdind(CodeEmitter il) { if (this == context.PrimitiveJavaTypeFactory.BOOLEAN) - il.Emit(OpCodes.Ldind_U1); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_U1); else if (this == context.PrimitiveJavaTypeFactory.BYTE) - il.Emit(OpCodes.Ldind_U1); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_U1); else if (this == context.PrimitiveJavaTypeFactory.CHAR) - il.Emit(OpCodes.Ldind_U2); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_U2); else if (this == context.PrimitiveJavaTypeFactory.SHORT) - il.Emit(OpCodes.Ldind_I2); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_I2); else if (this == context.PrimitiveJavaTypeFactory.INT) - il.Emit(OpCodes.Ldind_I4); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_I4); else if (this == context.PrimitiveJavaTypeFactory.LONG) - il.Emit(OpCodes.Ldind_I8); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_I8); else if (this == context.PrimitiveJavaTypeFactory.FLOAT) - il.Emit(OpCodes.Ldind_R4); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_R4); else if (this == context.PrimitiveJavaTypeFactory.DOUBLE) - il.Emit(OpCodes.Ldind_R8); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_R8); else - il.Emit(OpCodes.Ldind_Ref); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_Ref); } /// @@ -1389,23 +1389,23 @@ internal virtual void EmitLdind(CodeEmitter il) internal virtual void EmitStind(CodeEmitter il) { if (this == context.PrimitiveJavaTypeFactory.BOOLEAN) - il.Emit(OpCodes.Stind_I1); + il.Emit(System.Reflection.Emit.OpCodes.Stind_I1); else if (this == context.PrimitiveJavaTypeFactory.BYTE) - il.Emit(OpCodes.Stind_I1); + il.Emit(System.Reflection.Emit.OpCodes.Stind_I1); else if (this == context.PrimitiveJavaTypeFactory.CHAR) - il.Emit(OpCodes.Stind_I2); + il.Emit(System.Reflection.Emit.OpCodes.Stind_I2); else if (this == context.PrimitiveJavaTypeFactory.SHORT) - il.Emit(OpCodes.Stind_I2); + il.Emit(System.Reflection.Emit.OpCodes.Stind_I2); else if (this == context.PrimitiveJavaTypeFactory.INT) - il.Emit(OpCodes.Stind_I4); + il.Emit(System.Reflection.Emit.OpCodes.Stind_I4); else if (this == context.PrimitiveJavaTypeFactory.LONG) - il.Emit(OpCodes.Stind_I8); + il.Emit(System.Reflection.Emit.OpCodes.Stind_I8); else if (this == context.PrimitiveJavaTypeFactory.FLOAT) - il.Emit(OpCodes.Stind_R4); + il.Emit(System.Reflection.Emit.OpCodes.Stind_R4); else if (this == context.PrimitiveJavaTypeFactory.DOUBLE) - il.Emit(OpCodes.Stind_R8); + il.Emit(System.Reflection.Emit.OpCodes.Stind_R8); else - il.Emit(OpCodes.Stind_Ref); + il.Emit(System.Reflection.Emit.OpCodes.Stind_Ref); } #endif @@ -1479,7 +1479,7 @@ internal virtual string GetSourceFileName() return null; } - internal virtual int GetSourceLineNumber(MethodBase mb, int ilOffset) + internal virtual int GetSourceLineNumber(IMethodBaseSymbol mb, int ilOffset) { return -1; } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index f3cdaf1c55..e056821594 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -1280,7 +1280,7 @@ internal override string GetSourceFileName() return null; } - internal override int GetSourceLineNumber(MethodBase mb, int ilOffset) + internal override int GetSourceLineNumber(IMethodBaseSymbol mb, int ilOffset) { var attr = type.GetCustomAttribute(Context.Resolver.ResolveType(typeof(LineNumberTableAttribute))); if (attr != null && attr.Value.Constructor != null) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs index 6b2a6272b6..51ee91f3b2 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs @@ -545,14 +545,14 @@ ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, ob internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) { - if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.StructLayoutAttribute).FullName) && tb.Symbol.BaseType != loader.Context.Types.Object) + if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.StructLayoutAttribute).FullName) && tb.BaseType != loader.Context.Types.Object) { // we have to handle this explicitly, because if we apply an illegal StructLayoutAttribute, // TypeBuilder.CreateType() will later on throw an exception. #if IMPORTER - loader.Diagnostics.IgnoredCustomAttribute(type.FullName, $"Type '{tb.Symbol.FullName}' does not extend cli.System.Object"); + loader.Diagnostics.IgnoredCustomAttribute(type.FullName, $"Type '{tb.FullName}' does not extend cli.System.Object"); #else - loader.Diagnostics.GenericRuntimeError($"StructLayoutAttribute cannot be applied to {tb.Symbol.FullName}, because it does not directly extend cli.System.Object"); + loader.Diagnostics.GenericRuntimeError($"StructLayoutAttribute cannot be applied to {tb.FullName}, because it does not directly extend cli.System.Object"); #endif return; } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs index 678bb8f5e3..d04117a4f8 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateJavaMethod.cs @@ -75,25 +75,25 @@ internal override bool EmitIntrinsic(EmitIntrinsicContext context) var mw = targetType.GetMethodWrapper(GetDelegateInvokeStubName(DeclaringType.TypeAsTBD), iface.GetMethods()[0].Signature, true); if (mw == null || mw.IsStatic || !mw.IsPublic) { - context.Emitter.Emit(OpCodes.Ldftn, CreateErrorStub(context, targetType, mw == null || mw.IsStatic)); - context.Emitter.Emit(OpCodes.Newobj, delegateConstructor); + context.Emitter.Emit(System.Reflection.Emit.OpCodes.Ldftn, CreateErrorStub(context, targetType, mw == null || mw.IsStatic)); + context.Emitter.Emit(System.Reflection.Emit.OpCodes.Newobj, delegateConstructor); return true; } // TODO linking here is not safe mw.Link(); - context.Emitter.Emit(OpCodes.Dup); - context.Emitter.Emit(OpCodes.Ldvirtftn, mw.GetMethod()); - context.Emitter.Emit(OpCodes.Newobj, delegateConstructor); + context.Emitter.Emit(System.Reflection.Emit.OpCodes.Dup); + context.Emitter.Emit(System.Reflection.Emit.OpCodes.Ldvirtftn, mw.GetMethod()); + context.Emitter.Emit(System.Reflection.Emit.OpCodes.Newobj, delegateConstructor); return true; } - MethodInfo CreateErrorStub(EmitIntrinsicContext context, RuntimeJavaType targetType, bool isAbstract) + IMethodSymbol CreateErrorStub(EmitIntrinsicContext context, RuntimeJavaType targetType, bool isAbstract) { var invoke = delegateConstructor.DeclaringType.GetMethod("Invoke"); var parameters = invoke.GetParameters(); - var parameterTypes = new Type[parameters.Length + 1]; + var parameterTypes = new ITypeSymbol[parameters.Length + 1]; parameterTypes[0] = DeclaringType.Context.Types.Object; for (int i = 0; i < parameters.Length; i++) parameterTypes[i + 1] = parameters[i].ParameterType; @@ -107,12 +107,12 @@ MethodInfo CreateErrorStub(EmitIntrinsicContext context, RuntimeJavaType targetT internal override void EmitNewobj(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Ldtoken, delegateConstructor.DeclaringType); - ilgen.Emit(OpCodes.Call, DeclaringType.Context.CompilerFactory.GetTypeFromHandleMethod); - ilgen.Emit(OpCodes.Ldstr, GetDelegateInvokeStubName(DeclaringType.TypeAsTBD)); - ilgen.Emit(OpCodes.Ldstr, iface.GetMethods()[0].Signature); - ilgen.Emit(OpCodes.Call, DeclaringType.Context.ByteCodeHelperMethods.DynamicCreateDelegate); - ilgen.Emit(OpCodes.Castclass, delegateConstructor.DeclaringType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldtoken, delegateConstructor.DeclaringType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, DeclaringType.Context.CompilerFactory.GetTypeFromHandleMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, GetDelegateInvokeStubName(DeclaringType.TypeAsTBD)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, iface.GetMethods()[0].Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, DeclaringType.Context.ByteCodeHelperMethods.DynamicCreateDelegate); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, delegateConstructor.DeclaringType); } internal override void EmitCall(CodeEmitter ilgen) @@ -124,9 +124,9 @@ internal override void EmitCall(CodeEmitter ilgen) EmitNewobj(ilgen); // invoke the constructor, binding the delegate to the target delegate - ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Ldvirtftn, DeclaringType.Context.MethodHandleUtil.GetDelegateInvokeMethod(delegateConstructor.DeclaringType)); - ilgen.Emit(OpCodes.Call, delegateConstructor); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldvirtftn, DeclaringType.Context.MethodHandleUtil.GetDelegateInvokeMethod(delegateConstructor.DeclaringType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, delegateConstructor); } #endif diff --git a/src/IKVM.Runtime/Serialization.cs b/src/IKVM.Runtime/Serialization.cs index bf40867722..dc7142b5e1 100644 --- a/src/IKVM.Runtime/Serialization.cs +++ b/src/IKVM.Runtime/Serialization.cs @@ -24,6 +24,10 @@ Jeroen Frijters using System; using System.Runtime.Serialization; using System.Security; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; + + #if IMPORTER using IKVM.Reflection; @@ -90,9 +94,9 @@ bool IsSafeForAutomagicSerialization(RuntimeJavaType wrapper) return true; } - internal MethodBuilder AddAutomagicSerialization(RuntimeByteCodeJavaType wrapper, TypeBuilder typeBuilder) + internal IMethodSymbolBuilder AddAutomagicSerialization(RuntimeByteCodeJavaType wrapper, ITypeSymbolBuilder typeBuilder) { - MethodBuilder serializationCtor = null; + IMethodSymbolBuilder serializationCtor = null; if ((wrapper.Modifiers & IKVM.Attributes.Modifiers.Enum) != 0) { MarkSerializable(typeBuilder); @@ -149,7 +153,7 @@ internal MethodBuilder AddAutomagicSerialization(RuntimeByteCodeJavaType wrapper return serializationCtor; } - internal MethodBuilder AddAutomagicSerializationToWorkaroundBaseClass(TypeBuilder typeBuilderWorkaroundBaseClass, MethodBase baseCtor) + internal IMethodSymbolBuilder AddAutomagicSerializationToWorkaroundBaseClass(ITypeSymbolBuilder typeBuilderWorkaroundBaseClass, MethodBase baseCtor) { if (typeBuilderWorkaroundBaseClass.BaseType.IsSerializable) { @@ -161,36 +165,36 @@ internal MethodBuilder AddAutomagicSerializationToWorkaroundBaseClass(TypeBuilde return null; } - internal void MarkSerializable(TypeBuilder tb) + internal void MarkSerializable(ITypeSymbolBuilder tb) { tb.SetCustomAttribute(SerializableAttribute); } - internal void AddGetObjectData(TypeBuilder tb) + internal void AddGetObjectData(ITypeSymbolBuilder tb) { var name = tb.IsSealed ? "System.Runtime.Serialization.ISerializable.GetObjectData" : "GetObjectData"; var attr = tb.IsSealed ? MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final : MethodAttributes.Family | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.CheckAccessOnOverride; - tb.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(ISerializable).FullName).AsReflection()); - var getObjectData = tb.DefineMethod(name, attr, null, new Type[] { context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName).AsReflection(), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection() }); + tb.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(ISerializable).FullName)); + var getObjectData = tb.DefineMethod(name, attr, null, new ITypeSymbol[] { context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection() }); getObjectData.SetCustomAttribute(SecurityCriticalAttribute); context.AttributeHelper.HideFromJava(getObjectData); tb.DefineMethodOverride(getObjectData, context.Resolver.ResolveCoreType(typeof(ISerializable).FullName).GetMethod("GetObjectData").AsReflection()); - CodeEmitter ilgen = context.CodeEmitterFactory.Create(getObjectData); + var ilgen = context.CodeEmitterFactory.Create(getObjectData); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ldarg_1); - RuntimeJavaType serializationHelper = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.Serialization"); - RuntimeJavaMethod mw = serializationHelper.GetMethodWrapper("writeObject", "(Ljava.lang.Object;Lcli.System.Runtime.Serialization.SerializationInfo;)V", false); + var serializationHelper = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.Serialization"); + var mw = serializationHelper.GetMethodWrapper("writeObject", "(Ljava.lang.Object;Lcli.System.Runtime.Serialization.SerializationInfo;)V", false); mw.Link(); mw.EmitCall(ilgen); ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); } - MethodBuilder AddConstructor(TypeBuilder tb, RuntimeJavaMethod defaultConstructor, MethodBase serializationConstructor, bool callReadObject) + IMethodSymbolBuilder AddConstructor(ITypeSymbolBuilder tb, RuntimeJavaMethod defaultConstructor, IMethodBaseSymbol serializationConstructor, bool callReadObject) { - MethodBuilder ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Family, new Type[] { context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName).AsReflection(), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection() }); + var ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Family, new ITypeSymbol[] { context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName).AsReflection(), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection() }); context.AttributeHelper.HideFromJava(ctor); CodeEmitter ilgen = context.CodeEmitterFactory.Create(ctor); ilgen.Emit(OpCodes.Ldarg_0); @@ -218,13 +222,13 @@ MethodBuilder AddConstructor(TypeBuilder tb, RuntimeJavaMethod defaultConstructo return ctor; } - void AddReadResolve(RuntimeByteCodeJavaType wrapper, TypeBuilder tb) + void AddReadResolve(RuntimeByteCodeJavaType wrapper, ITypeSymbolBuilder tb) { var mw = wrapper.GetMethodWrapper("readResolve", "()Ljava.lang.Object;", false); if (mw != null && !wrapper.IsSubTypeOf(TypeOfIObjectReference)) { tb.AddInterfaceImplementation(wrapper.Context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).AsReflection()); - var getRealObject = tb.DefineMethod("IObjectReference.GetRealObject", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final, wrapper.Context.Types.Object, new Type[] { wrapper.Context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection() }); + var getRealObject = tb.DefineMethod("IObjectReference.GetRealObject", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final, wrapper.Context.Types.Object, new ITypeSymbol[] { wrapper.Context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName) }); getRealObject.SetCustomAttribute(SecurityCriticalAttribute); wrapper.Context.AttributeHelper.HideFromJava(getRealObject); tb.DefineMethodOverride(getRealObject, wrapper.Context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).GetMethod("GetRealObject").AsReflection()); @@ -237,7 +241,7 @@ void AddReadResolve(RuntimeByteCodeJavaType wrapper, TypeBuilder tb) ilgen.Emit(OpCodes.Callvirt, wrapper.Context.CompilerFactory.GetTypeMethod); ilgen.Emit(OpCodes.Ldtoken, wrapper.TypeAsBaseType); ilgen.Emit(OpCodes.Call, wrapper.Context.CompilerFactory.GetTypeFromHandleMethod); - CodeEmitterLabel label = ilgen.DefineLabel(); + var label = ilgen.DefineLabel(); ilgen.EmitBeq(label); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ret); @@ -250,14 +254,14 @@ void AddReadResolve(RuntimeByteCodeJavaType wrapper, TypeBuilder tb) } } - void RemoveReadResolve(TypeBuilder tb) + void RemoveReadResolve(ITypeSymbolBuilder tb) { tb.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).AsReflection()); - MethodBuilder getRealObject = tb.DefineMethod("IObjectReference.GetRealObject", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final, context.Types.Object, [context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection()]); + var getRealObject = tb.DefineMethod("IObjectReference.GetRealObject", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final, context.Types.Object, [context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName)]); getRealObject.SetCustomAttribute(SecurityCriticalAttribute); context.AttributeHelper.HideFromJava(getRealObject); tb.DefineMethodOverride(getRealObject, context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).GetMethod("GetRealObject").AsReflection()); - CodeEmitter ilgen = context.CodeEmitterFactory.Create(getRealObject); + var ilgen = context.CodeEmitterFactory.Create(getRealObject); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); diff --git a/src/IKVM.Runtime/SymbolExtensions.cs b/src/IKVM.Runtime/SymbolExtensions.cs index 14e3948b01..52745475af 100644 --- a/src/IKVM.Runtime/SymbolExtensions.cs +++ b/src/IKVM.Runtime/SymbolExtensions.cs @@ -29,9 +29,9 @@ public static Assembly AsReflection(this IAssemblySymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionAssemblySymbol)symbol).ReflectionObject; + return ((IIkvmReflectionAssemblySymbol)symbol).UnderlyingAssembly; #else - return ((ReflectionAssemblySymbol)symbol).ReflectionObject; + return ((IReflectionAssemblySymbol)symbol).UnderlyingAssembly; #endif } @@ -41,9 +41,9 @@ public static Module AsReflection(this IModuleSymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionModuleSymbol)symbol).ReflectionObject; + return ((IIkvmReflectionModuleSymbol)symbol).UnderlyingModule; #else - return ((ReflectionModuleSymbol)symbol).ReflectionObject; + return ((IReflectionModuleSymbol)symbol).UnderlyingModule; #endif } @@ -53,9 +53,9 @@ public static Type AsReflection(this ITypeSymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionTypeSymbol)symbol).ReflectionObject; + return ((IIkvmReflectionTypeSymbol)symbol).UnderlyingType; #else - return ((ReflectionTypeSymbol)symbol).ReflectionObject; + return ((IReflectionTypeSymbol)symbol).UnderlyingType; #endif } @@ -77,9 +77,9 @@ public static MethodBase AsReflection(this IMethodBaseSymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionMethodBaseSymbol)symbol).ReflectionObject; + return ((IIkvmReflectionMethodBaseSymbol)symbol).UnderlyingMethodBase; #else - return ((ReflectionMethodBaseSymbol)symbol).ReflectionObject; + return ((IReflectionMethodBaseSymbol)symbol).UnderlyingMethodBase; #endif } @@ -89,9 +89,9 @@ public static ConstructorInfo AsReflection(this IConstructorSymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionConstructorSymbol)symbol).ReflectionObject; + return ((IIkvmReflectionConstructorSymbol)symbol).UnderlyingConstructor; #else - return ((ReflectionConstructorSymbol)symbol).ReflectionObject; + return ((IReflectionConstructorSymbol)symbol).UnderlyingConstructor; #endif } @@ -101,9 +101,9 @@ public static MethodInfo AsReflection(this IMethodSymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionMethodSymbol)symbol).ReflectionObject; + return ((IIkvmReflectionMethodSymbol)symbol).UnderlyingMethod; #else - return ((ReflectionMethodSymbol)symbol).ReflectionObject; + return ((IReflectionMethodSymbol)symbol).UnderlyingMethod; #endif } @@ -113,9 +113,9 @@ public static FieldInfo AsReflection(this IFieldSymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionFieldSymbol)symbol).ReflectionObject; + return ((IIkvmReflectionFieldSymbol)symbol).UnderlyingField; #else - return ((ReflectionFieldSymbol)symbol).ReflectionObject; + return ((IReflectionFieldSymbol)symbol).UnderlyingField; #endif } @@ -137,9 +137,9 @@ public static PropertyInfo AsReflection(this IPropertySymbol symbol) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionPropertySymbol)symbol).ReflectionObject; + return ((IIkvmReflectionPropertySymbol)symbol).UnderlyingProperty; #else - return ((ReflectionPropertySymbol)symbol).ReflectionObject; + return ((IReflectionPropertySymbol)symbol).UnderlyingProperty; #endif } @@ -161,9 +161,9 @@ public static AssemblyBuilder AsReflection(this IAssemblySymbolBuilder builder) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionAssemblySymbolBuilder)builder).ReflectionBuilder; + return ((IIkvmReflectionAssemblySymbolBuilder)builder).UnderlyingAssemblyBuilder; #else - return ((ReflectionAssemblySymbolBuilder)builder).ReflectionBuilder; + return ((IReflectionAssemblySymbolBuilder)builder).UnderlyingAssemblyBuilder; #endif } @@ -173,9 +173,9 @@ public static ModuleBuilder AsReflection(this IModuleSymbolBuilder builder) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionModuleSymbolBuilder)builder).ReflectionBuilder; + return ((IIkvmReflectionModuleSymbolBuilder)builder).UnderlyingModuleBuilder; #else - return ((ReflectionModuleSymbolBuilder)builder).ReflectionBuilder; + return ((IReflectionModuleSymbolBuilder)builder).UnderlyingModuleBuilder; #endif } @@ -185,9 +185,9 @@ public static TypeBuilder AsReflection(this ITypeSymbolBuilder builder) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionTypeSymbolBuilder)builder).ReflectionBuilder; + return ((IIkvmReflectionTypeSymbolBuilder)builder).UnderlyingTypeBuilder; #else - return ((ReflectionTypeSymbolBuilder)builder).ReflectionBuilder; + return ((IReflectionTypeSymbolBuilder)builder).UnderlyingTypeBuilder; #endif } @@ -197,9 +197,9 @@ public static ConstructorBuilder AsReflection(this IConstructorSymbolBuilder bui return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionConstructorSymbolBuilder)builder).ReflectionBuilder; + return ((IIkvmReflectionConstructorSymbolBuilder)builder).UnderlyingConstructorBuilder; #else - return ((ReflectionConstructorSymbolBuilder)builder).ReflectionBuilder; + return ((IReflectionConstructorSymbolBuilder)builder).UnderlyingConstructorBuilder; #endif } @@ -209,9 +209,9 @@ public static MethodBuilder AsReflection(this IMethodSymbolBuilder builder) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionMethodSymbolBuilder)builder).ReflectionBuilder; + return ((IIkvmReflectionMethodSymbolBuilder)builder).UnderlyingMethodBuilder; #else - return ((ReflectionMethodSymbolBuilder)builder).ReflectionBuilder; + return ((IReflectionMethodSymbolBuilder)builder).UnderlyingMethodBuilder; #endif } @@ -221,9 +221,9 @@ public static FieldBuilder AsReflection(this IFieldSymbolBuilder builder) return null; #if IMPORTER || EXPORTER - return ((IkvmReflectionFieldSymbolBuilder)builder).ReflectionBuilder; + return ((IIkvmReflectionFieldSymbolBuilder)builder).UnderlyingFieldBuilder; #else - return ((ReflectionFieldSymbolBuilder)builder).ReflectionBuilder; + return ((IReflectionFieldSymbolBuilder)builder).UnderlyingFieldBuilder; #endif } diff --git a/src/IKVM.Runtime/atomic.cs b/src/IKVM.Runtime/atomic.cs index d200ca7211..3467e39924 100644 --- a/src/IKVM.Runtime/atomic.cs +++ b/src/IKVM.Runtime/atomic.cs @@ -22,17 +22,10 @@ Jeroen Frijters */ -using System; - -#if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else using System.Reflection; -using System.Reflection.Emit; -#endif + +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using InstructionFlags = IKVM.Runtime.ClassFile.Method.InstructionFlags; @@ -63,10 +56,10 @@ internal static bool Emit(RuntimeByteCodeJavaType.FinishContext context, Runtime if (field != null && !field.IsStatic && field.IsVolatile && field.DeclaringType == wrapper && field.FieldTypeWrapper == vclass) { // everything matches up, now call the actual emitter - ilgen.Emit(OpCodes.Pop); - ilgen.Emit(OpCodes.Pop); - ilgen.Emit(OpCodes.Pop); - ilgen.Emit(OpCodes.Newobj, context.GetAtomicReferenceFieldUpdater(field)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Newobj, context.GetAtomicReferenceFieldUpdater(field)); return true; } } @@ -74,58 +67,58 @@ internal static bool Emit(RuntimeByteCodeJavaType.FinishContext context, Runtime return false; } - internal static void EmitImpl(RuntimeContext context, TypeBuilder tb, FieldInfo field) + internal static void EmitImpl(RuntimeContext context, ITypeSymbolBuilder tb, IFieldSymbol field) { EmitCompareAndSet(context, "compareAndSet", tb, field); EmitGet(context, tb, field); EmitSet(context, "set", tb, field); } - private static void EmitCompareAndSet(RuntimeContext context, string name, TypeBuilder tb, FieldInfo field) + private static void EmitCompareAndSet(RuntimeContext context, string name, ITypeSymbolBuilder tb, IFieldSymbol field) { - MethodBuilder compareAndSet = tb.DefineMethod(name, MethodAttributes.Public | MethodAttributes.Virtual, context.Types.Boolean, new Type[] { context.Types.Object, context.Types.Object, context.Types.Object }); - ILGenerator ilgen = compareAndSet.GetILGenerator(); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Castclass, field.DeclaringType); - ilgen.Emit(OpCodes.Ldflda, field); - ilgen.Emit(OpCodes.Ldarg_3); - ilgen.Emit(OpCodes.Castclass, field.FieldType); - ilgen.Emit(OpCodes.Ldarg_2); - ilgen.Emit(OpCodes.Castclass, field.FieldType); - ilgen.Emit(OpCodes.Call, MakeCompareExchange(context, field.FieldType)); - ilgen.Emit(OpCodes.Ldarg_2); - ilgen.Emit(OpCodes.Ceq); - ilgen.Emit(OpCodes.Ret); + var compareAndSet = tb.DefineMethod(name, MethodAttributes.Public | MethodAttributes.Virtual, context.Types.Boolean, [context.Types.Object, context.Types.Object, context.Types.Object]); + var ilgen = compareAndSet.GetILGenerator(); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, field.DeclaringType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldflda, field); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_3); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, field.FieldType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_2); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, field.FieldType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, MakeCompareExchange(context, field.FieldType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_2); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ceq); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } - internal static MethodInfo MakeCompareExchange(RuntimeContext context, Type type) + internal static IMethodSymbol MakeCompareExchange(RuntimeContext context, ITypeSymbol type) { return context.InterlockedMethods.CompareExchangeOfT.MakeGenericMethod(type); } - static void EmitGet(RuntimeContext context, TypeBuilder tb, FieldInfo field) + static void EmitGet(RuntimeContext context, ITypeSymbolBuilder tb, IFieldSymbol field) { - MethodBuilder get = tb.DefineMethod("get", MethodAttributes.Public | MethodAttributes.Virtual, context.Types.Object, new Type[] { context.Types.Object }); - ILGenerator ilgen = get.GetILGenerator(); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Castclass, field.DeclaringType); - ilgen.Emit(OpCodes.Volatile); - ilgen.Emit(OpCodes.Ldfld, field); - ilgen.Emit(OpCodes.Ret); + var get = tb.DefineMethod("get", MethodAttributes.Public | MethodAttributes.Virtual, context.Types.Object, [context.Types.Object]); + var ilgen = get.GetILGenerator(); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, field.DeclaringType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Volatile); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldfld, field); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } - static void EmitSet(RuntimeContext context, string name, TypeBuilder tb, FieldInfo field) + static void EmitSet(RuntimeContext context, string name, ITypeSymbolBuilder tb, IFieldSymbol field) { - MethodBuilder set = tb.DefineMethod(name, MethodAttributes.Public | MethodAttributes.Virtual, context.Types.Void, new Type[] { context.Types.Object, context.Types.Object }); - CodeEmitter ilgen = context.CodeEmitterFactory.Create(set); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Castclass, field.DeclaringType); - ilgen.Emit(OpCodes.Ldarg_2); - ilgen.Emit(OpCodes.Castclass, field.FieldType); - ilgen.Emit(OpCodes.Volatile); - ilgen.Emit(OpCodes.Stfld, field); + var set = tb.DefineMethod(name, MethodAttributes.Public | MethodAttributes.Virtual, context.Types.Void, [context.Types.Object, context.Types.Object]); + var ilgen = context.CodeEmitterFactory.Create(set); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, field.DeclaringType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_2); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, field.FieldType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Volatile); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stfld, field); ilgen.EmitMemoryBarrier(); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); } @@ -136,11 +129,11 @@ class InterlockedMethods readonly RuntimeContext context; - internal readonly MethodInfo AddInt32; - internal readonly MethodInfo CompareExchangeInt32; - internal readonly MethodInfo CompareExchangeInt64; - internal readonly MethodInfo CompareExchangeOfT; - internal readonly MethodInfo ExchangeOfT; + internal readonly IMethodSymbol AddInt32; + internal readonly IMethodSymbol CompareExchangeInt32; + internal readonly IMethodSymbol CompareExchangeInt64; + internal readonly IMethodSymbol CompareExchangeOfT; + internal readonly IMethodSymbol ExchangeOfT; /// /// Initializes a new instance. @@ -150,11 +143,11 @@ public InterlockedMethods(RuntimeContext context) { this.context = context; - var type = context.Resolver.ResolveCoreType(typeof(System.Threading.Interlocked).FullName).AsReflection(); + var type = context.Resolver.ResolveCoreType(typeof(System.Threading.Interlocked).FullName); AddInt32 = type.GetMethod("Add", [context.Types.Int32.MakeByRefType(), context.Types.Int32]); - CompareExchangeInt32 = type.GetMethod("CompareExchange", new Type[] { context.Types.Int32.MakeByRefType(), context.Types.Int32, context.Types.Int32 }); - CompareExchangeInt64 = type.GetMethod("CompareExchange", new Type[] { context.Types.Int64.MakeByRefType(), context.Types.Int64, context.Types.Int64 }); - foreach (MethodInfo m in type.GetMethods()) + CompareExchangeInt32 = type.GetMethod("CompareExchange", [context.Types.Int32.MakeByRefType(), context.Types.Int32, context.Types.Int32]); + CompareExchangeInt64 = type.GetMethod("CompareExchange", [context.Types.Int64.MakeByRefType(), context.Types.Int64, context.Types.Int64]); + foreach (var m in type.GetMethods()) { if (m.IsGenericMethodDefinition) { diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index 72f7e81b48..54e99b691a 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -26,13 +26,12 @@ Jeroen Frijters using System.Diagnostics; using System.Diagnostics.SymbolStore; -using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Attributes; using IKVM.ByteCode; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; using Type = IKVM.Reflection.Type; @@ -45,7 +44,6 @@ Jeroen Frijters using LocalVariableTableEntry = IKVM.Runtime.ClassFile.Method.LocalVariableTableEntry; using Instruction = IKVM.Runtime.ClassFile.Method.Instruction; using InstructionFlags = IKVM.Runtime.ClassFile.Method.InstructionFlags; -using System.Runtime.CompilerServices; namespace IKVM.Runtime { @@ -85,12 +83,12 @@ class CompilerFactory readonly RuntimeContext context; readonly bool bootstrap; - MethodInfo unmapExceptionMethod; - MethodInfo fixateExceptionMethod; - MethodInfo suppressFillInStackTraceMethod; - MethodInfo getTypeFromHandleMethod; - MethodInfo getTypeMethod; - MethodInfo keepAliveMethod; + IMethodSymbol unmapExceptionMethod; + IMethodSymbol fixateExceptionMethod; + IMethodSymbol suppressFillInStackTraceMethod; + IMethodSymbol getTypeFromHandleMethod; + IMethodSymbol getTypeMethod; + IMethodSymbol keepAliveMethod; RuntimeJavaMethod getClassFromTypeHandle; RuntimeJavaMethod getClassFromTypeHandle2; @@ -104,7 +102,7 @@ public CompilerFactory(RuntimeContext context, bool bootstrap) this.context = context; this.bootstrap = bootstrap; - if (bootstrap && Throwable.TypeAsBaseType is TypeBuilder) + if (bootstrap && Throwable.TypeAsBaseType is ITypeSymbolBuilder) foreach (var m in Throwable.GetMethods()) m.Link(); @@ -114,17 +112,17 @@ public CompilerFactory(RuntimeContext context, bool bootstrap) public RuntimeJavaType Throwable => context.JavaBase.TypeOfjavaLangThrowable; - public MethodInfo UnmapExceptionMethod => unmapExceptionMethod ??= bootstrap ? (MethodInfo)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", new Type[] { context.Types.Exception }); + public IMethodSymbol UnmapExceptionMethod => unmapExceptionMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", new ITypeSymbol[] { context.Types.Exception }); - public MethodInfo FixateExceptionMethod => fixateExceptionMethod ??= bootstrap ? (MethodInfo)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", new Type[] { context.Types.Exception }); + public IMethodSymbol FixateExceptionMethod => fixateExceptionMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", new ITypeSymbol[] { context.Types.Exception }); - public MethodInfo SuppressFillInStackTraceMethod => suppressFillInStackTraceMethod ??= bootstrap ? (MethodInfo)Throwable.GetMethodWrapper("__", "()V", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", []); + public IMethodSymbol SuppressFillInStackTraceMethod => suppressFillInStackTraceMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "()V", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", []); - public MethodInfo GetTypeFromHandleMethod => getTypeFromHandleMethod ??= context.Types.Type.GetMethod("GetTypeFromHandle", BindingFlags.Static | BindingFlags.Public, null, [context.Types.RuntimeTypeHandle], null); + public IMethodSymbol GetTypeFromHandleMethod => getTypeFromHandleMethod ??= context.Types.Type.GetMethod("GetTypeFromHandle", BindingFlags.Static | BindingFlags.Public, [context.Types.RuntimeTypeHandle]); - public MethodInfo GetTypeMethod => getTypeMethod ??= context.Types.Object.GetMethod("GetType", BindingFlags.Public | BindingFlags.Instance, null, [], null); + public IMethodSymbol GetTypeMethod => getTypeMethod ??= context.Types.Object.GetMethod("GetType", BindingFlags.Public | BindingFlags.Instance, []); - public MethodInfo KeepAliveMethod => keepAliveMethod ??= context.Resolver.ResolveCoreType(typeof(GC).FullName).AsReflection().GetMethod("KeepAlive", BindingFlags.Static | BindingFlags.Public, null, [context.Types.Object], null); + public IMethodSymbol KeepAliveMethod => keepAliveMethod ??= context.Resolver.ResolveCoreType(typeof(GC).FullName).GetMethod("KeepAlive", BindingFlags.Static | BindingFlags.Public, [context.Types.Object]); public RuntimeJavaMethod GetClassFromTypeHandle => getClassFromTypeHandle ??= context.ClassLoaderFactory.LoadClassCritical("ikvm.runtime.Util").GetMethodWrapper("getClassFromTypeHandle", "(Lcli.System.RuntimeTypeHandle;)Ljava.lang.Class;", false); @@ -2723,19 +2721,19 @@ internal static bool HasUnloadable(RuntimeJavaType[] args, RuntimeJavaType ret) static class InvokeDynamicBuilder { - internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDynamic cpi, Type delegateType) + internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDynamic cpi, ITypeSymbol delegateType) { var typeofOpenIndyCallSite = compiler.finish.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.IndyCallSite`1").AsReflection(); var methodLookup = compiler.finish.Context.ClassLoaderFactory.LoadClassCritical("java.lang.invoke.MethodHandles").GetMethodWrapper("lookup", "()Ljava.lang.invoke.MethodHandles$Lookup;", false); methodLookup.Link(); var typeofIndyCallSite = typeofOpenIndyCallSite.MakeGenericType(delegateType); - MethodInfo methodCreateBootStrap; - MethodInfo methodGetTarget; + IMethodSymbol methodCreateBootStrap; + IMethodSymbol methodGetTarget; if (ReflectUtil.ContainsTypeBuilder(typeofIndyCallSite)) { - methodCreateBootStrap = TypeBuilder.GetMethod(typeofIndyCallSite, typeofOpenIndyCallSite.GetMethod("CreateBootstrap")); - methodGetTarget = TypeBuilder.GetMethod(typeofIndyCallSite, typeofOpenIndyCallSite.GetMethod("GetTarget")); + methodCreateBootStrap = ITypeSymbolBuilder.GetMethod(typeofIndyCallSite, typeofOpenIndyCallSite.GetMethod("CreateBootstrap")); + methodGetTarget = ITypeSymbolBuilder.GetMethod(typeofIndyCallSite, typeofOpenIndyCallSite.GetMethod("GetTarget")); } else { @@ -2758,7 +2756,7 @@ internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDyn compiler.ilGenerator.Emit(OpCodes.Call, methodGetTarget); } - static MethodBuilder CreateBootstrapStub(Compiler compiler, ClassFile.ConstantPoolItemInvokeDynamic cpi, Type delegateType, TypeBuilder tb, FieldBuilder fb, MethodInfo methodGetTarget) + static IMethodSymbolBuilder CreateBootstrapStub(Compiler compiler, ClassFile.ConstantPoolItemInvokeDynamic cpi, ITypeSymbol delegateType, ITypeSymbolBuilder tb, IFieldSymbolBuilder fb, IMethodSymbol methodGetTarget) { var typeofCallSite = compiler.finish.Context.ClassLoaderFactory.LoadClassCritical("java.lang.invoke.CallSite").TypeAsSignatureType; var args = []; @@ -3045,7 +3043,7 @@ void EmitInvokeDynamic(ClassFile.ConstantPoolItemInvokeDynamic cpi) sealed class MethodHandleConstant { - FieldBuilder field; + IFieldSymbolBuilder field; internal void Emit(Compiler compiler, CodeEmitter ilgen, MethodHandleConstantHandle handle) { @@ -3067,7 +3065,7 @@ internal void Emit(Compiler compiler, CodeEmitter ilgen, MethodHandleConstantHan sealed class MethodTypeConstant { - FieldBuilder field; + IFieldSymbolBuilder field; bool dynamic; internal void Emit(Compiler compiler, CodeEmitter ilgen, MethodTypeConstantHandle handle) @@ -3088,7 +3086,7 @@ internal void Emit(Compiler compiler, CodeEmitter ilgen, MethodTypeConstantHandl } } - static FieldBuilder CreateField(Compiler compiler, MethodTypeConstantHandle handle, ref bool dynamic) + static IFieldSymbolBuilder CreateField(Compiler compiler, MethodTypeConstantHandle handle, ref bool dynamic) { var cpi = compiler.classFile.GetConstantPoolConstantMethodType(handle); var args = cpi.GetArgTypes(); @@ -3504,10 +3502,11 @@ private void EmitInvokeMaxArity(CodeEmitter ilgen) temps[i] = ilgen.DeclareLocal(args[i].TypeAsSignatureType); ilgen.Emit(OpCodes.Stloc, temps[i]); } - Type delegateType = compiler.finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); + + var delegateType = compiler.finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodHandle.GetMethodWrapper("asType", "(Ljava.lang.invoke.MethodType;)Ljava.lang.invoke.MethodHandle;", false).EmitCallvirt(ilgen); - MethodInfo mi = compiler.finish.Context.ByteCodeHelperMethods.GetDelegateForInvokeExact.MakeGenericMethod(delegateType); + var mi = compiler.finish.Context.ByteCodeHelperMethods.GetDelegateForInvokeExact.MakeGenericMethod(delegateType); ilgen.Emit(OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) { @@ -3531,10 +3530,10 @@ private void EmitInvoke(CodeEmitter ilgen) ilgen.Emit(OpCodes.Stloc, temps[i]); } Type delegateType = compiler.finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); - MethodInfo mi = ilgen.Context.ByteCodeHelperMethods.GetDelegateForInvoke.MakeGenericMethod(delegateType); + var mi = ilgen.Context.ByteCodeHelperMethods.GetDelegateForInvoke.MakeGenericMethod(delegateType); var typeofInvokeCache = compiler.finish.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.InvokeCache`1").AsReflection(); - FieldBuilder fb = compiler.finish.DefineMethodHandleInvokeCacheField(typeofInvokeCache.MakeGenericType(delegateType)); + var fb = compiler.finish.DefineMethodHandleInvokeCacheField(typeofInvokeCache.MakeGenericType(delegateType)); ilgen.Emit(OpCodes.Ldloc, temps[0]); if (HasUnloadable(cpi.GetArgTypes(), cpi.GetRetType())) { @@ -3579,8 +3578,8 @@ internal static void EmitInvokeBasic(RuntimeContext context, CodeEmitter ilgen, } temps[0] = ilgen.DeclareLocal(args[0].TypeAsSignatureType); ilgen.Emit(OpCodes.Stloc, temps[0]); - Type delegateType = context.MethodHandleUtil.CreateMemberWrapperDelegateType(args, retType); - MethodInfo mi = context.ByteCodeHelperMethods.GetDelegateForInvokeBasic.MakeGenericMethod(delegateType); + var delegateType = context.MethodHandleUtil.CreateMemberWrapperDelegateType(args, retType); + var mi = context.ByteCodeHelperMethods.GetDelegateForInvokeBasic.MakeGenericMethod(delegateType); ilgen.Emit(OpCodes.Ldloc, temps[0]); ilgen.Emit(OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) @@ -3616,7 +3615,8 @@ internal override void EmitNewobj(CodeEmitter ilgen) private sealed class DynamicFieldBinder { - private MethodInfo method; + + private IMethodSymbol method; internal void Emit(Compiler compiler, ClassFile.ConstantPoolItemFieldref cpi, MethodHandleKind kind) { @@ -3626,7 +3626,7 @@ internal void Emit(Compiler compiler, ClassFile.ConstantPoolItemFieldref cpi, Me compiler.ilGenerator.Emit(OpCodes.Call, method); } - private static MethodInfo CreateMethod(Compiler compiler, ClassFile.ConstantPoolItemFieldref cpi, MethodHandleKind kind) + private static IMethodSymbol CreateMethod(Compiler compiler, ClassFile.ConstantPoolItemFieldref cpi, MethodHandleKind kind) { RuntimeJavaType ret; RuntimeJavaType[] args; @@ -3666,7 +3666,7 @@ internal RuntimeJavaMethod Get(Compiler compiler, MethodHandleKind kind, ClassFi return mw ??= new DynamicBinderMethodWrapper(cpi, Emit(compiler, kind, cpi, privileged), kind); } - private static MethodInfo Emit(Compiler compiler, MethodHandleKind kind, ClassFile.ConstantPoolItemMI cpi, bool privileged) + private static IMethodSymbol Emit(Compiler compiler, MethodHandleKind kind, ClassFile.ConstantPoolItemMI cpi, bool privileged) { RuntimeJavaType ret; RuntimeJavaType[] args; @@ -3688,23 +3688,23 @@ private static MethodInfo Emit(Compiler compiler, MethodHandleKind kind, ClassFi return Emit(compiler, kind, cpi, ret, args, privileged); } - internal static MethodInfo Emit(Compiler compiler, MethodHandleKind kind, ClassFile.ConstantPoolItemFMI cpi, RuntimeJavaType ret, RuntimeJavaType[] args, bool privileged) + internal static IMethodSymbol Emit(Compiler compiler, MethodHandleKind kind, ClassFile.ConstantPoolItemFMI cpi, RuntimeJavaType ret, RuntimeJavaType[] args, bool privileged) { var ghostTarget = (kind == MethodHandleKind.InvokeSpecial || kind == MethodHandleKind.InvokeVirtual || kind == MethodHandleKind.InvokeInterface) && args[0].IsGhost; var delegateType = compiler.finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, ret); var fb = compiler.finish.DefineMethodHandleInvokeCacheField(delegateType); - var types = new Type[args.Length]; + var types = new ITypeSymbol[args.Length]; for (int i = 0; i < types.Length; i++) types[i] = args[i].TypeAsSignatureType; if (ghostTarget) types[0] = types[0].MakeByRefType(); - MethodBuilder mb = compiler.finish.DefineMethodHandleDispatchStub(ret.TypeAsSignatureType, types); - CodeEmitter ilgen = compiler.finish.Context.CodeEmitterFactory.Create(mb); + var mb = compiler.finish.DefineMethodHandleDispatchStub(ret.TypeAsSignatureType, types); + var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldsfld, fb); - CodeEmitterLabel label = ilgen.DefineLabel(); + var label = ilgen.DefineLabel(); ilgen.EmitBrtrue(label); ilgen.EmitLdc_I4((int)kind); ilgen.Emit(OpCodes.Ldstr, cpi.Class); @@ -3740,9 +3740,9 @@ internal static MethodInfo Emit(Compiler compiler, MethodHandleKind kind, ClassF sealed class DynamicBinderMethodWrapper : RuntimeJavaMethod { - readonly MethodInfo method; + readonly IMethodSymbol method; - internal DynamicBinderMethodWrapper(ClassFile.ConstantPoolItemMI cpi, MethodInfo method, MethodHandleKind kind) : + internal DynamicBinderMethodWrapper(ClassFile.ConstantPoolItemMI cpi, IMethodSymbol method, MethodHandleKind kind) : base(cpi.GetClassType(), cpi.Name, cpi.Signature, null, cpi.GetRetType(), cpi.GetArgTypes(), kind == MethodHandleKind.InvokeStatic ? Modifiers.Public | Modifiers.Static : Modifiers.Public, MemberFlags.None) { this.method = method; @@ -3955,7 +3955,7 @@ LocalVar StoreLocal(int instructionIndex) return v; } - Type GetLocalBuilderType(RuntimeJavaType tw) + ITypeSymbol GetLocalBuilderType(RuntimeJavaType tw) { if (tw.IsUnloadable) return finish.Context.Types.Object; From 6425e9b95b7b0040c1b4356617d82abc70bf5878 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 20 Sep 2024 18:04:32 -0500 Subject: [PATCH 10/59] Rebuild. --- .../Collections/IndexRangeDictionaryTests.cs | 66 +- .../IkvmReflectionSymbolTests.cs | 54 +- .../Collections/IndexRangeDictionary.cs | 103 +-- src/IKVM.CoreLib/IKVM.CoreLib.csproj | 8 - src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs | 6 +- src/IKVM.CoreLib/Symbols/Emit/ILabel.cs | 4 + .../Symbols/Emit/IModuleSymbolBuilder.cs | 14 +- .../Symbols/Emit/ITypeSymbolBuilder.cs | 2 +- src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 21 +- .../IIkvmReflectionAssemblySymbolBuilder.cs | 9 +- ...IIkvmReflectionConstructorSymbolBuilder.cs | 5 +- .../Emit/IIkvmReflectionEventSymbolBuilder.cs | 5 +- .../Emit/IIkvmReflectionFieldSymbolBuilder.cs | 2 +- ...ectionGenericTypeParameterSymbolBuilder.cs | 2 +- .../IIkvmReflectionMemberSymbolBuilder.cs | 7 +- .../IIkvmReflectionMethodBaseSymbolBuilder.cs | 10 +- .../IIkvmReflectionMethodSymbolBuilder.cs | 9 +- .../IIkvmReflectionModuleSymbolBuilder.cs | 58 +- .../IIkvmReflectionParameterSymbolBuilder.cs | 2 +- .../IIkvmReflectionPropertySymbolBuilder.cs | 6 +- .../Emit/IIkvmReflectionSymbolBuilder.cs | 85 ++- .../Emit/IIkvmReflectionTypeSymbolBuilder.cs | 44 +- .../IkvmReflectionAssemblySymbolBuilder.cs | 43 +- .../IkvmReflectionConstructorSymbolBuilder.cs | 8 +- .../Emit/IkvmReflectionEventSymbolBuilder.cs | 2 +- .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 2 +- ...ectionGenericTypeParameterSymbolBuilder.cs | 467 +++++++----- .../Emit/IkvmReflectionILGenerator.cs | 499 ++++++++++++ .../Emit/IkvmReflectionLabel.cs | 28 + .../Emit/IkvmReflectionLocalBuilder.cs | 55 ++ .../Emit/IkvmReflectionMemberSymbolBuilder.cs | 259 ++++--- .../IkvmReflectionMethodBaseSymbolBuilder.cs | 27 +- .../Emit/IkvmReflectionMethodSymbolBuilder.cs | 48 +- .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 249 +++--- .../IkvmReflectionParameterSymbolBuilder.cs | 14 +- .../IkvmReflectionPropertySymbolBuilder.cs | 16 +- .../Emit/IkvmReflectionSymbolBuilder.cs | 12 +- .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 474 +++++++----- .../IIkvmReflectionAssemblySymbol.cs | 7 - .../IIkvmReflectionMethodBaseSymbol.cs | 7 + .../IIkvmReflectionMethodSymbol.cs | 7 + .../IIkvmReflectionModuleSymbol.cs | 48 +- .../IIkvmReflectionParameterSymbol.cs | 4 +- .../IIkvmReflectionPropertySymbol.cs | 7 + .../IkvmReflection/IIkvmReflectionSymbol.cs | 79 +- .../IIkvmReflectionTypeSymbol.cs | 85 ++- .../IkvmReflectionAssemblySymbol.cs | 33 +- .../IkvmReflectionEventTable.cs | 94 +++ .../IkvmReflectionFieldTable.cs | 80 ++ ...kvmReflectionGenericTypeParameterSymbol.cs | 456 ++++++----- ...IkvmReflectionGenericTypeParameterTable.cs | 82 ++ .../IkvmReflectionMemberSymbol.cs | 153 +--- .../IkvmReflectionMethodBaseSymbol.cs | 12 + .../IkvmReflectionMethodSpecTable.cs | 66 ++ .../IkvmReflectionMethodSymbol.cs | 15 + .../IkvmReflectionMethodTable.cs | 157 ++++ .../IkvmReflectionModuleMetadata.cs | 480 ------------ .../IkvmReflectionModuleSymbol.cs | 99 +-- ...tadata.cs => IkvmReflectionModuleTable.cs} | 31 +- .../IkvmReflectionParameterSymbol.cs | 10 +- .../IkvmReflectionParameterTable.cs | 94 +++ .../IkvmReflectionPropertySymbol.cs | 17 + .../IkvmReflectionPropertyTable.cs | 80 ++ .../IkvmReflection/IkvmReflectionSymbol.cs | 51 +- .../IkvmReflectionSymbolContext.cs | 76 +- .../IkvmReflection/IkvmReflectionTypeImpl.cs | 587 --------------- .../IkvmReflectionTypeSpecTable.cs | 129 ++++ .../IkvmReflectionTypeSymbol.cs | 437 ++++++----- .../IkvmReflection/IkvmReflectionTypeTable.cs | 76 ++ .../IkvmReflection/IkvmReflectionUtil.cs | 140 +++- src/IKVM.CoreLib/Symbols/InterfaceMapping.cs | 10 +- .../ReflectionConstructorSymbolBuilder.cs | 6 +- .../Reflection/Emit/ReflectionILGenerator.cs | 265 +++++++ .../Reflection/Emit/ReflectionLabel.cs | 29 + .../Reflection/Emit/ReflectionLocalBuilder.cs | 59 ++ .../Emit/ReflectionMethodSymbolBuilder.cs | 14 +- .../Emit/ReflectionModuleSymbolBuilder.cs | 13 +- .../Emit/ReflectionTypeSymbolBuilder.cs | 2 +- .../Symbols/Reflection/IReflectionSymbol.cs | 7 + .../Reflection/ReflectionAssemblyMetadata.cs | 2 +- .../Reflection/ReflectionModuleSymbol.cs | 2 - .../Symbols/Reflection/ReflectionSymbol.cs | 52 +- .../Reflection/ReflectionSymbolContext.cs | 28 + .../Symbols/Reflection/ReflectionTypeImpl.cs | 2 +- .../Symbols/Reflection/ReflectionUtil.cs | 89 +++ src/IKVM.Reflection/Emit/ILGenerator.cs | 19 + src/IKVM.Reflection/MemberInfo.cs | 2 + src/IKVM.Reflection/Type.cs | 2 +- src/IKVM.Runtime/AttributeHelper.cs | 4 +- src/IKVM.Runtime/CodeEmitter.cs | 26 +- src/IKVM.Runtime/CodeEmitterLocal.cs | 21 +- src/IKVM.Runtime/DynamicClassLoader.cs | 64 +- src/IKVM.Runtime/ExceptionHelper.cs | 34 +- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 35 +- .../Java/Externs/ikvm/runtime/Util.cs | 62 +- .../Java/Externs/java/lang/Package.cs | 2 +- .../Java/Externs/sun/misc/Unsafe.cs | 8 +- src/IKVM.Runtime/LambdaMetafactory.cs | 12 +- src/IKVM.Runtime/MethodHandleUtil.compiler.cs | 49 +- src/IKVM.Runtime/RuntimeArrayJavaType.cs | 2 +- .../RuntimeAssemblyClassLoader.cs | 24 +- .../RuntimeByteCodeJavaType.FinishContext.cs | 34 +- ...peImpl.DelegateConstructorMethodWrapper.cs | 22 +- ...ypeImpl.DelegateInvokeStubMethodWrapper.cs | 15 +- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 25 +- src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 13 +- src/IKVM.Runtime/RuntimeJavaType.cs | 10 +- .../RuntimeManagedByteCodeJavaType.cs | 22 +- .../RuntimeManagedJavaType.ByRefJavaMethod.cs | 13 +- .../RuntimeManagedJavaType.CloneJavaMethod.cs | 14 +- ...agedJavaType.DelegateInnerClassJavaType.cs | 2 +- ...RuntimeManagedJavaType.EnumEnumJavaType.cs | 13 +- src/IKVM.Runtime/RuntimeManagedJavaType.cs | 25 +- src/IKVM.Runtime/RuntimeUnloadableJavaType.cs | 12 +- src/IKVM.Runtime/Serialization.cs | 43 +- src/IKVM.Runtime/compiler.cs | 710 +++++++++--------- src/IKVM.Runtime/intrinsics.cs | 22 +- src/IKVM.Tools.Exporter/ExportImpl.cs | 6 +- .../ManagedTypeResolver.cs | 127 ++-- src/ikvmstub/Properties/launchSettings.json | 2 +- src/ikvmstub/ikvmstub.csproj | 2 +- testenvironments.json | 1 - 122 files changed, 5190 insertions(+), 3313 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLabel.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLocalBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs rename src/IKVM.CoreLib/Symbols/IkvmReflection/{IkvmReflectionAssemblyMetadata.cs => IkvmReflectionModuleTable.cs} (59%) create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLabel.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLocalBuilder.cs diff --git a/src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs b/src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs index b42cc97a80..04f64fc0cc 100644 --- a/src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs +++ b/src/IKVM.CoreLib.Tests/Collections/IndexRangeDictionaryTests.cs @@ -11,12 +11,47 @@ namespace IKVM.CoreLib.Tests.Collections public class IndexRangeDictionaryTests { + [TestMethod] + public void AlignTowardsInfinity() + { + IndexRangeDictionary.AlignTowardsInfinity(0).Should().Be(0); + IndexRangeDictionary.AlignTowardsInfinity(1).Should().Be(8); + IndexRangeDictionary.AlignTowardsInfinity(7).Should().Be(8); + IndexRangeDictionary.AlignTowardsInfinity(8).Should().Be(8); + IndexRangeDictionary.AlignTowardsInfinity(9).Should().Be(16); + + IndexRangeDictionary.AlignTowardsInfinity(-0).Should().Be(-0); + IndexRangeDictionary.AlignTowardsInfinity(-1).Should().Be(-8); + IndexRangeDictionary.AlignTowardsInfinity(-7).Should().Be(-8); + IndexRangeDictionary.AlignTowardsInfinity(-8).Should().Be(-8); + IndexRangeDictionary.AlignTowardsInfinity(-9).Should().Be(-16); + } + + [TestMethod] + public void AlignTowardsZero() + { + IndexRangeDictionary.AlignTowardsZero(0).Should().Be(0); + IndexRangeDictionary.AlignTowardsZero(1).Should().Be(0); + IndexRangeDictionary.AlignTowardsZero(7).Should().Be(0); + IndexRangeDictionary.AlignTowardsZero(8).Should().Be(8); + IndexRangeDictionary.AlignTowardsZero(9).Should().Be(8); + + IndexRangeDictionary.AlignTowardsZero(-0).Should().Be(-0); + IndexRangeDictionary.AlignTowardsZero(-1).Should().Be(-0); + IndexRangeDictionary.AlignTowardsZero(-7).Should().Be(-0); + IndexRangeDictionary.AlignTowardsZero(-8).Should().Be(-8); + IndexRangeDictionary.AlignTowardsZero(-9).Should().Be(-8); + } + [TestMethod] public void CanAddBasicItem() { var d = new IndexRangeDictionary(); d[0] = "Item1"; d[0].Should().Be("Item1"); + d._minKey.Should().Be(0); + d._maxKey.Should().Be(0); + d._items.Length.Should().Be(8); } [TestMethod] @@ -25,6 +60,9 @@ public void CanAddOffsetItem() var d = new IndexRangeDictionary(); d[10] = "Item1"; d[10].Should().Be("Item1"); + d._minKey.Should().Be(8); + d._maxKey.Should().Be(16); + d._items.Length.Should().Be(16); } [TestMethod] @@ -32,10 +70,19 @@ public void CanAddSparseRange() { var d = new IndexRangeDictionary(); d[10] = "Item1"; + d[10].Should().Be("Item1"); + d._minKey.Should().Be(8); + d._maxKey.Should().Be(16); + d._items.Length.Should().Be(16); d[20] = "Item2"; - d[9].Should().BeNull(); d[10].Should().Be("Item1"); - d[11].Should().BeNull(); + d[20].Should().Be("Item2"); + d._minKey.Should().Be(8); + d._maxKey.Should().Be(24); + d._items.Length.Should().Be(32); + d[5].Should().BeNull(); + d[10].Should().Be("Item1"); + d[15].Should().BeNull(); d[19].Should().BeNull(); d[20].Should().Be("Item2"); d[21].Should().BeNull(); @@ -46,9 +93,22 @@ public void CanAddMaxBeforeMin() { var d = new IndexRangeDictionary(); d[20] = "Item1"; - d[10] = "Item2"; d[20].Should().Be("Item1"); + d[10] = "Item2"; d[10].Should().Be("Item2"); + d[20] = "Item1"; + d[20].Should().Be("Item1"); + } + + [TestMethod] + public void ShiftShouldBeEmpty() + { + var d = new IndexRangeDictionary(); + d[2] = "Item2"; + d[2].Should().Be("Item2"); + d[0] = "Item0"; + d[0].Should().Be("Item0"); + d[1].Should().BeNull(); } } diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index b33adef9ee..0147fea237 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -66,7 +66,7 @@ public void Setup() [TestMethod] public void SameTypeShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); s1.Should().BeOfType(); @@ -76,7 +76,7 @@ public void SameTypeShouldBeSame() [TestMethod] public void GenericTypeDefinitionShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); var s2 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); s1.Should().BeSameAs(s2); @@ -85,7 +85,7 @@ public void GenericTypeDefinitionShouldBeSame() [TestMethod] public void GenericTypeShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); var s2 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); s1.Should().BeSameAs(s2); @@ -94,7 +94,7 @@ public void GenericTypeShouldBeSame() [TestMethod] public void ArrayTypeShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); s1.Should().BeSameAs(s2); @@ -103,7 +103,7 @@ public void ArrayTypeShouldBeSame() [TestMethod] public void SZArrayTypeShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); s1.Should().BeSameAs(s2); @@ -112,7 +112,7 @@ public void SZArrayTypeShouldBeSame() [TestMethod] public unsafe void PointerTypeShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakePointerType()); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakePointerType()); s1.Should().BeSameAs(s2); @@ -121,7 +121,7 @@ public unsafe void PointerTypeShouldBeSame() [TestMethod] public unsafe void ByRefTypeShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeByRefType()); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeByRefType()); s1.Should().BeSameAs(s2); @@ -130,7 +130,7 @@ public unsafe void ByRefTypeShouldBeSame() [TestMethod] public void EnumTypeShouldBeSame() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.AttributeTargets")); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.AttributeTargets")); s1.Should().BeSameAs(s2); @@ -139,7 +139,7 @@ public void EnumTypeShouldBeSame() [TestMethod] public void CanResolveType() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); s.Name.Should().Be("Object"); s.FullName.Should().Be("System.Object"); @@ -148,7 +148,7 @@ public void CanResolveType() [TestMethod] public void CanResolveFieldOfGenericTypeDefinition() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); s.IsGenericType.Should().BeTrue(); s.IsGenericTypeDefinition.Should().BeTrue(); @@ -161,7 +161,7 @@ public void CanResolveFieldOfGenericTypeDefinition() [TestMethod] public void CanResolveFieldOfGenericType() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); s.IsGenericType.Should().BeTrue(); s.IsGenericTypeDefinition.Should().BeFalse(); @@ -175,7 +175,7 @@ public void CanResolveFieldOfGenericType() [TestMethod] public void CanResolveMethod() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); var m = s.GetMethod("ToString"); m.Name.Should().Be("ToString"); @@ -190,7 +190,7 @@ public void CanResolveMethod() [TestMethod] public void CanResolveGenericMethod() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.ValueTuple")); var m = s.GetMethods().FirstOrDefault(i => i.Name == "Create" && i.GetGenericArguments().Length == 1); m.Name.Should().Be("Create"); @@ -205,7 +205,7 @@ public void CanResolveGenericMethod() [TestMethod] public void CanResolveParameters() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); var m = s.GetMethod("ReferenceEquals"); m.Name.Should().Be("ReferenceEquals"); @@ -247,7 +247,7 @@ class ClassWithAttributeWithType [TestMethod] public void CanReadCustomAttributes() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); var v = a.Value.ConstructorArguments[0].Value; @@ -257,7 +257,7 @@ public void CanReadCustomAttributes() [TestMethod] public void CanResolveAssemblyBuilder() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var assemblySymbol = c.GetOrCreateAssemblySymbol(a); assemblySymbol.Should().BeOfType(); @@ -267,7 +267,7 @@ public void CanResolveAssemblyBuilder() [TestMethod] public void CanResolveModuleBuilder() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var moduleSymbol = c.GetOrCreateModuleSymbol(m); @@ -278,7 +278,7 @@ public void CanResolveModuleBuilder() [TestMethod] public void CanResolveTypeBuilder() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); @@ -291,7 +291,7 @@ public void CanResolveTypeBuilder() [TestMethod] public void CanResolveMultipleTypeBuilders() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); @@ -310,7 +310,7 @@ public void CanResolveMultipleTypeBuilders() [TestMethod] public void CanResolveMethodBuilder() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -324,7 +324,7 @@ public void CanResolveMethodBuilder() [TestMethod] public void CanResolveMultipleMethodBuilders() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -343,7 +343,7 @@ public void CanResolveMultipleMethodBuilders() [TestMethod] public void CanResolveFieldBuilder() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -357,7 +357,7 @@ public void CanResolveFieldBuilder() [TestMethod] public void CanResolveMultipleFieldBuilders() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -376,7 +376,7 @@ public void CanResolveMultipleFieldBuilders() [TestMethod] public void CanResolvePropertyBuilder() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -390,7 +390,7 @@ public void CanResolvePropertyBuilder() [TestMethod] public void CanResolveMultiplePropertyBuilders() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -409,7 +409,7 @@ public void CanResolveMultiplePropertyBuilders() [TestMethod] public void CanResolveEventBuilder() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -423,7 +423,7 @@ public void CanResolveEventBuilder() [TestMethod] public void CanResolveMultipleEventBuilders() { - var c = new IkvmReflectionSymbolContext(); + var c = new IkvmReflectionSymbolContext(universe); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); diff --git a/src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs b/src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs index deae4e8aed..e361df9bbb 100644 --- a/src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs +++ b/src/IKVM.CoreLib/Collections/IndexRangeDictionary.cs @@ -1,5 +1,6 @@ using System; using System.Diagnostics; +using System.Runtime.CompilerServices; namespace IKVM.CoreLib.Collections { @@ -11,15 +12,35 @@ namespace IKVM.CoreLib.Collections struct IndexRangeDictionary { - int _initialCapacity; + const int ALIGNMENT = 8; + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + static internal int AlignTowardsInfinity(int i) + { + if (i >= 0) + return (i + (ALIGNMENT - 1)) & -ALIGNMENT; + else + return -((-i + (ALIGNMENT - 1)) & -ALIGNMENT); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + static internal int AlignTowardsZero(int i) + { + if (i >= 0) + return i - (i % ALIGNMENT); + else + return -(-i - (-i % ALIGNMENT)); + } + int _maxCapacity; - int _minKey; - T?[]? _items; + internal int _minKey = 0; + internal int _maxKey = 0; + internal T?[] _items = []; /// /// Initializes a new instance. /// - public IndexRangeDictionary() : this(initialCapacity: 4, maxCapacity: int.MaxValue) + public IndexRangeDictionary() : this(maxCapacity: int.MaxValue) { } @@ -27,21 +48,18 @@ public IndexRangeDictionary() : this(initialCapacity: 4, maxCapacity: int.MaxVal /// /// Initializes a new instance. /// - public IndexRangeDictionary(int initialCapacity = 4, int maxCapacity = int.MaxValue) + public IndexRangeDictionary(int maxCapacity = int.MaxValue) { - if (initialCapacity < 0) - throw new ArgumentOutOfRangeException(nameof(initialCapacity)); if (maxCapacity < 0) throw new ArgumentOutOfRangeException(nameof(maxCapacity)); - _initialCapacity = initialCapacity; _maxCapacity = maxCapacity; } /// /// Gets the capacity of the dictionary. /// - public readonly int Capacity => _items?.Length ?? 0; + public readonly int Capacity => _items.Length; /// /// Gets or sets the item with the specified key, optionally growing the list to accomidate. @@ -61,47 +79,48 @@ public T? this[int key] /// public void EnsureCapacity(int key) { - // initial state, first item, hold only that - if (_items == null) + // on first hit, set keys to this key (not 0) + if (_items.Length == 0) { _minKey = key; - _items = new T[_initialCapacity]; + _maxKey = key; } - // key is less than minKey, grow and shift by difference - if (key < _minKey) - { - // increase length until we encompass key - var len = _items.Length; - while (key - _minKey + len - _items.Length < 0) - len *= 2; - - if (len > _maxCapacity || len < 0) - throw new InvalidOperationException(); + // calculate new min and max aligned + var newMin = Math.Min(_minKey, Math.Min(AlignTowardsZero(key), AlignTowardsInfinity(key))); + var newMax = Math.Max(_maxKey, Math.Max(AlignTowardsZero(key), AlignTowardsInfinity(key))); - var end = _items.Length - 1; - Array.Resize(ref _items, len); - for (int i = end; i >= 0; i--) - _items[i + _minKey - key] = _items[i]; - Array.Clear(_items, 0, end); + // calculate desired length + var len = Math.Max(_items.Length, 8); + while (len < newMax - newMin + 1) + len *= 2; - _minKey = key; - } + // calculate amount to shift + int sft = 0; + if (newMin < _minKey) + sft = _minKey - newMin; - // desired position if after the end of the array, we need to grow, but no copies needed - if (key - _minKey >= _items.Length) + // if we calculated any resize or shift operation, apply + if (_items.Length != len || sft > 0) { - // increase length until we encompass key - var len = _items.Length; - while (key - _minKey >= len) - len *= 2; - - if (len > _maxCapacity || len < 0) - throw new InvalidOperationException(); - - Array.Resize(ref _items, len); + // we will be copying data either to either existing array or new array + var src = _items; + if (_items.Length != len) + _items = new T[len]; + + // copy source data to destination at shift + // clear newly exposed positions + if (src.Length > 0) + { + Array.Copy(src, 0, _items, sft, _maxKey - _minKey + 1); + Array.Clear(_items, 0, sft); + } } + // reset our min and max range + _minKey = newMin; + _maxKey = newMax; + Debug.Assert(key - _minKey >= 0); Debug.Assert(key - _minKey < _items.Length); } @@ -113,7 +132,7 @@ public void EnsureCapacity(int key) readonly T? Get(int key) { var pos = key - _minKey; - if (_items == null || pos < 0 || pos >= _items.Length) + if (pos < 0 || pos >= _items.Length) return default; else return _items[pos]; @@ -121,7 +140,7 @@ public void EnsureCapacity(int key) /// /// Adds a new item to the list. - /// + /// /// /// void Set(int key, T? value) diff --git a/src/IKVM.CoreLib/IKVM.CoreLib.csproj b/src/IKVM.CoreLib/IKVM.CoreLib.csproj index 13b96c3da6..13d67775f9 100644 --- a/src/IKVM.CoreLib/IKVM.CoreLib.csproj +++ b/src/IKVM.CoreLib/IKVM.CoreLib.csproj @@ -106,12 +106,4 @@ - - - - PreserveNewest - - - - diff --git a/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs index 1677d70764..bc74233ab5 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs @@ -54,19 +54,19 @@ interface IILGenerator /// Declares a new label. /// /// - System.Reflection.Emit.Label DefineLabel(); + ILabel DefineLabel(); /// /// Begins an exception block for a non-filtered exception. /// /// - System.Reflection.Emit.Label BeginExceptionBlock(); + ILabel BeginExceptionBlock(); /// /// Marks the Microsoft intermediate language (MSIL) stream's current position with the given label. /// /// - void MarkLabel(System.Reflection.Emit.Label loc); + void MarkLabel(ILabel loc); /// /// Begins an exception block for a filtered exception. diff --git a/src/IKVM.CoreLib/Symbols/Emit/ILabel.cs b/src/IKVM.CoreLib/Symbols/Emit/ILabel.cs index c36f9d801f..f8c926b723 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ILabel.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ILabel.cs @@ -2,5 +2,9 @@ { public interface ILabel { + + + } + } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index 72bb9e7d7e..90c4603e11 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -1,4 +1,6 @@ -using System.Reflection; +using System; +using System.Diagnostics.SymbolStore; +using System.Reflection; using System.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Emit @@ -7,6 +9,16 @@ namespace IKVM.CoreLib.Symbols.Emit interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol { + /// + /// Defines a document for source. + /// + /// + /// + /// + /// + /// + ISymbolDocumentWriter? DefineDocument(string url, Guid language, Guid languageVendor, Guid documentType); + /// /// Constructs a TypeBuilder for a private type with the specified name in this module. /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs index 6b4b44107c..e888e50285 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs @@ -145,7 +145,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - void DefineMethodOverride(IMethodSymbolBuilder methodInfoBody, IMethodSymbol methodInfoDeclaration); + void DefineMethodOverride(IMethodSymbol methodInfoBody, IMethodSymbol methodInfoDeclaration); /// /// Defines a nested type, given its name, attributes, the type that it extends, and the interfaces that it implements. diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index 81457295e8..adef5b72e6 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -1,4 +1,7 @@ -using IKVM.CoreLib.Symbols.Emit; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols { @@ -6,6 +9,22 @@ namespace IKVM.CoreLib.Symbols interface ISymbolContext { + /// + /// Defines a dynamic assembly that has the specified name and access rights. + /// + /// + /// + /// + IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access); + + /// + /// Defines a dynamic assembly that has the specified name and access rights. + /// + /// + /// + /// + IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access, ICustomAttributeBuilder[]? assemblyAttributes); + /// /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs index c8f4ce03eb..403ccdcd14 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionAssemblySymbolBuilder : IIkvmReflectionSymbolBuilder, IAssemblySymbolBuilder, IIkvmReflectionAssemblySymbol + interface IIkvmReflectionAssemblySymbolBuilder : IIkvmReflectionSymbolBuilder, IAssemblySymbolBuilder, IIkvmReflectionAssemblySymbol { /// @@ -12,6 +12,13 @@ interface IIkvmReflectionAssemblySymbolBuilder : IIkvmReflectionSymbolBuilder AssemblyBuilder UnderlyingAssemblyBuilder { get; } + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs index 86b966f989..5f0747645f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs @@ -4,9 +4,12 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionConstructorSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder, IIkvmReflectionConstructorSymbol + interface IIkvmReflectionConstructorSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder, IIkvmReflectionConstructorSymbol { + /// + /// Gets the underlying . + /// ConstructorBuilder UnderlyingConstructorBuilder { get; } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs index f5e3f728dc..d76fd2a4a8 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs @@ -4,9 +4,12 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionEventSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IEventSymbolBuilder, IIkvmReflectionEventSymbol + interface IIkvmReflectionEventSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IEventSymbolBuilder, IIkvmReflectionEventSymbol { + /// + /// Gets the underlying . + /// EventBuilder UnderlyingEventBuilder { get; } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs index fe61f4f345..b70305e9c7 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionFieldSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IFieldSymbolBuilder, IIkvmReflectionFieldSymbol + interface IIkvmReflectionFieldSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IFieldSymbolBuilder, IIkvmReflectionFieldSymbol { FieldBuilder UnderlyingFieldBuilder { get; } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs index 889de61f28..1395991f1e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionGenericTypeParameterSymbolBuilder : IIkvmReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IIkvmReflectionTypeSymbol + interface IIkvmReflectionGenericTypeParameterSymbolBuilder : IIkvmReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IIkvmReflectionTypeSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs index e6d8459ce3..7e936c5290 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs @@ -3,9 +3,14 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionMemberSymbolBuilder : IIkvmReflectionSymbolBuilder, IMemberSymbolBuilder, IIkvmReflectionMemberSymbol + interface IIkvmReflectionMemberSymbolBuilder : IIkvmReflectionSymbolBuilder, IMemberSymbolBuilder, IIkvmReflectionMemberSymbol { + /// + /// Gets the resolving . + /// + public IIkvmReflectionModuleSymbolBuilder ResolvingModuleBuilder { get; } + /// /// Invoked when the type responsible for this builder is completed. Implementations should update their /// underlying type, and optionally dispatch the OnComplete invocation to downstream elements. diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs index b5e6fcd571..89377fdd7e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs @@ -1,12 +1,18 @@ using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionMethodBaseSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IIkvmReflectionMethodBaseSymbol + interface IIkvmReflectionMethodBaseSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IIkvmReflectionMethodBaseSymbol { - + /// + /// Gets or creates a for the given . + /// + /// + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs index 8de0478935..aca0b7f63b 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionMethodSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder, IIkvmReflectionMethodSymbol + interface IIkvmReflectionMethodSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder, IIkvmReflectionMethodSymbol { /// @@ -12,6 +12,13 @@ interface IIkvmReflectionMethodSymbolBuilder : IIkvmReflectionSymbolBuilder MethodBuilder UnderlyingMethodBuilder { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs index 564c9e551e..fc5f3eb9db 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionModuleSymbolBuilder : IIkvmReflectionSymbolBuilder, IModuleSymbolBuilder, IIkvmReflectionModuleSymbol + interface IIkvmReflectionModuleSymbolBuilder : IIkvmReflectionSymbolBuilder, IModuleSymbolBuilder, IIkvmReflectionModuleSymbol { /// @@ -12,6 +12,62 @@ interface IIkvmReflectionModuleSymbolBuilder : IIkvmReflectionSymbolBuilder ModuleBuilder UnderlyingModuleBuilder { get; } + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs index 8d74fa945e..5b9b0305dd 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionParameterSymbolBuilder : IIkvmReflectionSymbolBuilder, IParameterSymbolBuilder, IIkvmReflectionParameterSymbol + interface IIkvmReflectionParameterSymbolBuilder : IIkvmReflectionSymbolBuilder, IParameterSymbolBuilder, IIkvmReflectionParameterSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs index a52039bdd6..723fc6ca04 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs @@ -1,12 +1,16 @@ using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionPropertySymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IPropertySymbolBuilder, IIkvmReflectionPropertySymbol + interface IIkvmReflectionPropertySymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, IPropertySymbolBuilder, IIkvmReflectionPropertySymbol { + /// + /// Gets the underlying . + /// PropertyBuilder UnderlyingPropertyBuilder { get; } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs index ce5e76e98c..c19769466f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs @@ -1,4 +1,7 @@ -using IKVM.CoreLib.Symbols.Emit; +using System.Diagnostics.CodeAnalysis; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { @@ -6,13 +9,85 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit interface IIkvmReflectionSymbolBuilder : ISymbolBuilder { - } + /// + /// Resolves the symbol for the specified assembly builder. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assembly))] + IIkvmReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); - interface IIkvmReflectionSymbolBuilder : IIkvmReflectionSymbolBuilder, ISymbolBuilder - where TSymbol : IIkvmReflectionSymbol - { + /// + /// Resolves the symbol for the specified module. + /// + /// + /// + [return: NotNullIfNotNull(nameof(module))] + IIkvmReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); + + /// + /// Resolves the symbol for the specified constructor. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctor))] + IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); + + /// + /// Resolves the symbol for the specified field. + /// + /// + /// + [return: NotNullIfNotNull(nameof(field))] + IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); + + /// + /// Resolves the symbol for the specified property. + /// + /// + /// + [return: NotNullIfNotNull(nameof(property))] + IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); + + /// + /// Resolves the symbol for the specified event. + /// + /// + /// + [return: NotNullIfNotNull(nameof(@event))] + IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); + /// + /// Resolves the symbol for the specified parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(parameter))] + IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(ParameterBuilder parameter); + /// + /// Resolves the symbol for the specified generic type parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(genericTypeParameter))] + IIkvmReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs index c16eeb22cd..cb7b100a4a 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionTypeSymbolBuilder : IIkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder, ITypeSymbolBuilder, IIkvmReflectionTypeSymbol + interface IIkvmReflectionTypeSymbolBuilder : IIkvmReflectionMemberSymbolBuilder, ITypeSymbolBuilder, IIkvmReflectionTypeSymbol { /// @@ -12,6 +12,48 @@ interface IIkvmReflectionTypeSymbolBuilder : IIkvmReflectionSymbolBuilder TypeBuilder UnderlyingTypeBuilder { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs index 21a7d7b028..d8e4da24a5 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -13,7 +13,8 @@ class IkvmReflectionAssemblySymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmRe { readonly AssemblyBuilder _builder; - IkvmReflectionAssemblyMetadata _metadata; + + IkvmReflectionModuleTable _moduleTable; /// /// Initializes a new instance. @@ -24,7 +25,7 @@ public IkvmReflectionAssemblySymbolBuilder(IkvmReflectionSymbolContext context, base(context) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _metadata = new IkvmReflectionAssemblyMetadata(this); + _moduleTable = new IkvmReflectionModuleTable(context, this); } /// @@ -33,6 +34,26 @@ public IkvmReflectionAssemblySymbolBuilder(IkvmReflectionSymbolContext context, /// public AssemblyBuilder UnderlyingAssemblyBuilder => _builder; + #region IIkvmReflectionAssemblySymbolBuilder + + /// + public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return _moduleTable.GetOrCreateModuleSymbol(module); + } + + #endregion + + #region IIkvmReflectionAssemblySymbol + + /// + public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _moduleTable.GetOrCreateModuleSymbol(module); + } + + #endregion + #region IAssemblySymbolBuilder /// @@ -120,19 +141,19 @@ public IModuleSymbol[] GetModules(bool getResourceModules) /// public System.Reflection.AssemblyName GetName() { - return UnderlyingAssembly.GetName().ToAssemblyName(); + return UnderlyingAssembly.GetName().Pack(); } /// public System.Reflection.AssemblyName GetName(bool copiedName) { - return UnderlyingAssembly.GetName(copiedName).ToAssemblyName(); + return UnderlyingAssembly.GetName(copiedName).Pack(); } /// public System.Reflection.AssemblyName[] GetReferencedAssemblies() { - return UnderlyingAssembly.GetReferencedAssemblies().ToAssemblyNames(); + return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } /// @@ -185,18 +206,6 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion - /// - public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - return _metadata.GetOrCreateModuleSymbol(module); - } - - /// - public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) - { - return (IIkvmReflectionModuleSymbolBuilder)_metadata.GetOrCreateModuleSymbol(module); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs index 962750a1a7..66e1ef64d2 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs @@ -13,6 +13,8 @@ class IkvmReflectionConstructorSymbolBuilder : IkvmReflectionMethodBaseSymbolBui ConstructorBuilder? _builder; ConstructorInfo _ctor; + IkvmReflectionILGenerator? _il; + /// /// Initializes a new instance. /// @@ -21,7 +23,7 @@ class IkvmReflectionConstructorSymbolBuilder : IkvmReflectionMethodBaseSymbolBui /// /// /// - public IkvmReflectionConstructorSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, ConstructorBuilder builder) : + public IkvmReflectionConstructorSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder resolvingType, ConstructorBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); @@ -54,13 +56,13 @@ public IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection. /// public IILGenerator GetILGenerator() { - throw new NotImplementedException(); + return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator()); } /// public IILGenerator GetILGenerator(int streamSize) { - throw new NotImplementedException(); + return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator(streamSize)); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs index 385d806554..b7c2ca9c35 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs @@ -21,7 +21,7 @@ class IkvmReflectionEventSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkv /// /// /// - public IkvmReflectionEventSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, EventBuilder builder) : + public IkvmReflectionEventSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder resolvingType, EventBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs index b485e6561b..342d6bce41 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs @@ -21,7 +21,7 @@ class IkvmReflectionFieldSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkv /// /// /// - public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, FieldBuilder builder) : + public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder? resolvingType, FieldBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs index 011eb99850..12c2606df5 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -11,28 +11,28 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit class IkvmReflectionGenericTypeParameterSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionGenericTypeParameterSymbolBuilder { - readonly IIkvmReflectionMethodSymbol? _resolvingMethod; + readonly IIkvmReflectionMemberSymbol? _resolvingMember; GenericTypeParameterBuilder? _builder; Type _type; - IkvmReflectionTypeImpl _impl; + + IkvmReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. /// /// /// - /// - /// + /// /// /// - public IkvmReflectionGenericTypeParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, IIkvmReflectionMethodSymbol? resolvingMethod, GenericTypeParameterBuilder builder) : - base(context, resolvingModule, resolvingType) + public IkvmReflectionGenericTypeParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionMemberSymbolBuilder resolvingMember, GenericTypeParameterBuilder builder) : + base(context, resolvingModule, resolvingMember as IIkvmReflectionTypeSymbolBuilder) { - _resolvingMethod = resolvingMethod; + _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _type = _builder; - _impl = new IkvmReflectionTypeImpl(this); + _specTable = new IkvmReflectionTypeSpecTable(); } /// @@ -41,9 +41,125 @@ public IkvmReflectionGenericTypeParameterSymbolBuilder(IkvmReflectionSymbolConte /// public override MemberInfo UnderlyingMember => UnderlyingType; + #region IIkvmReflectionGenericTypeParameterSymbolBuilder + /// public GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder => _builder ?? throw new InvalidOperationException(); + #endregion + + #region IIkvmReflectionTypeSymbol + + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type type) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeSymbol(GenericTypeParameterBuilder genericType) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion + #region ITypeSymbolBuilder /// @@ -69,506 +185,513 @@ public void SetInterfaceConstraints(params ITypeSymbol[]? interfaceConstraints) #region ITypeSymbol /// - public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)_impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public IAssemblySymbol Assembly => _impl.Assembly; + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? FullName => _impl.FullName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? Namespace => _impl.Namespace; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public TypeCode TypeCode => _impl.TypeCode; + public string? FullName => UnderlyingType.FullName; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public string? Namespace => UnderlyingType.Namespace; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)_impl.GenericParameterAttributes; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public bool HasElementType => UnderlyingType.HasElementType; /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsSZArray => UnderlyingType.IsSZArray; /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool HasElementType => _impl.HasElementType; + public bool IsClass => UnderlyingType.IsClass; /// - public bool IsClass => _impl.IsClass; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsValueType => _impl.IsValueType; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsInterface => _impl.IsInterface; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsArray => _impl.IsArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsEnum => _impl.IsEnum; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsPointer => UnderlyingType.IsPointer; /// - public bool IsNested => _impl.IsNested; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsSignatureType => throw new NotImplementedException(); /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// - public override bool IsComplete => _builder == null; + public int GetArrayRank() + { + return UnderlyingType.GetArrayRank(); + } /// - public int GetArrayRank() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetArrayRank(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol[] GetConstructors() { - return _impl.GetElementType(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public string[] GetEnumNames() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumNames(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol GetEnumUnderlyingType() + public ITypeSymbol? GetElementType() { - return _impl.GetEnumUnderlyingType(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericArguments() + public string? GetEnumName(object value) { - return _impl.GetGenericArguments(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string[] GetEnumNames() { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol GetGenericTypeDefinition() + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetGenericTypeDefinition(); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name) + public Array GetEnumValues() { - return _impl.GetInterface(name); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterface(name, ignoreCase); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol[] GetEvents() { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return _impl.GetField(name, bindingAttr); + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); } /// - public IFieldSymbol[] GetFields() + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetFields(bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + throw new NotImplementedException(); } /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperty(name, returnType); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties() { - return _impl.GetEvent(name, bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsAssignableFrom(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsEnumDefined(object value) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsEnumDefined(value); } /// - public bool IsEnumDefined(object value) + public bool IsSubclassOf(ITypeSymbol c) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); } /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + public ITypeSymbol MakeByRefType() { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); } /// - public ITypeSymbol MakeByRefType() + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs new file mode 100644 index 0000000000..f83e7c3904 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs @@ -0,0 +1,499 @@ +using System; +using System.Diagnostics.SymbolStore; +using System.Runtime.InteropServices; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionILGenerator : IILGenerator + { + + readonly IkvmReflectionSymbolContext _context; + readonly ILGenerator _il; + + /// + /// Initializes a new instance. + /// + /// + public IkvmReflectionILGenerator(IkvmReflectionSymbolContext context, ILGenerator il) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _il = il ?? throw new ArgumentNullException(nameof(il)); + } + + /// + public int ILOffset => _il.ILOffset; + + /// + public void BeginCatchBlock(ITypeSymbol? exceptionType) + { + _il.BeginCatchBlock(exceptionType?.Unpack()); + } + + /// + public void BeginExceptFilterBlock() + { + _il.BeginExceptFilterBlock(); + } + + /// + public ILabel BeginExceptionBlock() + { + return new IkvmReflectionLabel(_il.BeginExceptionBlock()); + } + + /// + public void BeginFaultBlock() + { + _il.BeginFaultBlock(); + } + + /// + public void BeginFinallyBlock() + { + _il.BeginFinallyBlock(); + } + + /// + public void BeginScope() + { + _il.BeginScope(); + } + + /// + public ILocalBuilder DeclareLocal(ITypeSymbol localType, bool pinned) + { + return new IkvmReflectionLocalBuilder(_context, _il.DeclareLocal(localType.Unpack(), pinned)); + } + + /// + public ILocalBuilder DeclareLocal(ITypeSymbol localType) + { + return new IkvmReflectionLocalBuilder(_context, _il.DeclareLocal(localType.Unpack())); + } + + /// + public ILabel DefineLabel() + { + return new IkvmReflectionLabel(_il.DefineLabel()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, ILocalBuilder local) + { + _il.Emit(Convert(opcode), local.Unpack()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, ITypeSymbol cls) + { + _il.Emit(Convert(opcode), cls.Unpack()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, string str) + { + _il.Emit(Convert(opcode), str); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, float arg) + { + _il.Emit(Convert(opcode), arg); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, sbyte arg) + { + _il.Emit(Convert(opcode), arg); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, IMethodSymbol meth) + { + _il.Emit(Convert(opcode), meth.Unpack()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, ISignatureHelper signature) + { + throw new NotImplementedException(); + //_il.Emit(Convert(opcode), signature.Unpack()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, ILabel[] labels) + { + _il.Emit(Convert(opcode), labels.Unpack()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, IFieldSymbol field) + { + _il.Emit(Convert(opcode), field.Unpack()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, IConstructorSymbol con) + { + _il.Emit(Convert(opcode), con.Unpack()); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, long arg) + { + _il.Emit(Convert(opcode), arg); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, int arg) + { + _il.Emit(Convert(opcode), arg); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, short arg) + { + _il.Emit(Convert(opcode), arg); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, double arg) + { + _il.Emit(Convert(opcode), arg); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, byte arg) + { + _il.Emit(Convert(opcode), arg); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode) + { + _il.Emit(Convert(opcode)); + } + + /// + public void Emit(System.Reflection.Emit.OpCode opcode, ILabel label) + { + _il.Emit(Convert(opcode), label.Unpack()); + } + + /// + public void EmitCall(System.Reflection.Emit.OpCode opcode, IMethodSymbol methodInfo, ITypeSymbol[]? optionalParameterTypes) + { + _il.EmitCall(Convert(opcode), methodInfo.Unpack(), optionalParameterTypes?.Unpack()); + } + + /// + public void EmitCalli(System.Reflection.Emit.OpCode opcode, CallingConvention unmanagedCallConv, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + { + _il.EmitCalli(Convert(opcode), unmanagedCallConv, returnType?.Unpack(), parameterTypes?.Unpack()); + } + + /// + public void EmitCalli(System.Reflection.Emit.OpCode opcode, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, ITypeSymbol[]? optionalParameterTypes) + { + _il.EmitCalli(Convert(opcode), (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), optionalParameterTypes?.Unpack()); + } + + /// + public void EmitWriteLine(string value) + { + throw new NotImplementedException(); + } + + /// + public void EmitWriteLine(IFieldSymbol fld) + { + throw new NotImplementedException(); + } + + /// + public void EmitWriteLine(ILocalBuilder localBuilder) + { + throw new NotImplementedException(); + } + + /// + public void EndExceptionBlock() + { + _il.EndExceptionBlock(); + } + + /// + public void EndScope() + { + _il.EndScope(); + } + + /// + public void MarkLabel(ILabel loc) + { + _il.MarkLabel(loc.Unpack()); + } + + /// + public void MarkSequencePoint(ISymbolDocumentWriter document, int startLine, int startColumn, int endLine, int endColumn) + { +#if NETFRAMEWORK + _il.MarkSequencePoint(document, startLine, startColumn, endLine, endColumn); +#endif + } + + /// + public void ThrowException(ITypeSymbol excType) + { + _il.ThrowException(excType.Unpack()); + } + + /// + public void UsingNamespace(string usingNamespace) + { + _il.UsingNamespace(usingNamespace); + } + + /// + /// Converts the given OpCode value into a IKVM OpCode value. + /// + /// + /// + /// + OpCode Convert(System.Reflection.Emit.OpCode opcode) + { + return (ushort)opcode.Value switch + { + 0x00 => OpCodes.Nop, + 0x01 => OpCodes.Break, + 0x02 => OpCodes.Ldarg_0, + 0x03 => OpCodes.Ldarg_1, + 0x04 => OpCodes.Ldarg_2, + 0x05 => OpCodes.Ldarg_3, + 0x06 => OpCodes.Ldloc_0, + 0x07 => OpCodes.Ldloc_1, + 0x08 => OpCodes.Ldloc_2, + 0x09 => OpCodes.Ldloc_3, + 0x0a => OpCodes.Stloc_0, + 0x0b => OpCodes.Stloc_1, + 0x0c => OpCodes.Stloc_2, + 0x0d => OpCodes.Stloc_3, + 0x0e => OpCodes.Ldarg_S, + 0x0f => OpCodes.Ldarga_S, + 0x10 => OpCodes.Starg_S, + 0x11 => OpCodes.Ldloc_S, + 0x12 => OpCodes.Ldloca_S, + 0x13 => OpCodes.Stloc_S, + 0x14 => OpCodes.Ldnull, + 0x15 => OpCodes.Ldc_I4_M1, + 0x16 => OpCodes.Ldc_I4_0, + 0x17 => OpCodes.Ldc_I4_1, + 0x18 => OpCodes.Ldc_I4_2, + 0x19 => OpCodes.Ldc_I4_3, + 0x1a => OpCodes.Ldc_I4_4, + 0x1b => OpCodes.Ldc_I4_5, + 0x1c => OpCodes.Ldc_I4_6, + 0x1d => OpCodes.Ldc_I4_7, + 0x1e => OpCodes.Ldc_I4_8, + 0x1f => OpCodes.Ldc_I4_S, + 0x20 => OpCodes.Ldc_I4, + 0x21 => OpCodes.Ldc_I8, + 0x22 => OpCodes.Ldc_R4, + 0x23 => OpCodes.Ldc_R8, + 0x25 => OpCodes.Dup, + 0x26 => OpCodes.Pop, + 0x27 => OpCodes.Jmp, + 0x28 => OpCodes.Call, + 0x29 => OpCodes.Calli, + 0x2a => OpCodes.Ret, + 0x2b => OpCodes.Br_S, + 0x2c => OpCodes.Brfalse_S, + 0x2d => OpCodes.Brtrue_S, + 0x2e => OpCodes.Beq_S, + 0x2f => OpCodes.Bge_S, + 0x30 => OpCodes.Bgt_S, + 0x31 => OpCodes.Ble_S, + 0x32 => OpCodes.Blt_S, + 0x33 => OpCodes.Bne_Un_S, + 0x34 => OpCodes.Bge_Un_S, + 0x35 => OpCodes.Bgt_Un_S, + 0x36 => OpCodes.Ble_Un_S, + 0x37 => OpCodes.Blt_Un_S, + 0x38 => OpCodes.Br, + 0x39 => OpCodes.Brfalse, + 0x3a => OpCodes.Brtrue, + 0x3b => OpCodes.Beq, + 0x3c => OpCodes.Bge, + 0x3d => OpCodes.Bgt, + 0x3e => OpCodes.Ble, + 0x3f => OpCodes.Blt, + 0x40 => OpCodes.Bne_Un, + 0x41 => OpCodes.Bge_Un, + 0x42 => OpCodes.Bgt_Un, + 0x43 => OpCodes.Ble_Un, + 0x44 => OpCodes.Blt_Un, + 0x45 => OpCodes.Switch, + 0x46 => OpCodes.Ldind_I1, + 0x47 => OpCodes.Ldind_U1, + 0x48 => OpCodes.Ldind_I2, + 0x49 => OpCodes.Ldind_U2, + 0x4a => OpCodes.Ldind_I4, + 0x4b => OpCodes.Ldind_U4, + 0x4c => OpCodes.Ldind_I8, + 0x4d => OpCodes.Ldind_I, + 0x4e => OpCodes.Ldind_R4, + 0x4f => OpCodes.Ldind_R8, + 0x50 => OpCodes.Ldind_Ref, + 0x51 => OpCodes.Stind_Ref, + 0x52 => OpCodes.Stind_I1, + 0x53 => OpCodes.Stind_I2, + 0x54 => OpCodes.Stind_I4, + 0x55 => OpCodes.Stind_I8, + 0x56 => OpCodes.Stind_R4, + 0x57 => OpCodes.Stind_R8, + 0x58 => OpCodes.Add, + 0x59 => OpCodes.Sub, + 0x5a => OpCodes.Mul, + 0x5b => OpCodes.Div, + 0x5c => OpCodes.Div_Un, + 0x5d => OpCodes.Rem, + 0x5e => OpCodes.Rem_Un, + 0x5f => OpCodes.And, + 0x60 => OpCodes.Or, + 0x61 => OpCodes.Xor, + 0x62 => OpCodes.Shl, + 0x63 => OpCodes.Shr, + 0x64 => OpCodes.Shr_Un, + 0x65 => OpCodes.Neg, + 0x66 => OpCodes.Not, + 0x67 => OpCodes.Conv_I1, + 0x68 => OpCodes.Conv_I2, + 0x69 => OpCodes.Conv_I4, + 0x6a => OpCodes.Conv_I8, + 0x6b => OpCodes.Conv_R4, + 0x6c => OpCodes.Conv_R8, + 0x6d => OpCodes.Conv_U4, + 0x6e => OpCodes.Conv_U8, + 0x6f => OpCodes.Callvirt, + 0x70 => OpCodes.Cpobj, + 0x71 => OpCodes.Ldobj, + 0x72 => OpCodes.Ldstr, + 0x73 => OpCodes.Newobj, + 0x74 => OpCodes.Castclass, + 0x75 => OpCodes.Isinst, + 0x76 => OpCodes.Conv_R_Un, + 0x79 => OpCodes.Unbox, + 0x7a => OpCodes.Throw, + 0x7b => OpCodes.Ldfld, + 0x7c => OpCodes.Ldflda, + 0x7d => OpCodes.Stfld, + 0x7e => OpCodes.Ldsfld, + 0x7f => OpCodes.Ldsflda, + 0x80 => OpCodes.Stsfld, + 0x81 => OpCodes.Stobj, + 0x82 => OpCodes.Conv_Ovf_I1_Un, + 0x83 => OpCodes.Conv_Ovf_I2_Un, + 0x84 => OpCodes.Conv_Ovf_I4_Un, + 0x85 => OpCodes.Conv_Ovf_I8_Un, + 0x86 => OpCodes.Conv_Ovf_U1_Un, + 0x87 => OpCodes.Conv_Ovf_U2_Un, + 0x88 => OpCodes.Conv_Ovf_U4_Un, + 0x89 => OpCodes.Conv_Ovf_U8_Un, + 0x8a => OpCodes.Conv_Ovf_I_Un, + 0x8b => OpCodes.Conv_Ovf_U_Un, + 0x8c => OpCodes.Box, + 0x8d => OpCodes.Newarr, + 0x8e => OpCodes.Ldlen, + 0x8f => OpCodes.Ldelema, + 0x90 => OpCodes.Ldelem_I1, + 0x91 => OpCodes.Ldelem_U1, + 0x92 => OpCodes.Ldelem_I2, + 0x93 => OpCodes.Ldelem_U2, + 0x94 => OpCodes.Ldelem_I4, + 0x95 => OpCodes.Ldelem_U4, + 0x96 => OpCodes.Ldelem_I8, + 0x97 => OpCodes.Ldelem_I, + 0x98 => OpCodes.Ldelem_R4, + 0x99 => OpCodes.Ldelem_R8, + 0x9a => OpCodes.Ldelem_Ref, + 0x9b => OpCodes.Stelem_I, + 0x9c => OpCodes.Stelem_I1, + 0x9d => OpCodes.Stelem_I2, + 0x9e => OpCodes.Stelem_I4, + 0x9f => OpCodes.Stelem_I8, + 0xa0 => OpCodes.Stelem_R4, + 0xa1 => OpCodes.Stelem_R8, + 0xa2 => OpCodes.Stelem_Ref, + 0xa3 => OpCodes.Ldelem, + 0xa4 => OpCodes.Stelem, + 0xa5 => OpCodes.Unbox_Any, + 0xb3 => OpCodes.Conv_Ovf_I1, + 0xb4 => OpCodes.Conv_Ovf_U1, + 0xb5 => OpCodes.Conv_Ovf_I2, + 0xb6 => OpCodes.Conv_Ovf_U2, + 0xb7 => OpCodes.Conv_Ovf_I4, + 0xb8 => OpCodes.Conv_Ovf_U4, + 0xb9 => OpCodes.Conv_Ovf_I8, + 0xba => OpCodes.Conv_Ovf_U8, + 0xc2 => OpCodes.Refanyval, + 0xc3 => OpCodes.Ckfinite, + 0xc6 => OpCodes.Mkrefany, + 0xd0 => OpCodes.Ldtoken, + 0xd1 => OpCodes.Conv_U2, + 0xd2 => OpCodes.Conv_U1, + 0xd3 => OpCodes.Conv_I, + 0xd4 => OpCodes.Conv_Ovf_I, + 0xd5 => OpCodes.Conv_Ovf_U, + 0xd6 => OpCodes.Add_Ovf, + 0xd7 => OpCodes.Add_Ovf_Un, + 0xd8 => OpCodes.Mul_Ovf, + 0xd9 => OpCodes.Mul_Ovf_Un, + 0xda => OpCodes.Sub_Ovf, + 0xdb => OpCodes.Sub_Ovf_Un, + 0xdc => OpCodes.Endfinally, + 0xdd => OpCodes.Leave, + 0xde => OpCodes.Leave_S, + 0xdf => OpCodes.Stind_I, + 0xe0 => OpCodes.Conv_U, + 0xf8 => OpCodes.Prefix7, + 0xf9 => OpCodes.Prefix6, + 0xfa => OpCodes.Prefix5, + 0xfb => OpCodes.Prefix4, + 0xfc => OpCodes.Prefix3, + 0xfd => OpCodes.Prefix2, + 0xfe => OpCodes.Prefix1, + 0xff => OpCodes.Prefixref, + 0xfe00 => OpCodes.Arglist, + 0xfe01 => OpCodes.Ceq, + 0xfe02 => OpCodes.Cgt, + 0xfe03 => OpCodes.Cgt_Un, + 0xfe04 => OpCodes.Clt, + 0xfe05 => OpCodes.Clt_Un, + 0xfe06 => OpCodes.Ldftn, + 0xfe07 => OpCodes.Ldvirtftn, + 0xfe09 => OpCodes.Ldarg, + 0xfe0a => OpCodes.Ldarga, + 0xfe0b => OpCodes.Starg, + 0xfe0c => OpCodes.Ldloc, + 0xfe0d => OpCodes.Ldloca, + 0xfe0e => OpCodes.Stloc, + 0xfe0f => OpCodes.Localloc, + 0xfe11 => OpCodes.Endfilter, + 0xfe15 => OpCodes.Initobj, + 0xfe17 => OpCodes.Cpblk, + 0xfe18 => OpCodes.Initblk, + 0xfe1a => OpCodes.Rethrow, + 0xfe1c => OpCodes.Sizeof, + 0xfe1d => OpCodes.Refanytype, + _ => throw new NotImplementedException(), + }; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLabel.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLabel.cs new file mode 100644 index 0000000000..bad25b1951 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLabel.cs @@ -0,0 +1,28 @@ +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionLabel : ILabel + { + + readonly Label _label; + + /// + /// Initializes a new instance. + /// + /// + public IkvmReflectionLabel(Label label) + { + _label = label; + } + + /// + /// Gets the underlying . + /// + public Label UnderlyingLabel => _label; + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLocalBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLocalBuilder.cs new file mode 100644 index 0000000000..edd6541b4c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLocalBuilder.cs @@ -0,0 +1,55 @@ +using System; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + class IkvmReflectionLocalBuilder : ILocalBuilder + { + + readonly IkvmReflectionSymbolContext _context; + readonly LocalBuilder _builder; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public IkvmReflectionLocalBuilder(IkvmReflectionSymbolContext context, LocalBuilder builder) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the underlying . + /// + public LocalBuilder UnderlyingLocalBuilder => _builder; + + /// + public bool IsPinned => _builder.IsPinned; + + /// + public int LocalIndex => _builder.LocalIndex; + + /// + public ITypeSymbol LocalType => _context.GetOrCreateTypeSymbol(_builder.LocalType); + + /// + public void SetLocalSymInfo(string name) + { + _builder.SetLocalSymInfo(name); + } + + /// + public void SetLocalSymInfo(string name, int startOffset, int endOffset) + { + _builder.SetLocalSymInfo(name, startOffset, endOffset); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs index 1b643dfdae..58ac56a0fd 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs @@ -13,8 +13,8 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit abstract class IkvmReflectionMemberSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmReflectionMemberSymbolBuilder { - readonly IIkvmReflectionModuleSymbol _resolvingModule; - readonly IIkvmReflectionTypeSymbol? _resolvingType; + readonly IIkvmReflectionModuleSymbolBuilder _resolvingModule; + readonly IIkvmReflectionTypeSymbolBuilder? _resolvingType; /// /// Initializes a new instance. @@ -22,14 +22,14 @@ abstract class IkvmReflectionMemberSymbolBuilder : IkvmReflectionSymbolBuilder, /// /// /// - public IkvmReflectionMemberSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : + public IkvmReflectionMemberSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder? resolvingType) : base(context) { _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); _resolvingType = resolvingType; } - #region IMemberSymbol + #region IIkvmReflectionMemberSymbol /// public abstract MemberInfo UnderlyingMember { get; } @@ -38,49 +38,128 @@ public IkvmReflectionMemberSymbolBuilder(IkvmReflectionSymbolContext context, II public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingModule; /// - public IIkvmReflectionTypeSymbol? ResolvingType => ResolvingType; + public IIkvmReflectionModuleSymbolBuilder ResolvingModuleBuilder => _resolvingModule; /// - public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + public IIkvmReflectionTypeSymbol? ResolvingType => _resolvingType; - /// - public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + #endregion + + #region IIkvmReflectionSymbolBuilder /// - public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + [return: NotNullIfNotNull("type")] + public override IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + + if (UnderlyingMember == type) + return (IIkvmReflectionTypeSymbolBuilder)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return (IIkvmReflectionTypeSymbolBuilder)_resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } /// - public virtual int MetadataToken => UnderlyingMember.MetadataToken; + [return: NotNullIfNotNull(nameof(ctor))] + public override IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) + { + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + + if (UnderlyingMember == ctor) + return (IIkvmReflectionConstructorSymbolBuilder)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); + } /// - public virtual string Name => UnderlyingMember.Name; + [return: NotNullIfNotNull(nameof(method))] + public override IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + if (UnderlyingMember == method) + return (IIkvmReflectionMethodSymbolBuilder)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); + } /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) + [return: NotNullIfNotNull(nameof(field))] + public override IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) { - return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(null, inherit)); + if (field is null) + throw new ArgumentNullException(nameof(field)); + + if (UnderlyingMember == field) + return (IIkvmReflectionFieldSymbolBuilder)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); } /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + [return: NotNullIfNotNull(nameof(property))] + public override IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) { - return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit)); + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (UnderlyingMember == property) + return (IIkvmReflectionPropertySymbolBuilder)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); } /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + [return: NotNullIfNotNull(nameof(@event))] + public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) { - return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + if (@event.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); } /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + [return: NotNullIfNotNull(nameof(parameter))] + public override IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) { - return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (parameter.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(parameter); + + return base.ResolveParameterSymbol(parameter); } #endregion + #region IIkvmReflectionSymbol + /// [return: NotNullIfNotNull(nameof(type))] public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) @@ -100,25 +179,6 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return base.ResolveTypeSymbol(type); } - /// - [return: NotNullIfNotNull("type")] - public override IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - - if (UnderlyingMember == type) - return (IIkvmReflectionTypeSymbolBuilder)this; - - if (_resolvingType != null && type == _resolvingType.UnderlyingType) - return (IIkvmReflectionTypeSymbolBuilder)_resolvingType; - - if (type.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateTypeSymbol(type); - - return base.ResolveTypeSymbol(type); - } - /// [return: NotNullIfNotNull(nameof(ctor))] public override IIkvmReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) @@ -135,22 +195,6 @@ public override IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder t return base.ResolveConstructorSymbol(ctor); } - /// - [return: NotNullIfNotNull(nameof(ctor))] - public override IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) - { - if (ctor is null) - throw new ArgumentNullException(nameof(ctor)); - - if (UnderlyingMember == ctor) - return (IIkvmReflectionConstructorSymbolBuilder)this; - - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); - - return base.ResolveConstructorSymbol(ctor); - } - /// [return: NotNullIfNotNull(nameof(method))] public override IIkvmReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) @@ -167,22 +211,6 @@ public override IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol return base.ResolveMethodSymbol(method); } - /// - [return: NotNullIfNotNull(nameof(method))] - public override IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - if (UnderlyingMember == method) - return (IIkvmReflectionMethodSymbolBuilder)this; - - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); - - return base.ResolveMethodSymbol(method); - } - /// [return: NotNullIfNotNull(nameof(field))] public override IIkvmReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) @@ -199,22 +227,6 @@ public override IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBui return base.ResolveFieldSymbol(field); } - /// - [return: NotNullIfNotNull(nameof(field))] - public override IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - if (UnderlyingMember == field) - return (IIkvmReflectionFieldSymbolBuilder)this; - - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); - - return base.ResolveFieldSymbol(field); - } - /// [return: NotNullIfNotNull(nameof(property))] public override IIkvmReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) @@ -231,22 +243,6 @@ public override IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilde return base.ResolvePropertySymbol(property); } - /// - [return: NotNullIfNotNull(nameof(property))] - public override IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - if (UnderlyingMember == property) - return (IIkvmReflectionPropertySymbolBuilder)this; - - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); - - return base.ResolvePropertySymbol(property); - } - /// [return: NotNullIfNotNull(nameof(@event))] public override IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) @@ -263,19 +259,6 @@ public override IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Prope return base.ResolveEventSymbol(@event); } - /// - [return: NotNullIfNotNull(nameof(@event))] - public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - if (@event.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); - - return base.ResolveEventSymbol(@event); - } - /// [return: NotNullIfNotNull(nameof(parameter))] public override IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) @@ -289,19 +272,51 @@ public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilde return base.ResolveParameterSymbol(parameter); } + #endregion + + #region IMemberSymbol + /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + + /// + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + + /// + public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + + /// + public virtual int MetadataToken => UnderlyingMember.MetadataToken; + + /// + public virtual string Name => UnderlyingMember.Name; + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(null, inherit)); + } - if (parameter.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } - return base.ResolveParameterSymbol(parameter); + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); } + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + /// public virtual void OnComplete() { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs index b6a2326dd6..573c98183f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs @@ -1,4 +1,5 @@ using IKVM.Reflection; +using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { @@ -6,16 +7,18 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit abstract class IkvmReflectionMethodBaseSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvmReflectionMethodBaseSymbolBuilder { + IkvmReflectionParameterTable _parameterTable; + /// /// Initializes a new instance. /// /// /// /// - public IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : + public IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder? resolvingType) : base(context, resolvingModule, resolvingType) { - + _parameterTable = new IkvmReflectionParameterTable(context, resolvingModule, this); } /// @@ -24,6 +27,26 @@ public IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context /// public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + #region IIkvmReflectionMethodBaseSymbolBuilder + + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + + #region IIkvmReflectionMethodBaseSymbol + + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + #region IMethodBaseSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs index db3c96967b..23b82a6387 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs @@ -4,6 +4,8 @@ using IKVM.Reflection; using IKVM.Reflection.Emit; +using Type = IKVM.Reflection.Type; + namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { @@ -13,6 +15,10 @@ class IkvmReflectionMethodSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, MethodBuilder? _builder; MethodInfo _method; + IkvmReflectionGenericTypeParameterTable _genericTypeParameterTable; + + IkvmReflectionILGenerator? _il; + /// /// Initializes a new instance. /// @@ -21,11 +27,12 @@ class IkvmReflectionMethodSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, /// /// /// - public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, MethodBuilder builder) : + public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder? resolvingType, MethodBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _method = _builder; + _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, resolvingModule, this); } /// @@ -37,6 +44,34 @@ public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, II /// public MethodBuilder UnderlyingMethodBuilder => _builder ?? throw new InvalidOperationException(); + #region IIkvmReflectionMethodSymbolBuilder + + /// + public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + #endregion + + #region IIkvmReflectionMethodSymbol + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + #endregion + + #region IIkvmReflectionMethodBaseSymbol + + #endregion + + #region IIkvmReflectionMethodBaseSymbolBuilder + + #endregion + #region IMethodSymbolBuilder /// @@ -68,7 +103,7 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin var l = UnderlyingMethodBuilder.DefineGenericParameters(names); var a = new IGenericTypeParameterSymbolBuilder[l.Length]; for (int i = 0; i < l.Length; i++) - a[i] = new IkvmReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, ResolvingType, this, l[i]); + a[i] = ResolveGenericTypeParameterSymbol(l[i]); return a; } @@ -79,14 +114,16 @@ public IParameterSymbolBuilder DefineParameter(int position, System.Reflection.P return ResolveParameterSymbol(UnderlyingMethodBuilder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); } + /// public IILGenerator GetILGenerator() { - throw new NotImplementedException(); + return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator()); } - public IILGenerator GetILGenerator(int size) + /// + public IILGenerator GetILGenerator(int streamSize) { - throw new NotImplementedException(); + return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); } /// @@ -144,7 +181,6 @@ public override void OnComplete() _builder = null; base.OnComplete(); } - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs index deb3feca4c..b5e84e7f52 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -1,4 +1,5 @@ using System; +using System.Diagnostics.SymbolStore; using System.Linq; using IKVM.CoreLib.Symbols.Emit; @@ -14,36 +15,184 @@ class IkvmReflectionModuleSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmRefl { readonly IIkvmReflectionAssemblySymbol _resolvingAssembly; + readonly ModuleBuilder _module; + + IkvmReflectionTypeTable _typeTable; + IkvmReflectionMethodTable _methodTable; + IkvmReflectionFieldTable _fieldTable; - readonly ModuleBuilder _builder; - IkvmReflectionModuleMetadata _metadata; /// /// Initializes a new instance. /// /// /// - /// + /// /// - public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionAssemblySymbol resolvingAssembly, ModuleBuilder builder) : + public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionAssemblySymbol resolvingAssembly, ModuleBuilder module) : base(context) { _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _metadata = new IkvmReflectionModuleMetadata(this); + _module = module ?? throw new ArgumentNullException(nameof(module)); + + _typeTable = new IkvmReflectionTypeTable(context, this, null); + _methodTable = new IkvmReflectionMethodTable(context, this, null); + _fieldTable = new IkvmReflectionFieldTable(context, this, null); } /// public Module UnderlyingModule => UnderlyingModuleBuilder; /// - public ModuleBuilder UnderlyingModuleBuilder => _builder; + public ModuleBuilder UnderlyingModuleBuilder => _module; /// public IIkvmReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; + #region IIkvmReflectionModuleSymbol + + /// + public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type.IsTypeDefinition()) + return _typeTable.GetOrCreateTypeSymbol(type); + else if (type.IsGenericType) + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + else if (type.IsSZArray) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreateSZArrayTypeSymbol(); + else if (type.IsArray) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreateArrayTypeSymbol(type.GetArrayRank()); + else if (type.IsPointer) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreatePointerTypeSymbol(); + else if (type.IsByRef) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreateByRefTypeSymbol(); + else + throw new InvalidOperationException(); + } + + /// + public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return (IIkvmReflectionTypeSymbolBuilder)_typeTable.GetOrCreateTypeSymbol((Type)type); + } + + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodBaseSymbol(method); + else + return _methodTable.GetOrCreateMethodBaseSymbol(method); + } + + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return ResolveTypeSymbol(ctor.DeclaringType).GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return ResolveTypeSymbol((TypeBuilder)ctor.DeclaringType).GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodSymbol(method); + else + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateMethodSymbol(method); + else + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateFieldSymbol(field); + else + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + if (field.DeclaringType is { } dt) + return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateFieldSymbol(field); + else + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return ResolveTypeSymbol(property.DeclaringType).GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return ResolveTypeSymbol((TypeBuilder)property.DeclaringType).GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return ResolveTypeSymbol(@event.DeclaringType).GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return ResolveTypeSymbol((TypeBuilder)@event.DeclaringType).GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return ResolveMemberSymbol(parameter.Member) switch + { + IIkvmReflectionMethodBaseSymbol method => method.GetOrCreateParameterSymbol(parameter), + IIkvmReflectionPropertySymbol property => property.GetOrCreateParameterSymbol(parameter), + _ => throw new InvalidOperationException(), + }; + } + + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return ResolveMethodSymbol((MethodBuilder)parameter.Method).GetOrCreateParameterSymbol(parameter); + } + + /// + public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) + { + if (genericParameterType.DeclaringMethod is MethodBuilder dm) + return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + else + return ResolveTypeSymbol((TypeBuilder)genericParameterType.DeclaringType).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + } + + #endregion + #region IModuleSymbolBuilder + /// + public ISymbolDocumentWriter? DefineDocument(string url, Guid language, Guid languageVendor, Guid documentType) + { + return UnderlyingModuleBuilder.DefineDocument(url, language, languageVendor, documentType); + } + /// public ITypeSymbolBuilder DefineType(string name) { @@ -121,7 +270,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) public string ScopeName => UnderlyingModule.ScopeName; /// - public override bool IsComplete => _builder == null; + public override bool IsComplete => _module == null; /// public IFieldSymbol? GetField(string name) @@ -293,90 +442,6 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion - /// - public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - return _metadata.GetOrCreateTypeSymbol(type); - } - - /// - public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - return _metadata.GetOrCreateTypeSymbol(type); - } - - /// - public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return _metadata.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return _metadata.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return _metadata.GetOrCreateMethodSymbol(method); - } - - /// - public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return _metadata.GetOrCreateMethodSymbol(method); - } - - /// - public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - return _metadata.GetOrCreateFieldSymbol(field); - } - - /// - public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - return _metadata.GetOrCreateFieldSymbol(field); - } - - /// - public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return _metadata.GetOrCreatePropertySymbol(property); - } - - /// - public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return _metadata.GetOrCreatePropertySymbol(property); - } - - /// - public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return _metadata.GetOrCreateEventSymbol(@event); - } - - /// - public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return _metadata.GetOrCreateEventSymbol(@event); - } - - /// - public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - return _metadata.GetOrCreateParameterSymbol(parameter); - } - - /// - public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return _metadata.GetOrCreateParameterSymbol(parameter); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs index fa7506bd8c..e49827c7dd 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs @@ -12,7 +12,7 @@ class IkvmReflectionParameterSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmR { readonly IIkvmReflectionModuleSymbol _resolvingModule; - readonly IIkvmReflectionMethodBaseSymbol _resolvingMethod; + readonly IIkvmReflectionMemberSymbol _resolvingMethod; ParameterBuilder? _builder; ParameterInfo _parameter; @@ -26,7 +26,7 @@ class IkvmReflectionParameterSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmR /// /// /// - public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMethodBaseSymbol resolvingMethod, ParameterBuilder builder) : + public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMemberSymbol resolvingMethod, ParameterBuilder builder) : base(context) { _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); @@ -39,7 +39,7 @@ public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingMethod.ResolvingModule; /// - public IIkvmReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; + public IIkvmReflectionMemberSymbol ResolvingMember => _resolvingMethod; /// public ParameterInfo UnderlyingParameter => _parameter; @@ -154,8 +154,12 @@ public ITypeSymbol[] GetRequiredCustomModifiers() /// public void OnComplete() { - var p = ResolvingMethod.UnderlyingMethodBase.GetParameters(); - _parameter = p[Position]; + if (ResolvingMember is IIkvmReflectionMethodBaseSymbolBuilder b) + _parameter = b.UnderlyingMethodBase.GetParameters()[Position]; + + if (ResolvingMember is IIkvmReflectionPropertySymbolBuilder p) + _parameter = p.UnderlyingPropertyBuilder.GetIndexParameters()[Position]; + _builder = null; } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs index 8ec05eeff6..731828bd75 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs @@ -13,6 +13,8 @@ class IkvmReflectionPropertySymbolBuilder : IkvmReflectionMemberSymbolBuilder, I PropertyBuilder? _builder; PropertyInfo _property; + IkvmReflectionParameterTable _parameterTable; + /// /// Initializes a new instance. /// @@ -21,11 +23,12 @@ class IkvmReflectionPropertySymbolBuilder : IkvmReflectionMemberSymbolBuilder, I /// /// /// - public IkvmReflectionPropertySymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol resolvingType, PropertyBuilder builder) : + public IkvmReflectionPropertySymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder resolvingType, PropertyBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _property = _builder; + _parameterTable = new IkvmReflectionParameterTable(context, resolvingModule, this); } /// @@ -37,6 +40,15 @@ public IkvmReflectionPropertySymbolBuilder(IkvmReflectionSymbolContext context, /// public override MemberInfo UnderlyingMember => UnderlyingProperty; + #region IIkvmPropertySymbol + + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + #region IPropertySymbol /// @@ -169,7 +181,7 @@ public ITypeSymbol[] GetRequiredCustomModifiers() return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); } -#endregion + #endregion /// public override void OnComplete() diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs index f00d737267..ffa16919e1 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs @@ -1,4 +1,7 @@ -using IKVM.CoreLib.Symbols.Emit; +using System.Diagnostics.CodeAnalysis; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { @@ -19,6 +22,13 @@ protected IkvmReflectionSymbolBuilder(IkvmReflectionSymbolContext context) : } + /// + [return: NotNullIfNotNull("genericTypeParameter")] + public IIkvmReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return Context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index 323f309d13..d4183cb187 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -15,7 +15,13 @@ class IkvmReflectionTypeSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvm TypeBuilder? _builder; Type _type; - IkvmReflectionTypeImpl _impl; + + IkvmReflectionMethodTable _methodTable; + IkvmReflectionFieldTable _fieldTable; + IkvmReflectionPropertyTable _propertyTable; + IkvmReflectionEventTable _eventTable; + IkvmReflectionGenericTypeParameterTable _genericTypeParameterTable; + IkvmReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. @@ -23,12 +29,16 @@ class IkvmReflectionTypeSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvm /// /// /// - public IkvmReflectionTypeSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, TypeBuilder builder) : + public IkvmReflectionTypeSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, TypeBuilder builder) : base(context, resolvingModule, null) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _type = _builder; - _impl = new IkvmReflectionTypeImpl(this); + _methodTable = new IkvmReflectionMethodTable(context, resolvingModule, this); + _fieldTable = new IkvmReflectionFieldTable(context, resolvingModule, this); + _propertyTable = new IkvmReflectionPropertyTable(context, resolvingModule, this); + _eventTable = new IkvmReflectionEventTable(context, resolvingModule, this); + _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, resolvingModule, this); } /// @@ -40,6 +50,128 @@ public IkvmReflectionTypeSymbolBuilder(IkvmReflectionSymbolContext context, IIkv /// public TypeBuilder UnderlyingTypeBuilder => _builder ?? throw new InvalidOperationException(); + #region IkvmReflectionTypeSymbol + + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + return _methodTable.GetOrCreateMethodBaseSymbol(method); + } + + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + /// + public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion + + #region IIkvmReflectionTypeSymbolBuilder + + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return ResolveMethodSymbol((MethodBuilder)parameter.Method).GetOrCreateParameterSymbol(parameter); + } + + #endregion + #region ITypeSymbolBuilder /// @@ -54,7 +186,7 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin var l = UnderlyingTypeBuilder.DefineGenericParameters(names); var a = new IGenericTypeParameterSymbolBuilder[l.Length]; for (int i = 0; i < l.Length; i++) - a[i] = new IkvmReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, this, null, l[i]); + a[i] = ResolveGenericTypeParameterSymbol(l[i]); return a; } @@ -132,7 +264,7 @@ public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAt } /// - public void DefineMethodOverride(IMethodSymbolBuilder methodInfoBody, IMethodSymbol methodInfoDeclaration) + public void DefineMethodOverride(IMethodSymbol methodInfoBody, IMethodSymbol methodInfoDeclaration) { UnderlyingTypeBuilder.DefineMethodOverride(methodInfoBody.Unpack(), methodInfoDeclaration.Unpack()); } @@ -243,506 +375,513 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) #region ITypeSymbol /// - public System.Reflection.TypeAttributes Attributes => _impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public IAssemblySymbol Assembly => _impl.Assembly; + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? FullName => _impl.FullName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? Namespace => _impl.Namespace; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public TypeCode TypeCode => _impl.TypeCode; + public string? FullName => UnderlyingType.FullName; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public string? Namespace => UnderlyingType.Namespace; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public bool HasElementType => UnderlyingType.HasElementType; /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsSZArray => UnderlyingType.IsSZArray; /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool HasElementType => _impl.HasElementType; + public bool IsClass => UnderlyingType.IsClass; /// - public bool IsClass => _impl.IsClass; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsValueType => _impl.IsValueType; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsInterface => _impl.IsInterface; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsArray => _impl.IsArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsEnum => _impl.IsEnum; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsPointer => UnderlyingType.IsPointer; /// - public bool IsNested => _impl.IsNested; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsSignatureType => throw new NotImplementedException(); /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// - public override bool IsComplete => _builder == null; + public int GetArrayRank() + { + return UnderlyingType.GetArrayRank(); + } /// - public int GetArrayRank() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetArrayRank(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol[] GetConstructors() { - return _impl.GetElementType(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public string[] GetEnumNames() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumNames(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol GetEnumUnderlyingType() + public ITypeSymbol? GetElementType() { - return _impl.GetEnumUnderlyingType(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericArguments() + public string? GetEnumName(object value) { - return _impl.GetGenericArguments(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string[] GetEnumNames() { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol GetGenericTypeDefinition() + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetGenericTypeDefinition(); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name) + public Array GetEnumValues() { - return _impl.GetInterface(name); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterface(name, ignoreCase); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol[] GetEvents() { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return _impl.GetField(name, bindingAttr); + throw new NotImplementedException(); } /// - public IFieldSymbol[] GetFields() + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetFields(bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + throw new NotImplementedException(); } /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperty(name, returnType); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties() { - return _impl.GetEvent(name, bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsAssignableFrom(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsEnumDefined(object value) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsEnumDefined(value); } /// - public bool IsEnumDefined(object value) + public bool IsSubclassOf(ITypeSymbol c) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(_type.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(_type.MakeArrayType(rank)); } /// public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(_type.MakeGenericType(typeArguments.Unpack())); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(_type.MakePointerType()); } /// public ITypeSymbol MakeByRefType() { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(_type.MakeByRefType()); } #endregion @@ -796,7 +935,6 @@ public override void OnComplete() base.OnComplete(); } - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs index 73df3a3be2..3d783ca7dc 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs @@ -20,13 +20,6 @@ interface IIkvmReflectionAssemblySymbol : IIkvmReflectionSymbol, IAssemblySymbol /// IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module); - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs index 483704f37c..86d071cfea 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs @@ -11,6 +11,13 @@ interface IIkvmReflectionMethodBaseSymbol : IIkvmReflectionMemberSymbol, IMethod /// MethodBase UnderlyingMethodBase { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs index c91b72a6b2..8e64ccaa46 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs @@ -11,6 +11,13 @@ interface IIkvmReflectionMethodSymbol : IIkvmReflectionMethodBaseSymbol, IMethod /// MethodInfo UnderlyingMethod { get; } + /// + /// Gets or creates a for the given generic type parameter. + /// + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs index 9c5129c3de..41a1252f2c 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs @@ -28,11 +28,11 @@ interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type); /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); + IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method); /// /// Gets or creates a for the specified . @@ -41,13 +41,6 @@ interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol /// IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); - /// /// Gets or creates a for the specified . /// @@ -55,13 +48,6 @@ interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol /// IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); - /// /// Gets or creates a for the specified . /// @@ -69,13 +55,6 @@ interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol /// IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); - /// /// Gets or creates a for the specified . /// @@ -83,13 +62,6 @@ interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol /// IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); - /// /// Gets or creates a for the specified . /// @@ -97,13 +69,6 @@ interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol /// IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); - /// /// Gets or creates a for the specified . /// @@ -111,13 +76,6 @@ interface IIkvmReflectionModuleSymbol : IIkvmReflectionSymbol, IModuleSymbol /// IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs index ddc2d8eb70..284719fb71 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs @@ -12,9 +12,9 @@ interface IIkvmReflectionParameterSymbol : IIkvmReflectionSymbol, IParameterSymb IIkvmReflectionModuleSymbol ResolvingModule { get; } /// - /// Gets the method that resolved the parameter. + /// Gets the member that resolved the parameter. /// - IIkvmReflectionMethodBaseSymbol ResolvingMethod { get; } + IIkvmReflectionMemberSymbol ResolvingMember { get; } /// /// Gets the underlying . diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs index 57e05528e4..f7c52268c9 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs @@ -11,6 +11,13 @@ interface IIkvmReflectionPropertySymbol : IIkvmReflectionMemberSymbol, IProperty /// PropertyInfo UnderlyingProperty { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs index 891dc53f80..af3369996d 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs @@ -27,14 +27,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(assembly))] IIkvmReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly); - /// - /// Resolves the symbol for the specified assembly builder. - /// - /// - /// - [return: NotNullIfNotNull(nameof(assembly))] - IIkvmReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); - /// /// Resolves the symbols for the specified assemblies. /// @@ -51,14 +43,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(module))] IIkvmReflectionModuleSymbol? ResolveModuleSymbol(Module? module); - /// - /// Resolves the symbol for the specified module. - /// - /// - /// - [return: NotNullIfNotNull(nameof(module))] - IIkvmReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); - /// /// Resolves the symbols for the specified modules. /// @@ -98,14 +82,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(type))] IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type); - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - [return: NotNullIfNotNull(nameof(type))] - IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); - /// /// Resolves the symbols for the specified types. /// @@ -137,14 +113,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(ctor))] IIkvmReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor); - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - [return: NotNullIfNotNull(nameof(ctor))] - IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); - /// /// Resolves the symbols for the specified constructors. /// @@ -161,14 +129,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(method))] IIkvmReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method); - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - [return: NotNullIfNotNull(nameof(method))] - IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); - /// /// Resolves the symbols for the specified methods. /// @@ -185,14 +145,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(field))] IIkvmReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field); - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - [return: NotNullIfNotNull(nameof(field))] - IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); - /// /// Resolves the symbols for the specified fields. /// @@ -209,14 +161,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(property))] IIkvmReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property); - /// - /// Resolves the symbol for the specified property. - /// - /// - /// - [return: NotNullIfNotNull(nameof(property))] - IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); - /// /// Resolves the symbols for the specified properties. /// @@ -233,14 +177,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(@event))] IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event); - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - [return: NotNullIfNotNull(nameof(@event))] - IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); - /// /// Resolves the symbols for the specified events. /// @@ -257,14 +193,6 @@ interface IIkvmReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(parameter))] IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter); - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - [return: NotNullIfNotNull(nameof(parameter))] - IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(ParameterBuilder parameter); - /// /// Resolves the symbols for the specified parameters. /// @@ -331,6 +259,13 @@ interface IIkvmReflectionSymbol : ISymbol /// CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(IKVM.Reflection.CustomAttributeNamedArgument arg); + /// + /// Transforms a into a symbol type. + /// + /// + /// + InterfaceMapping ResolveInterfaceMapping(IKVM.Reflection.InterfaceMapping arg); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs index fd6281149f..b2dac0f006 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs @@ -1,4 +1,6 @@ -using Type = IKVM.Reflection.Type; +using IKVM.Reflection; + +using Type = IKVM.Reflection.Type; namespace IKVM.CoreLib.Symbols.IkvmReflection { @@ -11,6 +13,87 @@ interface IIkvmReflectionTypeSymbol : IIkvmReflectionMemberSymbol, ITypeSymbol /// Type UnderlyingType { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); + + /// + /// Gets or creates a for the given generic type parameter type. + /// + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); + + /// + /// Gets or creates a for the given element type. + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol(); + + /// + /// Gets or creates a for the given element type. + /// + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank); + + /// + /// Gets or creates a for the given element type. + /// + /// + IIkvmReflectionTypeSymbol GetOrCreatePointerTypeSymbol(); + + /// + /// Gets or creates a for the given element type. + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol(); + + /// + /// Gets or creates a for the given element type. + /// + /// + /// + IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index eb728f5513..1b4b2ef00e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -2,9 +2,7 @@ using System.Collections.Generic; using System.Linq; -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; using IKVM.Reflection; -using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection { @@ -13,7 +11,8 @@ class IkvmReflectionAssemblySymbol : IkvmReflectionSymbol, IIkvmReflectionAssemb { readonly Assembly _assembly; - IkvmReflectionAssemblyMetadata _impl; + + IkvmReflectionModuleTable _moduleTable; /// /// Initializes a new instance. @@ -24,7 +23,7 @@ public IkvmReflectionAssemblySymbol(IkvmReflectionSymbolContext context, Assembl base(context) { _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); - _impl = new IkvmReflectionAssemblyMetadata(this); + _moduleTable = new IkvmReflectionModuleTable(context, this); } /// @@ -32,6 +31,16 @@ public IkvmReflectionAssemblySymbol(IkvmReflectionSymbolContext context, Assembl /// public Assembly UnderlyingAssembly => _assembly; + #region IIkvmAssemblySymbol + + /// + public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _moduleTable.GetOrCreateModuleSymbol(module); + } + + #endregion + #region IAssemblySymbol /// @@ -82,19 +91,19 @@ public IModuleSymbol[] GetModules(bool getResourceModules) /// public System.Reflection.AssemblyName GetName() { - return _assembly.GetName().ToAssemblyName(); + return _assembly.GetName().Pack(); } /// public System.Reflection.AssemblyName GetName(bool copiedName) { - return _assembly.GetName().ToAssemblyName(); + return _assembly.GetName().Pack(); } /// public System.Reflection.AssemblyName[] GetReferencedAssemblies() { - return _assembly.GetReferencedAssemblies().ToAssemblyNames(); + return _assembly.GetReferencedAssemblies().Pack(); } /// @@ -147,16 +156,6 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion - public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - return _impl.GetOrCreateModuleSymbol(module); - } - - public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) - { - return (IIkvmReflectionModuleSymbolBuilder)_impl.GetOrCreateModuleSymbol(module); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs new file mode 100644 index 0000000000..c131d4927c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs @@ -0,0 +1,94 @@ +using System; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionEventTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionEventTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type ?? throw new ArgumentNullException(nameof(type)); + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.MetadataToken)); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + return _table[row] ??= new IkvmReflectionEventSymbol(_context, _module, _type, @event); + else + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.GetEventToken().Token)); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + return (IIkvmReflectionEventSymbolBuilder)(_table[row] ??= new IkvmReflectionEventSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionTypeSymbolBuilder)_type, @event)); + else + return (IIkvmReflectionEventSymbolBuilder?)_table[row] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs new file mode 100644 index 0000000000..9158d9d19a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs @@ -0,0 +1,80 @@ +using System; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionFieldTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol? _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionFieldTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + if (field.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(field)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(field.MetadataToken)); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + if (field is FieldBuilder builder) + return _table[row] ??= new IkvmReflectionFieldSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionTypeSymbolBuilder?)_type, builder); + else + return _table[row] ??= new IkvmReflectionFieldSymbol(_context, _module, _type, field); + else + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return (IIkvmReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs index a685c97dc8..ec027dd931 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs @@ -11,25 +11,25 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionGenericTypeParameterSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionTypeSymbol { - readonly IIkvmReflectionMethodSymbol? _resolvingMethod; + readonly IIkvmReflectionMemberSymbol _resolvingMember; readonly Type _type; - IkvmReflectionTypeImpl _impl; + + IkvmReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. /// /// /// - /// - /// + /// /// /// - public IkvmReflectionGenericTypeParameterSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType, IIkvmReflectionMethodSymbol? resolvingMethod, Type type) : - base(context, resolvingModule, resolvingType) + public IkvmReflectionGenericTypeParameterSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMemberSymbol resolvingMember, Type type) : + base(context, resolvingModule, resolvingMember as IIkvmReflectionTypeSymbol) { - _resolvingMethod = resolvingMethod; + _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _type = type ?? throw new ArgumentNullException(nameof(type)); - _impl = new IkvmReflectionTypeImpl(this); + _specTable = new IkvmReflectionTypeSpecTable(); } /// @@ -41,526 +41,612 @@ public IkvmReflectionGenericTypeParameterSymbol(IkvmReflectionSymbolContext cont /// /// Gets the method base that declares this type parameter. /// - public IIkvmReflectionMethodBaseSymbol? ResolvingMethodBase => _resolvingMethod; + public IIkvmReflectionMemberSymbol? ResolvingMemberSymbol => _resolvingMember; + + #region IIkvmReflectionSymbol + + /// + [return: NotNullIfNotNull(nameof(type))] + public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + { + if (type == _type) + return this; + else + return base.ResolveTypeSymbol(type); + } + + #endregion + + #region IIkvmReflectionTypeSymbol + + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type type) + { + throw new NotSupportedException(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion #region ITypeSymbol /// - public System.Reflection.TypeAttributes Attributes => _impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public IAssemblySymbol Assembly => _impl.Assembly; + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? FullName => _impl.FullName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? Namespace => _impl.Namespace; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public TypeCode TypeCode => _impl.TypeCode; + public string? FullName => UnderlyingType.FullName; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public string? Namespace => UnderlyingType.Namespace; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public bool HasElementType => UnderlyingType.HasElementType; /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsSZArray => UnderlyingType.IsSZArray; /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool HasElementType => _impl.HasElementType; + public bool IsClass => UnderlyingType.IsClass; /// - public bool IsClass => _impl.IsClass; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsValueType => _impl.IsValueType; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsInterface => _impl.IsInterface; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsArray => _impl.IsArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsEnum => _impl.IsEnum; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsPointer => UnderlyingType.IsPointer; /// - public bool IsNested => _impl.IsNested; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsSignatureType => throw new NotImplementedException(); /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// public int GetArrayRank() { - return _impl.GetArrayRank(); + return UnderlyingType.GetArrayRank(); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetElementType(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors() { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string[] GetEnumNames() + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumNames(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public ITypeSymbol GetEnumUnderlyingType() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumUnderlyingType(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol[] GetGenericArguments() + public ITypeSymbol? GetElementType() { - return _impl.GetGenericArguments(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string? GetEnumName(object value) { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol GetGenericTypeDefinition() + public string[] GetEnumNames() { - return _impl.GetGenericTypeDefinition(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol? GetInterface(string name) + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetInterface(name); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public Array GetEnumValues() { - return _impl.GetInterface(name, ignoreCase); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents() { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, bindingAttr); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetConstructor(types); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructors(); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name, bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol[] GetFields() + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return _impl.GetFields(); + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); } /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(bindingAttr); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, types); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name, bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties() { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public bool IsAssignableFrom(ITypeSymbol? c) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.IsAssignableFrom(c); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// public bool IsEnumDefined(object value) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsEnumDefined(value); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); } /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + public ITypeSymbol MakeByRefType() { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); } /// - public ITypeSymbol MakeByRefType() + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } #endregion - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - [return: NotNullIfNotNull(nameof(type))] - public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) - { - if (type == _type) - return this; - else - return base.ResolveTypeSymbol(type); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs new file mode 100644 index 0000000000..7caf5453c1 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs @@ -0,0 +1,82 @@ +using System; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionGenericTypeParameterTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionMemberSymbol _member; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionGenericTypeParameterTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionMemberSymbol member) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _member = member; + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + if (genericTypeParameter is null) + throw new ArgumentNullException(nameof(genericTypeParameter)); + if (genericTypeParameter.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(genericTypeParameter)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var pos = genericTypeParameter.GenericParameterPosition; + if (_table[pos] == null) + using (_lock.CreateWriteLock()) + if (genericTypeParameter is GenericTypeParameterBuilder builder) + return _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionMemberSymbolBuilder)_member, builder); + else + return _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbol(_context, _module, _member, genericTypeParameter); + else + { + return _table[pos] ?? throw new InvalidOperationException(); + } + } + } + + /// + /// Gets or creates the cached for the module. + /// + /// + /// + public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return (IIkvmReflectionGenericTypeParameterSymbolBuilder)GetOrCreateGenericTypeParameterSymbol((Type)genericTypeParameter); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index 22ed03a6c9..69abb71899 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -1,5 +1,4 @@ using System; -using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Linq; @@ -48,49 +47,6 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl /// public IIkvmReflectionTypeSymbol? ResolvingType => _resolvingType; - #region IMemberSymbol - - /// - public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; - - /// - public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; - - /// - public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; - - /// - public virtual int MetadataToken => UnderlyingMember.MetadataToken; - - /// - public virtual string Name => UnderlyingMember.Name; - - /// - public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(null, inherit))!; - } - - /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit)); - } - - /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); - } - - /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); - } - - #endregion - /// [return: NotNullIfNotNull(nameof(type))] public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) @@ -126,19 +82,6 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return base.ResolveConstructorSymbol(ctor); } - /// - [return: NotNullIfNotNull(nameof(ctor))] - public override IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) - { - if (ctor is null) - throw new ArgumentNullException(nameof(ctor)); - - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); - - return base.ResolveConstructorSymbol(ctor); - } - /// [return: NotNullIfNotNull(nameof(method))] public override IIkvmReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) @@ -155,19 +98,6 @@ public override IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol return base.ResolveMethodSymbol(method); } - /// - [return: NotNullIfNotNull(nameof(method))] - public override IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); - - return base.ResolveMethodSymbol(method); - } - /// [return: NotNullIfNotNull(nameof(field))] public override IIkvmReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) @@ -184,19 +114,6 @@ public override IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBui return base.ResolveFieldSymbol(field); } - /// - [return: NotNullIfNotNull(nameof(field))] - public override IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); - - return base.ResolveFieldSymbol(field); - } - /// [return: NotNullIfNotNull(nameof(property))] public override IIkvmReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) @@ -213,19 +130,6 @@ public override IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilde return base.ResolvePropertySymbol(property); } - /// - [return: NotNullIfNotNull(nameof(property))] - public override IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); - - return base.ResolvePropertySymbol(property); - } - /// [return: NotNullIfNotNull(nameof(@event))] public override IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) @@ -242,19 +146,6 @@ public override IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Prope return base.ResolveEventSymbol(@event); } - /// - [return: NotNullIfNotNull(nameof(@event))] - public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - if (@event.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); - - return base.ResolveEventSymbol(@event); - } - /// [return: NotNullIfNotNull(nameof(parameter))] public override IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) @@ -268,19 +159,49 @@ public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilde return base.ResolveParameterSymbol(parameter); } + #region IMemberSymbol + /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + + /// + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + + /// + public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + + /// + public virtual int MetadataToken => UnderlyingMember.MetadataToken; + + /// + public virtual string Name => UnderlyingMember.Name; + + /// + public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(null, inherit))!; + } - if (parameter.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttributes(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit)); + } - return base.ResolveParameterSymbol(parameter); + /// + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); } + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs index 3e5a0a8365..9e3d71d816 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs @@ -6,6 +6,8 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection abstract class IkvmReflectionMethodBaseSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionMethodBaseSymbol { + IkvmReflectionParameterTable _parameterTable; + /// /// Initializes a new instance. /// @@ -15,9 +17,19 @@ abstract class IkvmReflectionMethodBaseSymbol : IkvmReflectionMemberSymbol, IIkv public IkvmReflectionMethodBaseSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : base(context, resolvingModule, resolvingType) { + _parameterTable = new IkvmReflectionParameterTable(context, resolvingModule, this); + } + #region IIkvmReflectionMethodBaseSymbol + + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); } + #endregion + #region IMethodBaseSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs new file mode 100644 index 0000000000..1a94625e77 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs @@ -0,0 +1,66 @@ +using System; +using System.Collections.Concurrent; +using System.Threading; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionMethodSpecTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol _type; + readonly IIkvmReflectionMethodSymbol _method; + + ConcurrentDictionary? _genericMethodSymbols; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public IkvmReflectionMethodSpecTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol type, IIkvmReflectionMethodSymbol method) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type ?? throw new ArgumentNullException(nameof(type)); + _method = method ?? throw new ArgumentNullException(nameof(method)); + } + + /// + /// Gets or creates a representing a specialized generic of this method. + /// + /// + /// + public IIkvmReflectionMethodSymbol GetOrCreateGenericMethodSymbol(Type[] genericTypeArguments) + { + if (genericTypeArguments is null) + throw new ArgumentNullException(nameof(genericTypeArguments)); + + if (_method.IsGenericMethodDefinition == false) + throw new InvalidOperationException(); + + if (_genericMethodSymbols == null) + Interlocked.CompareExchange(ref _genericMethodSymbols, new(TypeSymbolListEqualityComparer.Instance), null); + + return _genericMethodSymbols.GetOrAdd(_module.ResolveTypeSymbols(genericTypeArguments), CreateGenericMethodSymbol); + } + + /// + /// Creates a new representing a specialized generic of this type. + /// + /// + /// + readonly IIkvmReflectionMethodSymbol CreateGenericMethodSymbol(IIkvmReflectionTypeSymbol[] genericTypeArguments) + { + return new IkvmReflectionMethodSymbol(_context, _module, _type, _method.UnderlyingMethod.MakeGenericMethod(genericTypeArguments.Unpack())); + } + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs index 54dc46ff75..e0c8b8e3e6 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs @@ -2,6 +2,8 @@ using IKVM.Reflection; +using Type = IKVM.Reflection.Type; + namespace IKVM.CoreLib.Symbols.IkvmReflection { @@ -10,6 +12,8 @@ class IkvmReflectionMethodSymbol : IkvmReflectionMethodBaseSymbol, IIkvmReflecti readonly MethodInfo _method; + IkvmReflectionGenericTypeParameterTable _genericTypeParameterTable; + /// /// Initializes a new instance. /// @@ -21,6 +25,7 @@ public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IIkvmRefl base(context, module, type) { _method = method ?? throw new ArgumentNullException(nameof(method)); + _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, module, this); } /// @@ -29,6 +34,16 @@ public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IIkvmRefl /// public override MethodBase UnderlyingMethodBase => UnderlyingMethod; + #region IIkvmReflectionMethodSymbol + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + #endregion + #region IMethodSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs new file mode 100644 index 0000000000..cd1781c83a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs @@ -0,0 +1,157 @@ +using System; +using System.Collections.Concurrent; +using System.Collections.Generic; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionMethodTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol? _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + ConcurrentDictionary? _byName; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionMethodTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + if (method.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(method)); + if (method is MethodInfo m_ && m_.IsMethodDefinition() == false) + throw new ArgumentException(nameof(method)); + + var row = MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(method.MetadataToken)); + if (row == 0) + { + // we fall back to lookup by name if there is no valid metadata token + if (_byName == null) + Interlocked.CompareExchange(ref _byName, new(), null); + + var context_ = _context; + var module_ = _module; + var type_ = _type; + var method_ = method; + return _byName.GetOrAdd(method.ToString() ?? throw new InvalidOperationException(), _ => CreateMethodBaseSymbol(context_, module_, type_, method_)); + } + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + if (_table[row] == null) + using (_lock.CreateWriteLock()) + return _table[row] ??= CreateMethodBaseSymbol(_context, _module, _type, method); + + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Creates a new symbol. + /// + /// + /// + /// + static IIkvmReflectionMethodBaseSymbol CreateMethodBaseSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type, MethodBase method) + { + if (method is ConstructorInfo c) + { + if (type == null) + throw new InvalidOperationException(); + + if (method is ConstructorBuilder builder) + return new IkvmReflectionConstructorSymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, (IIkvmReflectionTypeSymbolBuilder)type, builder); + else + return new IkvmReflectionConstructorSymbol(context, module, type, c); + } + else if (method is MethodInfo m) + { + if (method is MethodBuilder builder) + return new IkvmReflectionMethodSymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, (IIkvmReflectionTypeSymbolBuilder?)type, builder); + else + return new IkvmReflectionMethodSymbol(context, module, type, m); + } + else + { + throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return (IIkvmReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return (IIkvmReflectionConstructorSymbolBuilder)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return (IIkvmReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return (IIkvmReflectionMethodSymbolBuilder)GetOrCreateMethodBaseSymbol(method); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs deleted file mode 100644 index 1d9b0a3e23..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleMetadata.cs +++ /dev/null @@ -1,480 +0,0 @@ -using System; -using System.Reflection.Metadata.Ecma335; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; -using IKVM.CoreLib.Threading; -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - /// - /// Provides the metadata resolution implementation for a module. - /// - struct IkvmReflectionModuleMetadata - { - - /// - /// Returns true if the given is a TypeDef. That is, not a modified or substituted or generic parameter type. - /// - /// - /// - static bool IsTypeDefinition(Type type) - { - return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; - } - - const int MAX_CAPACITY = 65536 * 2; - - readonly IIkvmReflectionModuleSymbol _symbol; - - IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _typeLock; - - IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _methodLock; - - IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _fieldLock; - - IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _propertyLock; - - IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _eventLock; - - IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _parameterLock; - - IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _genericParameterLock; - - /// - /// Initializes a new instance. - /// - /// - /// - public IkvmReflectionModuleMetadata(IIkvmReflectionModuleSymbol symbol) - { - _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - if (type.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(type)); - - // type is a generic parameter (GenericParam) - if (type.IsGenericParameter) - return GetOrCreateGenericTypeParameterSymbol(type); - - // type is not a type definition (TypeDef) - if (IsTypeDefinition(type) == false) - return GetOrCreateTypeSymbolForSpecification(type); - - // create lock on demand - if (_typeLock == null) - Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); - - using (_typeLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.TypeDefinitionHandle(type.MetadataToken)); - if (_typeSymbols[row] == null) - using (_typeLock.CreateWriteLock()) - if (type is TypeBuilder builder) - return _typeSymbols[row] ??= new IkvmReflectionTypeSymbolBuilder(_symbol.Context, _symbol, builder); - else - return _typeSymbols[row] ??= new IkvmReflectionTypeSymbol(_symbol.Context, _symbol, type); - else - return _typeSymbols[row] ?? throw new InvalidOperationException(); - } - } - - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - return (IIkvmReflectionTypeSymbolBuilder)GetOrCreateTypeSymbol((Type)type); - } - - /// - /// Gets or creates a for the specification type: array, pointer, generic, etc. - /// - /// - /// - /// - /// - IIkvmReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - if (type.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(type)); - - if (type.GetElementType() is { } elementType) - { - var elementTypeSymbol = _symbol.ResolveTypeSymbol(elementType)!; - - // handles both SZ arrays and normal arrays - if (type.IsArray) - return (IIkvmReflectionTypeSymbol)elementTypeSymbol.MakeArrayType(type.GetArrayRank()); - - if (type.IsPointer) - return (IIkvmReflectionTypeSymbol)elementTypeSymbol.MakePointerType(); - - if (type.IsByRef) - return (IIkvmReflectionTypeSymbol)elementTypeSymbol.MakeByRefType(); - - throw new InvalidOperationException(); - } - - if (type.IsGenericType) - { - var definitionTypeSymbol = _symbol.GetOrCreateTypeSymbol(type.GetGenericTypeDefinition()); - return (IIkvmReflectionTypeSymbol)definitionTypeSymbol.MakeGenericType(definitionTypeSymbol.ResolveTypeSymbols(type.GetGenericArguments())!); - } - - throw new InvalidOperationException(); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - if (method.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(method)); - - // create lock on demand - if (_methodLock == null) - Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); - - using (_methodLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(method.MetadataToken)); - if (_methodSymbols[row] == null) - { - using (_methodLock.CreateWriteLock()) - { - if (method is ConstructorInfo c) - { - if (method is ConstructorBuilder builder) - return _methodSymbols[row] ??= new IkvmReflectionConstructorSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), builder); - else - return _methodSymbols[row] ??= new IkvmReflectionConstructorSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), c); - } - else if (method is MethodInfo m) - { - if (method is MethodBuilder builder) - return _methodSymbols[row] ??= new IkvmReflectionMethodSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), builder); - else - return _methodSymbols[row] ??= new IkvmReflectionMethodSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), m); - } - else - { - throw new InvalidOperationException(); - } - } - } - else - { - return _methodSymbols[row] ?? throw new InvalidOperationException(); - } - } - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return (IIkvmReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return (IIkvmReflectionConstructorSymbolBuilder)GetOrCreateConstructorSymbol((ConstructorInfo)ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return (IIkvmReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return (IIkvmReflectionMethodSymbolBuilder)GetOrCreateMethodBaseSymbol((MethodInfo)method); - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - if (field.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(field)); - - // create lock on demand - if (_fieldLock == null) - Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); - - using (_fieldLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(field.MetadataToken)); - if (_fieldSymbols[row] == null) - using (_fieldLock.CreateWriteLock()) - if (field is FieldBuilder builder) - return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), builder); - else - return _fieldSymbols[row] ??= new IkvmReflectionFieldSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), field); - else - return _fieldSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - return (IIkvmReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field); - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - if (property.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(property)); - - // create lock on demand - if (_propertyLock == null) - Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); - - using (_propertyLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(property.MetadataToken)); - if (_propertySymbols[row] == null) - using (_propertyLock.CreateWriteLock()) - if (property is PropertyBuilder builder) - return _propertySymbols[row] ??= new IkvmReflectionPropertySymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), builder); - else - return _propertySymbols[row] ??= new IkvmReflectionPropertySymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), property); - else - return _propertySymbols[row] ?? throw new InvalidOperationException(); - } - } - - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return (IIkvmReflectionPropertySymbolBuilder)GetOrCreatePropertySymbol((PropertyInfo)property); - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - if (@event.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(@event)); - - // create lock on demand - if (_eventLock == null) - Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); - - using (_eventLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.MetadataToken)); - if (_eventSymbols[row] == null) - using (_eventLock.CreateWriteLock()) - return _eventSymbols[row] ??= new IkvmReflectionEventSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.DeclaringType!), @event); - else - return _eventSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - if (@event.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(@event)); - - // create lock on demand - if (_eventLock == null) - Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); - - using (_eventLock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.GetEventToken().Token)); - if (_eventSymbols[row] == null) - using (_eventLock.CreateWriteLock()) - return (IIkvmReflectionEventSymbolBuilder)(_eventSymbols[row] ??= new IkvmReflectionEventSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.DeclaringType), @event)); - else - return (IIkvmReflectionEventSymbolBuilder?)_eventSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - if (parameter.Member.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(parameter)); - - // create lock on demand - if (_parameterLock == null) - Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); - - using (_parameterLock.CreateUpgradeableReadLock()) - { - var position = parameter.Position; - if (_parameterSymbols[position] == null) - using (_parameterLock.CreateWriteLock()) - return _parameterSymbols[position] ??= new IkvmReflectionParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); - else - return _parameterSymbols[position] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - if (parameter.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(parameter)); - - // create lock on demand - if (_parameterLock == null) - Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); - - using (_parameterLock.CreateUpgradeableReadLock()) - { - var position = parameter.Position; - if (_parameterSymbols[position] == null) - using (_parameterLock.CreateWriteLock()) - return (IIkvmReflectionParameterSymbolBuilder)(_parameterSymbols[position] ??= new IkvmReflectionParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveMethodSymbol(parameter.Method), parameter)); - else - return (IIkvmReflectionParameterSymbolBuilder?)_parameterSymbols[position] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericParameterType) - { - if (genericParameterType is null) - throw new ArgumentNullException(nameof(genericParameterType)); - if (genericParameterType.Module.MetadataToken != _symbol.MetadataToken) - throw new ArgumentException(nameof(genericParameterType)); - - // create lock on demand - if (_genericParameterLock == null) - Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); - - using (_genericParameterLock.CreateUpgradeableReadLock()) - { - var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.MetadataToken); - var row = MetadataTokens.GetRowNumber(hnd); - if (_genericParameterSymbols[row] == null) - using (_genericParameterLock.CreateWriteLock()) - if (genericParameterType is GenericTypeParameterBuilder builder) - return _genericParameterSymbols[row] ??= new IkvmReflectionGenericTypeParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), builder); - else - return _genericParameterSymbols[row] ??= new IkvmReflectionGenericTypeParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), genericParameterType); - else - { - return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); - } - } - } - - /// - /// Gets or creates the cached for the module. - /// - /// - /// - IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) - { - return (IIkvmReflectionGenericTypeParameterSymbolBuilder)GetOrCreateGenericTypeParameterSymbol((Type)genericParameterType); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index 94913c88f8..1775a26925 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -1,9 +1,7 @@ using System; using System.Linq; -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; using IKVM.Reflection; -using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; @@ -18,7 +16,10 @@ class IkvmReflectionModuleSymbol : IkvmReflectionSymbol, IIkvmReflectionModuleSy readonly IIkvmReflectionAssemblySymbol _resolvingAssembly; readonly Module _module; - IkvmReflectionModuleMetadata _impl; + + IkvmReflectionTypeTable _typeTable; + IkvmReflectionMethodTable _methodTable; + IkvmReflectionFieldTable _fieldTable; /// /// Initializes a new instance. @@ -32,7 +33,10 @@ public IkvmReflectionModuleSymbol(IkvmReflectionSymbolContext context, IIkvmRefl { _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); _module = module ?? throw new ArgumentNullException(nameof(module)); - _impl = new IkvmReflectionModuleMetadata(this); + + _typeTable = new IkvmReflectionTypeTable(context, this, null); + _methodTable = new IkvmReflectionMethodTable(context, this, null); + _fieldTable = new IkvmReflectionFieldTable(context, this, null); } /// @@ -231,89 +235,88 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + #region IIkvmReflectionModuleSymbol + /// public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) { - return _impl.GetOrCreateTypeSymbol(type); - } + if (type.IsTypeDefinition()) + return _typeTable.GetOrCreateTypeSymbol(type); + else if (type.IsGenericType) + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + else if (type.IsSZArray) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreateSZArrayTypeSymbol(); + else if (type.IsArray) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreateArrayTypeSymbol(type.GetArrayRank()); + else if (type.IsPointer) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreatePointerTypeSymbol(); + else if (type.IsByRef) + return ResolveTypeSymbol(type.GetElementType()).GetOrCreateByRefTypeSymbol(); + else if (type.IsGenericParameter && type.DeclaringMethod is MethodInfo dm) + return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(type); + else if (type.IsGenericParameter && type.DeclaringType is Type t) + return ResolveTypeSymbol(t).GetOrCreateGenericTypeParameterSymbol(type); - /// - public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - return _impl.GetOrCreateTypeSymbol(type); + throw new InvalidOperationException(); } /// - public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) { - return _impl.GetOrCreateConstructorSymbol(ctor); + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodBaseSymbol(method); + else + return _methodTable.GetOrCreateMethodBaseSymbol(method); } /// - public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { - return _impl.GetOrCreateConstructorSymbol(ctor); + return ResolveTypeSymbol(ctor.DeclaringType).GetOrCreateConstructorSymbol(ctor); } /// public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { - return _impl.GetOrCreateMethodSymbol(method); - } - - /// - public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return _impl.GetOrCreateMethodSymbol(method); + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodSymbol(method); + else + return _methodTable.GetOrCreateMethodSymbol(method); } /// public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - return _impl.GetOrCreateFieldSymbol(field); - } - - /// - public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - return _impl.GetOrCreateFieldSymbol(field); + if (field.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateFieldSymbol(field); + else + return _fieldTable.GetOrCreateFieldSymbol(field); } /// public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { - return _impl.GetOrCreatePropertySymbol(property); - } - - /// - public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return _impl.GetOrCreatePropertySymbol(property); + return ResolveTypeSymbol(property.DeclaringType).GetOrCreatePropertySymbol(property); } /// public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { - return _impl.GetOrCreateEventSymbol(@event); - } - - /// - public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return _impl.GetOrCreateEventSymbol(@event); + return ResolveTypeSymbol(@event.DeclaringType).GetOrCreateEventSymbol(@event); } /// public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { - return _impl.GetOrCreateParameterSymbol(parameter); + return ResolveMemberSymbol(parameter.Member) switch + { + IIkvmReflectionMethodBaseSymbol method => method.GetOrCreateParameterSymbol(parameter), + IIkvmReflectionPropertySymbol property => property.GetOrCreateParameterSymbol(parameter), + _ => throw new InvalidOperationException(), + }; } - /// - public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return _impl.GetOrCreateParameterSymbol(parameter); - } + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblyMetadata.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs similarity index 59% rename from src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblyMetadata.cs rename to src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs index 11dfb71158..bb04071744 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblyMetadata.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs @@ -11,30 +11,31 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection { - struct IkvmReflectionAssemblyMetadata + struct IkvmReflectionModuleTable { - readonly IIkvmReflectionAssemblySymbol _symbol; + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionAssemblySymbol _assembly; - IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); + IndexRangeDictionary _moduleSymbols = new(); ReaderWriterLockSlim? _moduleLock; /// /// Initializes a new instance. /// - /// + /// /// - public IkvmReflectionAssemblyMetadata(IIkvmReflectionAssemblySymbol symbol) + public IkvmReflectionModuleTable(IkvmReflectionSymbolContext context, IIkvmReflectionAssemblySymbol assembly) { - _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + _context = context ?? throw new ArgumentNullException(nameof(context)); + _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); } /// - /// Gets or creates the cached for the module. + /// Gets or creates the cached for the module. /// /// /// - /// public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) { if (module is null) @@ -50,14 +51,24 @@ public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) if (_moduleSymbols[row] == null) using (_moduleLock.CreateWriteLock()) if (module is ModuleBuilder builder) - return _moduleSymbols[row] = new IkvmReflectionModuleSymbolBuilder(_symbol.Context, _symbol, builder); + return _moduleSymbols[row] = new IkvmReflectionModuleSymbolBuilder(_context, _assembly, builder); else - return _moduleSymbols[row] = new IkvmReflectionModuleSymbol(_symbol.Context, _symbol, module); + return _moduleSymbols[row] = new IkvmReflectionModuleSymbol(_context, _assembly, module); else return _moduleSymbols[row] ?? throw new InvalidOperationException(); } } + /// + /// Gets or creates the cached for the module. + /// + /// + /// + public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return (IIkvmReflectionModuleSymbolBuilder)GetOrCreateModuleSymbol((Module)module); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs index 58440f6c39..d23d839393 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs @@ -10,7 +10,7 @@ class IkvmReflectionParameterSymbol : IkvmReflectionSymbol, IIkvmReflectionParam { readonly IIkvmReflectionModuleSymbol _resolvingModule; - readonly IIkvmReflectionMethodBaseSymbol _resolvingMethod; + readonly IIkvmReflectionMemberSymbol _resolvingMember; readonly ParameterInfo _parameter; /// @@ -18,13 +18,13 @@ class IkvmReflectionParameterSymbol : IkvmReflectionSymbol, IIkvmReflectionParam /// /// /// - /// + /// /// - public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMethodBaseSymbol resolvingMethod, ParameterInfo parameter) : + public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMemberSymbol? resolvingMember, ParameterInfo parameter) : base(context) { _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); + _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); } @@ -32,7 +32,7 @@ public IkvmReflectionParameterSymbol(IkvmReflectionSymbolContext context, IIkvmR public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingModule; /// - public IIkvmReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; + public IIkvmReflectionMemberSymbol ResolvingMember => _resolvingMember; /// public ParameterInfo UnderlyingParameter => _parameter; diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs new file mode 100644 index 0000000000..452c861a43 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs @@ -0,0 +1,94 @@ +using System; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionParameterTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionMemberSymbol _member; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public IkvmReflectionParameterTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionMemberSymbol member) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _member = member ?? throw new ArgumentNullException(nameof(member)); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.Member.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_table[position] == null) + using (_lock.CreateWriteLock()) + return _table[position] ??= new IkvmReflectionParameterSymbol(_context, _module, _member, parameter); + + return _table[position] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (_table[position] == null) + using (_lock.CreateWriteLock()) + return (IIkvmReflectionParameterSymbolBuilder)(_table[position] ??= new IkvmReflectionParameterSymbolBuilder(_context, _module, (IIkvmReflectionMethodBaseSymbol)_member, parameter)); + + return (IIkvmReflectionParameterSymbolBuilder?)_table[position] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs index 96b8eb3582..6a60318549 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertySymbol.cs @@ -10,6 +10,8 @@ class IkvmReflectionPropertySymbol : IkvmReflectionMemberSymbol, IIkvmReflection readonly PropertyInfo _property; + IkvmReflectionParameterTable _parameterTable; + /// /// Initializes a new instance. /// @@ -21,6 +23,7 @@ public IkvmReflectionPropertySymbol(IkvmReflectionSymbolContext context, IIkvmRe base(context, module, type) { _property = property ?? throw new ArgumentNullException(nameof(property)); + _parameterTable = new IkvmReflectionParameterTable(context, module, this); } /// @@ -29,6 +32,18 @@ public IkvmReflectionPropertySymbol(IkvmReflectionSymbolContext context, IIkvmRe /// public override MemberInfo UnderlyingMember => UnderlyingProperty; + #region IIkvmReflectionPropertySymbol + + /// + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + + #region IPropertySymbol + /// public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)UnderlyingProperty.Attributes; @@ -116,6 +131,8 @@ public ITypeSymbol[] GetRequiredCustomModifiers() return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); } + #endregion + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs new file mode 100644 index 0000000000..6718e08988 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs @@ -0,0 +1,80 @@ +using System; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection; +using IKVM.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionPropertyTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionPropertyTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type ?? throw new ArgumentNullException(nameof(type)); + } + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + if (property.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(property)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(property.MetadataToken)); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + if (property is PropertyBuilder builder) + return _table[row] ??= new IkvmReflectionPropertySymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionTypeSymbolBuilder)_type, builder); + else + return _table[row] ??= new IkvmReflectionPropertySymbol(_context, _module, _type, property); + else + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return (IIkvmReflectionPropertySymbolBuilder)GetOrCreatePropertySymbol((PropertyInfo)property); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index 393b98db49..7d1eb10de9 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -430,11 +430,7 @@ public virtual IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(Para return a; } - /// - /// Transforms a custom set of custom attribute data records to a symbol record. - /// - /// - /// + /// public virtual IEnumerable ResolveCustomAttributes(IEnumerable attributes) { if (attributes is null) @@ -448,11 +444,7 @@ public virtual IEnumerable ResolveCustomAttributes(IEnumerable< return a.ToArray(); } - /// - /// Transforms a custom attribute data record to a symbol record. - /// - /// - /// + /// [return: NotNullIfNotNull(nameof(customAttributeData))] public virtual CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) { @@ -466,11 +458,7 @@ public virtual IEnumerable ResolveCustomAttributes(IEnumerable< ResolveCustomAttributeNamedArguments(customAttributeData.NamedArguments)); } - /// - /// Transforms a list of values into symbols. - /// - /// - /// + /// public ImmutableArray ResolveCustomAttributeTypedArguments(IList args) { if (args is null) @@ -485,11 +473,7 @@ public ImmutableArray ResolveCustomAttributeTypedA return a.ToImmutableArray(); } - /// - /// Transforms a values into a symbol. - /// - /// - /// + /// public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Reflection.CustomAttributeTypedArgument arg) { return new CustomAttributeTypedArgument( @@ -497,11 +481,7 @@ public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Ref ResolveCustomAttributeTypedValue(arg.Value)); } - /// - /// Transforms the type as appropriate. - /// - /// - /// + /// public object? ResolveCustomAttributeTypedValue(object? value) { return value switch @@ -511,11 +491,7 @@ public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Ref }; } - /// - /// Transforms a list of values into symbols. - /// - /// - /// + /// public ImmutableArray ResolveCustomAttributeNamedArguments(IList args) { if (args is null) @@ -530,11 +506,7 @@ public ImmutableArray ResolveCustomAttributeNamedA return ImmutableArray.Create(a); } - /// - /// Transforms a values into a symbol. - /// - /// - /// + /// public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(IKVM.Reflection.CustomAttributeNamedArgument arg) { return new CustomAttributeNamedArgument( @@ -544,6 +516,15 @@ public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(IKVM.Ref ResolveCustomAttributeTypedArgument(arg.TypedValue)); } + /// + public InterfaceMapping ResolveInterfaceMapping(IKVM.Reflection.InterfaceMapping mapping) + { + return new InterfaceMapping( + ResolveMethodSymbols(mapping.InterfaceMethods), + ResolveTypeSymbol(mapping.InterfaceType), + ResolveMethodSymbols(mapping.TargetMethods), + ResolveTypeSymbol(mapping.TargetType)); + } } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs index 8268ab17bb..d623f2d1c2 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -18,15 +18,45 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection class IkvmReflectionSymbolContext : ISymbolContext { + readonly Universe _universe; readonly ConcurrentDictionary> _symbolByName = new(); readonly ConditionalWeakTable _symbolByAssembly = new(); /// /// Initializes a new instance. /// - public IkvmReflectionSymbolContext() + /// + public IkvmReflectionSymbolContext(Universe universe) { + _universe = universe ?? throw new ArgumentNullException(nameof(universe)); + } + + /// + /// Defines a dynamic assembly that has the specified name and access rights. + /// + /// + /// + /// + public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name, System.Reflection.Emit.AssemblyBuilderAccess access) + { + if (name is null) + throw new ArgumentNullException(nameof(name)); + return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), (AssemblyBuilderAccess)access)); + } + + /// + /// Defines a dynamic assembly that has the specified name and access rights. + /// + /// + /// + /// + public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name, System.Reflection.Emit.AssemblyBuilderAccess access, ICustomAttributeBuilder[]? assemblyAttributes) + { + if (name is null) + throw new ArgumentNullException(nameof(name)); + + return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), (AssemblyBuilderAccess)access, assemblyAttributes?.Unpack())); } /// @@ -110,7 +140,7 @@ public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) /// public IIkvmReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) { - return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); + return GetOrCreateAssemblySymbol((AssemblyBuilder)module.Assembly).GetOrCreateModuleSymbol(module); } /// @@ -133,7 +163,20 @@ public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) /// public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) { - return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); + return GetOrCreateModuleSymbol((ModuleBuilder)type.Module).GetOrCreateTypeSymbol(type); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is ConstructorInfo ctor) + return GetOrCreateConstructorSymbol(ctor); + else + return GetOrCreateMethodSymbol((MethodInfo)method); } /// @@ -156,7 +199,7 @@ public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(Constructor /// public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) { - return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); + return GetOrCreateModuleSymbol((ModuleBuilder)ctor.Module).GetOrCreateConstructorSymbol(ctor); } /// @@ -179,7 +222,7 @@ public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) /// public IIkvmReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) { - return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); + return GetOrCreateModuleSymbol((ModuleBuilder)method.Module).GetOrCreateMethodSymbol(method); } /// @@ -199,7 +242,7 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p /// public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) { - return GetOrCreateModuleSymbol(parameter.Module).GetOrCreateParameterSymbol(parameter); + return GetOrCreateModuleSymbol((ModuleBuilder)parameter.Module).GetOrCreateParameterSymbol(parameter); } /// @@ -222,7 +265,7 @@ public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) /// public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) { - return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + return GetOrCreateModuleSymbol((ModuleBuilder)field.Module).GetOrCreateFieldSymbol(field); } /// @@ -245,7 +288,7 @@ public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo prop /// public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) { - return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); + return GetOrCreateModuleSymbol((ModuleBuilder)property.Module).GetOrCreatePropertySymbol(property); } /// @@ -255,7 +298,10 @@ public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBu /// public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { - return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + if (@event is EventBuilder builder) + return GetOrCreateEventSymbol(builder); + else + return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); } /// @@ -265,7 +311,17 @@ public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) /// public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) { - return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + return GetOrCreateModuleSymbol((ModuleBuilder)@event.Module).GetOrCreateEventSymbol(@event); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return GetOrCreateModuleSymbol((ModuleBuilder)genericTypeParameter.Module).GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs deleted file mode 100644 index e3b7d7fa9a..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeImpl.cs +++ /dev/null @@ -1,587 +0,0 @@ -using System; -using System.Collections.Concurrent; -using System.Threading; - -using IKVM.Reflection; - -using Type = IKVM.Reflection.Type; - -namespace IKVM.CoreLib.Symbols.IkvmReflection -{ - - /// - /// Provides common operations against a . - /// - struct IkvmReflectionTypeImpl - { - - readonly IIkvmReflectionTypeSymbol _symbol; - - IkvmReflectionTypeSymbol?[]? _asArray; - IkvmReflectionTypeSymbol? _asSZArray; - IkvmReflectionTypeSymbol? _asPointer; - IkvmReflectionTypeSymbol? _asByRef; - ConcurrentDictionary? _genericTypeSymbols; - - /// - /// Initializes a new instance. - /// - /// - /// - public IkvmReflectionTypeImpl(IIkvmReflectionTypeSymbol symbol) - { - _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); - } - - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) - { - if (genericTypeArguments is null) - throw new ArgumentNullException(nameof(genericTypeArguments)); - - if (_symbol.UnderlyingType.IsGenericTypeDefinition == false) - throw new InvalidOperationException(); - - if (_genericTypeSymbols == null) - Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); - - var __symbol = _symbol; - return _genericTypeSymbols.GetOrAdd(genericTypeArguments, _ => new IkvmReflectionTypeSymbol(__symbol.Context, __symbol.ResolvingModule, __symbol.UnderlyingType.MakeGenericType(genericTypeArguments.Unpack()))); - } - - /// - public readonly IAssemblySymbol Assembly => _symbol.ResolveAssemblySymbol(_symbol.UnderlyingType.Assembly); - - /// - public readonly string? AssemblyQualifiedName => _symbol.UnderlyingType.AssemblyQualifiedName; - - /// - public readonly System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)_symbol.UnderlyingType.Attributes; - - /// - public readonly ITypeSymbol? BaseType => _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.BaseType); - - /// - public readonly bool ContainsGenericParameters => _symbol.UnderlyingType.ContainsGenericParameters; - - /// - public readonly IMethodBaseSymbol? DeclaringMethod => _symbol.ResolveMethodBaseSymbol(_symbol.UnderlyingType.DeclaringMethod); - - /// - public readonly string? FullName => _symbol.UnderlyingType.FullName; - - /// - public readonly string? Namespace => _symbol.UnderlyingType.Namespace; - - /// - public readonly System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)_symbol.UnderlyingType.GenericParameterAttributes; - - /// - public readonly int GenericParameterPosition => _symbol.UnderlyingType.GenericParameterPosition; - - /// - public readonly ITypeSymbol[] GenericTypeArguments => _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GenericTypeArguments); - - /// - public readonly bool HasElementType => _symbol.UnderlyingType.HasElementType; - - /// - public readonly TypeCode TypeCode => Type.GetTypeCode(_symbol.UnderlyingType); - - /// - public readonly bool IsAbstract => _symbol.UnderlyingType.IsAbstract; - - /// - public readonly bool IsSZArray => _symbol.UnderlyingType.IsSZArray; - - /// - public readonly bool IsArray => _symbol.UnderlyingType.IsArray; - - /// - public readonly bool IsAutoLayout => _symbol.UnderlyingType.IsAutoLayout; - - /// - public readonly bool IsExplicitLayout => _symbol.UnderlyingType.IsExplicitLayout; - - /// - public readonly bool IsByRef => _symbol.UnderlyingType.IsByRef; - - /// - public readonly bool IsClass => _symbol.UnderlyingType.IsClass; - - /// - public readonly bool IsEnum => _symbol.UnderlyingType.IsEnum; - - /// - public readonly bool IsInterface => _symbol.UnderlyingType.IsInterface; - - /// - public readonly bool IsConstructedGenericType => _symbol.UnderlyingType.IsConstructedGenericType; - - /// - public readonly bool IsGenericParameter => _symbol.UnderlyingType.IsGenericParameter; - - /// - public readonly bool IsGenericType => _symbol.UnderlyingType.IsGenericType; - - /// - public readonly bool IsGenericTypeDefinition => _symbol.UnderlyingType.IsGenericTypeDefinition; - - /// - public readonly bool IsLayoutSequential => _symbol.UnderlyingType.IsLayoutSequential; - - /// - public readonly bool IsNested => _symbol.UnderlyingType.IsNested; - - /// - public readonly bool IsNestedAssembly => _symbol.UnderlyingType.IsNestedAssembly; - - /// - public readonly bool IsNestedFamANDAssem => _symbol.UnderlyingType.IsNestedFamANDAssem; - - /// - public readonly bool IsNestedFamORAssem => _symbol.UnderlyingType.IsNestedFamORAssem; - - /// - public readonly bool IsNestedFamily => _symbol.UnderlyingType.IsNestedFamily; - - /// - public readonly bool IsNestedPrivate => _symbol.UnderlyingType.IsNestedPrivate; - - /// - public readonly bool IsNestedPublic => _symbol.UnderlyingType.IsNestedPublic; - - /// - public readonly bool IsNotPublic => _symbol.UnderlyingType.IsNotPublic; - - /// - public readonly bool IsPointer => _symbol.UnderlyingType.IsPointer; - - /// - public readonly bool IsFunctionPointer => _symbol.UnderlyingType.IsFunctionPointer; - - /// - public readonly bool IsUnmanagedFunctionPointer => _symbol.UnderlyingType.IsUnmanagedFunctionPointer; - - /// - public readonly bool IsPrimitive => _symbol.UnderlyingType.IsPrimitive; - - /// - public readonly bool IsPublic => _symbol.UnderlyingType.IsPublic; - - /// - public readonly bool IsSealed => _symbol.UnderlyingType.IsSealed; - - /// - public readonly bool IsSerializable => _symbol.UnderlyingType.IsSerializable; - - /// - public readonly bool IsValueType => _symbol.UnderlyingType.IsValueType; - - /// - public readonly bool IsVisible => _symbol.UnderlyingType.IsVisible; - - /// - public readonly bool IsSignatureType => throw new NotImplementedException(); - - /// - public readonly bool IsSpecialName => _symbol.UnderlyingType.IsSpecialName; - - /// - public readonly IConstructorSymbol? TypeInitializer => _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.TypeInitializer); - - /// - public readonly int GetArrayRank() - { - return _symbol.UnderlyingType.GetArrayRank(); - } - - /// - public readonly IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public readonly IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public readonly IConstructorSymbol[] GetConstructors() - { - return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors()); - } - - /// - public readonly IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetDefaultMembers() - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetDefaultMembers()); - } - - /// - public readonly ITypeSymbol? GetElementType() - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetElementType()); - } - - /// - public readonly string? GetEnumName(object value) - { - return _symbol.UnderlyingType.GetEnumName(value); - } - - /// - public readonly string[] GetEnumNames() - { - return _symbol.UnderlyingType.GetEnumNames(); - } - - /// - public readonly ITypeSymbol GetEnumUnderlyingType() - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public readonly Array GetEnumValues() - { - return _symbol.UnderlyingType.GetEnumValues(); - } - - /// - public readonly IEventSymbol? GetEvent(string name) - { - return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name)); - } - - /// - public readonly IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); - } - - /// - public readonly IEventSymbol[] GetEvents() - { - return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents()); - } - - /// - public readonly IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents((BindingFlags)bindingAttr)); - } - - /// - public readonly IFieldSymbol? GetField(string name) - { - return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name)); - } - - /// - public readonly IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); - } - - /// - public readonly IFieldSymbol[] GetFields() - { - return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields()); - } - - /// - public readonly IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields((BindingFlags)bindingAttr)); - } - - /// - public readonly ITypeSymbol[] GetGenericArguments() - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericArguments()); - } - - /// - public readonly ITypeSymbol[] GetGenericParameterConstraints() - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public readonly ITypeSymbol GetGenericTypeDefinition() - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public readonly ITypeSymbol? GetInterface(string name) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name)); - } - - /// - public readonly ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public readonly InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - throw new NotImplementedException(); - } - - /// - public readonly ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public readonly IMemberSymbol[] GetMember(string name) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name)); - } - - /// - public readonly IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers((BindingFlags)bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetMembers() - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers()); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, types.Unpack())); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public readonly IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods((BindingFlags)bindingAttr)); - } - - /// - public readonly IMethodSymbol[] GetMethods() - { - return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods()); - } - - /// - public readonly ITypeSymbol? GetNestedType(string name) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name)); - } - - /// - public readonly ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); - } - - /// - public readonly ITypeSymbol[] GetNestedTypes() - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes()); - } - - /// - public readonly ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public readonly IPropertySymbol[] GetProperties() - { - return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties()); - } - - /// - public readonly IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); - } - - /// - public readonly IPropertySymbol? GetProperty(string name) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name)); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public readonly bool IsAssignableFrom(ITypeSymbol? c) - { - return _symbol.UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public readonly bool IsEnumDefined(object value) - { - return _symbol.UnderlyingType.IsEnumDefined(value); - } - - /// - public readonly bool IsSubclassOf(ITypeSymbol c) - { - return _symbol.UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public IIkvmReflectionTypeSymbol MakeArrayType() - { - if (_asSZArray == null) - Interlocked.CompareExchange(ref _asSZArray, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType()), null); - - return _asSZArray; - } - - /// - public IIkvmReflectionTypeSymbol MakeArrayType(int rank) - { - if (rank == 1) - return MakeArrayType(); - - if (_asArray == null) - Interlocked.CompareExchange(ref _asArray, new IkvmReflectionTypeSymbol?[32], null); - - ref var asArray = ref _asArray[rank]; - if (asArray == null) - Interlocked.CompareExchange(ref asArray, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType(rank)), null); - - return asArray; - } - - /// - public IIkvmReflectionTypeSymbol MakeByRefType() - { - if (_asByRef == null) - Interlocked.CompareExchange(ref _asByRef, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeByRefType()), null); - - return _asByRef; - } - - /// - public IIkvmReflectionTypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return GetOrCreateGenericTypeSymbol(typeArguments); - } - - /// - public IIkvmReflectionTypeSymbol MakePointerType() - { - if (_asPointer == null) - Interlocked.CompareExchange(ref _asPointer, new IkvmReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakePointerType()), null); - - return _asPointer; - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs new file mode 100644 index 0000000000..4a3de6e085 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs @@ -0,0 +1,129 @@ +using System; +using System.Collections.Concurrent; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Threading; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionTypeSpecTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol _elementType; + + IndexRangeDictionary _asArray; + ReaderWriterLockSlim? _asArrayLock; + IIkvmReflectionTypeSymbol? _asSZArray; + IIkvmReflectionTypeSymbol? _asPointer; + IIkvmReflectionTypeSymbol? _asByRef; + ConcurrentDictionary? _genericTypeSymbols; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionTypeSpecTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol elementType) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); + _asArray = new IndexRangeDictionary(); + } + + /// + /// Gets or creates a representing an Array of this type. + /// + /// + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + if (_asArrayLock == null) + Interlocked.CompareExchange(ref _asArrayLock, new(), null); + + using (_asArrayLock.CreateUpgradeableReadLock()) + { + if (_asArray[rank] == null) + using (_asArrayLock.CreateWriteLock()) + _asArray[rank] = new IkvmReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeArrayType(rank)); + + return _asArray[rank] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates a representing a SZArray of this type. + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + if (_asSZArray == null) + Interlocked.CompareExchange(ref _asSZArray, new IkvmReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeArrayType()), null); + + return _asSZArray; + } + + /// + /// Gets or creates a representing a pointer of this type. + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + if (_asPointer == null) + Interlocked.CompareExchange(ref _asPointer, new IkvmReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakePointerType()), null); + + return _asPointer; + } + + /// + /// Gets or creates a representing a by-ref of this type. + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + if (_asByRef == null) + Interlocked.CompareExchange(ref _asByRef, new IkvmReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakePointerType()), null); + + return _asByRef; + } + + /// + /// Gets or creates a representing a specialized generic of this type. + /// + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArguments) + { + if (genericTypeArguments is null) + throw new ArgumentNullException(nameof(genericTypeArguments)); + + if (_elementType.IsGenericTypeDefinition == false) + throw new InvalidOperationException(); + + if (_genericTypeSymbols == null) + Interlocked.CompareExchange(ref _genericTypeSymbols, new(TypeSymbolListEqualityComparer.Instance), null); + + return _genericTypeSymbols.GetOrAdd(_module.ResolveTypeSymbols(genericTypeArguments), CreateGenericTypeSymbol); + } + + /// + /// Creates a new representing a specialized generic of this type. + /// + /// + /// + readonly IIkvmReflectionTypeSymbol CreateGenericTypeSymbol(IIkvmReflectionTypeSymbol[] genericTypeArguments) + { + return new IkvmReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeGenericType(genericTypeArguments.Unpack())); + } + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index 99ef2c73c4..cad0ca9129 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -1,6 +1,8 @@ using System; using System.Diagnostics.CodeAnalysis; +using IKVM.Reflection; + using Type = IKVM.Reflection.Type; namespace IKVM.CoreLib.Symbols.IkvmReflection @@ -10,7 +12,13 @@ class IkvmReflectionTypeSymbol : IkvmReflectionMemberSymbol, IIkvmReflectionType { readonly Type _type; - IkvmReflectionTypeImpl _impl; + + IkvmReflectionMethodTable _methodTable; + IkvmReflectionFieldTable _fieldTable; + IkvmReflectionPropertyTable _propertyTable; + IkvmReflectionEventTable _eventTable; + IkvmReflectionGenericTypeParameterTable _genericTypeParameterTable; + IkvmReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. @@ -22,7 +30,12 @@ public IkvmReflectionTypeSymbol(IkvmReflectionSymbolContext context, IIkvmReflec base(context, resolvingModule, null) { _type = type ?? throw new ArgumentNullException(nameof(type)); - _impl = new IkvmReflectionTypeImpl(this); + _methodTable = new IkvmReflectionMethodTable(context, resolvingModule, this); + _fieldTable = new IkvmReflectionFieldTable(context, resolvingModule, this); + _propertyTable = new IkvmReflectionPropertyTable(context, resolvingModule, this); + _eventTable = new IkvmReflectionEventTable(context, resolvingModule, this); + _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, resolvingModule, this); + _specTable = new IkvmReflectionTypeSpecTable(context, resolvingModule, this); } /// @@ -31,11 +44,85 @@ public IkvmReflectionTypeSymbol(IkvmReflectionSymbolContext context, IIkvmReflec /// public override IKVM.Reflection.MemberInfo UnderlyingMember => UnderlyingType; - /// - /// Resolves the symbol for the specified type. - /// - /// - /// + #region IIkvmReflectionTypeSymbol + + /// + public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + return _methodTable.GetOrCreateMethodBaseSymbol(method); + } + + /// + public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + + /// + public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericType) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericType); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion + + #region IIkvmReflectionSymbol + + /// [return: NotNullIfNotNull(nameof(type))] public override IIkvmReflectionTypeSymbol? ResolveTypeSymbol(Type? type) { @@ -45,506 +132,518 @@ public IkvmReflectionTypeSymbol(IkvmReflectionSymbolContext context, IIkvmReflec return base.ResolveTypeSymbol(type); } + #endregion + #region ITypeSymbol /// - public System.Reflection.TypeAttributes Attributes => _impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public IAssemblySymbol Assembly => _impl.Assembly; + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? FullName => _impl.FullName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? Namespace => _impl.Namespace; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public TypeCode TypeCode => _impl.TypeCode; + public string? FullName => UnderlyingType.FullName; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public string? Namespace => UnderlyingType.Namespace; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public bool HasElementType => UnderlyingType.HasElementType; /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsSZArray => UnderlyingType.IsSZArray; /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool HasElementType => _impl.HasElementType; + public bool IsClass => UnderlyingType.IsClass; /// - public bool IsClass => _impl.IsClass; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsValueType => _impl.IsValueType; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsInterface => _impl.IsInterface; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsArray => _impl.IsArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsEnum => _impl.IsEnum; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsPointer => UnderlyingType.IsPointer; /// - public bool IsNested => _impl.IsNested; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsSignatureType => throw new NotImplementedException(); /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// public int GetArrayRank() { - return _impl.GetArrayRank(); + return UnderlyingType.GetArrayRank(); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetElementType(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors() { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string[] GetEnumNames() + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumNames(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public ITypeSymbol GetEnumUnderlyingType() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumUnderlyingType(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol[] GetGenericArguments() + public ITypeSymbol? GetElementType() { - return _impl.GetGenericArguments(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string? GetEnumName(object value) { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol GetGenericTypeDefinition() + public string[] GetEnumNames() { - return _impl.GetGenericTypeDefinition(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol? GetInterface(string name) + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetInterface(name); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public Array GetEnumValues() { - return _impl.GetInterface(name, ignoreCase); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents() { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, bindingAttr); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetConstructor(types); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructors(); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name, bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol[] GetFields() + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return _impl.GetFields(); + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); } /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(bindingAttr); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, types); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name, bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties() { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public bool IsAssignableFrom(ITypeSymbol? c) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.IsAssignableFrom(c); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// public bool IsEnumDefined(object value) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsEnumDefined(value); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); } /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + public ITypeSymbol MakeByRefType() { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); } /// - public ITypeSymbol MakeByRefType() + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs new file mode 100644 index 0000000000..d089438c75 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs @@ -0,0 +1,76 @@ +using System; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; +using IKVM.CoreLib.Threading; +using IKVM.Reflection.Emit; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.CoreLib.Symbols.IkvmReflection +{ + + struct IkvmReflectionTypeTable + { + + readonly IkvmReflectionSymbolContext _context; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol? _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public IkvmReflectionTypeTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + if (type.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(type)); + if (type.IsGenericParameter) + throw new ArgumentException(nameof(type)); + if (type.IsTypeDefinition() == false) + throw new ArgumentException(nameof(type)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = MetadataTokens.GetRowNumber(MetadataTokens.TypeDefinitionHandle(type.MetadataToken)); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + if (_table[row] == null) + if (type is TypeBuilder builder) + return _table[row] = new IkvmReflectionTypeSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, builder); + else + return _table[row] = new IkvmReflectionTypeSymbol(_context, _module, type); + + return _table[row] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs index 0aa5322ab7..5dbe9d7948 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -1,6 +1,9 @@ using System; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.IkvmReflection.Emit; using IKVM.Reflection; +using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; @@ -18,7 +21,7 @@ static class IkvmReflectionUtil /// /// /// - public static System.Reflection.AssemblyName ToAssemblyName(this AssemblyName n) + public static System.Reflection.AssemblyName Pack(this AssemblyName n) { return new System.Reflection.AssemblyName() { @@ -42,14 +45,58 @@ public static System.Reflection.AssemblyName ToAssemblyName(this AssemblyName n) /// /// /// - public static System.Reflection.AssemblyName[] ToAssemblyNames(this AssemblyName[] n) + public static System.Reflection.AssemblyName[] Pack(this AssemblyName[] n) { if (n.Length == 0) return []; var a = new System.Reflection.AssemblyName[n.Length]; for (int i = 0; i < n.Length; i++) - a[i] = n[i].ToAssemblyName(); + a[i] = n[i].Pack(); + + return a; + } + +#pragma warning disable SYSLIB0017 // Type or member is obsolete +#pragma warning disable SYSLIB0037 // Type or member is obsolete + + /// + /// Converts a to a . + /// + /// + /// + public static AssemblyName Unpack(this System.Reflection.AssemblyName n) + { + return new AssemblyName() + { + Name = n.Name, + Version = n.Version, + CultureInfo = n.CultureInfo, + CultureName = n.CultureName, + ProcessorArchitecture = (ProcessorArchitecture)n.ProcessorArchitecture, + Flags = (AssemblyNameFlags)n.Flags, + HashAlgorithm = (AssemblyHashAlgorithm)n.HashAlgorithm, + ContentType = (AssemblyContentType)n.ContentType, + VersionCompatibility = (AssemblyVersionCompatibility)n.VersionCompatibility, + }; + } + +#pragma warning restore SYSLIB0037 // Type or member is obsolete +#pragma warning restore SYSLIB0017 // Type or member is obsolete + + /// + /// Converts a set of to a set of . + /// + /// + /// + public static AssemblyName[] Unpack(this System.Reflection.AssemblyName[] n) + { + if (n.Length == 0) + return []; + + var a = new AssemblyName[n.Length]; + for (int i = 0; i < n.Length; i++) + a[i] = n[i].Unpack(); return a; } @@ -310,6 +357,93 @@ public static ParameterModifier[] Unpack(this System.Reflection.ParameterModifie return a; } + /// + /// Unpacks the . + /// + /// + /// + public static LocalBuilder Unpack(this ILocalBuilder builder) + { + return ((IkvmReflectionLocalBuilder)builder).UnderlyingLocalBuilder; + } + + /// + /// Unpacks the . + /// + /// + /// + public static Label Unpack(this ILabel label) + { + return ((IkvmReflectionLabel)label).UnderlyingLabel; + } + + /// + /// Unpacks the s. + /// + /// + /// + public static Label[] Unpack(this ILabel[] labels) + { + var a = new Label[labels.Length]; + for (int i = 0; i < labels.Length; i++) + a[i] = labels[i].Unpack(); + + return a; + } + + /// + /// Unpacks the . + /// + /// + /// + public static CustomAttributeBuilder Unpack(this ICustomAttributeBuilder customAttributes) + { + return ((IkvmReflectionCustomAttributeBuilder)customAttributes).UnderlyingBuilder; + } + + /// + /// Unpacks the s. + /// + /// + /// + public static CustomAttributeBuilder[] Unpack(this ICustomAttributeBuilder[] customAttributes) + { + if (customAttributes.Length == 0) + return []; + + var a = new CustomAttributeBuilder[customAttributes.Length]; + for (int i = 0; i < customAttributes.Length; i++) + a[i] = customAttributes[i].Unpack(); + + return a; + } + + /// + /// Returns true if the given type represents a type definition. + /// + /// + /// + public static bool IsTypeDefinition(this Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + + return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; + } + + /// + /// Returns true if the given method represents a method definition. + /// + /// + /// + public static bool IsMethodDefinition(this MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + return method.IsGenericMethod == false || (method.IsGenericMethod && method.IsGenericMethodDefinition == true); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs b/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs index e2208e0e02..ebc5c438ce 100644 --- a/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs +++ b/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs @@ -3,13 +3,13 @@ namespace IKVM.CoreLib.Symbols { - readonly struct InterfaceMapping + readonly struct InterfaceMapping(IMethodSymbol[] InterfaceMethods, ITypeSymbol InterfaceType, IMethodSymbol[] TargetMethods, ITypeSymbol TargetType) { - public readonly ImmutableArray InterfaceMethods; - public readonly ITypeSymbol InterfaceType; - public readonly ImmutableArray TargetMethods; - public readonly ITypeSymbol TargetType; + public readonly IMethodSymbol[] InterfaceMethods = InterfaceMethods; + public readonly ITypeSymbol InterfaceType = InterfaceType; + public readonly IMethodSymbol[] TargetMethods = TargetMethods; + public readonly ITypeSymbol TargetType = TargetType; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index e9692b2c95..1dcb3c58d7 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -13,6 +13,8 @@ class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IR ConstructorBuilder? _builder; ConstructorInfo _ctor; + ReflectionILGenerator? _il; + /// /// Initializes a new instance. /// @@ -54,13 +56,13 @@ public IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttribute /// public IILGenerator GetILGenerator() { - throw new NotImplementedException(); + return _il ??= new ReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator()); } /// public IILGenerator GetILGenerator(int streamSize) { - throw new NotImplementedException(); + return _il ??= new ReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator(streamSize)); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs new file mode 100644 index 0000000000..ee009451eb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs @@ -0,0 +1,265 @@ +using System; +using System.Diagnostics.SymbolStore; +using System.Reflection; +using System.Reflection.Emit; +using System.Runtime.InteropServices; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionILGenerator : IILGenerator + { + + readonly ReflectionSymbolContext _context; + readonly ILGenerator _il; + + /// + /// Initializes a new instance. + /// + /// + public ReflectionILGenerator(ReflectionSymbolContext context, ILGenerator il) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _il = il ?? throw new ArgumentNullException(nameof(il)); + } + + /// + public int ILOffset => _il.ILOffset; + + /// + public void BeginCatchBlock(ITypeSymbol? exceptionType) + { + _il.BeginCatchBlock(exceptionType?.Unpack()!); + + } + + /// + public void BeginExceptFilterBlock() + { + _il.BeginExceptFilterBlock(); + } + + /// + public ILabel BeginExceptionBlock() + { + return new ReflectionLabel(_il.BeginExceptionBlock()); + } + + /// + public void BeginFaultBlock() + { + _il.BeginFaultBlock(); + } + + /// + public void BeginFinallyBlock() + { + _il.BeginFinallyBlock(); + } + + /// + public void BeginScope() + { + _il.BeginScope(); + } + + /// + public ILocalBuilder DeclareLocal(ITypeSymbol localType, bool pinned) + { + return new ReflectionLocalBuilder(_context, _il.DeclareLocal(localType.Unpack(), pinned)); + } + + /// + public ILocalBuilder DeclareLocal(ITypeSymbol localType) + { + return new ReflectionLocalBuilder(_context, _il.DeclareLocal(localType.Unpack())); + } + + /// + public ILabel DefineLabel() + { + return new ReflectionLabel(_il.DefineLabel()); + } + + /// + public void Emit(OpCode opcode, ILocalBuilder local) + { + _il.Emit(opcode, local.Unpack()); + } + + /// + public void Emit(OpCode opcode, ITypeSymbol cls) + { + _il.Emit(opcode, cls.Unpack()); + } + + /// + public void Emit(OpCode opcode, string str) + { + _il.Emit(opcode, str); + } + + /// + public void Emit(OpCode opcode, float arg) + { + _il.Emit(opcode, arg); + } + + /// + public void Emit(OpCode opcode, sbyte arg) + { + _il.Emit(opcode, arg); + } + + /// + public void Emit(OpCode opcode, IMethodSymbol meth) + { + _il.Emit(opcode, meth.Unpack()); + } + + /// + public void Emit(OpCode opcode, ISignatureHelper signature) + { + throw new NotImplementedException(); + //_il.Emit(opcode, signature.Unpack()); + } + + /// + public void Emit(OpCode opcode, ILabel[] labels) + { + _il.Emit(opcode, labels.Unpack()); + } + + /// + public void Emit(OpCode opcode, IFieldSymbol field) + { + _il.Emit(opcode, field.Unpack()); + } + + /// + public void Emit(OpCode opcode, IConstructorSymbol con) + { + _il.Emit(opcode, con.Unpack()); + } + + /// + public void Emit(OpCode opcode, long arg) + { + _il.Emit(opcode, arg); + } + + /// + public void Emit(OpCode opcode, int arg) + { + _il.Emit(opcode, arg); + } + + /// + public void Emit(OpCode opcode, short arg) + { + _il.Emit(opcode, arg); + } + + /// + public void Emit(OpCode opcode, double arg) + { + _il.Emit(opcode, arg); + } + + /// + public void Emit(OpCode opcode, byte arg) + { + _il.Emit(opcode, arg); + } + + /// + public void Emit(OpCode opcode) + { + _il.Emit(opcode); + } + + /// + public void Emit(OpCode opcode, ILabel label) + { + _il.Emit(opcode, label.Unpack()); + } + + /// + public void EmitCall(OpCode opcode, IMethodSymbol methodInfo, ITypeSymbol[]? optionalParameterTypes) + { + _il.EmitCall(opcode, methodInfo.Unpack(), optionalParameterTypes?.Unpack()); + } + + /// + public void EmitCalli(OpCode opcode, CallingConvention unmanagedCallConv, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + { + _il.EmitCalli(opcode, unmanagedCallConv, returnType?.Unpack(), parameterTypes?.Unpack()); + } + + /// + public void EmitCalli(OpCode opcode, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, ITypeSymbol[]? optionalParameterTypes) + { + _il.EmitCalli(opcode, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), optionalParameterTypes?.Unpack()); + } + + /// + public void EmitWriteLine(string value) + { + _il.EmitWriteLine(value); + } + + /// + public void EmitWriteLine(IFieldSymbol fld) + { + _il.EmitWriteLine(fld.Unpack()); + } + + /// + public void EmitWriteLine(ILocalBuilder localBuilder) + { + _il.EmitWriteLine(localBuilder.Unpack()); + } + + /// + public void EndExceptionBlock() + { + _il.EndExceptionBlock(); + } + + /// + public void EndScope() + { + _il.EndScope(); + } + + /// + public void MarkLabel(ILabel loc) + { + _il.MarkLabel(loc.Unpack()); + } + + /// + public void MarkSequencePoint(ISymbolDocumentWriter document, int startLine, int startColumn, int endLine, int endColumn) + { +#if NETFRAMEWORK + _il.MarkSequencePoint(document, startLine, startColumn, endLine, endColumn); +#endif + } + + /// + public void ThrowException(ITypeSymbol excType) + { + _il.ThrowException(excType.Unpack()); + } + + /// + public void UsingNamespace(string usingNamespace) + { + _il.UsingNamespace(usingNamespace); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLabel.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLabel.cs new file mode 100644 index 0000000000..df05eb7edc --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLabel.cs @@ -0,0 +1,29 @@ +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionLabel : ILabel + { + + readonly Label _label; + + /// + /// Initializes a new instance. + /// + /// + public ReflectionLabel(Label label) + { + _label = label; + } + + /// + /// Gets the underlying . + /// + public Label UnderlyingLabel => _label; + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLocalBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLocalBuilder.cs new file mode 100644 index 0000000000..136ce59cf1 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLocalBuilder.cs @@ -0,0 +1,59 @@ +using System; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + class ReflectionLocalBuilder : ILocalBuilder + { + + readonly ReflectionSymbolContext _context; + readonly LocalBuilder _builder; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionLocalBuilder(ReflectionSymbolContext context, LocalBuilder builder) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + } + + /// + /// Gets the underlying . + /// + public LocalBuilder UnderlyingLocalBuilder => _builder; + + /// + public bool IsPinned => _builder.IsPinned; + + /// + public int LocalIndex => _builder.LocalIndex; + + /// + public ITypeSymbol LocalType => _context.GetOrCreateTypeSymbol(_builder.LocalType); + + /// + public void SetLocalSymInfo(string name) + { +#if NETFRAMEWORK + _builder.SetLocalSymInfo(name); +#endif + } + + /// + public void SetLocalSymInfo(string name, int startOffset, int endOffset) + { +#if NETFRAMEWORK + _builder.SetLocalSymInfo(name, startOffset, endOffset); +#endif + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index e0c2fb3e86..7fba722c59 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -13,6 +13,8 @@ class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflec MethodBuilder? _builder; MethodInfo _method; + ReflectionILGenerator? _il; + /// /// Initializes a new instance. /// @@ -68,7 +70,7 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin var l = UnderlyingMethodBuilder.DefineGenericParameters(names); var a = new IGenericTypeParameterSymbolBuilder[l.Length]; for (int i = 0; i < l.Length; i++) - a[i] = new ReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, ResolvingType, this, l[i]); + a[i] = (IGenericTypeParameterSymbolBuilder)ResolveTypeSymbol(l[i]); return a; } @@ -76,17 +78,19 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin /// public IParameterSymbolBuilder DefineParameter(int position, ParameterAttributes attributes, string? strParamName) { - return new ReflectionParameterSymbolBuilder(Context, ResolvingModule, this, UnderlyingMethodBuilder.DefineParameter(position, attributes, strParamName)); + return ResolveParameterSymbol(UnderlyingMethodBuilder.DefineParameter(position, attributes, strParamName)); } + /// public IILGenerator GetILGenerator() { - throw new NotImplementedException(); + return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator()); } - public IILGenerator GetILGenerator(int size) + /// + public IILGenerator GetILGenerator(int streamSize) { - throw new NotImplementedException(); + return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index 3a64b5df35..e5e3387557 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -1,4 +1,5 @@ using System; +using System.Diagnostics.SymbolStore; using System.Linq; using System.Reflection; using System.Reflection.Emit; @@ -42,6 +43,16 @@ public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, IReflectio #region IModuleSymbolBuilder + /// + public ISymbolDocumentWriter? DefineDocument(string url, Guid language, Guid languageVendor, Guid documentType) + { +#if NETFRAMEWORK + return UnderlyingModuleBuilder.DefineDocument(url, language, languageVendor, documentType); +#else + return null; +#endif + } + /// public ITypeSymbolBuilder DefineType(string name) { @@ -96,7 +107,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) UnderlyingModuleBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } - #endregion +#endregion #region IModuleSymbol diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 27eb448524..51a6db7e63 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -130,7 +130,7 @@ public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attribute } /// - public void DefineMethodOverride(IMethodSymbolBuilder methodInfoBody, IMethodSymbol methodInfoDeclaration) + public void DefineMethodOverride(IMethodSymbol methodInfoBody, IMethodSymbol methodInfoDeclaration) { UnderlyingTypeBuilder.DefineMethodOverride(methodInfoBody.Unpack(), methodInfoDeclaration.Unpack()); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs index 7db22745b1..1ee1657d8b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs @@ -330,6 +330,13 @@ interface IReflectionSymbol : ISymbol /// CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg); + /// + /// Transforms a into a symbol type. + /// + /// + /// + InterfaceMapping ResolveInterfaceMapping(System.Reflection.InterfaceMapping arg); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs index 7ba66dc3ed..c63ae51455 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs @@ -17,7 +17,7 @@ struct ReflectionAssemblyMetadata readonly IReflectionAssemblySymbol _symbol; - IndexRangeDictionary _moduleSymbols = new(initialCapacity: 1, maxCapacity: 32); + IndexRangeDictionary _moduleSymbols = new(maxCapacity: 32); ReaderWriterLockSlim? _moduleLock; /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index bd247f2e7f..60a8b9f32e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -14,8 +14,6 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionModuleSymbol : ReflectionSymbol, IReflectionModuleSymbol { - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; - readonly IReflectionAssemblySymbol _resolvingAssembly; readonly Module _module; ReflectionModuleMetadata _impl; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index bf9c87d3e4..9c719dd28d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -428,11 +428,7 @@ public virtual IReflectionParameterSymbolBuilder ResolveParameterSymbol(Paramete return a; } - /// - /// Transforms a custom set of custom attribute data records to a symbol record. - /// - /// - /// + /// public virtual IEnumerable ResolveCustomAttributes(IEnumerable attributes) { if (attributes is null) @@ -446,11 +442,7 @@ public virtual IEnumerable ResolveCustomAttributes(IEnumerable< return a.ToArray(); } - /// - /// Transforms a custom attribute data record to a symbol record. - /// - /// - /// + /// [return: NotNullIfNotNull(nameof(customAttributeData))] public virtual CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) { @@ -464,11 +456,7 @@ public virtual IEnumerable ResolveCustomAttributes(IEnumerable< ResolveCustomAttributeNamedArguments(customAttributeData.NamedArguments)); } - /// - /// Transforms a list of values into symbols. - /// - /// - /// + /// public ImmutableArray ResolveCustomAttributeTypedArguments(IList args) { if (args is null) @@ -483,11 +471,7 @@ public ImmutableArray ResolveCustomAttributeTypedA return a.ToImmutableArray(); } - /// - /// Transforms a values into a symbol. - /// - /// - /// + /// public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg) { return new CustomAttributeTypedArgument( @@ -495,11 +479,7 @@ public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.R ResolveCustomAttributeTypedValue(arg.Value)); } - /// - /// Transforms the type as appropriate. - /// - /// - /// + /// public object? ResolveCustomAttributeTypedValue(object? value) { return value switch @@ -509,11 +489,7 @@ public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.R }; } - /// - /// Transforms a list of values into symbols. - /// - /// - /// + /// public ImmutableArray ResolveCustomAttributeNamedArguments(IList args) { if (args is null) @@ -528,11 +504,7 @@ public ImmutableArray ResolveCustomAttributeNamedA return ImmutableArray.Create(a); } - /// - /// Transforms a values into a symbol. - /// - /// - /// + /// public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg) { return new CustomAttributeNamedArgument( @@ -542,6 +514,16 @@ public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.R ResolveCustomAttributeTypedArgument(arg.TypedValue)); } + /// + public InterfaceMapping ResolveInterfaceMapping(System.Reflection.InterfaceMapping mapping) + { + return new InterfaceMapping( + ResolveMethodSymbols(mapping.InterfaceMethods), + ResolveTypeSymbol(mapping.InterfaceType), + ResolveMethodSymbols(mapping.TargetMethods), + ResolveTypeSymbol(mapping.TargetType)); + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index cbd65e7c93..cb05d82fa3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -28,6 +28,34 @@ public ReflectionSymbolContext() } + /// + /// Defines a dynamic assembly that has the specified name and access rights. + /// + /// + /// + /// + public IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access) + { + if (name is null) + throw new ArgumentNullException(nameof(name)); + + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, access)); + } + + /// + /// Defines a dynamic assembly that has the specified name and access rights. + /// + /// + /// + /// + public IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access, ICustomAttributeBuilder[]? assemblyAttributes) + { + if (name is null) + throw new ArgumentNullException(nameof(name)); + + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, access, assemblyAttributes?.Unpack())); + } + /// /// Gets or creates a indexed based on the assembly's name. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs index e08a8a2c95..c7821414cf 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs @@ -375,7 +375,7 @@ public readonly ITypeSymbol GetGenericTypeDefinition() /// public readonly InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - throw new NotImplementedException(); + return _symbol.ResolveInterfaceMapping(_symbol.UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index fd823ad8ef..10f77d1848 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -1,5 +1,9 @@ using System; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -27,6 +31,9 @@ public static Module Unpack(this IModuleSymbol module) /// public static Module[] Unpack(this IModuleSymbol[] modules) { + if (modules.Length == 0) + return []; + var a = new Module[modules.Length]; for (int i = 0; i < modules.Length; i++) a[i] = modules[i].Unpack(); @@ -54,6 +61,9 @@ public static Type Unpack(this ITypeSymbol type) /// public static Type[] Unpack(this ITypeSymbol[] types) { + if (types.Length == 0) + return []; + var a = new Type[types.Length]; for (int i = 0; i < types.Length; i++) a[i] = types[i].Unpack(); @@ -68,6 +78,9 @@ public static Type[] Unpack(this ITypeSymbol[] types) /// public static Type[][] Unpack(this ITypeSymbol[][] types) { + if (types.Length == 0) + return []; + var a = new Type[types.Length][]; for (int i = 0; i < types.Length; i++) a[i] = types[i].Unpack(); @@ -95,6 +108,9 @@ public static MemberInfo Unpack(this IMemberSymbol member) /// public static MemberInfo[] Unpack(this IMemberSymbol[] members) { + if (members.Length == 0) + return []; + var a = new MemberInfo[members.Length]; for (int i = 0; i < members.Length; i++) a[i] = members[i].Unpack(); @@ -122,6 +138,9 @@ public static ConstructorInfo Unpack(this IConstructorSymbol ctor) /// public static ConstructorInfo[] Unpack(this IConstructorSymbol[] ctor) { + if (ctor.Length == 0) + return []; + var a = new ConstructorInfo[ctor.Length]; for (int i = 0; i < ctor.Length; i++) a[i] = ctor[i].Unpack(); @@ -149,6 +168,9 @@ public static MethodInfo Unpack(this IMethodSymbol ctor) /// public static MethodInfo[] Unpack(this IMethodSymbol[] ctor) { + if (ctor.Length == 0) + return []; + var a = new MethodInfo[ctor.Length]; for (int i = 0; i < ctor.Length; i++) a[i] = ctor[i].Unpack(); @@ -176,6 +198,9 @@ public static FieldInfo Unpack(this IFieldSymbol field) /// public static FieldInfo[] Unpack(this IFieldSymbol[] fields) { + if (fields.Length == 0) + return []; + var a = new FieldInfo[fields.Length]; for (int i = 0; i < fields.Length; i++) a[i] = fields[i].Unpack(); @@ -203,6 +228,9 @@ public static PropertyInfo Unpack(this IPropertySymbol property) /// public static PropertyInfo[] Unpack(this IPropertySymbol[] properties) { + if (properties.Length == 0) + return []; + var a = new PropertyInfo[properties.Length]; for (int i = 0; i < properties.Length; i++) a[i] = properties[i].Unpack(); @@ -210,6 +238,67 @@ public static PropertyInfo[] Unpack(this IPropertySymbol[] properties) return a; } + /// + /// Unpacks the . + /// + /// + /// + public static LocalBuilder Unpack(this ILocalBuilder builder) + { + return ((ReflectionLocalBuilder)builder).UnderlyingLocalBuilder; + } + + /// + /// Unpacks the . + /// + /// + /// + public static Label Unpack(this ILabel label) + { + return ((ReflectionLabel)label).UnderlyingLabel; + } + + /// + /// Unpacks the s. + /// + /// + /// + public static Label[] Unpack(this ILabel[] labels) + { + var a = new Label[labels.Length]; + for (int i = 0; i < labels.Length; i++) + a[i] = labels[i].Unpack(); + + return a; + } + + /// + /// Unpacks the . + /// + /// + /// + public static CustomAttributeBuilder Unpack(this ICustomAttributeBuilder customAttributes) + { + return ((ReflectionCustomAttributeBuilder)customAttributes).UnderlyingBuilder; + } + + /// + /// Unpacks the s. + /// + /// + /// + public static CustomAttributeBuilder[] Unpack(this ICustomAttributeBuilder[] customAttributes) + { + if (customAttributes.Length == 0) + return []; + + var a = new CustomAttributeBuilder[customAttributes.Length]; + for (int i = 0; i < customAttributes.Length; i++) + a[i] = customAttributes[i].Unpack(); + + return a; + } + } } diff --git a/src/IKVM.Reflection/Emit/ILGenerator.cs b/src/IKVM.Reflection/Emit/ILGenerator.cs index 146241b4bb..5731f7edde 100644 --- a/src/IKVM.Reflection/Emit/ILGenerator.cs +++ b/src/IKVM.Reflection/Emit/ILGenerator.cs @@ -9,6 +9,7 @@ using System; using System.Buffers.Binary; using System.Diagnostics; +using System.Diagnostics.CodeAnalysis; using System.Diagnostics.Contracts; using System.Diagnostics.SymbolStore; using System.Runtime.CompilerServices; @@ -940,6 +941,24 @@ public void Emit(OpCode opcode, LocalBuilder local) #endregion #region Exceptions + + public virtual void ThrowException(Type excType) + { + if (excType is null) + throw new ArgumentNullException(nameof(excType)); + + // TODO figure out how to load type here + //if (!excType.IsSubclassOf( typeof(Exception)) && excType != typeof(Exception)) + //throw new ArgumentException(nameof(excType)); + + var con = excType.GetConstructor(Type.EmptyTypes); + if (con == null) + throw new ArgumentException(nameof(excType)); + + Emit(OpCodes.Newobj, con); + Emit(OpCodes.Throw); + } + public Label BeginExceptionBlock() { // Begin an Exception block. Creating an Exception block records some information, diff --git a/src/IKVM.Reflection/MemberInfo.cs b/src/IKVM.Reflection/MemberInfo.cs index 83a45531fd..2ac8d83e64 100644 --- a/src/IKVM.Reflection/MemberInfo.cs +++ b/src/IKVM.Reflection/MemberInfo.cs @@ -43,7 +43,9 @@ internal MemberInfo() } public abstract string Name { get; } + public abstract Type DeclaringType { get; } + public abstract MemberTypes MemberType { get; } public virtual Type ReflectedType diff --git a/src/IKVM.Reflection/Type.cs b/src/IKVM.Reflection/Type.cs index 38bea7747b..5eecf0c1ea 100644 --- a/src/IKVM.Reflection/Type.cs +++ b/src/IKVM.Reflection/Type.cs @@ -162,7 +162,7 @@ public virtual EventInfo[] __GetDeclaredEvents() { return Array.Empty(); } - + public virtual PropertyInfo[] __GetDeclaredProperties() { return Array.Empty(); diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index cf883ce9ae..4979b00172 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -1020,7 +1020,7 @@ internal RemappedInterfaceMethodAttribute[] GetRemappedInterfaceMethods(ITypeSym internal RemappedTypeAttribute GetRemappedType(ITypeSymbol type) { foreach (var cad in type.GetCustomAttributes(TypeOfRemappedTypeAttribute)) - return new RemappedTypeAttribute((Type)cad.ConstructorArguments[0].Value); + return new RemappedTypeAttribute(((ITypeSymbol)cad.ConstructorArguments[0].Value).AsReflection()); return null; } @@ -1032,7 +1032,7 @@ internal RemappedClassAttribute[] GetRemappedClasses(IAssemblySymbol coreAssembl foreach (var cad in coreAssembly.GetCustomAttributes(TypeOfRemappedClassAttribute)) { var args = cad.ConstructorArguments; - attrs.Add(new RemappedClassAttribute((string)args[0].Value, (Type)args[1].Value)); + attrs.Add(new RemappedClassAttribute((string)args[0].Value, ((ITypeSymbol)args[1].Value).AsReflection())); } return attrs.ToArray(); diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index cf4cb20cb2..b32b34ba9c 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -23,20 +23,16 @@ Jeroen Frijters */ using System; using System.Collections.Generic; -using System.Runtime.InteropServices; -using System.Diagnostics.SymbolStore; using System.Diagnostics; +using System.Diagnostics.SymbolStore; +using System.Reflection; +using System.Reflection.Emit; +using System.Runtime.InteropServices; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; - -#if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif +using IKVM.CoreLib.Symbols.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.Runtime { @@ -80,7 +76,7 @@ public CodeEmitterFactory(RuntimeContext context) /// public CodeEmitter Create(IMethodSymbolBuilder mb) { - return new CodeEmitter(context, mb.GetILGenerator(), context.Resolver.ResolveType(mb.DeclaringType)); + return new CodeEmitter(context, mb.GetILGenerator(), mb.DeclaringType); } #if IMPORTER == false @@ -92,7 +88,7 @@ public CodeEmitter Create(IMethodSymbolBuilder mb) /// public CodeEmitter Create(DynamicMethod dm) { - return new CodeEmitter(context, dm.GetILGenerator(), null); + return new CodeEmitter(context, new ReflectionILGenerator((ReflectionSymbolContext)context.Resolver.Symbols, dm.GetILGenerator()), null); } #endif @@ -2109,11 +2105,9 @@ internal void DumpMethod() } } - internal void DefineSymbolDocument(ModuleBuilder module, string url, Guid language, Guid languageVendor, Guid documentType) + internal void DefineSymbolDocument(IModuleSymbolBuilder module, string url, Guid language, Guid languageVendor, Guid documentType) { -#if NETFRAMEWORK || IMPORTER symbols = module.DefineDocument(url, language, languageVendor, documentType); -#endif } internal CodeEmitterLocal UnsafeAllocTempLocal(ITypeSymbol type) @@ -2427,7 +2421,7 @@ internal byte[] GetLineNumberTable() #if IMPORTER - internal void EmitLineNumberTable(MethodBuilder mb) + internal void EmitLineNumberTable(IMethodSymbolBuilder mb) { if (linenums != null) context.AttributeHelper.SetLineNumberTable(mb, linenums); diff --git a/src/IKVM.Runtime/CodeEmitterLocal.cs b/src/IKVM.Runtime/CodeEmitterLocal.cs index 6f9161b3a7..bda872337f 100644 --- a/src/IKVM.Runtime/CodeEmitterLocal.cs +++ b/src/IKVM.Runtime/CodeEmitterLocal.cs @@ -21,14 +21,10 @@ Jeroen Frijters jeroen@frijters.net */ -using IKVM.CoreLib.Symbols; - -#if IMPORTER -using IKVM.Reflection.Emit; -#else using System.Reflection.Emit; -#endif +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.Runtime { @@ -38,7 +34,7 @@ sealed class CodeEmitterLocal private ITypeSymbol type; private string name; - private LocalBuilder local; + private ILocalBuilder local; internal CodeEmitterLocal(ITypeSymbol type) { @@ -60,22 +56,19 @@ internal int __LocalIndex get { return local == null ? 0xFFFF : local.LocalIndex; } } - internal void Emit(ILGenerator ilgen, OpCode opcode) + internal void Emit(IILGenerator ilgen, OpCode opcode) { // it's a temporary local that is only allocated on-demand - local ??= ilgen.DeclareLocal(type.AsReflection()); + local ??= ilgen.DeclareLocal(type); ilgen.Emit(opcode, local); } - internal void Declare(ILGenerator ilgen) + internal void Declare(IILGenerator ilgen) { - local = ilgen.DeclareLocal(type.AsReflection()); + local = ilgen.DeclareLocal(type); -#if NETFRAMEWORK || IMPORTER if (name != null) local.SetLocalSymInfo(name); -#endif - } } diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index c22efbdfa3..8a82599a4e 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -27,13 +27,11 @@ Jeroen Frijters using System.Runtime.Serialization; using System.Collections.Concurrent; -using static System.Diagnostics.DebuggableAttribute; using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols; - - +using static System.Diagnostics.DebuggableAttribute; #if IMPORTER using IKVM.Reflection; @@ -106,7 +104,7 @@ Assembly Resolve(ConcurrentDictionary dict, string name try { type.Finish(); - return type.TypeAsTBD.Assembly; + return type.TypeAsTBD.Assembly.AsReflection(); } catch (RetargetableJavaException e) { @@ -135,7 +133,7 @@ public DynamicClassLoader GetOrCreate(RuntimeClassLoader loader) if (loader is RuntimeAssemblyClassLoader acl) { var name = acl.MainAssembly.GetName().Name + context.Options.DynamicAssemblySuffixAndPublicKey; - foreach (var attr in acl.MainAssembly.GetCustomAttributes()) + foreach (var attr in acl.MainAssembly.AsReflection().GetCustomAttributes()) { if (attr.AssemblyName == name) { @@ -201,7 +199,7 @@ internal sealed class DynamicClassLoader : RuntimeJavaTypeFactory { #if !IMPORTER - static AssemblyBuilder jniProxyAssemblyBuilder; + static IAssemblySymbolBuilder jniProxyAssemblyBuilder; #endif readonly RuntimeContext context; @@ -349,7 +347,7 @@ internal override ITypeSymbol DefineUnloadable(string name) type = unloadableContainer.DefineNestedType(TypeNameUtil.MangleNestedTypeName(name), System.Reflection.TypeAttributes.NestedPrivate | System.Reflection.TypeAttributes.Interface | System.Reflection.TypeAttributes.Abstract); unloadables.Add(name, type); - return type.Symbol; + return type; } } @@ -374,7 +372,7 @@ internal override ITypeSymbol DefineDelegate(int parameterCount, bool returnVoid names[names.Length - 1] = "R"; var genericParameters = tb.DefineGenericParameters(names); - var parameterTypes = genericParameters; + var parameterTypes = (ITypeSymbol[])genericParameters; if (!returnVoid) { parameterTypes = new ITypeSymbol[genericParameters.Length - 1]; @@ -388,8 +386,8 @@ internal override ITypeSymbol DefineDelegate(int parameterCount, bool returnVoid mb.SetImplementationFlags(System.Reflection.MethodImplAttributes.Runtime); tb.Complete(); - delegates[index] = tb.Symbol; - return tb.Symbol; + delegates[index] = tb; + return tb; } } @@ -422,17 +420,18 @@ internal void FinishAll() if (unloadableContainer != null) { - unloadableContainer.CreateType(); + unloadableContainer.Complete(); foreach (var tb in unloadables.Values) - tb.CreateType(); + tb.Complete(); } #if IMPORTER + if (proxiesContainer != null) { - proxiesContainer.CreateType(); + proxiesContainer.Complete(); foreach (var tb in proxies) - tb.CreateType(); + tb.Complete(); } #endif @@ -441,12 +440,11 @@ internal void FinishAll() #if !IMPORTER - internal static ModuleBuilder CreateJniProxyModuleBuilder() + internal static IModuleSymbolBuilder CreateJniProxyModuleBuilder(RuntimeContext context) { - AssemblyName name = new AssemblyName(); - name.Name = "jniproxy"; - jniProxyAssemblyBuilder = DefineDynamicAssembly(name, AssemblyBuilderAccess.Run, null); - return jniProxyAssemblyBuilder.DefineDynamicModule("jniproxy.dll"); + var name = new AssemblyName("jniproxy"); + jniProxyAssemblyBuilder = DefineDynamicAssembly(context, name, AssemblyBuilderAccess.Run, null); + return jniProxyAssemblyBuilder.DefineModule("jniproxy.dll"); } #endif @@ -515,26 +513,26 @@ private static SerializationInfo ToInfo(byte[] publicKey) #endif - public static ModuleBuilder CreateModuleBuilder(RuntimeContext context) + public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context) { AssemblyName name = new AssemblyName(); name.Name = "ikvm_dynamic_assembly__" + (uint)Environment.TickCount; return CreateModuleBuilder(context, name); } - public static ModuleBuilder CreateModuleBuilder(RuntimeContext context, AssemblyName name) + public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, AssemblyName name) { var now = DateTime.Now; name.Version = new Version(now.Year, (now.Month * 100) + now.Day, (now.Hour * 100) + now.Minute, (now.Second * 1000) + now.Millisecond); - var attribs = new List(); - AssemblyBuilderAccess access = AssemblyBuilderAccess.Run; + var attribs = new List(); + var access = AssemblyBuilderAccess.Run; #if NETFRAMEWORK if (!AppDomain.CurrentDomain.IsFullyTrusted) - attribs.Add(new CustomAttributeBuilder(typeof(System.Security.SecurityTransparentAttribute).GetConstructor([]), [])); + attribs.Add(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(System.Security.SecurityTransparentAttribute).FullName).GetConstructor([]), [])); #endif - var assemblyBuilder = DefineDynamicAssembly(name, access, attribs); + var assemblyBuilder = DefineDynamicAssembly(context, name, access, attribs.ToArray()); context.AttributeHelper.SetRuntimeCompatibilityAttribute(assemblyBuilder); // determine debugging mode @@ -544,23 +542,15 @@ public static ModuleBuilder CreateModuleBuilder(RuntimeContext context, Assembly context.AttributeHelper.SetDebuggingModes(assemblyBuilder, debugMode); -#if NETFRAMEWORK - var moduleBuilder = assemblyBuilder.DefineDynamicModule(name.Name, JVM.EmitSymbols); -#else - var moduleBuilder = assemblyBuilder.DefineDynamicModule(name.Name); -#endif + var moduleBuilder = assemblyBuilder.DefineModule(name.Name, null, JVM.EmitSymbols); - moduleBuilder.SetCustomAttribute(new CustomAttributeBuilder(typeof(IKVM.Attributes.JavaModuleAttribute).GetConstructor([]), [])); + moduleBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.JavaModuleAttribute).FullName).GetConstructor([]), [])); return moduleBuilder; } - static AssemblyBuilder DefineDynamicAssembly(AssemblyName name, AssemblyBuilderAccess access, IEnumerable assemblyAttributes) + static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyName name, AssemblyBuilderAccess access, ICustomAttributeBuilder[] assemblyAttributes) { -#if NETFRAMEWORK - return AppDomain.CurrentDomain.DefineDynamicAssembly(name, access, null, true, assemblyAttributes); -#else - return AssemblyBuilder.DefineDynamicAssembly(name, access, assemblyAttributes); -#endif + return context.Resolver.Symbols.DefineAssembly(name, access, assemblyAttributes); } #endif diff --git a/src/IKVM.Runtime/ExceptionHelper.cs b/src/IKVM.Runtime/ExceptionHelper.cs index 1356850dfd..d9151e11a4 100644 --- a/src/IKVM.Runtime/ExceptionHelper.cs +++ b/src/IKVM.Runtime/ExceptionHelper.cs @@ -30,8 +30,8 @@ Jeroen Frijters using System.Security; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; -using IDictionary = System.Collections.IDictionary; using Interlocked = System.Threading.Interlocked; using MethodBase = System.Reflection.MethodBase; @@ -218,8 +218,8 @@ internal static void Append(ExceptionHelper exceptionHelper, List - /// Gets the associated with the specified type. + /// Gets the associated with the specified assembly. /// /// /// - IAssemblySymbol ResolveAssembly(Assembly assembly); + IAssemblySymbol? ResolveAssembly(Assembly? assembly); /// - /// Gets the associated with the specified type. + /// Gets the associated with the specified module. /// /// /// - IModuleSymbol ResolveModule(Module module); + IModuleSymbol? ResolveModule(Module? module); /// /// Gets the associated with the specified type. /// /// /// - ITypeSymbol ResolveType(Type type); + ITypeSymbol? ResolveType(Type? type); + + /// + /// Gets the associated with the specified method. + /// + /// + /// + IMethodBaseSymbol? ResolveMethodBase(MethodBase? type); + + /// + /// Gets the associated with the specified method. + /// + /// + /// + IConstructorSymbol? ResolveConstructor(ConstructorInfo? ctor); + + /// + /// Gets the associated with the specified method. + /// + /// + /// + IMethodSymbol? ResolveMethod(MethodInfo? method); } diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs index 1fbc79ad5c..98f7c118a6 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Runtime; namespace IKVM.Java.Externs.ikvm.runtime @@ -48,19 +50,20 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, return ghostType; var t = o.GetType(); - if (t.IsPrimitive || context.ClassLoaderFactory.IsRemappedType(t) && !t.IsSealed) - return context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(t); + var ts = context.Resolver.ResolveType(t); + if (t.IsPrimitive || context.ClassLoaderFactory.IsRemappedType(ts) && !ts.IsSealed) + return context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts); for (; ; ) { // if GetWrapperFromType returns null (or if tw.IsAbstract), that // must mean that the Type of the object is an implementation helper class // (e.g. an AtomicReferenceFieldUpdater or ThreadLocal instrinsic subclass) - var tw = context.ClassLoaderFactory.GetJavaTypeFromType(t); + var tw = context.ClassLoaderFactory.GetJavaTypeFromType(ts); if (tw != null && (!tw.IsAbstract || tw.IsArray)) return tw; - t = t.BaseType; + ts = ts.BaseType; } } @@ -70,13 +73,14 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, throw new NotImplementedException(); #else var t = Type.GetTypeFromHandle(handle); - if (t.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(t) || t == typeof(void)) - return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(t).ClassObject; + var ts = JVM.Context.Resolver.ResolveType(t); + if (t.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || t == typeof(void)) + return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).ClassObject; - if (!IsVisibleAsClass(t)) + if (!IsVisibleAsClass(ts)) return null; - var tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(t); + var tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(ts); if (tw != null) return tw.ClassObject; @@ -90,13 +94,14 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, throw new NotImplementedException(); #else var t = Type.GetTypeFromHandle(handle); - if (t.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(t) || t == typeof(void)) - return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(t).MakeArrayType(rank).ClassObject; + var ts = JVM.Context.Resolver.ResolveType(t); + if (ts.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || ts == typeof(void)) + return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).MakeArrayType(rank).ClassObject; if (!IsVisibleAsClass(t)) return null; - var tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(t); + var tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(ts); if (tw != null) return tw.MakeArrayType(rank).ClassObject; @@ -109,20 +114,22 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, #if FIRST_PASS throw new NotImplementedException(); #else + var ts = JVM.Context.Resolver.ResolveType(type); + int rank = 0; - while (ReflectUtil.IsVector(type)) + while (ReflectUtil.IsVector(ts)) { - type = type.GetElementType(); + ts = ts.GetElementType(); rank++; } - if (type.DeclaringType != null && JVM.Context.AttributeHelper.IsGhostInterface(type.DeclaringType)) - type = type.DeclaringType; + if (ts.DeclaringType != null && JVM.Context.AttributeHelper.IsGhostInterface(ts.DeclaringType)) + ts = ts.DeclaringType; if (!IsVisibleAsClass(type)) return null; - var wrapper = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(type); + var wrapper = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(ts); if (wrapper == null) return null; @@ -133,25 +140,22 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, #endif } - private static bool IsVisibleAsClass(Type type) + private static bool IsVisibleAsClass(ITypeSymbol type) { while (type.HasElementType) { if (type.IsPointer || type.IsByRef) - { return false; - } + type = type.GetElementType(); } + if (type.ContainsGenericParameters && !type.IsGenericTypeDefinition) - { return false; - } - System.Reflection.Emit.TypeBuilder tb = type as System.Reflection.Emit.TypeBuilder; - if (tb != null && !tb.IsCreated()) - { + + if (type is ITypeSymbolBuilder tb && !tb.IsComplete) return false; - } + return true; } @@ -164,9 +168,9 @@ public static Type getInstanceTypeFromClass(global::java.lang.Class classObject) { var wrapper = RuntimeJavaType.FromClass(classObject); if (wrapper.IsRemapped && wrapper.IsFinal) - return wrapper.TypeAsTBD; + return wrapper.TypeAsTBD.AsReflection(); else - return wrapper.TypeAsBaseType; + return wrapper.TypeAsBaseType.AsReflection(); } /// @@ -180,9 +184,9 @@ public static Type getRuntimeTypeFromClass(global::java.lang.Class classObject) wrapper.Finish(); if (wrapper.IsRemapped && wrapper.IsFinal) - return wrapper.TypeAsTBD; + return wrapper.TypeAsTBD.AsReflection(); else - return wrapper.TypeAsBaseType; + return wrapper.TypeAsBaseType.AsReflection(); } [HideFromJava] diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs b/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs index 57fbfbd9f0..ce41e7611b 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs @@ -32,7 +32,7 @@ Jeroen Frijters namespace IKVM.Java.Externs.java.lang { - static class Package + static class Package { static Dictionary systemPackages; diff --git a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs index 229822b1dc..621a5b980c 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs @@ -2475,11 +2475,11 @@ static Delegate CreateCompareExchangeArrayDelegate(RuntimeJavaType tw) var e = Expression.Parameter(typeof(object)); return Expression.Lambda>( Expression.Call( - compareAndSwapArrayMethodInfo.MakeGenericMethod(tw.TypeAsTBD), - Expression.Convert(p, tw.MakeArrayType(1).TypeAsTBD), + compareAndSwapArrayMethodInfo.MakeGenericMethod(tw.TypeAsTBD.AsReflection()), + Expression.Convert(p, tw.MakeArrayType(1).TypeAsTBD.AsReflection()), i, - Expression.Convert(v, tw.TypeAsTBD), - Expression.Convert(e, tw.TypeAsTBD)), + Expression.Convert(v, tw.TypeAsTBD.AsReflection()), + Expression.Convert(e, tw.TypeAsTBD.AsReflection())), p, i, v, e) .Compile(); } diff --git a/src/IKVM.Runtime/LambdaMetafactory.cs b/src/IKVM.Runtime/LambdaMetafactory.cs index 50877f45be..92079c97a7 100644 --- a/src/IKVM.Runtime/LambdaMetafactory.cs +++ b/src/IKVM.Runtime/LambdaMetafactory.cs @@ -24,19 +24,15 @@ Jeroen Frijters using System; using System.Collections.Generic; using System.Diagnostics; +using System.Reflection; +using System.Reflection.Emit; using IKVM.ByteCode; -using IKVM.CoreLib.Diagnostics; -using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; #endif namespace IKVM.Runtime @@ -529,7 +525,7 @@ private static void EmitDispatch(RuntimeByteCodeJavaType.FinishContext context, var mb = interfaceMethod.GetDefineMethodHelper().DefineMethod(context.TypeWrapper, tb, interfaceMethod.Name, MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final); if (interfaceMethod.Name != interfaceMethod.RealName) { - tb.DefineMethodOverride(mb, (MethodInfo)interfaceMethod.GetMethod()); + tb.DefineMethodOverride(mb, (IMethodSymbol)interfaceMethod.GetMethod()); } context.Context.AttributeHelper.HideFromJava(mb); diff --git a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs index 01ef18ff18..4772fd86ec 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs @@ -1,14 +1,7 @@ -using System; - -#if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; +using System.Reflection; using System.Reflection.Emit; -#endif + +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { @@ -16,12 +9,12 @@ namespace IKVM.Runtime partial class MethodHandleUtil { - internal void EmitCallDelegateInvokeMethod(CodeEmitter ilgen, Type delegateType) + internal void EmitCallDelegateInvokeMethod(CodeEmitter ilgen, ITypeSymbol delegateType) { if (delegateType.IsGenericType) { // MONOBUG we don't look at the invoke method directly here, because Mono doesn't support GetParameters() on a builder instantiation - Type[] typeArgs = delegateType.GetGenericArguments(); + var typeArgs = delegateType.GetGenericArguments(); if (IsPackedArgsContainer(typeArgs[typeArgs.Length - 1])) { WrapArgs(ilgen, typeArgs[typeArgs.Length - 1]); @@ -31,24 +24,24 @@ internal void EmitCallDelegateInvokeMethod(CodeEmitter ilgen, Type delegateType) WrapArgs(ilgen, typeArgs[typeArgs.Length - 2]); } } + ilgen.Emit(OpCodes.Callvirt, GetDelegateInvokeMethod(delegateType)); } - private void WrapArgs(CodeEmitter ilgen, Type type) + private void WrapArgs(CodeEmitter ilgen, ITypeSymbol type) { - Type last = type.GetGenericArguments()[MaxArity - 1]; + var last = type.GetGenericArguments()[MaxArity - 1]; if (IsPackedArgsContainer(last)) - { WrapArgs(ilgen, last); - } + ilgen.Emit(OpCodes.Newobj, GetDelegateOrPackedArgsConstructor(type)); } - internal MethodInfo GetDelegateInvokeMethod(Type delegateType) + internal IMethodSymbol GetDelegateInvokeMethod(ITypeSymbol delegateType) { if (ReflectUtil.ContainsTypeBuilder(delegateType)) { - return TypeBuilder.GetMethod(delegateType, delegateType.GetGenericTypeDefinition().GetMethod("Invoke")); + return delegateType.GetGenericTypeDefinition().GetMethod("Invoke"); } else { @@ -56,16 +49,16 @@ internal MethodInfo GetDelegateInvokeMethod(Type delegateType) } } - internal ConstructorInfo GetDelegateConstructor(Type delegateType) + internal IConstructorSymbol GetDelegateConstructor(ITypeSymbol delegateType) { return GetDelegateOrPackedArgsConstructor(delegateType); } - private ConstructorInfo GetDelegateOrPackedArgsConstructor(Type type) + private IConstructorSymbol GetDelegateOrPackedArgsConstructor(ITypeSymbol type) { if (ReflectUtil.ContainsTypeBuilder(type)) { - return TypeBuilder.GetConstructor(type, type.GetGenericTypeDefinition().GetConstructors()[0]); + return type.GetGenericTypeDefinition().GetConstructors()[0]; } else { @@ -74,26 +67,24 @@ private ConstructorInfo GetDelegateOrPackedArgsConstructor(Type type) } // for delegate types used for "ldc " we don't want ghost arrays to be erased - internal Type CreateDelegateTypeForLoadConstant(RuntimeJavaType[] args, RuntimeJavaType ret) + internal ITypeSymbol CreateDelegateTypeForLoadConstant(RuntimeJavaType[] args, RuntimeJavaType ret) { - Type[] typeArgs = new Type[args.Length]; + var typeArgs = new ITypeSymbol[args.Length]; for (int i = 0; i < args.Length; i++) - { typeArgs[i] = TypeWrapperToTypeForLoadConstant(args[i]); - } + return CreateDelegateType(typeArgs, TypeWrapperToTypeForLoadConstant(ret)); } - private Type TypeWrapperToTypeForLoadConstant(RuntimeJavaType tw) + ITypeSymbol TypeWrapperToTypeForLoadConstant(RuntimeJavaType tw) { if (tw.IsGhostArray) { int dims = tw.ArrayRank; while (tw.IsArray) - { tw = tw.ElementTypeWrapper; - } - return RuntimeArrayJavaType.MakeArrayType(tw.TypeAsSignatureType, dims); + + return tw.TypeAsSignatureType.MakeArrayType(dims); } else { diff --git a/src/IKVM.Runtime/RuntimeArrayJavaType.cs b/src/IKVM.Runtime/RuntimeArrayJavaType.cs index 5295a96b6e..72934b2d59 100644 --- a/src/IKVM.Runtime/RuntimeArrayJavaType.cs +++ b/src/IKVM.Runtime/RuntimeArrayJavaType.cs @@ -119,7 +119,7 @@ internal override ITypeSymbol TypeAsTBD while (arrayType == null) { bool prevFinished = finished; - var type = MakeArrayType(ultimateElementTypeWrapper.TypeAsArrayType, this.ArrayRank); + var type = ultimateElementTypeWrapper.TypeAsArrayType.MakeArrayType(ArrayRank); if (prevFinished) { // We were already finished prior to the call to MakeArrayType, so we can safely diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index 8ce64aa785..86cdeeb73f 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -22,30 +22,20 @@ Jeroen Frijters */ using System; -using System.IO; using System.Collections.Generic; using System.Diagnostics; -using System.Threading; -using System.Runtime.Serialization; +using System.IO; +using System.Reflection; using System.Runtime.CompilerServices; +using System.Runtime.Serialization; +using System.Threading; -using IKVM.CoreLib.Diagnostics; using IKVM.Attributes; -using IKVM.Runtime.Syntax; +using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; - - - -#if IMPORTER || EXPORTER -using IKVM.Reflection; - -using Type = IKVM.Reflection.Type; -#else +using IKVM.Runtime.Syntax; using IKVM.Runtime.Vfs; -using System.Reflection; -#endif - #if IMPORTER using IKVM.Tools.Importer; #endif @@ -1141,7 +1131,7 @@ internal List> GetPackageInfo() var list = new List>(); foreach (var m in assemblyLoader.Assembly.GetModules(false)) { - var attr = m.GetCustomAttributes(); + var attr = m.AsReflection().GetCustomAttributes(); foreach (var p in attr) list.Add(new KeyValuePair(p.jar, p.packages)); } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index 1001ff45ac..8c18ded242 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using System.Collections.Generic; using System.Diagnostics; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.ByteCode; @@ -36,8 +38,6 @@ Jeroen Frijters using DynamicOrAotTypeWrapper = IKVM.Tools.Importer.RuntimeImportByteCodeJavaType; #else -using System.Reflection; -using System.Reflection.Emit; using DynamicOrAotTypeWrapper = IKVM.Runtime.RuntimeByteCodeJavaType; #endif @@ -195,13 +195,13 @@ private void CreateGetCallerID() ilgen.DoEmit(); } - private void RegisterNestedTypeBuilder(TypeBuilder tb) + private void RegisterNestedTypeBuilder(ITypeSymbolBuilder tb) { - nestedTypeBuilders ??= new List(); + nestedTypeBuilders ??= new List(); nestedTypeBuilders.Add(tb); } - internal Type FinishImpl() + internal ITypeSymbol FinishImpl() { var methods = wrapper.GetMethods(); var fields = wrapper.GetFields(); @@ -665,7 +665,7 @@ internal Type FinishImpl() if (m.Annotations != null) { - ParameterBuilder returnParameter = null; + IParameterSymbolBuilder returnParameter = null; foreach (object[] def in m.Annotations) { var annotation = Annotation.Load(wrapper, def); @@ -741,7 +741,7 @@ internal Type FinishImpl() } #if !IMPORTER if (liveObjects != null) - context.Resolver.ResolveRuntimeType("IKVM.Runtime.LiveObjectHolder`1").GetField("values", BindingFlags.Static | BindingFlags.Public).AsReflection().SetValue(liveObjects.ToArray()); + context.Resolver.ResolveRuntimeType("IKVM.Runtime.LiveObjectHolder`1").GetField("values", BindingFlags.Static | BindingFlags.Public).AsReflection().SetValue(null, liveObjects.ToArray()); #endif } finally @@ -1005,7 +1005,7 @@ private bool EmitInterlockedCompareAndSet(RuntimeJavaMethod method, string field private void AddMethodParameterInfo(ClassFile.Method m, RuntimeJavaMethod mw, IMethodSymbolBuilder mb, out string[] parameterNames) { parameterNames = null; - ParameterBuilder[] parameterBuilders = null; + IParameterSymbolBuilder[] parameterBuilders = null; if (wrapper.ClassLoader.EmitSymbols #if IMPORTER @@ -1660,7 +1660,7 @@ public JniBuilder(RuntimeContext context) this.context = context ?? throw new ArgumentNullException(nameof(context)); } - Type LocalRefStructType => context.Resolver.ResolveRuntimeType("IKVM.Runtime.JNI.JNIFrame").AsReflection(); + ITypeSymbol LocalRefStructType => context.Resolver.ResolveRuntimeType("IKVM.Runtime.JNI.JNIFrame"); IMethodSymbol JniFuncPtrMethod => LocalRefStructType.GetMethod("GetFuncPtr"); @@ -1781,7 +1781,7 @@ internal void Generate(RuntimeByteCodeJavaType.FinishContext context, CodeEmitte ilGenerator.Emit(OpCodes.Ldsfld, methodPtr); - Type realRetType; + ITypeSymbol realRetType; if (retTypeWrapper == context.Context.PrimitiveJavaTypeFactory.BOOLEAN) realRetType = context.Context.Types.Byte; else if (retTypeWrapper.IsPrimitive) @@ -1940,16 +1940,16 @@ void ImplementInterfaces(RuntimeJavaType[] interfaces, List int // look for "magic" interfaces that imply a .NET interface if (iface.ClassLoader == context.JavaBase.TypeOfJavaLangObject.ClassLoader) { - if (iface.Name == "java.lang.Iterable" && !wrapper.ImplementsInterface(context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName).AsReflection()))) + if (iface.Name == "java.lang.Iterable" && !wrapper.ImplementsInterface(context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName)))) { var enumeratorType = context.ClassLoaderFactory.GetBootstrapClassLoader().TryLoadClassByName("ikvm.lang.IterableEnumerator"); if (enumeratorType != null) { - typeBuilder.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName).AsReflection()); + typeBuilder.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName)); // FXBUG we're using the same method name as the C# compiler here because both the .NET and Mono implementations of Xml serialization depend on this method name - var mb = typeBuilder.DefineMethod("System.Collections.IEnumerable.GetEnumerator", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final | MethodAttributes.SpecialName, context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerator).FullName).AsReflection(), []); + var mb = typeBuilder.DefineMethod("System.Collections.IEnumerable.GetEnumerator", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final | MethodAttributes.SpecialName, context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerator).FullName), []); context.AttributeHelper.HideFromJava(mb); - typeBuilder.DefineMethodOverride(mb, context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName).GetMethod("GetEnumerator").AsReflection()); + typeBuilder.DefineMethodOverride(mb, context.Resolver.ResolveCoreType(typeof(System.Collections.IEnumerable).FullName).GetMethod("GetEnumerator")); var ilgen = context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldarg_0); var mw = enumeratorType.GetMethodWrapper("", "(Ljava.lang.Iterable;)V", false); @@ -1990,7 +1990,7 @@ void AddUnsupportedAbstractMethods() if (RuntimeManagedJavaType.IsUnsupportedAbstractMethod(mb)) GenerateUnsupportedAbstractMethodStub(mb); - var h = new Dictionary(); + var h = new Dictionary(); var tw = (RuntimeJavaType)wrapper; while (tw != null) { @@ -2096,7 +2096,7 @@ static bool IsCompatibleArgList(RuntimeJavaType[] caller, RuntimeJavaType[] call return false; } - void EmitCallerIDInitialization(CodeEmitter ilGenerator, FieldInfo callerIDField) + void EmitCallerIDInitialization(CodeEmitter ilGenerator, IFieldSymbol callerIDField) { var tw = context.JavaBase.TypeOfIkvmInternalCallerID; if (tw.InternalsVisibleTo(wrapper)) @@ -2193,7 +2193,7 @@ internal IMethodSymbolBuilder DefineThreadLocalType() int id = nestedTypeBuilders == null ? 0 : nestedTypeBuilders.Count; var tb = typeBuilder.DefineNestedType(NestedTypeName.ThreadLocal + id, TypeAttributes.NestedPrivate | TypeAttributes.Sealed, threadLocal.TypeAsBaseType); var fb = tb.DefineField("field", context.Types.Object, FieldAttributes.Private | FieldAttributes.Static); - fb.SetCustomAttribute(new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(ThreadStaticAttribute).FullName).GetConstructor([]).AsReflection(), [])); + fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ThreadStaticAttribute).FullName).GetConstructor([]), [])); var mbGet = tb.DefineMethod("get", MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.Final, context.Types.Object, []); var ilgen = mbGet.GetILGenerator(); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs index a964df954a..ea6793966e 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs @@ -21,17 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ -using System; - -#if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else using System.Reflection; using System.Reflection.Emit; -#endif + +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.Runtime { @@ -45,8 +39,8 @@ private sealed partial class JavaTypeImpl sealed class DelegateConstructorMethodWrapper : RuntimeJavaMethod { - MethodBuilder constructor; - MethodInfo invoke; + IMethodSymbolBuilder constructor; + IMethodSymbol invoke; /// /// Initializes a new instance. @@ -59,14 +53,14 @@ internal DelegateConstructorMethodWrapper(RuntimeByteCodeJavaType tw, ClassFile. } - internal void DoLink(TypeBuilder typeBuilder) + internal void DoLink(ITypeSymbolBuilder typeBuilder) { var attribs = MethodAttributes.HideBySig | MethodAttributes.Public; - constructor = ReflectUtil.DefineConstructor(typeBuilder, attribs, new Type[] { DeclaringType.Context.Types.Object, DeclaringType.Context.Types.IntPtr }); + constructor = ReflectUtil.DefineConstructor(typeBuilder, attribs, [DeclaringType.Context.Types.Object, DeclaringType.Context.Types.IntPtr]); constructor.SetImplementationFlags(MethodImplAttributes.Runtime); var mw = GetParameters()[0].GetMethods()[0]; mw.Link(); - invoke = (MethodInfo)mw.GetMethod(); + invoke = (IMethodSymbol)mw.GetMethod(); } internal override void EmitNewobj(CodeEmitter ilgen) diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs index 7e4a7f3ecd..ad9115d70e 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs @@ -21,21 +21,18 @@ Jeroen Frijters jeroen@frijters.net */ -using System; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; using Type = IKVM.Reflection.Type; using RuntimeDynamicOrImportJavaType = IKVM.Tools.Importer.RuntimeImportByteCodeJavaType; -#else -using System.Reflection; -using System.Reflection.Emit; #endif namespace IKVM.Runtime @@ -64,7 +61,7 @@ internal DelegateInvokeStubMethodWrapper(RuntimeJavaType declaringType, ITypeSym this.delegateType = delegateType; } - internal MethodInfo DoLink(TypeBuilder tb) + internal IMethodSymbol DoLink(ITypeSymbolBuilder tb) { var mw = DeclaringType.GetMethodWrapper("Invoke", Signature, true); @@ -74,7 +71,7 @@ internal MethodInfo DoLink(TypeBuilder tb) for (int i = 0; i < parameterTypes.Length; i++) parameterTypes[i] = parameters[i].ParameterType; - var mb = tb.DefineMethod(Name, MethodAttributes.Public, invoke.ReturnType.AsReflection(), parameterTypes.AsReflection()); + var mb = tb.DefineMethod(Name, MethodAttributes.Public, invoke.ReturnType, parameterTypes); DeclaringType.Context.AttributeHelper.HideFromReflection(mb); var ilgen = DeclaringType.Context.CodeEmitterFactory.Create(mb); if (mw == null || mw.IsStatic || !mw.IsPublic) @@ -90,7 +87,7 @@ internal MethodInfo DoLink(TypeBuilder tb) if (parameters[i].ParameterType.IsByRef) { var elemType = parameters[i].ParameterType.GetElementType(); - var local = ilgen.DeclareLocal(RuntimeArrayJavaType.MakeArrayType(elemType, 1)); + var local = ilgen.DeclareLocal(elemType.MakeArrayType(1)); byrefs[i] = local; ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.Emit(OpCodes.Newarr, elemType); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index 5f50536199..af8b03ae0d 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -26,20 +26,18 @@ Jeroen Frijters using System.Diagnostics; using System.Collections.Concurrent; +using System.Reflection; +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; -using Type = IKVM.Reflection.Type; using RuntimeDynamicOrImportJavaType = IKVM.Tools.Importer.RuntimeImportByteCodeJavaType; #else -using System.Reflection; -using System.Reflection.Emit; using RuntimeDynamicOrImportJavaType = IKVM.Runtime.RuntimeByteCodeJavaType; #endif @@ -1109,11 +1107,13 @@ internal override IFieldSymbol LinkField(RuntimeJavaField fw) field = DefineField(realFieldName, fw.FieldTypeWrapper, attribs, fld.IsVolatile); } + if (fld.IsTransient) { - var transientAttrib = new CustomAttributeBuilder(wrapper.Context.Resolver.ResolveCoreType(typeof(NonSerializedAttribute).FullName).GetConstructor([]).AsReflection(), []); + var transientAttrib = wrapper.Context.Resolver.Symbols.CreateCustomAttribute(wrapper.Context.Resolver.ResolveCoreType(typeof(NonSerializedAttribute).FullName).GetConstructor([]), []); field.SetCustomAttribute(transientAttrib); } + #if IMPORTER { // if the Java modifiers cannot be expressed in .NET, we emit the Modifiers attribute to store @@ -1137,8 +1137,7 @@ internal override IFieldSymbol LinkField(RuntimeJavaField fw) IFieldSymbolBuilder DefineField(string name, RuntimeJavaType tw, FieldAttributes attribs, bool isVolatile) { - var modreq = isVolatile ? [wrapper.Context.Types.IsVolatile] : []; - return typeBuilder.DefineField(name, tw.TypeAsSignatureType, modreq, wrapper.GetModOpt(tw, false), attribs); + return typeBuilder.DefineField(name, tw.TypeAsSignatureType, isVolatile ? [wrapper.Context.Types.IsVolatile] : [], wrapper.GetModOpt(tw, false), attribs); } internal override void EmitRunClassConstructor(CodeEmitter ilgen) @@ -1301,7 +1300,7 @@ FinishedTypeImpl FinishCore() privateInterfaceMethods.CreateType(); } #endif - var finishedClinitMethod = (MethodInfo)clinitMethod; + var finishedClinitMethod = (IMethodSymbol)clinitMethod; #if !IMPORTER if (finishedClinitMethod != null) { @@ -2129,7 +2128,7 @@ bool IsAccessibleInternal(RuntimeJavaMethod mw) return mw.IsInternal && mw.DeclaringType.InternalsVisibleTo(wrapper); } - static IMethodSymbol LinkAndGetMethod(RuntimeJavaMethod mw) + static IMethodBaseSymbol LinkAndGetMethod(RuntimeJavaMethod mw) { mw.Link(); return mw.GetMethod(); @@ -2288,7 +2287,7 @@ static IMethodSymbol GetBaseFinalizeMethod(RuntimeJavaType wrapper) } var type = wrapper.TypeAsBaseType; - var baseFinalize = type.GetMethod("__", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, [], null); + var baseFinalize = type.GetMethod("__", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, []); if (baseFinalize != null) return baseFinalize; @@ -2716,7 +2715,7 @@ IMethodSymbolBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setM { bool needFinalize = false; bool needDispatch = false; - MethodInfo baseFinalize = null; + IMethodSymbol baseFinalize = null; if (baseMethods[index] != null && ReferenceEquals(m.Name, StringConstants.FINALIZE) && ReferenceEquals(m.Signature, StringConstants.SIG_VOID)) { baseFinalize = GetBaseFinalizeMethod(wrapper.BaseTypeWrapper); @@ -2805,7 +2804,7 @@ IMethodSymbolBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setM } else if (subsequent || methods[index].IsExplicitOverride || baseMethod.RealName != name) { - typeBuilder.DefineMethodOverride(mb, (MethodInfo)baseMethod.GetMethod()); + typeBuilder.DefineMethodOverride(mb, (IMethodSymbol)baseMethod.GetMethod()); } // the non-primary base methods always need an explicit method override diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index 5eb072d7c3..d7801d44f1 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -24,6 +24,8 @@ Jeroen Frijters using System; using System.Collections.Generic; using System.Diagnostics; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Diagnostics; @@ -31,16 +33,9 @@ Jeroen Frijters using IKVM.CoreLib.Symbols.Emit; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; using ProtectionDomain = System.Object; #else -using System.Reflection; -using System.Reflection.Emit; - using ProtectionDomain = java.security.ProtectionDomain; #endif @@ -406,7 +401,7 @@ void GenerateOverrideStub(ITypeSymbolBuilder typeBuilder, RuntimeJavaMethod base Debug.Assert(!baseMethod.HasCallerID); var overrideStub = baseMethod.GetDefineMethodHelper().DefineMethod(this, typeBuilder, "__" + baseMethod.DeclaringType.Name + "::" + baseMethod.Name, MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final); - typeBuilder.DefineMethodOverride(overrideStub, (MethodInfo)baseMethod.GetMethod()); + typeBuilder.DefineMethodOverride(overrideStub, (IMethodSymbol)baseMethod.GetMethod()); var stubargs = baseMethod.GetParameters(); var targetArgs = targetMethod.GetParameters(); @@ -939,7 +934,7 @@ static ITypeSymbol GetModOptHelper(RuntimeJavaType tw) if (tw.IsArray) { - return RuntimeArrayJavaType.MakeArrayType(GetModOptHelper(tw.GetUltimateElementTypeWrapper()), tw.ArrayRank); + return GetModOptHelper(tw.GetUltimateElementTypeWrapper()).MakeArrayType(tw.ArrayRank); } else if (tw.IsGhost) { diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 319b7455a1..53d61e8300 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -146,7 +146,7 @@ ITypeSymbol GetClassLiteralType() while (tw.IsArray) tw = tw.ElementTypeWrapper; - return RuntimeArrayJavaType.MakeArrayType(tw.TypeAsTBD, rank); + return tw.TypeAsTBD.MakeArrayType(rank); } else { @@ -929,7 +929,7 @@ internal ITypeSymbol TypeAsSignatureType return ((RuntimeUnloadableJavaType)this).MissingType ?? context.Types.Object; if (IsGhostArray) - return RuntimeArrayJavaType.MakeArrayType(context.Types.Object, ArrayRank); + return context.Types.Object.MakeArrayType(ArrayRank); return TypeAsTBD; } @@ -953,7 +953,7 @@ internal ITypeSymbol TypeAsLocalOrStackType } if (IsGhostArray) - return RuntimeArrayJavaType.MakeArrayType(context.Types.Object, ArrayRank); + return context.Types.Object.MakeArrayType(ArrayRank); return TypeAsTBD; } @@ -968,7 +968,7 @@ internal ITypeSymbol TypeAsArrayType return context.Types.Object; if (IsGhostArray) - return RuntimeArrayJavaType.MakeArrayType(context.Types.Object, ArrayRank); + return context.Types.Object.MakeArrayType(ArrayRank); return TypeAsTBD; } @@ -1318,7 +1318,7 @@ internal virtual void EmitCheckcast(CodeEmitter ilgen) } ilgen.EmitLdc_I4(rank); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, tw.TypeAsTBD.GetMethod("CastArray")); - ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(context.Types.Object, rank)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, context.Types.Object.MakeArrayType(rank)); } else { diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index e056821594..dc1156c110 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -25,23 +25,15 @@ Jeroen Frijters using System.Collections.Generic; using System.Diagnostics; using System.Linq; +using System.Reflection; +using System.Reflection.Emit; -using IKVM.CoreLib.Diagnostics; -using IKVM.CoreLib.Symbols; using IKVM.Attributes; -using IKVM.Runtime.Syntax; using IKVM.ByteCode; +using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif +using IKVM.Runtime.Syntax; #if IMPORTER using IKVM.Tools.Importer; @@ -1109,7 +1101,7 @@ internal override string[] GetEnclosingMethod() { var enc = Context.AttributeHelper.GetEnclosingMethodAttribute(type); if (enc != null) - return new string[] { enc.ClassName, enc.MethodName, enc.MethodSignature }; + return [enc.ClassName, enc.MethodName, enc.MethodSignature]; return null; } @@ -1125,7 +1117,7 @@ object[] CastArray(CustomAttribute[] l) internal override object[] GetDeclaredAnnotations() { - return CastArray(type.GetCustomAttribute(false)); + return CastArray(type.GetCustomAttributes(false)); } internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs index ee8ee78f2c..fbafd618a1 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs @@ -21,18 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { @@ -96,7 +89,7 @@ void ConvertByRefArgs(CodeEmitter ilgen) { var type = args[i]; if (type.IsByRef) - type = RuntimeArrayJavaType.MakeArrayType(type.GetElementType(), 1); + type = type.GetElementType().MakeArrayType(1); locals[i] = ilgen.DeclareLocal(type); ilgen.Emit(OpCodes.Stloc, locals[i]); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs index 669a191746..d50ce108f7 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.CloneJavaMethod.cs @@ -22,18 +22,10 @@ Jeroen Frijters */ using System; - -using IKVM.Attributes; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else using System.Reflection; using System.Reflection.Emit; -#endif + +using IKVM.Attributes; namespace IKVM.Runtime { @@ -71,7 +63,7 @@ internal override void EmitCall(CodeEmitter ilgen) ilgen.MarkLabel(label2); ilgen.EmitThrow("java.lang.NullPointerException"); ilgen.MarkLabel(label1); - ilgen.Emit(OpCodes.Call, DeclaringType.Context.Types.Object.GetMethod("MemberwiseClone", BindingFlags.Instance | BindingFlags.NonPublic, null, [], null)); + ilgen.Emit(OpCodes.Call, DeclaringType.Context.Types.Object.GetMethod("MemberwiseClone", BindingFlags.Instance | BindingFlags.NonPublic, [])); } internal override void EmitCallvirt(CodeEmitter ilgen) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs index 6d00693b27..ed2ff469c4 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs @@ -67,7 +67,7 @@ internal DelegateInnerClassJavaType(RuntimeContext context, string name, ITypeSy if (parameterType.IsByRef) { flags |= MemberFlags.DelegateInvokeWithByRefParameter; - parameterType = RuntimeArrayJavaType.MakeArrayType(parameterType.GetElementType(), 1); + parameterType = parameterType.GetElementType().MakeArrayType(1); } argTypeWrappers[i] = Context.ClassLoaderFactory.GetJavaTypeFromType(parameterType); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs index 9d5dc4e1ab..a3412f98ca 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs @@ -23,21 +23,12 @@ Jeroen Frijters */ using System; using System.Collections.Generic; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - #if IMPORTER using IKVM.Tools.Importer; #endif diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index 0eaac509bb..7d96814302 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -24,19 +24,12 @@ Jeroen Frijters using System; using System.Collections.Generic; using System.Diagnostics; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.Runtime { @@ -308,7 +301,7 @@ internal static RuntimeJavaType Create(RuntimeContext context, ITypeSymbol type, Debug.Assert(!type.IsByRef, type.FullName); Debug.Assert(!type.IsPointer, type.FullName); Debug.Assert(!type.Name.EndsWith("[]"), type.FullName); - Debug.Assert(type.AsReflection() is not TypeBuilder, type.FullName); + Debug.Assert(type is not ITypeSymbolBuilder, type.FullName); Debug.Assert(!Context.AttributeHelper.IsJavaModule(type.Module)); this.type = type; @@ -605,7 +598,11 @@ static bool IsPointerType(ITypeSymbol type) type = type.GetElementType(); } - return type.IsUnmanagedFunctionPointer; +#if IMPORTER || EXPORTER + return type.IsFunctionPointer; +#else + return false; +#endif } bool MakeMethodDescriptor(IMethodBaseSymbol mb, out string name, out string sig, out RuntimeJavaType[] args, out RuntimeJavaType ret) @@ -637,7 +634,7 @@ bool MakeMethodDescriptor(IMethodBaseSymbol mb, out string name, out string sig, if (type.IsByRef) { - type = RuntimeArrayJavaType.MakeArrayType(type.GetElementType(), 1); + type = type.GetElementType().MakeArrayType(1); if (mb.IsAbstract) { // Since we cannot override methods with byref arguments, we don't report abstract @@ -655,7 +652,7 @@ bool MakeMethodDescriptor(IMethodBaseSymbol mb, out string name, out string sig, sb.Append(tw.SigName); } sb.Append(')'); - if (mb is ConstructorInfo) + if (mb is IConstructorSymbol) { ret = Context.PrimitiveJavaTypeFactory.VOID; name = mb.IsStatic ? "" : ""; diff --git a/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs b/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs index 7c4e3cf260..4dc3d85bd0 100644 --- a/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs +++ b/src/IKVM.Runtime/RuntimeUnloadableJavaType.cs @@ -25,14 +25,6 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -#endif - #if IMPORTER using IKVM.Tools.Importer; #endif @@ -150,10 +142,10 @@ internal void SetCustomModifier(ITypeSymbol type) #if EMITTERS - internal Type GetCustomModifier(RuntimeJavaTypeFactory context) + internal ITypeSymbol GetCustomModifier(RuntimeJavaTypeFactory context) { // we don't need to lock, because we're only supposed to be called while holding the finish lock - return customModifier ?? (customModifier = context.DefineUnloadable(this.Name)); + return customModifier ??= context.DefineUnloadable(Name); } internal override void EmitCheckcast(CodeEmitter ilgen) diff --git a/src/IKVM.Runtime/Serialization.cs b/src/IKVM.Runtime/Serialization.cs index dc7142b5e1..c11630dbbf 100644 --- a/src/IKVM.Runtime/Serialization.cs +++ b/src/IKVM.Runtime/Serialization.cs @@ -24,20 +24,15 @@ Jeroen Frijters using System; using System.Runtime.Serialization; using System.Security; +using System.Reflection; +using System.Reflection.Emit; + using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; - - #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; #else -using System.Reflection; -using System.Reflection.Emit; #endif namespace IKVM.Runtime @@ -48,8 +43,8 @@ class Serialization readonly RuntimeContext context; - CustomAttributeBuilder serializableAttribute; - CustomAttributeBuilder securityCriticalAttribute; + ICustomAttributeBuilder serializableAttribute; + ICustomAttributeBuilder securityCriticalAttribute; RuntimeJavaType typeOfISerializable; RuntimeJavaType typeofIObjectreference; RuntimeJavaType typeOfExternalizable; @@ -63,13 +58,13 @@ public Serialization(RuntimeContext context) this.context = context ?? throw new ArgumentNullException(nameof(context)); } - CustomAttributeBuilder SerializableAttribute => serializableAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(SerializableAttribute).FullName).GetConstructor([]).AsReflection(), []); + ICustomAttributeBuilder SerializableAttribute => serializableAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(SerializableAttribute).FullName).GetConstructor([]), []); - CustomAttributeBuilder SecurityCriticalAttribute => securityCriticalAttribute ??= new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(SecurityCriticalAttribute).FullName).GetConstructor([]).AsReflection(), []); + ICustomAttributeBuilder SecurityCriticalAttribute => securityCriticalAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(SecurityCriticalAttribute).FullName).GetConstructor([]), []); - RuntimeJavaType TypeOfISerializable => typeOfISerializable ??= context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveCoreType(typeof(ISerializable).FullName).AsReflection()); + RuntimeJavaType TypeOfISerializable => typeOfISerializable ??= context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveCoreType(typeof(ISerializable).FullName)); - RuntimeJavaType TypeOfIObjectReference => typeofIObjectreference ??= context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).AsReflection()); + RuntimeJavaType TypeOfIObjectReference => typeofIObjectreference ??= context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName)); RuntimeJavaType TypeOfExternalizable => typeOfExternalizable ??= context.ClassLoaderFactory.LoadClassCritical("java.io.Externalizable"); @@ -153,7 +148,7 @@ internal IMethodSymbolBuilder AddAutomagicSerialization(RuntimeByteCodeJavaType return serializationCtor; } - internal IMethodSymbolBuilder AddAutomagicSerializationToWorkaroundBaseClass(ITypeSymbolBuilder typeBuilderWorkaroundBaseClass, MethodBase baseCtor) + internal IMethodSymbolBuilder AddAutomagicSerializationToWorkaroundBaseClass(ITypeSymbolBuilder typeBuilderWorkaroundBaseClass, IMethodBaseSymbol baseCtor) { if (typeBuilderWorkaroundBaseClass.BaseType.IsSerializable) { @@ -177,10 +172,10 @@ internal void AddGetObjectData(ITypeSymbolBuilder tb) ? MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final : MethodAttributes.Family | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.CheckAccessOnOverride; tb.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(ISerializable).FullName)); - var getObjectData = tb.DefineMethod(name, attr, null, new ITypeSymbol[] { context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection() }); + var getObjectData = tb.DefineMethod(name, attr, null, [context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName)]); getObjectData.SetCustomAttribute(SecurityCriticalAttribute); context.AttributeHelper.HideFromJava(getObjectData); - tb.DefineMethodOverride(getObjectData, context.Resolver.ResolveCoreType(typeof(ISerializable).FullName).GetMethod("GetObjectData").AsReflection()); + tb.DefineMethodOverride(getObjectData, context.Resolver.ResolveCoreType(typeof(ISerializable).FullName).GetMethod("GetObjectData")); var ilgen = context.CodeEmitterFactory.Create(getObjectData); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ldarg_1); @@ -194,9 +189,9 @@ internal void AddGetObjectData(ITypeSymbolBuilder tb) IMethodSymbolBuilder AddConstructor(ITypeSymbolBuilder tb, RuntimeJavaMethod defaultConstructor, IMethodBaseSymbol serializationConstructor, bool callReadObject) { - var ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Family, new ITypeSymbol[] { context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName).AsReflection(), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName).AsReflection() }); + var ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Family, [context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName)]); context.AttributeHelper.HideFromJava(ctor); - CodeEmitter ilgen = context.CodeEmitterFactory.Create(ctor); + var ilgen = context.CodeEmitterFactory.Create(ctor); ilgen.Emit(OpCodes.Ldarg_0); if (defaultConstructor != null) { @@ -227,11 +222,11 @@ void AddReadResolve(RuntimeByteCodeJavaType wrapper, ITypeSymbolBuilder tb) var mw = wrapper.GetMethodWrapper("readResolve", "()Ljava.lang.Object;", false); if (mw != null && !wrapper.IsSubTypeOf(TypeOfIObjectReference)) { - tb.AddInterfaceImplementation(wrapper.Context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).AsReflection()); - var getRealObject = tb.DefineMethod("IObjectReference.GetRealObject", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final, wrapper.Context.Types.Object, new ITypeSymbol[] { wrapper.Context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName) }); + tb.AddInterfaceImplementation(wrapper.Context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName)); + var getRealObject = tb.DefineMethod("IObjectReference.GetRealObject", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final, wrapper.Context.Types.Object, [wrapper.Context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName)]); getRealObject.SetCustomAttribute(SecurityCriticalAttribute); wrapper.Context.AttributeHelper.HideFromJava(getRealObject); - tb.DefineMethodOverride(getRealObject, wrapper.Context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).GetMethod("GetRealObject").AsReflection()); + tb.DefineMethodOverride(getRealObject, wrapper.Context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).GetMethod("GetRealObject")); var ilgen = context.CodeEmitterFactory.Create(getRealObject); mw.Link(); if (!wrapper.IsFinal) @@ -256,11 +251,11 @@ void AddReadResolve(RuntimeByteCodeJavaType wrapper, ITypeSymbolBuilder tb) void RemoveReadResolve(ITypeSymbolBuilder tb) { - tb.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).AsReflection()); + tb.AddInterfaceImplementation(context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName)); var getRealObject = tb.DefineMethod("IObjectReference.GetRealObject", MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.Final, context.Types.Object, [context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName)]); getRealObject.SetCustomAttribute(SecurityCriticalAttribute); context.AttributeHelper.HideFromJava(getRealObject); - tb.DefineMethodOverride(getRealObject, context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).GetMethod("GetRealObject").AsReflection()); + tb.DefineMethodOverride(getRealObject, context.Resolver.ResolveCoreType(typeof(IObjectReference).FullName).GetMethod("GetRealObject")); var ilgen = context.CodeEmitterFactory.Create(getRealObject); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ret); diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index 54e99b691a..c209e71e2f 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -25,6 +25,7 @@ Jeroen Frijters using System.Collections.Generic; using System.Diagnostics; using System.Diagnostics.SymbolStore; +using System.Reflection; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; @@ -33,11 +34,6 @@ Jeroen Frijters #if IMPORTER using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; #endif using ExceptionTableEntry = IKVM.Runtime.ClassFile.Method.ExceptionTableEntry; @@ -112,13 +108,13 @@ public CompilerFactory(RuntimeContext context, bool bootstrap) public RuntimeJavaType Throwable => context.JavaBase.TypeOfjavaLangThrowable; - public IMethodSymbol UnmapExceptionMethod => unmapExceptionMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", new ITypeSymbol[] { context.Types.Exception }); + public IMethodSymbol UnmapExceptionMethod => unmapExceptionMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", [context.Types.Exception]); - public IMethodSymbol FixateExceptionMethod => fixateExceptionMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", new ITypeSymbol[] { context.Types.Exception }); + public IMethodSymbol FixateExceptionMethod => fixateExceptionMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", [context.Types.Exception]); public IMethodSymbol SuppressFillInStackTraceMethod => suppressFillInStackTraceMethod ??= bootstrap ? (IMethodSymbol)Throwable.GetMethodWrapper("__", "()V", false).GetMethod() : Throwable.TypeAsBaseType.GetMethod("__", []); - public IMethodSymbol GetTypeFromHandleMethod => getTypeFromHandleMethod ??= context.Types.Type.GetMethod("GetTypeFromHandle", BindingFlags.Static | BindingFlags.Public, [context.Types.RuntimeTypeHandle]); + public IMethodSymbol GetTypeFromHandleMethod => getTypeFromHandleMethod ??= context.Types.Type.GetMethod("GetTypeFromHandle", BindingFlags.Static | BindingFlags.Public, [context.Types.RuntimeTypeHandle]); public IMethodSymbol GetTypeMethod => getTypeMethod ??= context.Types.Object.GetMethod("GetType", BindingFlags.Public | BindingFlags.Instance, []); @@ -192,7 +188,7 @@ sealed class Compiler { ilGenerator.EmitLdarg(i + (m.IsStatic ? 0 : 1)); EmitDynamicCast(args[i]); - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } } @@ -282,7 +278,7 @@ sealed class Compiler v.isArg = false; ilGenerator.EmitLdarg(arg); tw.EmitConvSignatureTypeToStackType(ilGenerator); - ilGenerator.Emit(OpCodes.Stloc, v.builder); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, v.builder); } } } @@ -342,7 +338,7 @@ private void Workaroundx64JitBug(RuntimeJavaType[] args) { // TODO prevent this from getting optimized away ilGenerator.EmitLdarga(i); - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } } } @@ -416,9 +412,9 @@ internal void EmitRet(CodeEmitter ilgen) ilgen.MarkLabel(stub); if (local != null) { - ilgen.Emit(OpCodes.Ldloc, local); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, local); } - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } } @@ -522,7 +518,7 @@ internal void Load(int i) switch (types[i]) { case StackType.Null: - compiler.ilGenerator.Emit(OpCodes.Ldnull); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldnull); break; case StackType.New: case StackType.FaultBlockException: @@ -530,10 +526,10 @@ internal void Load(int i) break; case StackType.This: case StackType.UnitializedThis: - compiler.ilGenerator.Emit(OpCodes.Ldarg_0); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); break; case StackType.Other: - compiler.ilGenerator.Emit(OpCodes.Ldloc, locals[i]); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, locals[i]); break; default: throw new InvalidOperationException(); @@ -547,14 +543,14 @@ internal void Store(int i) case StackType.Null: case StackType.This: case StackType.UnitializedThis: - compiler.ilGenerator.Emit(OpCodes.Pop); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); break; case StackType.New: case StackType.FaultBlockException: // objects aren't really there on the stack break; case StackType.Other: - compiler.ilGenerator.Emit(OpCodes.Stloc, locals[i]); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, locals[i]); break; default: throw new InvalidOperationException(); @@ -635,18 +631,18 @@ internal static void Compile(RuntimeByteCodeJavaType.FinishContext finish, Runti if (m.IsSynchronized && m.IsStatic) { clazz.EmitClassLiteral(ilGenerator); - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); CodeEmitterLocal monitor = ilGenerator.DeclareLocal(finish.Context.Types.Object); - ilGenerator.Emit(OpCodes.Stloc, monitor); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, monitor); ilGenerator.EmitMonitorEnter(); ilGenerator.BeginExceptionBlock(); var b = new Block(c, 0, int.MaxValue, -1, new List(), true); c.Compile(b, 0); b.Leave(); ilGenerator.BeginFinallyBlock(); - ilGenerator.Emit(OpCodes.Ldloc, monitor); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, monitor); ilGenerator.EmitMonitorExit(); - ilGenerator.Emit(OpCodes.Endfinally); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Endfinally); ilGenerator.EndExceptionBlock(); b.LeaveStubs(new Block(c, 0, int.MaxValue, -1, null, false)); } @@ -961,7 +957,8 @@ void Compile(Block block, int startIndex) exceptionTypeWrapper = classFile.GetConstantPoolClassType(exc.catchType); remap = exceptionTypeWrapper.IsUnloadable || !exceptionTypeWrapper.IsSubTypeOf(finish.Context.JavaBase.TypeOfCliSystemException); } - Type excType = exceptionTypeWrapper.TypeAsExceptionType; + + var excType = exceptionTypeWrapper.TypeAsExceptionType; bool mapSafe = !exceptionTypeWrapper.IsUnloadable && !exceptionTypeWrapper.IsMapUnsafeException && !exceptionTypeWrapper.IsRemapped; if (mapSafe) { @@ -971,12 +968,12 @@ void Compile(Block block, int startIndex) { ilGenerator.BeginCatchBlock(finish.Context.Types.Exception); } - BranchCookie bc = new BranchCookie(this, 1, exc.handlerIndex); + + var bc = new BranchCookie(this, 1, exc.handlerIndex); prevBlock.AddExitHack(bc); - Instruction handlerInstr = code[handlerIndex]; - bool unusedException = (handlerInstr.NormalizedOpCode == NormalizedByteCode.__pop || - (handlerInstr.NormalizedOpCode == NormalizedByteCode.__astore && - localVars.GetLocalVar(handlerIndex) == null)); + + var handlerInstr = code[handlerIndex]; + var unusedException = (handlerInstr.NormalizedOpCode == NormalizedByteCode.__pop || (handlerInstr.NormalizedOpCode == NormalizedByteCode.__astore && localVars.GetLocalVar(handlerIndex) == null)); int mapFlags = unusedException ? 2 : 0; if (mapSafe && unusedException) { @@ -985,12 +982,12 @@ void Compile(Block block, int startIndex) else if (mapSafe) { ilGenerator.EmitLdc_I4(mapFlags | 1); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(excType)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(excType)); } else if (exceptionTypeWrapper == finish.Context.JavaBase.TypeOfjavaLangThrowable) { ilGenerator.EmitLdc_I4(mapFlags); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(finish.Context.Types.Exception)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(finish.Context.Types.Exception)); } else { @@ -999,19 +996,21 @@ void Compile(Block block, int startIndex) { Profiler.Count("EmitDynamicExceptionHandler"); EmitDynamicClassLiteral(exceptionTypeWrapper); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicMapException); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicMapException); } else { - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(excType)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(excType)); } + if (!unusedException) { - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); } - CodeEmitterLabel leave = ilGenerator.DefineLabel(); + + var leave = ilGenerator.DefineLabel(); ilGenerator.EmitBrtrue(leave); - ilGenerator.Emit(OpCodes.Rethrow); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Rethrow); ilGenerator.MarkLabel(leave); } if (unusedException) @@ -1118,23 +1117,23 @@ void Compile(Block block, int startIndex) switch (ByteCodeMetaData.GetFlowControl(instr.NormalizedOpCode)) { case ByteCodeFlowControl.Return: - ilGenerator.Emit(OpCodes.Ldarg_0); - ilGenerator.Emit(OpCodes.Call, finish.Context.CompilerFactory.KeepAliveMethod); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.CompilerFactory.KeepAliveMethod); break; case ByteCodeFlowControl.Branch: case ByteCodeFlowControl.CondBranch: if (instr.TargetIndex <= i) { - ilGenerator.Emit(OpCodes.Ldarg_0); - ilGenerator.Emit(OpCodes.Call, finish.Context.CompilerFactory.KeepAliveMethod); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.CompilerFactory.KeepAliveMethod); } break; case ByteCodeFlowControl.Throw: case ByteCodeFlowControl.Switch: if (ma.GetLocalTypeWrapper(i, 0) != finish.Context.VerifierJavaTypeFactory.UninitializedThis) { - ilGenerator.Emit(OpCodes.Ldarg_0); - ilGenerator.Emit(OpCodes.Call, finish.Context.CompilerFactory.KeepAliveMethod); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.CompilerFactory.KeepAliveMethod); } break; } @@ -1155,8 +1154,8 @@ void Compile(Block block, int startIndex) } case NormalizedByteCode.__getfield: { - ClassFile.ConstantPoolItemFieldref cpi = classFile.GetFieldref(instr.Arg1); - RuntimeJavaField field = cpi.GetField(); + var cpi = classFile.GetFieldref(instr.Arg1); + var field = cpi.GetField(); if (ma.GetStackTypeWrapper(i, 0).IsUnloadable) { if (field.IsProtected) @@ -1179,8 +1178,9 @@ void Compile(Block block, int startIndex) var cpi = classFile.GetFieldref(instr.Arg1); if (cpi.GetClassType() != clazz) nonleaf = true; // we may trigger a static initializer, which is equivalent to a call - RuntimeJavaField field = cpi.GetField(); - RuntimeJavaType tw = field.FieldTypeWrapper; + + var field = cpi.GetField(); + var tw = field.FieldTypeWrapper; tw.EmitConvStackTypeToSignatureType(ilGenerator, ma.GetStackTypeWrapper(i, 0)); if (strictfp) { @@ -1188,20 +1188,20 @@ void Compile(Block block, int startIndex) } else if (tw == finish.Context.PrimitiveJavaTypeFactory.DOUBLE) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } field.EmitSet(ilGenerator); break; } case NormalizedByteCode.__putfield: { - ClassFile.ConstantPoolItemFieldref cpi = classFile.GetFieldref(instr.Arg1); - RuntimeJavaField field = cpi.GetField(); - RuntimeJavaType tw = field.FieldTypeWrapper; + var cpi = classFile.GetFieldref(instr.Arg1); + var field = cpi.GetField(); + var tw = field.FieldTypeWrapper; if (ma.GetStackTypeWrapper(i, 1).IsUnloadable) { CodeEmitterLocal temp = ilGenerator.UnsafeAllocTempLocal(tw.TypeAsLocalOrStackType); - ilGenerator.Emit(OpCodes.Stloc, temp); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, temp); if (field.IsProtected) { // downcast receiver to our type @@ -1212,7 +1212,7 @@ void Compile(Block block, int startIndex) // downcast receiver to field declaring type field.DeclaringType.EmitCheckcast(ilGenerator); } - ilGenerator.Emit(OpCodes.Ldloc, temp); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, temp); } tw.EmitConvStackTypeToSignatureType(ilGenerator, ma.GetStackTypeWrapper(i, 0)); if (strictfp) @@ -1221,7 +1221,7 @@ void Compile(Block block, int startIndex) } else if (tw == finish.Context.PrimitiveJavaTypeFactory.DOUBLE) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } field.EmitSet(ilGenerator); break; @@ -1234,7 +1234,7 @@ void Compile(Block block, int startIndex) DynamicGetPutField(instr, i); break; case NormalizedByteCode.__aconst_null: - ilGenerator.Emit(OpCodes.Ldnull); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldnull); break; case NormalizedByteCode.__iconst: ilGenerator.EmitLdc_I4(instr.NormalizedArg1); @@ -1310,7 +1310,7 @@ void Compile(Block block, int startIndex) var method = GetMethodCallEmitter(instr.NormalizedOpCode, instr.Arg1); var argcount = method.GetParameters().Length; var type = ma.GetRawStackTypeWrapper(i, argcount); - RuntimeJavaType thisType = ComputeThisType(type, method, instr.NormalizedOpCode); + var thisType = ComputeThisType(type, method, instr.NormalizedOpCode); var eic = new EmitIntrinsicContext(method, finish, ilGenerator, ma, i, mw, classFile, code, flags); if (method.IsIntrinsic && method.EmitIntrinsic(eic)) @@ -1405,7 +1405,7 @@ void Compile(Block block, int startIndex) if (code[i + 1].NormalizedOpCode == NormalizedByteCode.__athrow) { if (thisType.GetMethodWrapper("fillInStackTrace", "()Ljava.lang.Throwable;", true).DeclaringType == finish.Context.JavaBase.TypeOfjavaLangThrowable) - ilGenerator.Emit(OpCodes.Call, finish.Context.CompilerFactory.SuppressFillInStackTraceMethod); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.CompilerFactory.SuppressFillInStackTraceMethod); if ((flags[i + 1] & InstructionFlags.BranchTarget) == 0) code[i + 1].PatchOpCode(NormalizedByteCode.__athrow_no_unmap); } @@ -1415,7 +1415,7 @@ void Compile(Block block, int startIndex) if (!thisType.IsUnloadable && thisType.IsSubTypeOf(finish.Context.JavaBase.TypeOfCliSystemException)) { // we call Throwable.__() to disable remapping the exception - ilGenerator.Emit(OpCodes.Call, finish.Context.CompilerFactory.FixateExceptionMethod); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.CompilerFactory.FixateExceptionMethod); } if (nontrivial) @@ -1424,7 +1424,7 @@ void Compile(Block block, int startIndex) // code never runs (for code compiled from Java source) it doesn't // really matter var newobj = ilGenerator.DeclareLocal(GetLocalBuilderType(thisType)); - ilGenerator.Emit(OpCodes.Stloc, newobj); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, newobj); var tempstack = new CodeEmitterLocal[stackfix.Length]; for (int j = 0; j < stackfix.Length; j++) { @@ -1437,12 +1437,12 @@ void Compile(Block block, int startIndex) { // NOTE we abuse the newobj local as a cookie to signal null! tempstack[j] = newobj; - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } else if (!RuntimeVerifierJavaType.IsNotPresentOnStack(stacktype)) { var lb = ilGenerator.DeclareLocal(GetLocalBuilderType(stacktype)); - ilGenerator.Emit(OpCodes.Stloc, lb); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, lb); tempstack[j] = lb; } } @@ -1452,15 +1452,15 @@ void Compile(Block block, int startIndex) { if (stackfix[j]) { - ilGenerator.Emit(OpCodes.Ldloc, newobj); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, newobj); } else if (tempstack[j] != null) { // NOTE we abuse the newobj local as a cookie to signal null! if (tempstack[j] == newobj) - ilGenerator.Emit(OpCodes.Ldnull); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldnull); else - ilGenerator.Emit(OpCodes.Ldloc, tempstack[j]); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, tempstack[j]); } } @@ -1474,8 +1474,8 @@ void Compile(Block block, int startIndex) // for invokespecial the resulting type can never be null locals[j].builder = ilGenerator.DeclareLocal(GetLocalBuilderType(locals[j].type)); } - ilGenerator.Emit(OpCodes.Ldloc, newobj); - ilGenerator.Emit(OpCodes.Stloc, locals[j].builder); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, newobj); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, locals[j].builder); } } } @@ -1483,13 +1483,13 @@ void Compile(Block block, int startIndex) { if (trivcount == 0) { - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } else { for (int j = 1; j < trivcount; j++) { - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); } } } @@ -1508,8 +1508,8 @@ void Compile(Block block, int startIndex) // for invokespecial the resulting type can never be null locals[j].builder = ilGenerator.DeclareLocal(GetLocalBuilderType(locals[j].type)); } - ilGenerator.Emit(OpCodes.Ldarg_0); - ilGenerator.Emit(OpCodes.Stloc, locals[j].builder); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, locals[j].builder); } } } @@ -1536,7 +1536,7 @@ void Compile(Block block, int startIndex) } else { - ilGenerator.Emit(OpCodes.Callvirt, finish.GetInvokeSpecialStub(method)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Callvirt, finish.GetInvokeSpecialStub(method)); } } else @@ -1565,7 +1565,7 @@ void Compile(Block block, int startIndex) break; } case NormalizedByteCode.__clone_array: - ilGenerator.Emit(OpCodes.Callvirt, RuntimeArrayJavaType.GetCloneMethod(finish.Context)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Callvirt, RuntimeArrayJavaType.GetCloneMethod(finish.Context)); break; case NormalizedByteCode.__return: case NormalizedByteCode.__areturn: @@ -1583,7 +1583,7 @@ void Compile(Block block, int startIndex) var retTypeWrapper = mw.ReturnType; retTypeWrapper.EmitConvStackTypeToSignatureType(ilGenerator, ma.GetStackTypeWrapper(i, 0)); local = ilGenerator.UnsafeAllocTempLocal(retTypeWrapper.TypeAsSignatureType); - ilGenerator.Emit(OpCodes.Stloc, local); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, local); } var label = ilGenerator.DefineLabel(); @@ -1623,7 +1623,7 @@ void Compile(Block block, int startIndex) if (stackHeight != 0 || x64hack) ilGenerator.EmitClearStack(); - ilGenerator.Emit(OpCodes.Ret); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ret); } else { @@ -1632,9 +1632,9 @@ void Compile(Block block, int startIndex) if (stackHeight != 1) { var local = ilGenerator.AllocTempLocal(retTypeWrapper.TypeAsSignatureType); - ilGenerator.Emit(OpCodes.Stloc, local); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, local); ilGenerator.EmitClearStack(); - ilGenerator.Emit(OpCodes.Ldloc, local); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, local); ilGenerator.ReleaseTempLocal(local); } else if (x64hack) @@ -1642,7 +1642,7 @@ void Compile(Block block, int startIndex) ilGenerator.EmitTailCallPrevention(); } - ilGenerator.Emit(OpCodes.Ret); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ret); } } break; @@ -1653,7 +1653,7 @@ void Compile(Block block, int startIndex) if (type == finish.Context.VerifierJavaTypeFactory.Null) { // if the local is known to be null, we just emit a null - ilGenerator.Emit(OpCodes.Ldnull); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldnull); } else if (RuntimeVerifierJavaType.IsNotPresentOnStack(type)) { @@ -1661,7 +1661,7 @@ void Compile(Block block, int startIndex) } else if (RuntimeVerifierJavaType.IsThis(type)) { - ilGenerator.Emit(OpCodes.Ldarg_0); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); } else if (type == finish.Context.VerifierJavaTypeFactory.UninitializedThis) { @@ -1669,7 +1669,7 @@ void Compile(Block block, int startIndex) // NOTE if the method overwrites the this references, it will always end up in // a different local (due to the way the local variable liveness analysis works), // so we don't have to worry about that. - ilGenerator.Emit(OpCodes.Ldarg_0); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); } else { @@ -1693,7 +1693,7 @@ void Compile(Block block, int startIndex) // any unitialized reference is always the this reference, we don't store anything // here (because CLR won't allow unitialized references in locals) and then when // the unitialized ref is loaded we redirect to the this reference - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } else { @@ -1717,7 +1717,7 @@ void Compile(Block block, int startIndex) case NormalizedByteCode.__dstore: if (ma.IsStackTypeExtendedDouble(i, 0)) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } StoreLocal(i); break; @@ -1730,7 +1730,7 @@ void Compile(Block block, int startIndex) // this is here to make sure we throw the exception in the right location (before // evaluating the constructor arguments) EmitDynamicClassLiteral(wrapper); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicNewCheckOnly); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicNewCheckOnly); } else if (wrapper != clazz && RequiresExplicitClassInit(wrapper, i + 1, flags)) { @@ -1743,26 +1743,26 @@ void Compile(Block block, int startIndex) } case NormalizedByteCode.__multianewarray: { - var localArray = ilGenerator.UnsafeAllocTempLocal(finish.Context.Resolver.ResolveCoreType(typeof(int).FullName).MakeArrayType().AsReflection()); + var localArray = ilGenerator.UnsafeAllocTempLocal(finish.Context.Resolver.ResolveCoreType(typeof(int).FullName).MakeArrayType()); var localInt = ilGenerator.UnsafeAllocTempLocal(finish.Context.Types.Int32); ilGenerator.EmitLdc_I4(instr.Arg2); - ilGenerator.Emit(OpCodes.Newarr, finish.Context.Types.Int32); - ilGenerator.Emit(OpCodes.Stloc, localArray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.Types.Int32); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, localArray); for (int j = 1; j <= instr.Arg2; j++) { - ilGenerator.Emit(OpCodes.Stloc, localInt); - ilGenerator.Emit(OpCodes.Ldloc, localArray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, localInt); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, localArray); ilGenerator.EmitLdc_I4(instr.Arg2 - j); - ilGenerator.Emit(OpCodes.Ldloc, localInt); - ilGenerator.Emit(OpCodes.Stelem_I4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, localInt); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_I4); } var wrapper = classFile.GetConstantPoolClassType(instr.Arg1); if (wrapper.IsUnloadable) { Profiler.Count("EmitDynamicMultianewarray"); - ilGenerator.Emit(OpCodes.Ldloc, localArray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, localArray); EmitDynamicClassLiteral(wrapper); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicMultianewarray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicMultianewarray); } else if (wrapper.IsGhost || wrapper.IsGhostArray) { @@ -1770,18 +1770,18 @@ void Compile(Block block, int startIndex) while (tw.IsArray) tw = tw.ElementTypeWrapper; - ilGenerator.Emit(OpCodes.Ldtoken, RuntimeArrayJavaType.MakeArrayType(tw.TypeAsTBD, wrapper.ArrayRank)); - ilGenerator.Emit(OpCodes.Ldloc, localArray); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.multianewarray_ghost); - ilGenerator.Emit(OpCodes.Castclass, wrapper.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, tw.TypeAsTBD.MakeArrayType(wrapper.ArrayRank)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, localArray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.multianewarray_ghost); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, wrapper.TypeAsArrayType); } else { - Type type = wrapper.TypeAsArrayType; - ilGenerator.Emit(OpCodes.Ldtoken, type); - ilGenerator.Emit(OpCodes.Ldloc, localArray); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.multianewarray); - ilGenerator.Emit(OpCodes.Castclass, type); + var type = wrapper.TypeAsArrayType; + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, type); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, localArray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.multianewarray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, type); } break; } @@ -1792,7 +1792,7 @@ void Compile(Block block, int startIndex) { Profiler.Count("EmitDynamicNewarray"); EmitDynamicClassLiteral(wrapper); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicNewarray); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicNewarray); } else if (wrapper.IsGhost || wrapper.IsGhostArray) { @@ -1810,12 +1810,12 @@ void Compile(Block block, int startIndex) while (tw.IsArray) tw = tw.ElementTypeWrapper; - ilGenerator.Emit(OpCodes.Ldtoken, RuntimeArrayJavaType.MakeArrayType(tw.TypeAsTBD, wrapper.ArrayRank + 1)); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.anewarray_ghost.MakeGenericMethod(wrapper.TypeAsArrayType)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, tw.TypeAsTBD.MakeArrayType(wrapper.ArrayRank + 1)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.anewarray_ghost.MakeGenericMethod(wrapper.TypeAsArrayType)); } else { - ilGenerator.Emit(OpCodes.Newarr, wrapper.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, wrapper.TypeAsArrayType); } break; @@ -1824,28 +1824,28 @@ void Compile(Block block, int startIndex) switch (instr.Arg1) { case 4: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.BOOLEAN.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.BOOLEAN.TypeAsArrayType); break; case 5: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.CHAR.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.CHAR.TypeAsArrayType); break; case 6: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.FLOAT.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.FLOAT.TypeAsArrayType); break; case 7: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.DOUBLE.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.DOUBLE.TypeAsArrayType); break; case 8: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.BYTE.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.BYTE.TypeAsArrayType); break; case 9: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.SHORT.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.SHORT.TypeAsArrayType); break; case 10: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.INT.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.INT.TypeAsArrayType); break; case 11: - ilGenerator.Emit(OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.LONG.TypeAsArrayType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.PrimitiveJavaTypeFactory.LONG.TypeAsArrayType); break; default: // this can't happen, the verifier would have caught it @@ -1878,7 +1878,7 @@ void Compile(Block block, int startIndex) if (tw.IsUnloadable) { Profiler.Count("EmitDynamicAaload"); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicAaload); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicAaload); } else { @@ -1886,13 +1886,13 @@ void Compile(Block block, int startIndex) if (elem.IsNonPrimitiveValueType) { var t = elem.TypeAsTBD; - ilGenerator.Emit(OpCodes.Ldelema, t); - ilGenerator.Emit(OpCodes.Ldobj, t); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelema, t); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldobj, t); elem.EmitBox(ilGenerator); } else { - ilGenerator.Emit(OpCodes.Ldelem_Ref); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_Ref); } } @@ -1900,48 +1900,48 @@ void Compile(Block block, int startIndex) } case NormalizedByteCode.__baload: // NOTE both the JVM and the CLR use signed bytes for boolean arrays (how convenient!) - ilGenerator.Emit(OpCodes.Ldelem_I1); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_I1); break; case NormalizedByteCode.__bastore: - ilGenerator.Emit(OpCodes.Stelem_I1); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_I1); break; case NormalizedByteCode.__caload: - ilGenerator.Emit(OpCodes.Ldelem_U2); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_U2); break; case NormalizedByteCode.__castore: - ilGenerator.Emit(OpCodes.Stelem_I2); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_I2); break; case NormalizedByteCode.__saload: - ilGenerator.Emit(OpCodes.Ldelem_I2); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_I2); break; case NormalizedByteCode.__sastore: - ilGenerator.Emit(OpCodes.Stelem_I2); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_I2); break; case NormalizedByteCode.__iaload: - ilGenerator.Emit(OpCodes.Ldelem_I4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_I4); break; case NormalizedByteCode.__iastore: - ilGenerator.Emit(OpCodes.Stelem_I4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_I4); break; case NormalizedByteCode.__laload: - ilGenerator.Emit(OpCodes.Ldelem_I8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_I8); break; case NormalizedByteCode.__lastore: - ilGenerator.Emit(OpCodes.Stelem_I8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_I8); break; case NormalizedByteCode.__faload: - ilGenerator.Emit(OpCodes.Ldelem_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_R4); break; case NormalizedByteCode.__fastore: - ilGenerator.Emit(OpCodes.Stelem_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_R4); break; case NormalizedByteCode.__daload: - ilGenerator.Emit(OpCodes.Ldelem_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelem_R8); break; case NormalizedByteCode.__dastore: if (ma.IsStackTypeExtendedDouble(i, 0)) - ilGenerator.Emit(OpCodes.Conv_R8); - ilGenerator.Emit(OpCodes.Stelem_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_R8); break; case NormalizedByteCode.__aastore: { @@ -1949,7 +1949,7 @@ void Compile(Block block, int startIndex) if (tw.IsUnloadable) { Profiler.Count("EmitDynamicAastore"); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicAastore); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicAastore); } else { @@ -1958,18 +1958,18 @@ void Compile(Block block, int startIndex) { var t = elem.TypeAsTBD; var local = ilGenerator.UnsafeAllocTempLocal(finish.Context.Types.Object); - ilGenerator.Emit(OpCodes.Stloc, local); - ilGenerator.Emit(OpCodes.Ldelema, t); - ilGenerator.Emit(OpCodes.Ldloc, local); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, local); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldelema, t); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, local); elem.EmitUnbox(ilGenerator); - ilGenerator.Emit(OpCodes.Stobj, t); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stobj, t); } else { // NOTE for verifiability it is expressly *not* required that the // value matches the array type, so we don't need to handle interface // references here. - ilGenerator.Emit(OpCodes.Stelem_Ref); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stelem_Ref); } } @@ -1978,12 +1978,12 @@ void Compile(Block block, int startIndex) case NormalizedByteCode.__arraylength: if (ma.GetRawStackTypeWrapper(i, 0).IsUnloadable) { - ilGenerator.Emit(OpCodes.Castclass, finish.Context.Types.Array); - ilGenerator.Emit(OpCodes.Callvirt, finish.Context.Types.Array.GetMethod("get_Length")); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, finish.Context.Types.Array); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Callvirt, finish.Context.Types.Array.GetMethod("get_Length")); } else { - ilGenerator.Emit(OpCodes.Ldlen); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldlen); } break; case NormalizedByteCode.__lcmp: @@ -2053,63 +2053,63 @@ void Compile(Block block, int startIndex) case NormalizedByteCode.__lneg: case NormalizedByteCode.__fneg: case NormalizedByteCode.__dneg: - ilGenerator.Emit(OpCodes.Neg); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Neg); break; case NormalizedByteCode.__iadd: case NormalizedByteCode.__ladd: - ilGenerator.Emit(OpCodes.Add); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Add); break; case NormalizedByteCode.__fadd: - ilGenerator.Emit(OpCodes.Add); - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Add); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); break; case NormalizedByteCode.__dadd: - ilGenerator.Emit(OpCodes.Add); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Add); if (strictfp) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } break; case NormalizedByteCode.__isub: case NormalizedByteCode.__lsub: - ilGenerator.Emit(OpCodes.Sub); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Sub); break; case NormalizedByteCode.__fsub: - ilGenerator.Emit(OpCodes.Sub); - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Sub); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); break; case NormalizedByteCode.__dsub: - ilGenerator.Emit(OpCodes.Sub); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Sub); if (strictfp) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } break; case NormalizedByteCode.__ixor: case NormalizedByteCode.__lxor: - ilGenerator.Emit(OpCodes.Xor); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Xor); break; case NormalizedByteCode.__ior: case NormalizedByteCode.__lor: - ilGenerator.Emit(OpCodes.Or); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Or); break; case NormalizedByteCode.__iand: case NormalizedByteCode.__land: - ilGenerator.Emit(OpCodes.And); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.And); break; case NormalizedByteCode.__imul: case NormalizedByteCode.__lmul: - ilGenerator.Emit(OpCodes.Mul); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Mul); break; case NormalizedByteCode.__fmul: - ilGenerator.Emit(OpCodes.Mul); - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Mul); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); break; case NormalizedByteCode.__dmul: - ilGenerator.Emit(OpCodes.Mul); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Mul); if (strictfp) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } break; case NormalizedByteCode.__idiv: @@ -2119,14 +2119,14 @@ void Compile(Block block, int startIndex) ilGenerator.Emit_ldiv(); break; case NormalizedByteCode.__fdiv: - ilGenerator.Emit(OpCodes.Div); - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Div); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); break; case NormalizedByteCode.__ddiv: - ilGenerator.Emit(OpCodes.Div); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Div); if (strictfp) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } break; case NormalizedByteCode.__irem: @@ -2136,58 +2136,58 @@ void Compile(Block block, int startIndex) // because the CLR rem instruction throws an OverflowException when // taking the remainder of dividing Int32.MinValue by -1, and // Java just silently overflows - ilGenerator.Emit(OpCodes.Dup); - ilGenerator.Emit(OpCodes.Ldc_I4_M1); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldc_I4_M1); if (instr.NormalizedOpCode == NormalizedByteCode.__lrem) - ilGenerator.Emit(OpCodes.Conv_I8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_I8); var label = ilGenerator.DefineLabel(); ilGenerator.EmitBne_Un(label); - ilGenerator.Emit(OpCodes.Pop); - ilGenerator.Emit(OpCodes.Pop); - ilGenerator.Emit(OpCodes.Ldc_I4_0); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldc_I4_0); if (instr.NormalizedOpCode == NormalizedByteCode.__lrem) { - ilGenerator.Emit(OpCodes.Conv_I8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_I8); } var label2 = ilGenerator.DefineLabel(); ilGenerator.EmitBr(label2); ilGenerator.MarkLabel(label); - ilGenerator.Emit(OpCodes.Rem); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Rem); ilGenerator.MarkLabel(label2); break; } case NormalizedByteCode.__frem: - ilGenerator.Emit(OpCodes.Rem); - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Rem); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); break; case NormalizedByteCode.__drem: - ilGenerator.Emit(OpCodes.Rem); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Rem); if (strictfp) - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); break; case NormalizedByteCode.__ishl: ilGenerator.Emit_And_I4(31); - ilGenerator.Emit(OpCodes.Shl); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Shl); break; case NormalizedByteCode.__lshl: ilGenerator.Emit_And_I4(63); - ilGenerator.Emit(OpCodes.Shl); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Shl); break; case NormalizedByteCode.__iushr: ilGenerator.Emit_And_I4(31); - ilGenerator.Emit(OpCodes.Shr_Un); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Shr_Un); break; case NormalizedByteCode.__lushr: ilGenerator.Emit_And_I4(63); - ilGenerator.Emit(OpCodes.Shr_Un); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Shr_Un); break; case NormalizedByteCode.__ishr: ilGenerator.Emit_And_I4(31); - ilGenerator.Emit(OpCodes.Shr); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Shr); break; case NormalizedByteCode.__lshr: ilGenerator.Emit_And_I4(63); - ilGenerator.Emit(OpCodes.Shr); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Shr); break; case NormalizedByteCode.__swap: { @@ -2204,7 +2204,7 @@ void Compile(Block block, int startIndex) case NormalizedByteCode.__dup: // if the TOS contains a "new" object or a fault block exception, it isn't really there, so we don't dup it if (!RuntimeVerifierJavaType.IsNotPresentOnStack(ma.GetRawStackTypeWrapper(i, 0))) - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); break; case NormalizedByteCode.__dup2: @@ -2212,7 +2212,7 @@ void Compile(Block block, int startIndex) var type1 = ma.GetRawStackTypeWrapper(i, 0); if (type1.IsWidePrimitive) { - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); } else { @@ -2393,14 +2393,14 @@ void Compile(Block block, int startIndex) var type1 = ma.GetRawStackTypeWrapper(i, 0); if (type1.IsWidePrimitive) { - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } else { if (!RuntimeVerifierJavaType.IsNotPresentOnStack(type1)) - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); if (!RuntimeVerifierJavaType.IsNotPresentOnStack(ma.GetRawStackTypeWrapper(i, 1))) - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } break; } @@ -2408,7 +2408,7 @@ void Compile(Block block, int startIndex) // if the TOS is a new object or a fault block exception, it isn't really there, so we don't need to pop it if (!RuntimeVerifierJavaType.IsNotPresentOnStack(ma.GetRawStackTypeWrapper(i, 0))) { - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } break; case NormalizedByteCode.__monitorenter: @@ -2420,23 +2420,23 @@ void Compile(Block block, int startIndex) case NormalizedByteCode.__athrow_no_unmap: if (ma.GetRawStackTypeWrapper(i, 0).IsUnloadable) { - ilGenerator.Emit(OpCodes.Castclass, finish.Context.Types.Exception); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, finish.Context.Types.Exception); } - ilGenerator.Emit(OpCodes.Throw); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Throw); break; case NormalizedByteCode.__athrow: if (RuntimeVerifierJavaType.IsFaultBlockException(ma.GetRawStackTypeWrapper(i, 0))) { - ilGenerator.Emit(OpCodes.Endfinally); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Endfinally); } else { if (ma.GetRawStackTypeWrapper(i, 0).IsUnloadable) { - ilGenerator.Emit(OpCodes.Castclass, finish.Context.Types.Exception); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, finish.Context.Types.Exception); } - ilGenerator.Emit(OpCodes.Call, finish.Context.CompilerFactory.UnmapExceptionMethod); - ilGenerator.Emit(OpCodes.Throw); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.CompilerFactory.UnmapExceptionMethod); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Throw); } break; case NormalizedByteCode.__tableswitch: @@ -2451,7 +2451,7 @@ void Compile(Block block, int startIndex) if (instr.GetSwitchValue(0) != 0) { ilGenerator.EmitLdc_I4(instr.GetSwitchValue(0)); - ilGenerator.Emit(OpCodes.Sub); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Sub); } ilGenerator.EmitSwitch(labels); ilGenerator.EmitBr(block.GetLabel(instr.DefaultTarget)); @@ -2460,65 +2460,65 @@ void Compile(Block block, int startIndex) case NormalizedByteCode.__lookupswitch: for (int j = 0; j < instr.SwitchEntryCount; j++) { - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); ilGenerator.EmitLdc_I4(instr.GetSwitchValue(j)); CodeEmitterLabel label = ilGenerator.DefineLabel(); ilGenerator.EmitBne_Un(label); - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); ilGenerator.EmitBr(block.GetLabel(instr.GetSwitchTargetIndex(j))); ilGenerator.MarkLabel(label); } - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); ilGenerator.EmitBr(block.GetLabel(instr.DefaultTarget)); break; case NormalizedByteCode.__iinc: LoadLocal(i); ilGenerator.EmitLdc_I4(instr.Arg2); - ilGenerator.Emit(OpCodes.Add); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Add); StoreLocal(i); break; case NormalizedByteCode.__i2b: - ilGenerator.Emit(OpCodes.Conv_I1); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_I1); break; case NormalizedByteCode.__i2c: - ilGenerator.Emit(OpCodes.Conv_U2); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_U2); break; case NormalizedByteCode.__i2s: - ilGenerator.Emit(OpCodes.Conv_I2); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_I2); break; case NormalizedByteCode.__l2i: - ilGenerator.Emit(OpCodes.Conv_I4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_I4); break; case NormalizedByteCode.__f2i: - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.f2i); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.f2i); break; case NormalizedByteCode.__d2i: - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.d2i); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.d2i); break; case NormalizedByteCode.__f2l: - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.f2l); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.f2l); break; case NormalizedByteCode.__d2l: - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.d2l); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.d2l); break; case NormalizedByteCode.__i2l: - ilGenerator.Emit(OpCodes.Conv_I8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_I8); break; case NormalizedByteCode.__i2f: case NormalizedByteCode.__l2f: case NormalizedByteCode.__d2f: - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); break; case NormalizedByteCode.__i2d: case NormalizedByteCode.__l2d: case NormalizedByteCode.__f2d: - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); break; case NormalizedByteCode.__nop: - ilGenerator.Emit(OpCodes.Nop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Nop); break; case NormalizedByteCode.__intrinsic_gettype: - ilGenerator.Emit(OpCodes.Callvirt, finish.Context.CompilerFactory.GetTypeMethod); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Callvirt, finish.Context.CompilerFactory.GetTypeMethod); break; case NormalizedByteCode.__static_error: { @@ -2564,7 +2564,7 @@ void Compile(Block block, int startIndex) var message = harderrors[instr.HardErrorMessageId]; clazz.ClassLoader.Diagnostics.GenericCompilerError($"{exceptionType.Name}: {message}\n\tat {classFile.Name}.{m.Name}{m.Signature}"); - ilGenerator.Emit(OpCodes.Ldstr, message); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldstr, message); RuntimeJavaMethod method = exceptionType.GetMethodWrapper("", "(Ljava.lang.String;)V", false); method.Link(); method.EmitNewobj(ilGenerator); @@ -2572,7 +2572,7 @@ void Compile(Block block, int startIndex) { finish.Context.JavaBase.TypeOfjavaLangThrowable.GetMethodWrapper("initCause", "(Ljava.lang.Throwable;)Ljava.lang.Throwable;", false).EmitCallvirt(ilGenerator); } - ilGenerator.Emit(OpCodes.Throw); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Throw); break; } default: @@ -2614,11 +2614,11 @@ void EmitReturnTypeConversion(RuntimeJavaType returnType) } else if (returnType == finish.Context.PrimitiveJavaTypeFactory.DOUBLE) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } else if (returnType == finish.Context.PrimitiveJavaTypeFactory.FLOAT) { - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); } } @@ -2639,7 +2639,7 @@ void EmitLoadConstant(CodeEmitter ilgen, ConstantHandle constant) ilgen.EmitLdc_I8(classFile.GetConstantPoolConstantLong((LongConstantHandle)constant)); break; case ClassFile.ConstantType.String: - ilgen.Emit(OpCodes.Ldstr, classFile.GetConstantPoolConstantString((StringConstantHandle)constant)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, classFile.GetConstantPoolConstantString((StringConstantHandle)constant)); break; case ClassFile.ConstantType.Class: EmitLoadClass(ilgen, classFile.GetConstantPoolClassType((ClassConstantHandle)constant)); @@ -2667,10 +2667,10 @@ private void EmitDynamicCast(RuntimeJavaType tw) // NOTE it's important that we don't try to load the class if obj == null var ok = ilGenerator.DefineLabel(); - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); ilGenerator.EmitBrfalse(ok); EmitDynamicClassLiteral(tw); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicCast); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicCast); ilGenerator.MarkLabel(ok); } @@ -2679,14 +2679,14 @@ void EmitDynamicInstanceOf(RuntimeJavaType tw) // NOTE it's important that we don't try to load the class if obj == null var notnull = ilGenerator.DefineLabel(); var end = ilGenerator.DefineLabel(); - ilGenerator.Emit(OpCodes.Dup); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Dup); ilGenerator.EmitBrtrue(notnull); - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); ilGenerator.EmitLdc_I4(0); ilGenerator.EmitBr(end); ilGenerator.MarkLabel(notnull); EmitDynamicClassLiteral(tw); - ilGenerator.Emit(OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicInstanceOf); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.DynamicInstanceOf); ilGenerator.MarkLabel(end); } @@ -2723,7 +2723,7 @@ static class InvokeDynamicBuilder internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDynamic cpi, ITypeSymbol delegateType) { - var typeofOpenIndyCallSite = compiler.finish.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.IndyCallSite`1").AsReflection(); + var typeofOpenIndyCallSite = compiler.finish.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.IndyCallSite`1"); var methodLookup = compiler.finish.Context.ClassLoaderFactory.LoadClassCritical("java.lang.invoke.MethodHandles").GetMethodWrapper("lookup", "()Ljava.lang.invoke.MethodHandles$Lookup;", false); methodLookup.Link(); @@ -2732,8 +2732,8 @@ internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDyn IMethodSymbol methodGetTarget; if (ReflectUtil.ContainsTypeBuilder(typeofIndyCallSite)) { - methodCreateBootStrap = ITypeSymbolBuilder.GetMethod(typeofIndyCallSite, typeofOpenIndyCallSite.GetMethod("CreateBootstrap")); - methodGetTarget = ITypeSymbolBuilder.GetMethod(typeofIndyCallSite, typeofOpenIndyCallSite.GetMethod("GetTarget")); + methodCreateBootStrap = typeofOpenIndyCallSite.GetMethod("CreateBootstrap"); + methodGetTarget = typeofOpenIndyCallSite.GetMethod("GetTarget"); } else { @@ -2744,22 +2744,22 @@ internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDyn var tb = compiler.finish.DefineIndyCallSiteType(); var fb = tb.DefineField("value", typeofIndyCallSite, FieldAttributes.Static | FieldAttributes.Assembly); var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(ReflectUtil.DefineTypeInitializer(tb, compiler.clazz.ClassLoader)); - ilgen.Emit(OpCodes.Ldnull); - ilgen.Emit(OpCodes.Ldftn, CreateBootstrapStub(compiler, cpi, delegateType, tb, fb, methodGetTarget)); - ilgen.Emit(OpCodes.Newobj, compiler.finish.Context.MethodHandleUtil.GetDelegateConstructor(delegateType)); - ilgen.Emit(OpCodes.Call, methodCreateBootStrap); - ilgen.Emit(OpCodes.Stsfld, fb); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldnull); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldftn, CreateBootstrapStub(compiler, cpi, delegateType, tb, fb, methodGetTarget)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Newobj, compiler.finish.Context.MethodHandleUtil.GetDelegateConstructor(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, methodCreateBootStrap); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stsfld, fb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); - compiler.ilGenerator.Emit(OpCodes.Ldsfld, fb); - compiler.ilGenerator.Emit(OpCodes.Call, methodGetTarget); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldsfld, fb); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, methodGetTarget); } static IMethodSymbolBuilder CreateBootstrapStub(Compiler compiler, ClassFile.ConstantPoolItemInvokeDynamic cpi, ITypeSymbol delegateType, ITypeSymbolBuilder tb, IFieldSymbolBuilder fb, IMethodSymbol methodGetTarget) { var typeofCallSite = compiler.finish.Context.ClassLoaderFactory.LoadClassCritical("java.lang.invoke.CallSite").TypeAsSignatureType; - var args = []; + var args = Array.Empty(); if (delegateType.IsGenericType) { @@ -2779,43 +2779,43 @@ static IMethodSymbolBuilder CreateBootstrapStub(Compiler compiler, ClassFile.Con if (EmitCallBootstrapMethod(compiler, cpi, ilgen, ok)) { - ilgen.Emit(OpCodes.Isinst, typeofCallSite); - ilgen.Emit(OpCodes.Stloc, cs); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, typeofCallSite); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, cs); } ilgen.EmitLeave(label); ilgen.BeginCatchBlock(compiler.finish.Context.Types.Exception); - ilgen.Emit(OpCodes.Stloc, ex); - ilgen.Emit(OpCodes.Ldloc, ok); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, ex); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, ok); var label2 = ilgen.DefineLabel(); ilgen.EmitBrtrue(label2); - ilgen.Emit(OpCodes.Rethrow); + ilgen.Emit(System.Reflection.Emit.OpCodes.Rethrow); ilgen.MarkLabel(label2); ilgen.EmitLeave(label); ilgen.EndExceptionBlock(); ilgen.MarkLabel(label); - ilgen.Emit(OpCodes.Ldsflda, fb); - ilgen.Emit(OpCodes.Ldloc, cs); - ilgen.Emit(OpCodes.Ldloc, ex); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsflda, fb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, cs); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, ex); if (HasUnloadable(cpi.GetArgTypes(), cpi.GetRetType())) { - ilgen.Emit(OpCodes.Ldstr, cpi.Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Signature); compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormHidden); - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLinkIndyCallSite.MakeGenericMethod(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLinkIndyCallSite.MakeGenericMethod(delegateType)); } else { - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LinkIndyCallSite.MakeGenericMethod(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LinkIndyCallSite.MakeGenericMethod(delegateType)); } - ilgen.Emit(OpCodes.Ldsfld, fb); - ilgen.Emit(OpCodes.Call, methodGetTarget); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsfld, fb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, methodGetTarget); for (int i = 0; i < args.Length; i++) ilgen.EmitLdarg(i); - ilgen.Emit(OpCodes.Callvirt, compiler.finish.Context.MethodHandleUtil.GetDelegateInvokeMethod(delegateType)); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, compiler.finish.Context.MethodHandleUtil.GetDelegateInvokeMethod(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); return mb; } @@ -2847,9 +2847,9 @@ static bool EmitCallBootstrapMethod(Compiler compiler, ClassFile.ConstantPoolIte default: // to throw the right exception, we have to resolve the MH constant here compiler.finish.GetValue(bsm.BootstrapMethodIndex.Slot).Emit(compiler, ilgen, bsm.BootstrapMethodIndex); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); ilgen.EmitLdc_I4(1); - ilgen.Emit(OpCodes.Stloc, ok); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, ok); ilgen.EmitThrow("java.lang.invoke.WrongMethodTypeException"); return false; } @@ -2858,7 +2858,7 @@ static bool EmitCallBootstrapMethod(Compiler compiler, ClassFile.ConstantPoolIte { // to throw the right exception (i.e. without wrapping it in a BootstrapMethodError), we have to resolve the MH constant here compiler.finish.GetValue(bsm.BootstrapMethodIndex.Slot).Emit(compiler, ilgen, bsm.BootstrapMethodIndex); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); if (mh.MemberConstantPoolItem is ClassFile.ConstantPoolItemMI cpiMI) { mw = new DynamicBinder().Get(compiler, mh.Kind, cpiMI, false); @@ -2866,7 +2866,7 @@ static bool EmitCallBootstrapMethod(Compiler compiler, ClassFile.ConstantPoolIte else { ilgen.EmitLdc_I4(1); - ilgen.Emit(OpCodes.Stloc, ok); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, ok); ilgen.EmitThrow("java.lang.invoke.WrongMethodTypeException"); return false; } @@ -2884,7 +2884,7 @@ static bool EmitCallBootstrapMethod(Compiler compiler, ClassFile.ConstantPoolIte else if (extraArgs != bsm.ArgumentCount) { ilgen.EmitLdc_I4(1); - ilgen.Emit(OpCodes.Stloc, ok); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, ok); ilgen.EmitThrow("java.lang.invoke.WrongMethodTypeException"); return false; } @@ -2896,20 +2896,20 @@ static bool EmitCallBootstrapMethod(Compiler compiler, ClassFile.ConstantPoolIte compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormCompiled); methodLookup.EmitCall(ilgen); - ilgen.Emit(OpCodes.Ldstr, cpi.Name); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Name); parameters[1].EmitConvStackTypeToSignatureType(ilgen, compiler.finish.Context.JavaBase.TypeOfJavaLangString); if (HasUnloadable(cpi.GetArgTypes(), cpi.GetRetType())) { // the cache is useless since we only run once, so we use a local - ilgen.Emit(OpCodes.Ldloca, ilgen.DeclareLocal(compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodType.TypeAsSignatureType)); - ilgen.Emit(OpCodes.Ldstr, cpi.Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloca, ilgen.DeclareLocal(compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodType.TypeAsSignatureType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Signature); compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormCompiled); - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLoadMethodType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLoadMethodType); } else { - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(compiler.finish.Context.MethodHandleUtil.CreateDelegateTypeForLoadConstant(cpi.GetArgTypes(), cpi.GetRetType()))); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(compiler.finish.Context.MethodHandleUtil.CreateDelegateTypeForLoadConstant(cpi.GetArgTypes(), cpi.GetRetType()))); } parameters[2].EmitConvStackTypeToSignatureType(ilgen, compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodType); @@ -2921,17 +2921,17 @@ static bool EmitCallBootstrapMethod(Compiler compiler, ClassFile.ConstantPoolIte { ilgen.EmitLdc_I4(varArgs); var elemType = parameters[parameters.Length - 1].ElementTypeWrapper; - ilgen.Emit(OpCodes.Newarr, elemType.TypeAsArrayType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Newarr, elemType.TypeAsArrayType); for (int i = 0; i < varArgs; i++) { - ilgen.Emit(OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); ilgen.EmitLdc_I4(i); EmitExtraArg(compiler, ilgen, bsm, i + fixedArgs, elemType, ok); - ilgen.Emit(OpCodes.Stelem_Ref); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stelem_Ref); } } ilgen.EmitLdc_I4(1); - ilgen.Emit(OpCodes.Stloc, ok); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, ok); if (mw.IsConstructor) mw.EmitNewobj(ilgen); @@ -2962,7 +2962,7 @@ static void EmitExtraArg(Compiler compiler, CodeEmitter ilgen, ClassFile.Bootstr if (constType != targetType) { ilgen.EmitLdc_I4(1); - ilgen.Emit(OpCodes.Stloc, wrapException); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, wrapException); if (constType.IsPrimitive) { @@ -2977,17 +2977,17 @@ static void EmitExtraArg(Compiler compiler, CodeEmitter ilgen, ClassFile.Bootstr else if (targetType.IsPrimitive) { var wrapper = GetWrapperType(targetType, out var unbox); - ilgen.Emit(OpCodes.Castclass, wrapper.TypeAsBaseType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, wrapper.TypeAsBaseType); wrapper.GetMethodWrapper(unbox, "()" + targetType.SigName, false).EmitCallvirt(ilgen); } else if (!constType.IsAssignableTo(targetType)) { - ilgen.Emit(OpCodes.Castclass, targetType.TypeAsBaseType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, targetType.TypeAsBaseType); } targetType.EmitConvStackTypeToSignatureType(ilgen, targetType); ilgen.EmitLdc_I4(0); - ilgen.Emit(OpCodes.Stloc, wrapException); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, wrapException); } } @@ -3029,13 +3029,13 @@ void EmitInvokeDynamic(ClassFile.ConstantPoolItemInvokeDynamic cpi) for (int i = args.Length - 1; i >= 0; i--) { temps[i] = ilgen.DeclareLocal(args[i].TypeAsSignatureType); - ilgen.Emit(OpCodes.Stloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } var delegateType = finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); InvokeDynamicBuilder.Emit(this, cpi, delegateType); for (int i = 0; i < args.Length; i++) - ilgen.Emit(OpCodes.Ldloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); finish.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } @@ -3051,13 +3051,13 @@ internal void Emit(Compiler compiler, CodeEmitter ilgen, MethodHandleConstantHan field = compiler.finish.DefineDynamicMethodHandleCacheField(); var mh = compiler.classFile.GetConstantPoolConstantMethodHandle(handle); - ilgen.Emit(OpCodes.Ldsflda, field); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsflda, field); ilgen.EmitLdc_I4((int)mh.Kind); - ilgen.Emit(OpCodes.Ldstr, mh.Class); - ilgen.Emit(OpCodes.Ldstr, mh.Name); - ilgen.Emit(OpCodes.Ldstr, mh.Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, mh.Class); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, mh.Name); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, mh.Signature); compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormCompiled); - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLoadMethodHandle); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLoadMethodHandle); } } @@ -3075,14 +3075,14 @@ internal void Emit(Compiler compiler, CodeEmitter ilgen, MethodTypeConstantHandl if (dynamic) { - ilgen.Emit(OpCodes.Ldsflda, field); - ilgen.Emit(OpCodes.Ldstr, compiler.classFile.GetConstantPoolConstantMethodType(handle).Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsflda, field); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, compiler.classFile.GetConstantPoolConstantMethodType(handle).Signature); compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormCompiled); - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLoadMethodType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicLoadMethodType); } else { - ilgen.Emit(OpCodes.Ldsfld, field); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsfld, field); } } @@ -3103,9 +3103,9 @@ static IFieldSymbolBuilder CreateField(Compiler compiler, MethodTypeConstantHand var field = tb.DefineField("value", compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodType.TypeAsSignatureType, FieldAttributes.Assembly | FieldAttributes.Static | FieldAttributes.InitOnly); var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(ReflectUtil.DefineTypeInitializer(tb, compiler.clazz.ClassLoader)); var delegateType = compiler.finish.Context.MethodHandleUtil.CreateDelegateTypeForLoadConstant(args, ret); - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); - ilgen.Emit(OpCodes.Stsfld, field); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stsfld, field); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); return field; } @@ -3224,11 +3224,11 @@ void CastInterfaceArgs(RuntimeJavaType declaringType, RuntimeJavaType[] args, in } else if (declaringType.IsNonPrimitiveValueType) { - ilGenerator.Emit(OpCodes.Unbox, declaringType.TypeAsTBD); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Unbox, declaringType.TypeAsTBD); } else { - ilGenerator.Emit(OpCodes.Castclass, declaringType.TypeAsSignatureType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, declaringType.TypeAsSignatureType); } } for (int i = firstCastArg; i < args.Length; i++) @@ -3251,24 +3251,24 @@ void CastInterfaceArgs(RuntimeJavaType declaringType, RuntimeJavaType[] args, in // the wrapper value onto the stack if (!instanceMethod || i != 0) { - ilGenerator.Emit(OpCodes.Ldobj, args[i].TypeAsSignatureType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldobj, args[i].TypeAsSignatureType); } } else { CodeEmitterLocal ghost = ilGenerator.AllocTempLocal(finish.Context.Types.Object); - ilGenerator.Emit(OpCodes.Stloc, ghost); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, ghost); CodeEmitterLocal local = ilGenerator.AllocTempLocal(args[i].TypeAsSignatureType); - ilGenerator.Emit(OpCodes.Ldloca, local); - ilGenerator.Emit(OpCodes.Ldloc, ghost); - ilGenerator.Emit(OpCodes.Stfld, args[i].GhostRefField); - ilGenerator.Emit(OpCodes.Ldloca, local); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloca, local); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, ghost); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stfld, args[i].GhostRefField); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloca, local); ilGenerator.ReleaseTempLocal(local); ilGenerator.ReleaseTempLocal(ghost); // NOTE when the this argument is a value type, we need the address on the stack instead of the value if (i != 0 || !instanceMethod) { - ilGenerator.Emit(OpCodes.Ldobj, args[i].TypeAsSignatureType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldobj, args[i].TypeAsSignatureType); } } } @@ -3283,7 +3283,7 @@ void CastInterfaceArgs(RuntimeJavaType declaringType, RuntimeJavaType[] args, in // we only need to unbox if the method was actually declared on the value type if (declaringType == args[i]) { - ilGenerator.Emit(OpCodes.Unbox, args[i].TypeAsTBD); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Unbox, args[i].TypeAsTBD); } } else @@ -3293,7 +3293,7 @@ void CastInterfaceArgs(RuntimeJavaType declaringType, RuntimeJavaType[] args, in } else if (ma.GetRawStackTypeWrapper(instructionIndex, args.Length - 1 - i).IsUnloadable) { - ilGenerator.Emit(OpCodes.Castclass, args[i].TypeAsSignatureType); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, args[i].TypeAsSignatureType); } } } @@ -3350,7 +3350,7 @@ private void DynamicGetPutField(Instruction instr, int i) } else if (fieldType == finish.Context.PrimitiveJavaTypeFactory.DOUBLE) { - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); } } finish.GetValue(instr.Arg1 | ((byte)kind << 24)).Emit(this, cpi, kind); @@ -3368,16 +3368,16 @@ private static void EmitReturnTypeConversion(CodeEmitter ilgen, RuntimeJavaType } else if (typeWrapper == ilgen.Context.PrimitiveJavaTypeFactory.VOID) { - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); } else if (typeWrapper.IsPrimitive) { // NOTE we don't need to use TypeWrapper.EmitUnbox, because the return value cannot be null - ilgen.Emit(OpCodes.Unbox, typeWrapper.TypeAsTBD); - ilgen.Emit(OpCodes.Ldobj, typeWrapper.TypeAsTBD); + ilgen.Emit(System.Reflection.Emit.OpCodes.Unbox, typeWrapper.TypeAsTBD); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldobj, typeWrapper.TypeAsTBD); if (typeWrapper == ilgen.Context.PrimitiveJavaTypeFactory.BYTE) { - ilgen.Emit(OpCodes.Conv_I1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Conv_I1); } } else @@ -3443,23 +3443,23 @@ internal static void EmitLinkToCall(RuntimeContext context, CodeEmitter ilgen, R { temps[i] = ilgen.DeclareLocal(context.MethodHandleUtil.AsBasicType(args[i])); ToBasic(args[i], ilgen); - ilgen.Emit(OpCodes.Stloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } temps[0] = ilgen.DeclareLocal(args[0].TypeAsSignatureType); - ilgen.Emit(OpCodes.Stloc, temps[0]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[0]); Array.Resize(ref args, args.Length - 1); Type delegateType = context.MethodHandleUtil.CreateMemberWrapperDelegateType(args, retType); - ilgen.Emit(OpCodes.Ldloc, temps[args.Length]); - ilgen.Emit(OpCodes.Ldfld, typeof(java.lang.invoke.MemberName).GetField("vmtarget", BindingFlags.Instance | BindingFlags.NonPublic)); - ilgen.Emit(OpCodes.Castclass, delegateType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[args.Length]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldfld, typeof(java.lang.invoke.MemberName).GetField("vmtarget", BindingFlags.Instance | BindingFlags.NonPublic)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, delegateType); for (int i = 0; i < args.Length; i++) { - ilgen.Emit(OpCodes.Ldloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); } context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); FromBasic(retType, ilgen); #else - throw new InvalidOperationException(); + throw new InvalidOperationException(); #endif } @@ -3470,25 +3470,25 @@ private void EmitInvokeExact(CodeEmitter ilgen) for (int i = args.Length - 1; i >= 0; i--) { temps[i] = ilgen.DeclareLocal(args[i].TypeAsSignatureType); - ilgen.Emit(OpCodes.Stloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } var delegateType = ilgen.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); if (HasUnloadable(cpi.GetArgTypes(), cpi.GetRetType())) { // TODO consider sharing the cache for the same signatures - ilgen.Emit(OpCodes.Ldsflda, compiler.finish.DefineDynamicMethodTypeCacheField()); - ilgen.Emit(OpCodes.Ldstr, cpi.Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsflda, compiler.finish.DefineDynamicMethodTypeCacheField()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Signature); compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormCompiled); - ilgen.Emit(OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.DynamicLoadMethodType); - ilgen.Emit(OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); - ilgen.Emit(OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.DynamicEraseInvokeExact); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.DynamicLoadMethodType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.DynamicEraseInvokeExact); } var mi = ilgen.Context.ByteCodeHelperMethods.GetDelegateForInvokeExact.MakeGenericMethod(delegateType); - ilgen.Emit(OpCodes.Call, mi); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) - ilgen.Emit(OpCodes.Ldloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); ilgen.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } @@ -3500,58 +3500,60 @@ private void EmitInvokeMaxArity(CodeEmitter ilgen) for (int i = args.Length - 1; i >= 0; i--) { temps[i] = ilgen.DeclareLocal(args[i].TypeAsSignatureType); - ilgen.Emit(OpCodes.Stloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } var delegateType = compiler.finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodHandle.GetMethodWrapper("asType", "(Ljava.lang.invoke.MethodType;)Ljava.lang.invoke.MethodHandle;", false).EmitCallvirt(ilgen); var mi = compiler.finish.Context.ByteCodeHelperMethods.GetDelegateForInvokeExact.MakeGenericMethod(delegateType); - ilgen.Emit(OpCodes.Call, mi); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) { - ilgen.Emit(OpCodes.Ldloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); } compiler.finish.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } - private void EmitInvoke(CodeEmitter ilgen) + void EmitInvoke(CodeEmitter ilgen) { if (cpi.GetArgTypes().Length >= 127 && compiler.finish.Context.MethodHandleUtil.SlotCount(cpi.GetArgTypes()) >= 254) { EmitInvokeMaxArity(ilgen); return; } - RuntimeJavaType[] args = ArrayUtil.Concat(compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodHandle, cpi.GetArgTypes()); - CodeEmitterLocal[] temps = new CodeEmitterLocal[args.Length]; + + var args = ArrayUtil.Concat(compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodHandle, cpi.GetArgTypes()); + var temps = new CodeEmitterLocal[args.Length]; for (int i = args.Length - 1; i >= 0; i--) { temps[i] = ilgen.DeclareLocal(args[i].TypeAsSignatureType); - ilgen.Emit(OpCodes.Stloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } - Type delegateType = compiler.finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); + + var delegateType = compiler.finish.Context.MethodHandleUtil.CreateMethodHandleDelegateType(args, cpi.GetRetType()); var mi = ilgen.Context.ByteCodeHelperMethods.GetDelegateForInvoke.MakeGenericMethod(delegateType); - var typeofInvokeCache = compiler.finish.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.InvokeCache`1").AsReflection(); + var typeofInvokeCache = compiler.finish.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.InvokeCache`1"); var fb = compiler.finish.DefineMethodHandleInvokeCacheField(typeofInvokeCache.MakeGenericType(delegateType)); - ilgen.Emit(OpCodes.Ldloc, temps[0]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[0]); if (HasUnloadable(cpi.GetArgTypes(), cpi.GetRetType())) { // TODO consider sharing the cache for the same signatures - ilgen.Emit(OpCodes.Ldsflda, compiler.finish.DefineDynamicMethodTypeCacheField()); - ilgen.Emit(OpCodes.Ldstr, cpi.Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsflda, compiler.finish.DefineDynamicMethodTypeCacheField()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Signature); compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormCompiled); - ilgen.Emit(OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.DynamicLoadMethodType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ilgen.Context.ByteCodeHelperMethods.DynamicLoadMethodType); } else { - ilgen.Emit(OpCodes.Ldnull); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldnull); } - ilgen.Emit(OpCodes.Ldsflda, fb); - ilgen.Emit(OpCodes.Call, mi); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsflda, fb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) { - ilgen.Emit(OpCodes.Ldloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); } compiler.finish.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } @@ -3574,17 +3576,17 @@ internal static void EmitInvokeBasic(RuntimeContext context, CodeEmitter ilgen, { ToBasic(args[i], ilgen); } - ilgen.Emit(OpCodes.Stloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } temps[0] = ilgen.DeclareLocal(args[0].TypeAsSignatureType); - ilgen.Emit(OpCodes.Stloc, temps[0]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[0]); var delegateType = context.MethodHandleUtil.CreateMemberWrapperDelegateType(args, retType); var mi = context.ByteCodeHelperMethods.GetDelegateForInvokeBasic.MakeGenericMethod(delegateType); - ilgen.Emit(OpCodes.Ldloc, temps[0]); - ilgen.Emit(OpCodes.Call, mi); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[0]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) { - ilgen.Emit(OpCodes.Ldloc, temps[i]); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); } context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } @@ -3623,7 +3625,7 @@ internal void Emit(Compiler compiler, ClassFile.ConstantPoolItemFieldref cpi, Me if (method == null) method = CreateMethod(compiler, cpi, kind); - compiler.ilGenerator.Emit(OpCodes.Call, method); + compiler.ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, method); } private static IMethodSymbol CreateMethod(Compiler compiler, ClassFile.ConstantPoolItemFieldref cpi, MethodHandleKind kind) @@ -3703,13 +3705,13 @@ internal static IMethodSymbol Emit(Compiler compiler, MethodHandleKind kind, Cla var mb = compiler.finish.DefineMethodHandleDispatchStub(ret.TypeAsSignatureType, types); var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(mb); - ilgen.Emit(OpCodes.Ldsfld, fb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsfld, fb); var label = ilgen.DefineLabel(); ilgen.EmitBrtrue(label); ilgen.EmitLdc_I4((int)kind); - ilgen.Emit(OpCodes.Ldstr, cpi.Class); - ilgen.Emit(OpCodes.Ldstr, cpi.Name); - ilgen.Emit(OpCodes.Ldstr, cpi.Signature); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Class); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Name); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, cpi.Signature); if (privileged) { compiler.finish.EmitHostCallerID(ilgen); @@ -3718,21 +3720,21 @@ internal static IMethodSymbol Emit(Compiler compiler, MethodHandleKind kind, Cla { compiler.finish.EmitCallerID(ilgen, compiler.m.IsLambdaFormCompiled); } - ilgen.Emit(OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicBinderMemberLookup.MakeGenericMethod(delegateType)); - ilgen.Emit(OpCodes.Volatile); - ilgen.Emit(OpCodes.Stsfld, fb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.DynamicBinderMemberLookup.MakeGenericMethod(delegateType)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Volatile); + ilgen.Emit(System.Reflection.Emit.OpCodes.Stsfld, fb); ilgen.MarkLabel(label); - ilgen.Emit(OpCodes.Ldsfld, fb); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsfld, fb); for (int i = 0; i < args.Length; i++) { ilgen.EmitLdarg(i); if (i == 0 && ghostTarget) { - ilgen.Emit(OpCodes.Ldobj, args[0].TypeAsSignatureType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldobj, args[0].TypeAsSignatureType); } } compiler.finish.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); return mb; } @@ -3750,17 +3752,17 @@ internal DynamicBinderMethodWrapper(ClassFile.ConstantPoolItemMI cpi, IMethodSym internal override void EmitCall(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Call, method); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, method); } internal override void EmitCallvirt(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Call, method); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, method); } internal override void EmitNewobj(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Call, method); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, method); } } @@ -3900,13 +3902,13 @@ private LocalVar LoadLocal(int instructionIndex) int i = m.ArgMap[instr.NormalizedArg1]; ilGenerator.EmitLdarg(i); if (v.type == finish.Context.PrimitiveJavaTypeFactory.DOUBLE) - ilGenerator.Emit(OpCodes.Conv_R8); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R8); if (v.type == finish.Context.PrimitiveJavaTypeFactory.FLOAT) - ilGenerator.Emit(OpCodes.Conv_R4); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Conv_R4); } else if (v.type == finish.Context.VerifierJavaTypeFactory.Null) { - ilGenerator.Emit(OpCodes.Ldnull); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldnull); } else { @@ -3917,7 +3919,7 @@ private LocalVar LoadLocal(int instructionIndex) v.builder.SetLocalSymInfo(v.name); } - ilGenerator.Emit(OpCodes.Ldloc, v.builder); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, v.builder); } return v; @@ -3929,7 +3931,7 @@ LocalVar StoreLocal(int instructionIndex) if (v == null) { // dead store - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } else if (v.isArg) { @@ -3939,7 +3941,7 @@ LocalVar StoreLocal(int instructionIndex) } else if (v.type == finish.Context.VerifierJavaTypeFactory.Null) { - ilGenerator.Emit(OpCodes.Pop); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Pop); } else { @@ -3949,7 +3951,7 @@ LocalVar StoreLocal(int instructionIndex) if (debug && v.name != null) v.builder.SetLocalSymInfo(v.name); } - ilGenerator.Emit(OpCodes.Stloc, v.builder); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Stloc, v.builder); } return v; diff --git a/src/IKVM.Runtime/intrinsics.cs b/src/IKVM.Runtime/intrinsics.cs index fab8a4e379..14f5c24ff0 100644 --- a/src/IKVM.Runtime/intrinsics.cs +++ b/src/IKVM.Runtime/intrinsics.cs @@ -24,18 +24,14 @@ Jeroen Frijters using System; using System.Collections.Generic; +using System.Reflection; +using System.Reflection.Emit; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; #if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; #endif using Instruction = IKVM.Runtime.ClassFile.Method.Instruction; @@ -228,29 +224,29 @@ private static bool IsSafeForGetClassOptimization(RuntimeJavaType tw) private static bool Float_floatToRawIntBits(EmitIntrinsicContext eic) { - EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.FloatConverter").AsReflection(), "ToInt"); + EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.FloatConverter"), "ToInt"); return true; } private static bool Float_intBitsToFloat(EmitIntrinsicContext eic) { - EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.FloatConverter").AsReflection(), "ToFloat"); + EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.FloatConverter"), "ToFloat"); return true; } private static bool Double_doubleToRawLongBits(EmitIntrinsicContext eic) { - EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.DoubleConverter").AsReflection(), "ToLong"); + EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.DoubleConverter"), "ToLong"); return true; } static bool Double_longBitsToDouble(EmitIntrinsicContext eic) { - EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.DoubleConverter").AsReflection(), "ToDouble"); + EmitConversion(eic.Emitter, eic.Method.DeclaringType.Context.Resolver.ResolveRuntimeType("IKVM.Runtime.DoubleConverter"), "ToDouble"); return true; } - static void EmitConversion(CodeEmitter ilgen, Type converterType, string method) + static void EmitConversion(CodeEmitter ilgen, ITypeSymbol converterType, string method) { var converter = ilgen.UnsafeAllocTempLocal(converterType); ilgen.Emit(OpCodes.Ldloca, converter); @@ -1003,7 +999,7 @@ static bool Unsafe_compareAndSwapLong(EmitIntrinsicContext eic) } } - internal static MethodInfo MakeExchange(RuntimeContext context, Type type) + internal static IMethodSymbol MakeExchange(RuntimeContext context, ITypeSymbol type) { return context.InterlockedMethods.ExchangeOfT.MakeGenericMethod(type); } diff --git a/src/IKVM.Tools.Exporter/ExportImpl.cs b/src/IKVM.Tools.Exporter/ExportImpl.cs index dc57fffe85..322042b354 100644 --- a/src/IKVM.Tools.Exporter/ExportImpl.cs +++ b/src/IKVM.Tools.Exporter/ExportImpl.cs @@ -8,6 +8,7 @@ using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.IkvmReflection; using IKVM.Reflection; using IKVM.Runtime; using IKVM.Tools.Importer; @@ -78,6 +79,7 @@ public int Execute() // build universe and resolver against universe and references var universe = new Universe(coreLibName); + var symbols = new IkvmReflectionSymbolContext(universe); var assemblyResolver = new AssemblyResolver(); assemblyResolver.Warning += new AssemblyResolver.WarningEvent(Resolver_Warning); assemblyResolver.Init(universe, options.NoStdLib, references, libpaths); @@ -145,7 +147,7 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(compiler, null), true, compiler); + context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(symbols, compiler, null), true, compiler); context.ClassLoaderFactory.SetBootstrapClassLoader(new RuntimeBootstrapClassLoader(context)); } else @@ -172,7 +174,7 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(compiler, baseAssembly), false, compiler); + context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(symbols, compiler, baseAssembly), false, compiler); } if (context.AttributeHelper.IsJavaModule(context.Resolver.ResolveModule(assembly.ManifestModule))) diff --git a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs index 3d99416287..111b284f64 100644 --- a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs +++ b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs @@ -1,4 +1,6 @@ -using System; +#nullable enable + +using System; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.IkvmReflection; @@ -11,85 +13,104 @@ namespace IKVM.Tools.Exporter { class ManagedTypeResolver : IRuntimeSymbolResolver - { + { - readonly StaticCompiler compiler; - readonly Assembly baseAssembly; - readonly IkvmReflectionSymbolContext symbols = new(); + readonly StaticCompiler compiler; + readonly Assembly baseAssembly; + readonly IkvmReflectionSymbolContext symbols; /// /// Initializes a new instance. /// /// /// - public ManagedTypeResolver(StaticCompiler compiler, Assembly baseAssembly) - { - this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); - this.baseAssembly = baseAssembly; + public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, StaticCompiler compiler, Assembly baseAssembly) + { + this.symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); + this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); + this.baseAssembly = baseAssembly; } - /// + /// public ISymbolContext Symbols => symbols; /// /// Attempts to resolve the base Java assembly. /// /// - public IAssemblySymbol ResolveBaseAssembly() - { - return baseAssembly != null ? symbols.GetOrCreateAssemblySymbol(baseAssembly) : null; - } - - /// - /// Attempts to resolve an assembly from one of the assembly sources. - /// - /// - /// - public IAssemblySymbol ResolveAssembly(string assemblyName) - { - return compiler.Load(assemblyName) is { } a ? symbols.GetOrCreateAssemblySymbol(a) : null; - } - - /// - /// Attempts to resolve a type from one of the assembly sources. - /// - /// - /// - public ITypeSymbol ResolveCoreType(string typeName) - { - foreach (var assembly in compiler.Universe.GetAssemblies()) - if (assembly.GetType(typeName) is Type t) - return ResolveType(t); - - return null; - } - - /// - /// Attempts to resolve a type from the IKVM runtime assembly. - /// - /// - /// - public ITypeSymbol ResolveRuntimeType(string typeName) - { - return compiler.GetRuntimeType(typeName) is { } t ? symbols.GetOrCreateTypeSymbol(t) : null; + public IAssemblySymbol? ResolveBaseAssembly() + { + return ResolveAssembly(baseAssembly); + } + + /// + /// Attempts to resolve an assembly from one of the assembly sources. + /// + /// + /// + public IAssemblySymbol? ResolveAssembly(string assemblyName) + { + return ResolveAssembly(compiler.Load(assemblyName)); + } + + /// + /// Attempts to resolve a type from one of the assembly sources. + /// + /// + /// + public ITypeSymbol? ResolveCoreType(string typeName) + { + foreach (var assembly in compiler.Universe.GetAssemblies()) + if (assembly.GetType(typeName) is Type t) + return ResolveType(t); + + return null; + } + + /// + /// Attempts to resolve a type from the IKVM runtime assembly. + /// + /// + /// + public ITypeSymbol? ResolveRuntimeType(string typeName) + { + return ResolveType(compiler.GetRuntimeType(typeName)); + } + + /// + public IAssemblySymbol? ResolveAssembly(Assembly? assembly) + { + return assembly != null ? symbols.GetOrCreateAssemblySymbol(assembly) : null; + } + + /// + public IModuleSymbol? ResolveModule(Module? module) + { + return module != null ? symbols.GetOrCreateModuleSymbol(module) : null; + } + + /// + public ITypeSymbol? ResolveType(Type? type) + { + return type != null ? symbols.GetOrCreateTypeSymbol(type) : null; } /// - public IAssemblySymbol ResolveAssembly(Assembly assembly) + public IMethodBaseSymbol? ResolveMethodBase(MethodBase? method) { - return symbols.GetOrCreateAssemblySymbol(assembly); + return method != null ? symbols.GetOrCreateMethodBaseSymbol(method) : null; } /// - public IModuleSymbol ResolveModule(Module module) + public IConstructorSymbol? ResolveConstructor(ConstructorInfo? ctor) { - return symbols.GetOrCreateModuleSymbol(module); + return ctor != null ? symbols.GetOrCreateConstructorSymbol(ctor) : null; } /// - public ITypeSymbol ResolveType(Type type) + public IMethodSymbol? ResolveMethod(MethodInfo? method) { - return symbols.GetOrCreateTypeSymbol(type); + return method != null ? symbols.GetOrCreateMethodSymbol(method) : null; } } diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json index 88236f0daf..7cb1e73723 100644 --- a/src/ikvmstub/Properties/launchSettings.json +++ b/src/ikvmstub/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmstub": { "commandName": "Project", - "commandLineArgs": "foo.dll -out foo.jar -log json" + "commandLineArgs": "--bootstrap --nostdlib --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.VisualBasic.Core.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.IO.FileSystem.DriveInfo.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"C:\\Users\\jhaltom\\Microsoft.VisualBasic.Core.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.VisualBasic.Core.dll\"" } } } \ No newline at end of file diff --git a/src/ikvmstub/ikvmstub.csproj b/src/ikvmstub/ikvmstub.csproj index 1d89f5a4df..15e796a6b8 100644 --- a/src/ikvmstub/ikvmstub.csproj +++ b/src/ikvmstub/ikvmstub.csproj @@ -1,7 +1,7 @@  Exe - net472;net6.0;net8.0 + net8.0;net472;net6.0 $(_SupportedToolRuntimes) true true diff --git a/testenvironments.json b/testenvironments.json index 051d6ff28a..9e94f92b25 100644 --- a/testenvironments.json +++ b/testenvironments.json @@ -13,4 +13,3 @@ } ] } - From 1da941c1fac49efaeeb4c8f638277c9a67bb312d Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 20 Sep 2024 20:45:57 -0500 Subject: [PATCH 11/59] Fix array length. Turn on -skiperror. Need to figure out what happened here. Fix libpath for discovery of corelibname. --- .../IkvmReflection/IkvmReflectionTypeSpecTable.cs | 2 +- .../targets/IKVM.Java.Core.NoTasks.targets | 1 + src/IKVM.Runtime/MethodHandleUtil.compiler.cs | 5 ++++- src/IKVM.Runtime/RuntimeArrayJavaType.cs | 2 +- ...e.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs | 2 +- src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 5 ++++- src/IKVM.Runtime/RuntimeJavaType.cs | 12 +++++++----- .../RuntimeManagedJavaType.ByRefJavaMethod.cs | 2 +- ...timeManagedJavaType.DelegateInnerClassJavaType.cs | 2 +- src/IKVM.Runtime/RuntimeManagedJavaType.cs | 2 +- src/IKVM.Runtime/compiler.cs | 5 +++-- src/IKVM.Tools.Exporter/ExportImpl.cs | 6 ++++++ src/ikvmstub/Properties/launchSettings.json | 4 ++-- 13 files changed, 33 insertions(+), 17 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs index 4a3de6e085..f52e96eb45 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs @@ -91,7 +91,7 @@ public IIkvmReflectionTypeSymbol GetOrCreatePointerTypeSymbol() public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() { if (_asByRef == null) - Interlocked.CompareExchange(ref _asByRef, new IkvmReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakePointerType()), null); + Interlocked.CompareExchange(ref _asByRef, new IkvmReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeByRefType()), null); return _asByRef; } diff --git a/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets b/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets index 15b39348c9..5d20169208 100644 --- a/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets +++ b/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets @@ -137,6 +137,7 @@ Value = b.ToString(); <_IkvmExporterArgs Remove="@(_IkvmExporterArgs)" /> <_IkvmExporterArgs Include="--bootstrap" Condition=" '%(ReferenceExport.Bootstrap)' == 'true' " /> <_IkvmExporterArgs Include="--nostdlib" Condition=" '%(ReferenceExport.NoStdLib)' == 'true' " /> + <_IkvmExporterArgs Include="--skiperror" /> <_IkvmExporterArgs Include="--non-public-types" Condition=" '%(ReferenceExport.IncludeNonPublicTypes)' == 'true' " /> <_IkvmExporterArgs Include="--non-public-interfaces" Condition=" '%(ReferenceExport.IncludeNonPublicInterfaces)' == 'true' " /> <_IkvmExporterArgs Include="--non-public-members" Condition=" '%(ReferenceExport.IncludeNonPublicMembers)' == 'true' " /> diff --git a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs index 4772fd86ec..5015c8972e 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs @@ -84,7 +84,10 @@ ITypeSymbol TypeWrapperToTypeForLoadConstant(RuntimeJavaType tw) while (tw.IsArray) tw = tw.ElementTypeWrapper; - return tw.TypeAsSignatureType.MakeArrayType(dims); + if (dims == 1) + return tw.TypeAsSignatureType.MakeArrayType(); + else + return tw.TypeAsSignatureType.MakeArrayType(dims); } else { diff --git a/src/IKVM.Runtime/RuntimeArrayJavaType.cs b/src/IKVM.Runtime/RuntimeArrayJavaType.cs index 72934b2d59..4d681af32c 100644 --- a/src/IKVM.Runtime/RuntimeArrayJavaType.cs +++ b/src/IKVM.Runtime/RuntimeArrayJavaType.cs @@ -119,7 +119,7 @@ internal override ITypeSymbol TypeAsTBD while (arrayType == null) { bool prevFinished = finished; - var type = ultimateElementTypeWrapper.TypeAsArrayType.MakeArrayType(ArrayRank); + var type = ArrayRank == 1 ? ultimateElementTypeWrapper.TypeAsArrayType.MakeArrayType() : ultimateElementTypeWrapper.TypeAsArrayType.MakeArrayType(ArrayRank); if (prevFinished) { // We were already finished prior to the call to MakeArrayType, so we can safely diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs index ad9115d70e..364179d83f 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateInvokeStubMethodWrapper.cs @@ -87,7 +87,7 @@ internal IMethodSymbol DoLink(ITypeSymbolBuilder tb) if (parameters[i].ParameterType.IsByRef) { var elemType = parameters[i].ParameterType.GetElementType(); - var local = ilgen.DeclareLocal(elemType.MakeArrayType(1)); + var local = ilgen.DeclareLocal(elemType.MakeArrayType()); byrefs[i] = local; ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.Emit(OpCodes.Newarr, elemType); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index d7801d44f1..f58a1df740 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -934,7 +934,10 @@ static ITypeSymbol GetModOptHelper(RuntimeJavaType tw) if (tw.IsArray) { - return GetModOptHelper(tw.GetUltimateElementTypeWrapper()).MakeArrayType(tw.ArrayRank); + if (tw.ArrayRank == 1) + return GetModOptHelper(tw.GetUltimateElementTypeWrapper()).MakeArrayType(); + else + return GetModOptHelper(tw.GetUltimateElementTypeWrapper()).MakeArrayType(tw.ArrayRank); } else if (tw.IsGhost) { diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 53d61e8300..70d6189dd8 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -929,7 +929,7 @@ internal ITypeSymbol TypeAsSignatureType return ((RuntimeUnloadableJavaType)this).MissingType ?? context.Types.Object; if (IsGhostArray) - return context.Types.Object.MakeArrayType(ArrayRank); + return ArrayRank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(ArrayRank); return TypeAsTBD; } @@ -953,7 +953,7 @@ internal ITypeSymbol TypeAsLocalOrStackType } if (IsGhostArray) - return context.Types.Object.MakeArrayType(ArrayRank); + return ArrayRank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(ArrayRank); return TypeAsTBD; } @@ -968,7 +968,7 @@ internal ITypeSymbol TypeAsArrayType return context.Types.Object; if (IsGhostArray) - return context.Types.Object.MakeArrayType(ArrayRank); + return ArrayRank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(ArrayRank); return TypeAsTBD; } @@ -1306,19 +1306,21 @@ internal virtual void EmitCheckcast(CodeEmitter ilgen) else if (IsGhostArray) { ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); + // TODO make sure we get the right "CastArray" method and cache it // NOTE for dynamic ghosts we don't end up here because AotTypeWrapper overrides this method, // so we're safe to call GetMethod on TypeAsTBD (because it has to be a compiled type, if we're here) - RuntimeJavaType tw = this; + var tw = this; int rank = 0; while (tw.IsArray) { rank++; tw = tw.ElementTypeWrapper; } + ilgen.EmitLdc_I4(rank); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, tw.TypeAsTBD.GetMethod("CastArray")); - ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, context.Types.Object.MakeArrayType(rank)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, rank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(rank)); } else { diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs index fbafd618a1..683a6b82a3 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.ByRefJavaMethod.cs @@ -89,7 +89,7 @@ void ConvertByRefArgs(CodeEmitter ilgen) { var type = args[i]; if (type.IsByRef) - type = type.GetElementType().MakeArrayType(1); + type = type.GetElementType().MakeArrayType(); locals[i] = ilgen.DeclareLocal(type); ilgen.Emit(OpCodes.Stloc, locals[i]); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs index ed2ff469c4..7d47c90905 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs @@ -67,7 +67,7 @@ internal DelegateInnerClassJavaType(RuntimeContext context, string name, ITypeSy if (parameterType.IsByRef) { flags |= MemberFlags.DelegateInvokeWithByRefParameter; - parameterType = parameterType.GetElementType().MakeArrayType(1); + parameterType = parameterType.GetElementType().MakeArrayType(); } argTypeWrappers[i] = Context.ClassLoaderFactory.GetJavaTypeFromType(parameterType); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index 7d96814302..a4df662c17 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -634,7 +634,7 @@ bool MakeMethodDescriptor(IMethodBaseSymbol mb, out string name, out string sig, if (type.IsByRef) { - type = type.GetElementType().MakeArrayType(1); + type = type.GetElementType().MakeArrayType(); if (mb.IsAbstract) { // Since we cannot override methods with byref arguments, we don't report abstract diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index c209e71e2f..b2da6523b3 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -1770,7 +1770,7 @@ void Compile(Block block, int startIndex) while (tw.IsArray) tw = tw.ElementTypeWrapper; - ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, tw.TypeAsTBD.MakeArrayType(wrapper.ArrayRank)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, wrapper.ArrayRank == 1 ? tw.TypeAsTBD.MakeArrayType() : tw.TypeAsTBD.MakeArrayType(wrapper.ArrayRank)); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, localArray); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.multianewarray_ghost); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, wrapper.TypeAsArrayType); @@ -1810,7 +1810,8 @@ void Compile(Block block, int startIndex) while (tw.IsArray) tw = tw.ElementTypeWrapper; - ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, tw.TypeAsTBD.MakeArrayType(wrapper.ArrayRank + 1)); + var rank = wrapper.ArrayRank + 1; + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, rank == 1 ? tw.TypeAsTBD.MakeArrayType() : tw.TypeAsTBD.MakeArrayType(rank)); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.anewarray_ghost.MakeGenericMethod(wrapper.TypeAsArrayType)); } else diff --git a/src/IKVM.Tools.Exporter/ExportImpl.cs b/src/IKVM.Tools.Exporter/ExportImpl.cs index 322042b354..149aaf0557 100644 --- a/src/IKVM.Tools.Exporter/ExportImpl.cs +++ b/src/IKVM.Tools.Exporter/ExportImpl.cs @@ -246,6 +246,12 @@ static string FindCoreLibName(List references, List libpaths) if (GetAssemblyNameIfCoreLib(reference) is string coreLibName) return coreLibName; + foreach (var libpath in libpaths) + if (Directory.Exists(libpath)) + foreach (var reference in Directory.EnumerateFiles(libpath, "*.dll")) + if (GetAssemblyNameIfCoreLib(reference) is string coreLibName) + return coreLibName; + return null; } diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json index 7cb1e73723..c08101f8e5 100644 --- a/src/ikvmstub/Properties/launchSettings.json +++ b/src/ikvmstub/Properties/launchSettings.json @@ -1,8 +1,8 @@ { "profiles": { "ikvmstub": { - "commandName": "Project", - "commandLineArgs": "--bootstrap --nostdlib --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.VisualBasic.Core.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.IO.FileSystem.DriveInfo.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"C:\\Users\\jhaltom\\Microsoft.VisualBasic.Core.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.VisualBasic.Core.dll\"" + "commandName": "Project", + "commandLineArgs": "--bootstrap --skiperror --nostdlib --parameters --lib:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\" --reference:\"D:\\ikvm\\src\\IKVM.Java-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"C:\\Users\\jhaltom\\System.Threading.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Threading.dll\"" } } } \ No newline at end of file From ae381ec4111045766e824e35466b4767359f49c0 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 22 Sep 2024 14:59:48 -0500 Subject: [PATCH 12/59] It builds. --- .../Diagnostics/DiagnosticEvent.cs | 5 + .../Symbols/Emit/IAssemblySymbolBuilder.cs | 55 +- .../Symbols/Emit/IModuleSymbolBuilder.cs | 96 +++ .../Symbols/Emit/ITypeSymbolBuilder.cs | 8 + src/IKVM.CoreLib/Symbols/Emit/PEFileKinds.cs | 28 + src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs | 37 ++ src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 6 +- .../IkvmReflectionAssemblySymbolBuilder.cs | 73 +- .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 79 +++ .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 6 + .../IIkvmReflectionAssemblySymbol.cs | 4 +- .../IkvmReflectionAssemblySymbol.cs | 66 +- .../IkvmReflection/IkvmReflectionSymbol.cs | 7 + .../IkvmReflectionSymbolContext.cs | 93 +-- .../IkvmReflection/IkvmReflectionUtil.cs | 13 + src/IKVM.CoreLib/Symbols/ImageFileMachine.cs | 15 + .../Symbols/ManifestResourceInfo.cs | 29 + .../Emit/ReflectionAssemblySymbolBuilder.cs | 80 ++- .../Emit/ReflectionModuleSymbolBuilder.cs | 104 ++- .../Emit/ReflectionTypeSymbolBuilder.cs | 6 + .../Reflection/ReflectionAssemblySymbol.cs | 22 + .../Symbols/Reflection/ReflectionSymbol.cs | 6 + .../Reflection/ReflectionSymbolContext.cs | 8 +- .../Symbols/TypeSymbolExtensions.cs | 43 ++ src/IKVM.Reflection/Assembly.cs | 30 + src/IKVM.Runtime/Annotation.cs | 9 +- src/IKVM.Runtime/AttributeHelper.cs | 42 +- src/IKVM.Runtime/CodeEmitter.cs | 16 +- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 24 + src/IKVM.Runtime/ReflectUtil.cs | 12 +- .../RuntimeAccessStubJavaMethod.cs | 8 +- .../RuntimeAssemblyClassLoader.cs | 4 +- .../RuntimeByteCodeJavaType.FinishContext.cs | 80 ++- ...peImpl.DelegateConstructorMethodWrapper.cs | 2 +- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 131 ++-- src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 6 +- .../RuntimeByteCodePropertyJavaField.cs | 11 +- src/IKVM.Runtime/RuntimeConstantJavaField.cs | 14 +- .../RuntimeConstructorAccessStubJavaMethod.cs | 8 +- .../RuntimeDefaultInterfaceJavaMethod.cs | 8 +- src/IKVM.Runtime/RuntimeGhostJavaMethod.cs | 14 +- src/IKVM.Runtime/RuntimeJavaMethod.cs | 64 +- src/IKVM.Runtime/RuntimeJavaType.cs | 13 +- ...ntimeManagedByteCodeAccessStubJavaField.cs | 19 +- ...eJavaType.DelegateConstructorJavaMethod.cs | 12 +- ...agedByteCodeJavaType.RemappedJavaMethod.cs | 7 +- .../RuntimeManagedByteCodeJavaType.cs | 56 +- ...RuntimeManagedByteCodePropertyJavaField.cs | 12 +- ...ntimeManagedJavaType.EnumValueJavaField.cs | 13 +- ...ntimeManagedJavaType.FinalizeJavaMethod.cs | 7 +- ...JavaType.ValueTypeDefaultCtorJavaMethod.cs | 9 +- src/IKVM.Runtime/RuntimeMirandaJavaMethod.cs | 8 +- src/IKVM.Runtime/RuntimePrimitiveJavaType.cs | 12 +- .../RuntimePrivateInterfaceJavaMethod.cs | 8 +- .../RuntimeSimpleCallJavaMethod.cs | 6 - src/IKVM.Runtime/RuntimeSimpleJavaField.cs | 16 +- src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs | 13 +- .../RuntimeVolatileLongDoubleJavaField.cs | 9 +- src/IKVM.Runtime/Serialization.cs | 8 +- .../ManagedTypeResolver.cs | 61 +- src/IKVM.Tools.Importer/AssemblyResolver.cs | 44 +- src/IKVM.Tools.Importer/FakeTypes.cs | 47 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 626 +++++++++--------- src/IKVM.Tools.Importer/ImportContext.cs | 151 ++++- src/IKVM.Tools.Importer/ImportOptions.cs | 2 +- .../ImportRuntimeSymbolResolver.cs | 141 ++++ src/IKVM.Tools.Importer/ImportState.cs | 50 +- src/IKVM.Tools.Importer/ImportTarget.cs | 2 +- src/IKVM.Tools.Importer/ManagedResolver.cs | 75 --- src/IKVM.Tools.Importer/MapXml/Add.cs | 3 +- src/IKVM.Tools.Importer/MapXml/And.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Box.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Call.cs | 28 +- src/IKVM.Tools.Importer/MapXml/Callvirt.cs | 4 +- src/IKVM.Tools.Importer/MapXml/Castclass.cs | 2 +- .../MapXml/Castclass_impl.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Ceq.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_I.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_I1.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_I2.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_I4.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_I8.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_U1.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_U2.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_U4.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Conv_U8.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Cpblk.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Div_Un.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Dup.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Endfinally.cs | 3 +- .../MapXml/ExceptionBlock.cs | 5 +- src/IKVM.Tools.Importer/MapXml/IsInst.cs | 2 +- src/IKVM.Tools.Importer/MapXml/LdArg_0.cs | 3 +- src/IKVM.Tools.Importer/MapXml/LdArg_1.cs | 3 +- src/IKVM.Tools.Importer/MapXml/LdArg_2.cs | 3 +- src/IKVM.Tools.Importer/MapXml/LdArg_3.cs | 3 +- src/IKVM.Tools.Importer/MapXml/LdLoc.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Ldc_I4_0.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldc_I4_1.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldc_I4_M1.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldelema.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Ldfld.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Ldflda.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Ldftn.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldind_i1.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldind_i2.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldind_i4.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldind_i8.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldind_r4.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldind_r8.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldind_ref.cs | 4 +- src/IKVM.Tools.Importer/MapXml/Ldlen.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldnull.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldobj.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ldsfld.cs | 4 +- src/IKVM.Tools.Importer/MapXml/Ldstr.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Ldtoken.cs | 30 +- src/IKVM.Tools.Importer/MapXml/Ldvirtftn.cs | 5 +- .../MapXml/MapXmlSerializer.cs | 3 +- src/IKVM.Tools.Importer/MapXml/MethodBase.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Mul.cs | 3 +- src/IKVM.Tools.Importer/MapXml/NewObj.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Newarr.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Not.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Or.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Pop.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Redirect.cs | 10 +- src/IKVM.Tools.Importer/MapXml/Rem_Un.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Ret.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Simple.cs | 3 +- src/IKVM.Tools.Importer/MapXml/StLoc.cs | 7 +- src/IKVM.Tools.Importer/MapXml/Stfld.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Stind_i1.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Stind_i2.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Stind_i4.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Stind_i8.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Stind_ref.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Stsfld.cs | 2 +- src/IKVM.Tools.Importer/MapXml/Sub.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Throw.cs | 3 +- .../MapXml/TypeInstruction.cs | 7 +- .../MapXml/TypeOrTypeWrapperInstruction.cs | 5 +- src/IKVM.Tools.Importer/MapXml/Unbox.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Volatile.cs | 3 +- src/IKVM.Tools.Importer/MapXml/Xor.cs | 3 +- src/IKVM.Tools.Importer/Proxy.cs | 23 +- .../RuntimeImportByteCodeJavaType.cs | 69 +- src/IKVM.Tools.Importer/StaticCompiler.cs | 77 ++- 148 files changed, 2006 insertions(+), 1253 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/Emit/PEFileKinds.cs create mode 100644 src/IKVM.CoreLib/Symbols/ImageFileMachine.cs create mode 100644 src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs create mode 100644 src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs delete mode 100644 src/IKVM.Tools.Importer/ManagedResolver.cs diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs index 4b2ebd0f16..c90a66a892 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs @@ -26,6 +26,11 @@ readonly partial struct DiagnosticEvent(Diagnostic Diagnostic, object?[] Args, E /// public readonly DiagnosticLocation Location = Location; + internal static DiagnosticEvent RuntimeMismatch(object location, string fullName1, string fullName2) + { + throw new NotImplementedException(); + } + /// /// Formats the diagnostic event message. /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs index d99608a52e..5df264c934 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs @@ -1,4 +1,6 @@ -namespace IKVM.CoreLib.Symbols.Emit +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit { interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySymbol @@ -41,6 +43,57 @@ interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySym /// void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + /// + /// Sets a Win32 icon on the generated assembly. + /// + /// + void DefineIconResource(byte[] bytes); + + /// + /// Sets a manifest resource on the generated assembly. + /// + /// + void DefineManifestResource(byte[] bytes); + + /// + /// Sets a Win32 version info resource on the generated assembly. + /// + void DefineVersionInfoResource(); + + /// + /// Sets the entry point for this assembly, assuming that a console application is being built. + /// + /// + void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy); + + /// + /// Sets the entry point for this assembly and defines the type of the portable executable (PE file) being built. + /// + /// + /// + void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, PEFileKinds target); + + /// + /// Adds a forwarded type to this assembly. + /// + /// + void AddTypeForwarder(ITypeSymbol type); + + /// + /// Adds an external resource file to the assembly. + /// + /// + /// + void AddResourceFile(string name, string fileName); + + /// + /// Saves this assembly to disk. + /// + /// + /// + /// + void Save(string assemblyFileName, PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine); + } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index 90c4603e11..79737a1767 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -1,7 +1,10 @@ using System; using System.Diagnostics.SymbolStore; +using System.IO; using System.Reflection; using System.Reflection.Emit; +using System.Reflection.PortableExecutable; +using System.Resources; namespace IKVM.CoreLib.Symbols.Emit { @@ -9,6 +12,21 @@ namespace IKVM.CoreLib.Symbols.Emit interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol { + /// + /// Gets or sets the preferred address of the first byte of the image when it is loaded into memory. + /// + ulong ImageBase { get; set; } + + /// + /// Gets or sets the alignment factor (in bytes) that is used to align the raw data of sections in the image file. + /// + uint FileAlignment { get; set; } + + /// + /// Gets or sets the characteristics of a dynamic link library. + /// + DllCharacteristics DllCharacteristics { get; set; } + /// /// Defines a document for source. /// @@ -19,6 +37,67 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol /// ISymbolDocumentWriter? DefineDocument(string url, Guid language, Guid languageVendor, Guid documentType); + /// + /// Defines a binary large object (BLOB) that represents a manifest resource to be embedded in the dynamic assembly. + /// + /// + /// + /// + void DefineManifestResource(string name, Stream stream, ResourceAttributes attribute); + + /// + /// Defines the named managed embedded resource to be stored in this module. + /// + /// + /// + /// + IResourceWriter DefineResource(string name, string description); + + /// + /// Defines the named managed embedded resource with the given attributes that is to be stored in this module. + /// + /// + /// + /// + /// + IResourceWriter DefineResource(string name, string description, ResourceAttributes attribute); + + /// + /// Defines a global method with the specified name, attributes, calling convention, return type, and parameter types. + /// + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] parameterTypes); + + /// + /// Defines a global method with the specified name, attributes, calling convention, return type, custom modifiers for the return type, parameter types, and custom modifiers for the parameter types. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] requiredReturnTypeCustomModifiers, ITypeSymbol[] optionalReturnTypeCustomModifiers, ITypeSymbol[] parameterTypes, ITypeSymbol[][] requiredParameterTypeCustomModifiers, ITypeSymbol[][] optionalParameterTypeCustomModifiers); + + /// + /// Defines a global method with the specified name, attributes, return type, and parameter types. + /// + /// + /// + /// + /// + /// + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol returnType, ITypeSymbol[] parameterTypes); + /// /// Constructs a TypeBuilder for a private type with the specified name in this module. /// @@ -97,6 +176,23 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol /// void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + /// + /// Explicitely adds a reference to the specified assembly. + /// + /// + void AddReference(IAssemblySymbol assembly); + + /// + /// Finishes the module. + /// + void Complete(); + + /// + /// Saves this module assembly to disk. + /// + /// + /// + void Save(PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs index e888e50285..1afc22d77d 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs @@ -31,6 +31,14 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// void AddInterfaceImplementation(ITypeSymbol interfaceType); + /// + /// Adds a new constructor to the type, with the given attributes and signature and the standard calling convention. + /// + /// + /// + /// + IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, ITypeSymbol[]? parameterTypes); + /// /// Adds a new constructor to the type, with the given attributes and signature. /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/PEFileKinds.cs b/src/IKVM.CoreLib/Symbols/Emit/PEFileKinds.cs new file mode 100644 index 0000000000..475eacd6dc --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/PEFileKinds.cs @@ -0,0 +1,28 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + /// + /// Specifies the type of the portable executable (PE) file. + /// + enum PEFileKinds + { + + /// + /// The portable executable (PE) file is a DLL. + /// + Dll = 1, + + /// + /// The application is a console (not a Windows-based) application. + /// + ConsoleApplication = 2, + + /// + /// The application is a Windows-based application. + /// + WindowApplication = 3, + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs index 3d3d399759..4e14036aba 100644 --- a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs @@ -1,4 +1,5 @@ using System.Collections.Generic; +using System.IO; using System.Reflection; using IKVM.CoreLib.Symbols.Emit; @@ -15,14 +16,50 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider IEnumerable ExportedTypes { get; } + /// + /// Gets the display name of the assembly. + /// string? FullName { get; } + /// + /// Gets a string representing the version of the common language runtime (CLR) saved in the file containing the manifest. + /// string ImageRuntimeVersion { get; } + /// + /// Gets the full path or UNC location of the loaded file that contains the manifest. + /// + string Location { get; } + + /// + /// Gets the module that contains the manifest for the current assembly. + /// IModuleSymbol ManifestModule { get; } IEnumerable Modules { get; } + /// + /// Loads the specified manifest resource from this assembly. + /// + /// + /// + ManifestResourceInfo? GetManifestResourceInfo(string resourceName); + + /// + /// Loads the specified manifest resource from this assembly. + /// + /// + /// + Stream? GetManifestResourceStream(string name); + + /// + /// Loads the specified manifest resource, scoped by the namespace of the specified type, from this assembly. + /// + /// + /// + /// + Stream? GetManifestResourceStream(ITypeSymbol type, string name); + ITypeSymbol[] GetExportedTypes(); IModuleSymbol? GetModule(string name); diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index adef5b72e6..47a832f043 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -13,17 +13,15 @@ interface ISymbolContext /// Defines a dynamic assembly that has the specified name and access rights. /// /// - /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access); + IAssemblySymbolBuilder DefineAssembly(AssemblyName name); /// /// Defines a dynamic assembly that has the specified name and access rights. /// /// - /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access, ICustomAttributeBuilder[]? assemblyAttributes); + IAssemblySymbolBuilder DefineAssembly(AssemblyName name, ICustomAttributeBuilder[]? assemblyAttributes); /// /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs index d8e4da24a5..bafa374cf0 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.IO; using System.Linq; using IKVM.CoreLib.Symbols.Emit; @@ -77,13 +78,61 @@ public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emit /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingAssemblyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingAssemblyBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + } + + /// + public void DefineIconResource(byte[] bytes) + { + UnderlyingAssemblyBuilder.__DefineIconResource(bytes); + } + + /// + public void DefineManifestResource(byte[] bytes) + { + UnderlyingAssemblyBuilder.__DefineManifestResource(bytes); + } + + /// + public void DefineVersionInfoResource() + { + UnderlyingAssemblyBuilder.DefineVersionInfoResource(); + } + + /// + public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy) + { + UnderlyingAssemblyBuilder.SetEntryPoint(mainMethodProxy.Unpack()); + } + + /// + public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, IKVM.CoreLib.Symbols.Emit.PEFileKinds target) + { + UnderlyingAssemblyBuilder.SetEntryPoint(mainMethodProxy.Unpack(), (IKVM.Reflection.Emit.PEFileKinds)target); + } + + /// + public void AddTypeForwarder(ITypeSymbol type) + { + UnderlyingAssemblyBuilder.__AddTypeForwarder(type.Unpack()); + } + + /// + public void AddResourceFile(string name, string value) + { + UnderlyingAssemblyBuilder.AddResourceFile(name, value); + } + + /// + public void Save(string assemblyFileName, System.Reflection.PortableExecutableKinds portableExecutableKind, IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine) + { + UnderlyingAssemblyBuilder.Save(assemblyFileName, (PortableExecutableKinds)portableExecutableKind, (IKVM.Reflection.ImageFileMachine)imageFileMachine); } #endregion @@ -114,6 +163,8 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) /// public override bool IsComplete => _builder == null; + public string Location => throw new NotImplementedException(); + /// public ITypeSymbol[] GetExportedTypes() { @@ -204,6 +255,24 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); } + /// + public ManifestResourceInfo? GetManifestResourceInfo(string resourceName) + { + return ResolveManifestResourceInfo(UnderlyingAssembly.GetManifestResourceInfo(resourceName)); + } + + /// + public Stream? GetManifestResourceStream(string name) + { + return UnderlyingAssembly.GetManifestResourceStream(name); + } + + /// + public Stream? GetManifestResourceStream(ITypeSymbol type, string name) + { + return UnderlyingAssembly.GetManifestResourceStream(type.Unpack(), name); + } + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs index b5e84e7f52..1ac802ff40 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -1,6 +1,8 @@ using System; using System.Diagnostics.SymbolStore; +using System.IO; using System.Linq; +using System.Resources; using IKVM.CoreLib.Symbols.Emit; using IKVM.Reflection; @@ -193,6 +195,42 @@ public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypePa return UnderlyingModuleBuilder.DefineDocument(url, language, languageVendor, documentType); } + /// + public void DefineManifestResource(string name, Stream stream, System.Reflection.ResourceAttributes attribute) + { + UnderlyingModuleBuilder.DefineManifestResource(name, stream, (ResourceAttributes)attribute); + } + + /// + public IResourceWriter DefineResource(string name, string description) + { + return UnderlyingModuleBuilder.DefineResource(name, description); + } + + /// + public IResourceWriter DefineResource(string name, string description, System.Reflection.ResourceAttributes attribute) + { + return UnderlyingModuleBuilder.DefineResource(name, description, (ResourceAttributes)attribute); + } + + /// + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + { + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), parameterTypes.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] requiredReturnTypeCustomModifiers, ITypeSymbol[] optionalReturnTypeCustomModifiers, ITypeSymbol[] parameterTypes, ITypeSymbol[][] requiredParameterTypeCustomModifiers, ITypeSymbol[][] optionalParameterTypeCustomModifiers) + { + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), requiredReturnTypeCustomModifiers.Unpack(), optionalReturnTypeCustomModifiers.Unpack(), parameterTypes.Unpack(), requiredParameterTypeCustomModifiers.Unpack(), optionalParameterTypeCustomModifiers.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + { + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, returnType.Unpack(), parameterTypes.Unpack())); + } + /// public ITypeSymbolBuilder DefineType(string name) { @@ -247,6 +285,26 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) UnderlyingModuleBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } + /// + public void AddReference(IAssemblySymbol assembly) + { + var t = ((IIkvmReflectionAssemblySymbol)assembly).GetExportedTypes(); + if (t.Length > 0) + UnderlyingModuleBuilder.GetTypeToken(t[0].Unpack()); + } + + /// + public void Complete() + { + UnderlyingModuleBuilder.CreateGlobalFunctions(); + } + + /// + public void Save(System.Reflection.PortableExecutableKinds portableExecutableKind, IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine) + { + UnderlyingModuleBuilder.__Save((PortableExecutableKinds)portableExecutableKind, (IKVM.Reflection.ImageFileMachine)imageFileMachine); + } + #endregion #region IModuleSymbol @@ -272,6 +330,27 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) /// public override bool IsComplete => _module == null; + /// + public ulong ImageBase + { + get => UnderlyingModule.__ImageBase; + set => UnderlyingModuleBuilder.__ImageBase = value; + } + + /// + public uint FileAlignment + { + get => UnderlyingModule.__FileAlignment; + set => UnderlyingModuleBuilder.__FileAlignment = value; + } + + /// + public System.Reflection.PortableExecutable.DllCharacteristics DllCharacteristics + { + get => (System.Reflection.PortableExecutable.DllCharacteristics)UnderlyingModule.__DllCharacteristics; + set => UnderlyingModuleBuilder.__DllCharacteristics = (IKVM.Reflection.DllCharacteristics)value; + } + /// public IFieldSymbol? GetField(string name) { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index d4183cb187..f392d45025 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -197,6 +197,12 @@ public void AddInterfaceImplementation(ITypeSymbol interfaceType) UnderlyingTypeBuilder.AddInterfaceImplementation(interfaceType.Unpack()); } + /// + public IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, ITypeSymbol[]? parameterTypes) + { + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor((MethodAttributes)attributes, CallingConventions.Standard, parameterTypes?.Unpack())); + } + /// public IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol[]? parameterTypes) { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs index 3d783ca7dc..1f608eaf82 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs @@ -1,6 +1,4 @@ -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; +using IKVM.Reflection; namespace IKVM.CoreLib.Symbols.IkvmReflection { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 1b4b2ef00e..61b83f6297 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.IO; using System.Linq; using IKVM.Reflection; @@ -44,114 +45,135 @@ public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) #region IAssemblySymbol /// - public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); + public IEnumerable DefinedTypes => ResolveTypeSymbols(UnderlyingAssembly.DefinedTypes); /// - public IMethodSymbol? EntryPoint => ResolveMethodSymbol(_assembly.EntryPoint); + public IMethodSymbol? EntryPoint => ResolveMethodSymbol(UnderlyingAssembly.EntryPoint); /// - public IEnumerable ExportedTypes => ResolveTypeSymbols(_assembly.ExportedTypes); + public IEnumerable ExportedTypes => ResolveTypeSymbols(UnderlyingAssembly.ExportedTypes); /// - public string? FullName => _assembly.FullName; + public string? FullName => UnderlyingAssembly.FullName; /// - public string ImageRuntimeVersion => _assembly.ImageRuntimeVersion; + public string ImageRuntimeVersion => UnderlyingAssembly.ImageRuntimeVersion; /// - public IModuleSymbol ManifestModule => ResolveModuleSymbol(_assembly.ManifestModule); + public string Location => UnderlyingAssembly.Location; /// - public IEnumerable Modules => ResolveModuleSymbols(_assembly.Modules); + public IModuleSymbol ManifestModule => ResolveModuleSymbol(UnderlyingAssembly.ManifestModule); + + /// + public IEnumerable Modules => ResolveModuleSymbols(UnderlyingAssembly.Modules); /// public ITypeSymbol[] GetExportedTypes() { - return ResolveTypeSymbols(_assembly.GetExportedTypes()); + return ResolveTypeSymbols(UnderlyingAssembly.GetExportedTypes()); } /// public IModuleSymbol? GetModule(string name) { - return ResolveModuleSymbol(_assembly.GetModule(name)); + return ResolveModuleSymbol(UnderlyingAssembly.GetModule(name)); } /// public IModuleSymbol[] GetModules() { - return ResolveModuleSymbols(_assembly.GetModules()); + return ResolveModuleSymbols(UnderlyingAssembly.GetModules()); } /// public IModuleSymbol[] GetModules(bool getResourceModules) { - return ResolveModuleSymbols(_assembly.GetModules(getResourceModules)); + return ResolveModuleSymbols(UnderlyingAssembly.GetModules(getResourceModules)); } /// public System.Reflection.AssemblyName GetName() { - return _assembly.GetName().Pack(); + return UnderlyingAssembly.GetName().Pack(); } /// public System.Reflection.AssemblyName GetName(bool copiedName) { - return _assembly.GetName().Pack(); + return UnderlyingAssembly.GetName().Pack(); } /// public System.Reflection.AssemblyName[] GetReferencedAssemblies() { - return _assembly.GetReferencedAssemblies().Pack(); + return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } /// public ITypeSymbol? GetType(string name, bool throwOnError) { - return ResolveTypeSymbol(_assembly.GetType(name, throwOnError)); + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError)); } /// public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) { - return ResolveTypeSymbol(_assembly.GetType(name, throwOnError, ignoreCase)); + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError, ignoreCase)); } /// public ITypeSymbol? GetType(string name) { - return ResolveTypeSymbol(_assembly.GetType(name)); + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name)); } /// public ITypeSymbol[] GetTypes() { - return ResolveTypeSymbols(_assembly.GetTypes()); + return ResolveTypeSymbols(UnderlyingAssembly.GetTypes()); } /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); + return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData()); } /// public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttributes(_assembly.__GetCustomAttributes(attributeType.Unpack(), inherit)); + return ResolveCustomAttributes(UnderlyingAssembly.__GetCustomAttributes(attributeType.Unpack(), inherit)); } /// public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(_assembly.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + return ResolveCustomAttribute(UnderlyingAssembly.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); } /// public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _assembly.IsDefined(attributeType.Unpack(), inherit); + return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); + } + + /// + public ManifestResourceInfo? GetManifestResourceInfo(string resourceName) + { + return ResolveManifestResourceInfo(UnderlyingAssembly.GetManifestResourceInfo(resourceName)); + } + + /// + public Stream? GetManifestResourceStream(string name) + { + return UnderlyingAssembly.GetManifestResourceStream(name); + } + + /// + public Stream? GetManifestResourceStream(ITypeSymbol type, string name) + { + return UnderlyingAssembly.GetManifestResourceStream(type.Unpack(), name); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index 7d1eb10de9..9780e79974 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -525,6 +525,13 @@ public InterfaceMapping ResolveInterfaceMapping(IKVM.Reflection.InterfaceMapping ResolveMethodSymbols(mapping.TargetMethods), ResolveTypeSymbol(mapping.TargetType)); } + + /// + public ManifestResourceInfo? ResolveManifestResourceInfo(IKVM.Reflection.ManifestResourceInfo? info) + { + return info != null ? new ManifestResourceInfo((System.Reflection.ResourceLocation)info.ResourceLocation, info.FileName, ResolveAssemblySymbol(info.ReferencedAssembly)) : null; + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs index d623f2d1c2..c7a1c06ee5 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -31,32 +31,22 @@ public IkvmReflectionSymbolContext(Universe universe) _universe = universe ?? throw new ArgumentNullException(nameof(universe)); } - /// - /// Defines a dynamic assembly that has the specified name and access rights. - /// - /// - /// - /// - public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name, System.Reflection.Emit.AssemblyBuilderAccess access) + /// + public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name) { if (name is null) throw new ArgumentNullException(nameof(name)); - return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), (AssemblyBuilderAccess)access)); + return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Save)); } - /// - /// Defines a dynamic assembly that has the specified name and access rights. - /// - /// - /// - /// - public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name, System.Reflection.Emit.AssemblyBuilderAccess access, ICustomAttributeBuilder[]? assemblyAttributes) + /// + public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name, ICustomAttributeBuilder[]? assemblyAttributes) { if (name is null) throw new ArgumentNullException(nameof(name)); - return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), (AssemblyBuilderAccess)access, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Save, assemblyAttributes?.Unpack())); } /// @@ -166,6 +156,23 @@ public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) return GetOrCreateModuleSymbol((ModuleBuilder)type.Module).GetOrCreateTypeSymbol(type); } + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IIkvmReflectionMemberSymbol GetOrCreateMemberSymbol(MemberInfo member) + { + return member switch + { + MethodBase method => GetOrCreateMethodBaseSymbol(method), + FieldInfo field => GetOrCreateFieldSymbol(field), + PropertyInfo property => GetOrCreatePropertySymbol(property), + EventInfo @event => GetOrCreateEventSymbol(@event), + _ => throw new InvalidOperationException(), + }; + } + /// /// Gets or creates a for the specified . /// @@ -173,10 +180,11 @@ public IIkvmReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) /// public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) { - if (method is ConstructorInfo ctor) - return GetOrCreateConstructorSymbol(ctor); - else - return GetOrCreateMethodSymbol((MethodInfo)method); + return method switch + { + ConstructorInfo ctor => GetOrCreateConstructorSymbol(ctor), + _ => GetOrCreateMethodSymbol((MethodInfo)method) + }; } /// @@ -186,10 +194,11 @@ public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase me /// public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { - if (ctor is ConstructorBuilder builder) - return GetOrCreateConstructorSymbol(builder); - else - return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); + return ctor switch + { + ConstructorBuilder builder => GetOrCreateConstructorSymbol(builder), + _ => GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor) + }; } /// @@ -209,10 +218,11 @@ public IIkvmReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(Cons /// public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { - if (method is MethodBuilder builder) - return GetOrCreateMethodSymbol(builder); - else - return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); + return method switch + { + MethodBuilder builder => GetOrCreateMethodSymbol(builder), + _ => GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method) + }; } /// @@ -252,10 +262,11 @@ public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(Paramete /// public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - if (field is FieldBuilder builder) - return GetOrCreateFieldSymbol(builder); - else - return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + return field switch + { + FieldBuilder builder => GetOrCreateFieldSymbol(builder), + _ => GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field) + }; } /// @@ -275,10 +286,11 @@ public IIkvmReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder fie /// public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { - if (property is PropertyBuilder builder) - return GetOrCreatePropertySymbol(builder); - else - return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); + return property switch + { + PropertyBuilder builder => GetOrCreatePropertySymbol(builder), + _ => GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property) + }; } /// @@ -298,10 +310,11 @@ public IIkvmReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBu /// public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { - if (@event is EventBuilder builder) - return GetOrCreateEventSymbol(builder); - else - return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + return @event switch + { + EventBuilder builder => GetOrCreateEventSymbol(builder), + _ => GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event) + }; } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs index 5dbe9d7948..7a7d30082c 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -101,6 +101,19 @@ public static AssemblyName[] Unpack(this System.Reflection.AssemblyName[] n) return a; } + /// + /// Unpacks the symbol into their original assembly. + /// + /// + /// + public static Assembly Unpack(this IAssemblySymbol type) + { + if (type is IIkvmReflectionAssemblySymbol symbol) + return symbol.UnderlyingAssembly; + + throw new InvalidOperationException(); + } + /// /// Unpacks the symbol into their original type. /// diff --git a/src/IKVM.CoreLib/Symbols/ImageFileMachine.cs b/src/IKVM.CoreLib/Symbols/ImageFileMachine.cs new file mode 100644 index 0000000000..ea0a8fa692 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ImageFileMachine.cs @@ -0,0 +1,15 @@ +namespace IKVM.CoreLib.Symbols +{ + enum ImageFileMachine + { + + Unknown = 0, + I386 = 0x14c, + ARM = 0x01c0, + IA64 = 0x0200, + AMD64 = 0x8664, + ARM64 = 0xAA64, + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs b/src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs new file mode 100644 index 0000000000..df44e1eea9 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs @@ -0,0 +1,29 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Provides access to manifest resources, which are XML files that describe application dependencies. + /// + readonly struct ManifestResourceInfo(ResourceLocation ResourceLocation, string? FileName, IAssemblySymbol? ReferencedAssembly) + { + + /// + /// Gets the manifest resource's location. + /// + public readonly ResourceLocation ResourceLocation = ResourceLocation; + + /// + /// Gets the name of the file that contains the manifest resource, if it is not the same as the manifest file. + /// + public readonly string? FileName = FileName; + + /// + /// Gets the containing assembly for the manifest resource. + /// + public readonly IAssemblySymbol? ReferencedAssembly = ReferencedAssembly; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index 2d3e9e071b..941d04e53d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.IO; using System.Linq; using System.Reflection; using System.Reflection.Emit; @@ -73,6 +74,64 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } + public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy) + { + throw new NotImplementedException(); + } + + public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, Symbols.Emit.PEFileKinds target) + { + throw new NotImplementedException(); + } + + /// + public void DefineIconResource(byte[] bytes) + { + throw new NotSupportedException(); + } + + /// + public void DefineManifestResource(byte[] bytes) + { + throw new NotSupportedException(); + } + + /// + public void DefineVersionInfoResource() + { +#if NETFRAMEWORK + UnderlyingAssemblyBuilder.DefineVersionInfoResource(); +#else + throw new NotSupportedException(); +#endif + } + + /// + public void AddTypeForwarder(ITypeSymbol type) + { + throw new NotSupportedException(); + } + + /// + public void AddResourceFile(string name, string fileName) + { +#if NETFRAMEWORK + UnderlyingAssemblyBuilder.AddResourceFile(name, fileName); +#else + throw new NotSupportedException(); +#endif + } + + /// + public void Save(string assemblyFileName, PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine) + { +#if NETFRAMEWORK + UnderlyingAssemblyBuilder.Save(assemblyFileName, portableExecutableKind, (System.Reflection.ImageFileMachine)imageFileMachine); +#else + throw new NotSupportedException(); +#endif + } + #endregion #region IAssemblySymbol @@ -101,6 +160,8 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) /// public override bool IsComplete => _builder == null; + public string Location => throw new NotImplementedException(); + /// public ITypeSymbol[] GetExportedTypes() { @@ -192,6 +253,24 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); } + /// + public ManifestResourceInfo? GetManifestResourceInfo(string resourceName) + { + return ResolveManifestResourceInfo(UnderlyingAssembly.GetManifestResourceInfo(resourceName)); + } + + /// + public Stream? GetManifestResourceStream(string name) + { + return UnderlyingAssembly.GetManifestResourceStream(name); + } + + /// + public Stream? GetManifestResourceStream(ITypeSymbol type, string name) + { + return UnderlyingAssembly.GetManifestResourceStream(type.Unpack(), name); + } + #endregion /// @@ -205,7 +284,6 @@ public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder modu { return (IReflectionModuleSymbolBuilder)_metadata.GetOrCreateModuleSymbol(module); } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index e5e3387557..0c6e91d2f0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -1,8 +1,11 @@ using System; using System.Diagnostics.SymbolStore; +using System.IO; using System.Linq; using System.Reflection; using System.Reflection.Emit; +using System.Reflection.PortableExecutable; +using System.Resources; using IKVM.CoreLib.Symbols.Emit; @@ -53,6 +56,54 @@ public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, IReflectio #endif } + /// + public void DefineManifestResource(string name, Stream stream, ResourceAttributes attribute) + { +#if NETFRAMEWORK + UnderlyingModuleBuilder.DefineManifestResource(name, stream, attribute); +#else + throw new NotSupportedException(); +#endif + } + + /// + public IResourceWriter DefineResource(string name, string description) + { +#if NETFRAMEWORK + return UnderlyingModuleBuilder.DefineResource(name, description); +#else + throw new NotImplementedException(); +#endif + } + + /// + public IResourceWriter DefineResource(string name, string description, ResourceAttributes attribute) + { +#if NETFRAMEWORK + return UnderlyingModuleBuilder.DefineResource(name, description, attribute); +#else + throw new NotImplementedException(); +#endif + } + + /// + public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + { + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType.Unpack(), parameterTypes.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] requiredReturnTypeCustomModifiers, ITypeSymbol[] optionalReturnTypeCustomModifiers, ITypeSymbol[] parameterTypes, ITypeSymbol[][] requiredParameterTypeCustomModifiers, ITypeSymbol[][] optionalParameterTypeCustomModifiers) + { + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType.Unpack(), requiredReturnTypeCustomModifiers.Unpack(), optionalReturnTypeCustomModifiers.Unpack(), parameterTypes.Unpack(), requiredParameterTypeCustomModifiers.Unpack(), optionalParameterTypeCustomModifiers.Unpack())); + } + + /// + public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + { + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, returnType.Unpack(), parameterTypes.Unpack())); + } + /// public ITypeSymbolBuilder DefineType(string name) { @@ -107,7 +158,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) UnderlyingModuleBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } -#endregion + #endregion #region IModuleSymbol @@ -129,6 +180,27 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) /// public string ScopeName => UnderlyingModule.ScopeName; + /// + public ulong ImageBase + { + get => throw new NotSupportedException(); + set => throw new NotSupportedException(); + } + + /// + public uint FileAlignment + { + get => throw new NotSupportedException(); + set => throw new NotSupportedException(); + } + + /// + public DllCharacteristics DllCharacteristics + { + get => throw new NotSupportedException(); + set => throw new NotSupportedException(); + } + /// public override bool IsComplete => _builder == null; @@ -301,6 +373,36 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return UnderlyingModule.IsDefined(attributeType.Unpack(), false); } + /// + public void AddReference(IAssemblySymbol assembly) + { +#if NETFRAMEWORK + var t = ((IReflectionAssemblySymbol)assembly).GetExportedTypes(); + if (t.Length > 0) + UnderlyingModuleBuilder.GetTypeToken(t[0].Unpack()); +#else + throw new NotSupportedException(); +#endif + } + + /// + public void AddTypeForwarder(ITypeSymbol type) + { + throw new NotImplementedException(); + } + + /// + public void Complete() + { + UnderlyingModuleBuilder.CreateGlobalFunctions(); + } + + /// + public void Save(PortableExecutableKinds pekind, ImageFileMachine imageFileMachine) + { + throw new NotSupportedException(); + } + #endregion /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 51a6db7e63..8c64b611ed 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -63,6 +63,12 @@ public void AddInterfaceImplementation(ITypeSymbol interfaceType) UnderlyingTypeBuilder.AddInterfaceImplementation(interfaceType.Unpack()); } + /// + public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, ITypeSymbol[]? parameterTypes) + { + return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor(attributes, CallingConventions.Standard, parameterTypes?.Unpack())); + } + /// public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes) { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index 3280e999ba..951f0c2430 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.IO; using System.Linq; using System.Reflection; using System.Reflection.Emit; @@ -49,6 +50,9 @@ public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly assemb /// public string ImageRuntimeVersion => _assembly.ImageRuntimeVersion; + /// + public string Location => _assembly.Location; + /// public IModuleSymbol ManifestModule => ResolveModuleSymbol(_assembly.ManifestModule); @@ -146,6 +150,24 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return _assembly.IsDefined(attributeType.Unpack(), inherit); } + /// + public ManifestResourceInfo? GetManifestResourceInfo(string resourceName) + { + return ResolveManifestResourceInfo(UnderlyingAssembly.GetManifestResourceInfo(resourceName)); + } + + /// + public Stream? GetManifestResourceStream(string name) + { + return UnderlyingAssembly.GetManifestResourceStream(name); + } + + /// + public Stream? GetManifestResourceStream(ITypeSymbol type, string name) + { + return UnderlyingAssembly.GetManifestResourceStream(type.Unpack(), name); + } + #endregion public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index 9c719dd28d..822ba085c0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -524,6 +524,12 @@ public InterfaceMapping ResolveInterfaceMapping(System.Reflection.InterfaceMappi ResolveTypeSymbol(mapping.TargetType)); } + /// + public ManifestResourceInfo? ResolveManifestResourceInfo(System.Reflection.ManifestResourceInfo? info) + { + return info != null ? new ManifestResourceInfo(info.ResourceLocation, info.FileName, ResolveAssemblySymbol(info.ReferencedAssembly)) : null; + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index cb05d82fa3..369833fb7a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -34,12 +34,12 @@ public ReflectionSymbolContext() /// /// /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access) + public IAssemblySymbolBuilder DefineAssembly(AssemblyName name) { if (name is null) throw new ArgumentNullException(nameof(name)); - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, access)); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, AssemblyBuilderAccess.RunAndCollect)); } /// @@ -48,12 +48,12 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderA /// /// /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyName name, AssemblyBuilderAccess access, ICustomAttributeBuilder[]? assemblyAttributes) + public IAssemblySymbolBuilder DefineAssembly(AssemblyName name, ICustomAttributeBuilder[]? assemblyAttributes) { if (name is null) throw new ArgumentNullException(nameof(name)); - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, access, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); } /// diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs new file mode 100644 index 0000000000..f6c3ac835a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs @@ -0,0 +1,43 @@ +using System; + +namespace IKVM.CoreLib.Symbols +{ + + static class TypeSymbolExtensions + { + + /// + /// Gets the associated for the specified type code. + /// + /// + /// + /// + public static Type GetSystemType(this ITypeSymbol symbol) + { + return symbol.TypeCode switch + { + TypeCode.Empty => typeof(void), + TypeCode.Object => typeof(object), + TypeCode.DBNull => typeof(DBNull), + TypeCode.Boolean => typeof(bool), + TypeCode.Char => typeof(Char), + TypeCode.SByte => typeof(SByte), + TypeCode.Byte => typeof(Byte), + TypeCode.Int16 => typeof(Int16), + TypeCode.UInt16 => typeof(UInt16), + TypeCode.Int32 => typeof(Int32), + TypeCode.UInt32 => typeof(UInt32), + TypeCode.Int64 => typeof(Int64), + TypeCode.UInt64 => typeof(UInt64), + TypeCode.Single => typeof(Single), + TypeCode.Double => typeof(Double), + TypeCode.Decimal => typeof(Decimal), + TypeCode.DateTime => typeof(DateTime), + TypeCode.String => typeof(string), + _ => throw new InvalidOperationException(), + }; + } + + } + +} diff --git a/src/IKVM.Reflection/Assembly.cs b/src/IKVM.Reflection/Assembly.cs index b77e7fa09c..f83059e79f 100644 --- a/src/IKVM.Reflection/Assembly.cs +++ b/src/IKVM.Reflection/Assembly.cs @@ -23,6 +23,8 @@ Jeroen Frijters */ using System; using System.Collections.Generic; +using System.IO; +using System.Text; namespace IKVM.Reflection { @@ -83,6 +85,34 @@ public event ModuleResolveEventHandler ModuleResolve public abstract ManifestResourceInfo GetManifestResourceInfo(string resourceName); public abstract System.IO.Stream GetManifestResourceStream(string name); + public virtual System.IO.Stream GetManifestResourceStream(Type type, string name) + { + var sb = new StringBuilder(); + if (type == null) + { + throw new ArgumentNullException(nameof(type)); + } + else + { + string? nameSpace = type.Namespace; + if (nameSpace != null) + { + sb.Append(nameSpace); + if (name != null) + { + sb.Append(System.Type.Delimiter); + } + } + } + + if (name != null) + { + sb.Append(name); + } + + return GetManifestResourceStream(sb.ToString()); + } + internal abstract Type FindType(TypeName name); internal abstract Type FindTypeIgnoreCase(TypeName lowerCaseName); diff --git a/src/IKVM.Runtime/Annotation.cs b/src/IKVM.Runtime/Annotation.cs index 9e4d156f49..69d77735fa 100644 --- a/src/IKVM.Runtime/Annotation.cs +++ b/src/IKVM.Runtime/Annotation.cs @@ -28,13 +28,6 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { @@ -100,7 +93,7 @@ internal static Annotation Load(RuntimeJavaType owner, object[] def) owner.Diagnostics.GenericCompilerWarning($"Unable to load annotation class {annotationClass}"); #if IMPORTER - return new RuntimeManagedByteCodeJavaType.CompiledAnnotation(owner.Context, owner.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").AsReflection()); + return new RuntimeManagedByteCodeJavaType.CompiledAnnotation(owner.Context, owner.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute")); #else return null; #endif diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index 4979b00172..fd2195cb43 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -34,8 +34,6 @@ Jeroen Frijters using IKVM.ByteCode.Encoding; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; -using IKVM.CoreLib.Symbols.IkvmReflection; - #if IMPORTER || EXPORTER using IKVM.Reflection; @@ -267,6 +265,11 @@ internal void SetCustomAttribute(RuntimeClassLoader loader, IParameterSymbolBuil pb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); } + internal void SetCustomAttribute(RuntimeClassLoader loader, IConstructorSymbolBuilder mb, IKVM.Tools.Importer.MapXml.Attribute attr) + { + mb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); + } + internal void SetCustomAttribute(RuntimeClassLoader loader, IMethodSymbolBuilder mb, IKVM.Tools.Importer.MapXml.Attribute attr) { mb.SetCustomAttribute(CreateCustomAttribute(loader, attr)); @@ -298,7 +301,7 @@ void GetAttributeArgsAndTypes(RuntimeClassLoader loader, IKVM.Tools.Importer.Map if (tw.IsArray) { - var arr = Array.CreateInstance(Type.__GetSystemType(tw.ElementTypeWrapper.TypeAsArrayType.TypeCode), attr.Params[i].Elements.Length); + var arr = Array.CreateInstance(tw.ElementTypeWrapper.TypeAsArrayType.GetSystemType(), attr.Params[i].Elements.Length); for (int j = 0; j < arr.Length; j++) arr.SetValue(ParseValue(loader, tw.ElementTypeWrapper, attr.Params[i].Elements[j].Value), j); @@ -416,6 +419,11 @@ internal void SetEditorBrowsableNever(ITypeSymbolBuilder tb) tb.SetCustomAttribute(GetEditorBrowsableNever()); } + internal void SetEditorBrowsableNever(IConstructorSymbolBuilder mb) + { + mb.SetCustomAttribute(GetEditorBrowsableNever()); + } + internal void SetEditorBrowsableNever(IMethodSymbolBuilder mb) { mb.SetCustomAttribute(GetEditorBrowsableNever()); @@ -450,6 +458,16 @@ internal void SetDeprecatedAttribute(IPropertySymbolBuilder pb) pb.SetCustomAttribute(deprecatedAttribute); } + internal void SetThrowsAttribute(IConstructorSymbolBuilder mb, string[] exceptions) + { + if (exceptions != null && exceptions.Length != 0) + { + throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); + exceptions = UnicodeUtil.EscapeInvalidSurrogates(exceptions); + mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(throwsAttribute, [exceptions])); + } + } + internal void SetThrowsAttribute(IMethodSymbolBuilder mb, string[] exceptions) { if (exceptions != null && exceptions.Length != 0) @@ -500,6 +518,11 @@ internal void HideFromJava(ITypeSymbolBuilder typeBuilder) typeBuilder.SetCustomAttribute(HideFromJavaAttributeBuilder); } + internal void HideFromJava(IConstructorSymbolBuilder ctor) + { + ctor.SetCustomAttribute(HideFromJavaAttributeBuilder); + } + internal void HideFromJava(IMethodSymbolBuilder mb) { mb.SetCustomAttribute(HideFromJavaAttributeBuilder); @@ -726,6 +749,17 @@ internal void SetDebuggingModes(IAssemblySymbolBuilder assemblyBuilder, Debuggab #if IMPORTER + internal void SetModifiers(IConstructorSymbolBuilder cb, Modifiers modifiers, bool isInternal) + { + ICustomAttributeBuilder customAttributeBuilder; + if (isInternal) + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); + else + customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); + + cb.SetCustomAttribute(customAttributeBuilder); + } + internal void SetModifiers(IMethodSymbolBuilder mb, Modifiers modifiers, bool isInternal) { ICustomAttributeBuilder customAttributeBuilder; @@ -791,7 +825,7 @@ internal void SetSourceFile(ITypeSymbolBuilder typeBuilder, string filename) typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(sourceFileAttribute, [filename])); } - internal void SetSourceFile(IMethodSymbolBuilder moduleBuilder, string filename) + internal void SetSourceFile(IModuleSymbolBuilder moduleBuilder, string filename) { sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor([context.Types.String]); moduleBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(sourceFileAttribute, [filename])); diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index b32b34ba9c..59f1fde78b 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -72,11 +72,21 @@ public CodeEmitterFactory(RuntimeContext context) /// /// Creates a new instance. /// - /// + /// /// - public CodeEmitter Create(IMethodSymbolBuilder mb) + public CodeEmitter Create(IMethodSymbolBuilder method) { - return new CodeEmitter(context, mb.GetILGenerator(), mb.DeclaringType); + return new CodeEmitter(context, method.GetILGenerator(), method.DeclaringType); + } + + /// + /// Creates a new instance. + /// + /// + /// + public CodeEmitter Create(IConstructorSymbolBuilder ctor) + { + return new CodeEmitter(context, ctor.GetILGenerator(), ctor.DeclaringType); } #if IMPORTER == false diff --git a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs index 9f5843661a..6c48e74ad5 100644 --- a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs +++ b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs @@ -3,13 +3,16 @@ using System; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER || EXPORTER using IKVM.Reflection; +using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; #else using System.Reflection; +using System.Reflection.Emit; #endif namespace IKVM.Runtime @@ -33,6 +36,13 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// IAssemblySymbol? ResolveAssembly(Assembly? assembly); + /// + /// Gets the associated with the specified assembly. + /// + /// + /// + IAssemblySymbolBuilder? ResolveAssembly(AssemblyBuilder? assembly); + /// /// Gets the associated with the specified module. /// @@ -40,6 +50,13 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// IModuleSymbol? ResolveModule(Module? module); + /// + /// Gets the associated with the specified module. + /// + /// + /// + IModuleSymbolBuilder? ResolveModule(ModuleBuilder? module); + /// /// Gets the associated with the specified type. /// @@ -47,6 +64,13 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// ITypeSymbol? ResolveType(Type? type); + /// + /// Gets the associated with the specified member. + /// + /// + /// + IMemberSymbol? ResolveMember(MemberInfo? memberInfo); + /// /// Gets the associated with the specified method. /// diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index f684f71ef3..86868c4bb0 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -146,9 +146,9 @@ internal static bool IsConstructor(IMethodBaseSymbol method) return method.IsSpecialName && method.Name == ConstructorInfo.ConstructorName; } - internal static IMethodSymbolBuilder DefineConstructor(ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs, ITypeSymbol[] parameterTypes) + internal static IConstructorSymbolBuilder DefineConstructor(ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs, ITypeSymbol[] parameterTypes) { - return tb.DefineMethod(ConstructorInfo.ConstructorName, attribs | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName, null, parameterTypes); + return tb.DefineConstructor(attribs | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName, parameterTypes); } /// @@ -156,7 +156,7 @@ internal static IMethodSymbolBuilder DefineConstructor(ITypeSymbolBuilder tb, Sy /// /// /// - internal static bool CanOwnDynamicMethod(Type type) + internal static bool CanOwnDynamicMethod(ITypeSymbol type) { return type != null && !type.IsInterface && !type.HasElementType && !type.IsGenericTypeDefinition && !type.IsGenericParameter; } @@ -192,13 +192,9 @@ private static bool MatchTypes(ITypeSymbol[] t1, ITypeSymbol[] t2) return false; } - internal static bool IsVector(Type type) + internal static bool IsVector(ITypeSymbol type) { -#if NET return type.IsSZArray; -#else - return type.IsArray && type.Name.EndsWith("[]"); -#endif } #if IMPORTER diff --git a/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs b/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs index e5d2c4518c..de3211c8c9 100644 --- a/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeAccessStubJavaMethod.cs @@ -21,15 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index 86cdeeb73f..e44241a4a3 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -450,11 +450,11 @@ internal RuntimeAssemblyClassLoader(RuntimeContext context, IAssemblySymbol asse #if IMPORTER - internal static void PreloadExportedAssemblies(StaticCompiler compiler, Assembly assembly) + internal static void PreloadExportedAssemblies(StaticCompiler compiler, IAssemblySymbol assembly) { if (assembly.GetManifestResourceInfo("ikvm.exports") != null) { - using (Stream stream = assembly.GetManifestResourceStream("ikvm.exports")) + using (var stream = assembly.GetManifestResourceStream("ikvm.exports")) { var rdr = new BinaryReader(stream); var assemblyCount = rdr.ReadInt32(); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index 8c18ded242..c884f801a6 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -59,7 +59,7 @@ internal sealed class FinishContext List nestedTypeBuilders; IMethodSymbol callerIDMethod; List items; - Dictionary arfuMap; + Dictionary arfuMap; Dictionary invokespecialstubcache; Dictionary dynamicClassLiteral; #if IMPORTER @@ -289,7 +289,7 @@ internal ITypeSymbol FinishImpl() } } #if IMPORTER - TypeBuilder tbDefaultMethods = null; + ITypeSymbolBuilder tbDefaultMethods = null; #endif bool basehasclinit = wrapper.BaseTypeWrapper != null && wrapper.BaseTypeWrapper.HasStaticInitializer; int clinitIndex = -1; @@ -389,7 +389,7 @@ internal ITypeSymbol FinishImpl() #if IMPORTER // see if there exists a "managed JNI" class for this type - var nativeCodeType = context.Resolver.ResolveRuntimeType("IKVM.Java.Externs." + classFile.Name.Replace("$", "+")).AsReflection(); + var nativeCodeType = context.Resolver.ResolveRuntimeType("IKVM.Java.Externs." + classFile.Name.Replace("$", "+")); if (nativeCodeType != null) { if (!m.IsStatic) @@ -398,7 +398,7 @@ internal ITypeSymbol FinishImpl() if (methods[i].HasCallerID) nargs = ArrayUtil.Concat(nargs, context.JavaBase.TypeOfIkvmInternalCallerID); - foreach (var method in nativeCodeType.GetMethods(BindingFlags.Static | BindingFlags.Public)) + foreach (var method in nativeCodeType.GetMethods(System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public)) { var param = method.GetParameters(); int paramLength = param.Length; @@ -762,7 +762,7 @@ internal ITypeSymbol FinishImpl() #if IMPORTER - static void AddConstantPoolAttributeIfNecessary(RuntimeContext context, ClassFile classFile, TypeBuilder typeBuilder) + static void AddConstantPoolAttributeIfNecessary(RuntimeContext context, ClassFile classFile, ITypeSymbolBuilder typeBuilder) { object[] constantPool = null; bool[] inUse = null; @@ -974,11 +974,10 @@ private bool EmitInterlockedCompareAndSet(RuntimeJavaMethod method, string field return false; } - FieldInfo fi = casField.GetField(); + var fi = casField.GetField(); if (fi == null) - { return false; - } + ilGenerator.EmitLdarg(0); ilGenerator.Emit(OpCodes.Ldflda, fi); ilGenerator.EmitLdarg(2); @@ -1059,14 +1058,14 @@ private void AddMethodParameterInfo(ClassFile.Method m, RuntimeJavaMethod mw, IM #if IMPORTER - private void AddImplementsAttribute() + void AddImplementsAttribute() { var interfaces = wrapper.Interfaces; if (wrapper.BaseTypeWrapper == context.JavaBase.TypeOfJavaLangObject) { // We special case classes extending java.lang.Object to optimize the metadata encoding // for anonymous classes that implement an interface. - Type[] actualInterfaces = typeBuilder.GetInterfaces(); + var actualInterfaces = typeBuilder.GetInterfaces(); if (actualInterfaces.Length == 0) { return; @@ -1089,14 +1088,13 @@ private void AddImplementsAttribute() context.AttributeHelper.SetImplementsAttribute(typeBuilder, interfaces); } - private TypeBuilder DefineNestedInteropType(string name) + ITypeSymbolBuilder DefineNestedInteropType(string name) { - ImportClassLoader ccl = wrapper.classLoader; + var ccl = wrapper.classLoader; while (!ccl.ReserveName(classFile.Name + "$" + name)) - { name += "_"; - } - TypeBuilder tb = typeBuilder.DefineNestedType(name, TypeAttributes.Class | TypeAttributes.NestedPublic | TypeAttributes.Sealed | TypeAttributes.Abstract); + + var tb = typeBuilder.DefineNestedType(name, TypeAttributes.Class | TypeAttributes.NestedPublic | TypeAttributes.Sealed | TypeAttributes.Abstract); RegisterNestedTypeBuilder(tb); context.AttributeHelper.HideFromJava(tb); return tb; @@ -1112,17 +1110,13 @@ void AddInterfaceMethodsInterop(RuntimeJavaMethod[] methods) } - private void CreateDefaultMethodInterop(ref TypeBuilder tbDefaultMethods, IMethodSymbolBuilder defaultMethod, RuntimeJavaMethod mw) + private void CreateDefaultMethodInterop(ref ITypeSymbolBuilder tbDefaultMethods, IMethodSymbolBuilder defaultMethod, RuntimeJavaMethod mw) { if (!ParametersAreAccessible(mw)) - { return; - } if (tbDefaultMethods == null) - { tbDefaultMethods = DefineNestedInteropType(NestedTypeName.DefaultMethods); - } var mb = mw.GetDefineMethodHelper().DefineMethod(wrapper.ClassLoader.GetTypeWrapperFactory(), tbDefaultMethods, mw.Name, MethodAttributes.Public | MethodAttributes.Static, wrapper.TypeAsSignatureType, true); var ilgen = context.CodeEmitterFactory.Create(mb); @@ -1303,7 +1297,7 @@ void GenerateAccessStub(RuntimeJavaField fw, bool type1) // we append the IKVM.Attributes.AccessStub type to the modopt array for use in the property accessor method signature // to make sure they never conflict with any user defined methhods - var modopt2 = ArrayUtil.Concat(modopt, context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName).AsReflection()); + var modopt2 = ArrayUtil.Concat(modopt, context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName)); var getter = typeBuilder.DefineMethod("get_" + fw.Name, attribs, CallingConventions.Standard, propType, null, modopt2, [], null, null); context.AttributeHelper.HideFromJava(getter); pb.SetGetMethod(getter); @@ -1400,7 +1394,7 @@ void GenerateAccessStub(int id, RuntimeJavaMethod mw, bool virt, bool type1) } var returnType = mw.ReturnType.TypeAsPublicSignatureType; - var modoptReturnType = ArrayUtil.Concat(wrapper.GetModOpt(mw.ReturnType, true), context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName).AsReflection()); + var modoptReturnType = ArrayUtil.Concat(wrapper.GetModOpt(mw.ReturnType, true), context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName)); string name; if (mw.Name == StringConstants.INIT) @@ -1594,7 +1588,7 @@ IMethodSymbolBuilder DefineInterfaceStubMethod(string name, RuntimeJavaMethod mw internal static class JniProxyBuilder { - readonly static ModuleBuilder mod; + readonly static IModuleSymbolBuilder mod; static int count; /// @@ -1602,8 +1596,8 @@ internal static class JniProxyBuilder /// static JniProxyBuilder() { - mod = DynamicClassLoader.CreateJniProxyModuleBuilder(); - var cab = new CustomAttributeBuilder(JVM.Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName).GetConstructor([]).AsReflection(), []); + mod = DynamicClassLoader.CreateJniProxyModuleBuilder(JVM.Context); + var cab = JVM.Context.Resolver.Symbols.CreateCustomAttribute(JVM.Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName).GetConstructor([]), []); mod.SetCustomAttribute(cab); } @@ -1611,36 +1605,34 @@ internal static void Generate(RuntimeByteCodeJavaType.FinishContext context, Cod { var tb = mod.DefineType("__" + System.Threading.Interlocked.Increment(ref count), TypeAttributes.Public | TypeAttributes.Class); int instance = m.IsStatic ? 0 : 1; - var argTypes = new ITypeSymbolvvvvvvvvvvvvvvvv[args.Length + instance + 1]; + var argTypes = new ITypeSymbol[args.Length + instance + 1]; if (instance != 0) - { - argTypes[0] = typeof(object); - } + argTypes[0] = context.Context.Types.Object; + for (int i = 0; i < args.Length; i++) { // NOTE we take a shortcut here by assuming that all "special" types (i.e. ghost or value types) // are public and so we can get away with replacing all other types with object. - argTypes[i + instance] = !args[i].IsUnloadable && (args[i].IsPrimitive || args[i].IsGhost || args[i].IsNonPrimitiveValueType) ? args[i].TypeAsSignatureType : typeof(object); + argTypes[i + instance] = !args[i].IsUnloadable && (args[i].IsPrimitive || args[i].IsGhost || args[i].IsNonPrimitiveValueType) ? args[i].TypeAsSignatureType : context.Context.Types.Object; } argTypes[argTypes.Length - 1] = context.context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType; - var retType = !mw.ReturnType.IsUnloadable && (mw.ReturnType.IsPrimitive || mw.ReturnType.IsGhost || mw.ReturnType.IsNonPrimitiveValueType) ? mw.ReturnType.TypeAsSignatureType : typeof(object); + var retType = !mw.ReturnType.IsUnloadable && (mw.ReturnType.IsPrimitive || mw.ReturnType.IsGhost || mw.ReturnType.IsNonPrimitiveValueType) ? mw.ReturnType.TypeAsSignatureType : context.Context.Types.Object; var mb = tb.DefineMethod("method", MethodAttributes.Public | MethodAttributes.Static, retType, argTypes); context.context.AttributeHelper.HideFromJava(mb); - CodeEmitter ilgen = context.context.CodeEmitterFactory.Create(mb); + var ilgen = context.context.CodeEmitterFactory.Create(mb); new JniBuilder(context.context).Generate(context, ilgen, wrapper, mw, tb, classFile, m, args, true); ilgen.DoEmit(); - tb.CreateType(); + tb.Complete(); + for (int i = 0; i < argTypes.Length - 1; i++) - { ilGenerator.EmitLdarg(i); - } + context.EmitCallerID(ilGenerator, m.IsLambdaFormCompiled); ilGenerator.Emit(OpCodes.Call, mb); if (!mw.ReturnType.IsUnloadable && !mw.ReturnType.IsPrimitive && !mw.ReturnType.IsGhost && !mw.ReturnType.IsNonPrimitiveValueType) - { ilGenerator.Emit(OpCodes.Castclass, mw.ReturnType.TypeAsSignatureType); - } + ilGenerator.Emit(OpCodes.Ret); } } @@ -1907,7 +1899,7 @@ void EmitCallerIDStub(RuntimeJavaMethod mw, string[] parameterNames) } ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.Emit(OpCodes.Ldc_I4_0); - ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveCoreType(typeof(StackFrame).FullName).AsReflection().GetConstructor(new ITypeSymbol[] { context.Types.Int32, context.Types.Boolean })); + ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveCoreType(typeof(StackFrame).FullName).GetConstructor(new ITypeSymbol[] { context.Types.Int32, context.Types.Boolean })); var callerID = context.JavaBase.TypeOfIkvmInternalCallerID.GetMethodWrapper("create", "(Lcli.System.Diagnostics.StackFrame;)Likvm.internal.CallerID;", false); callerID.Link(); callerID.EmitCall(ilgen); @@ -2187,7 +2179,7 @@ void EmitConstantValueInitialization(RuntimeJavaField[] fields, CodeEmitter ilGe } } - internal IMethodSymbolBuilder DefineThreadLocalType() + internal IConstructorSymbolBuilder DefineThreadLocalType() { var threadLocal = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicThreadLocal"); int id = nestedTypeBuilders == null ? 0 : nestedTypeBuilders.Count; @@ -2219,26 +2211,28 @@ internal IMethodSymbolBuilder DefineThreadLocalType() return cb; } - internal IMethodSymbolBuilder GetAtomicReferenceFieldUpdater(RuntimeJavaField field) + internal IConstructorSymbolBuilder GetAtomicReferenceFieldUpdater(RuntimeJavaField field) { - arfuMap ??= new Dictionary(); + arfuMap ??= new Dictionary(); if (!arfuMap.TryGetValue(field, out var cb)) { var arfuTypeWrapper = context.ClassLoaderFactory.LoadClassCritical("ikvm.internal.IntrinsicAtomicReferenceFieldUpdater"); var tb = typeBuilder.DefineNestedType(NestedTypeName.AtomicReferenceFieldUpdater + arfuMap.Count, TypeAttributes.NestedPrivate | TypeAttributes.Sealed, arfuTypeWrapper.TypeAsBaseType); AtomicReferenceFieldUpdaterEmitter.EmitImpl(context, tb, field.GetField()); + cb = ReflectUtil.DefineConstructor(tb, MethodAttributes.Assembly, []); arfuMap.Add(field, cb); - CodeEmitter ctorilgen = context.CodeEmitterFactory.Create(cb); + var ctorilgen = context.CodeEmitterFactory.Create(cb); ctorilgen.Emit(OpCodes.Ldarg_0); - RuntimeJavaMethod basector = arfuTypeWrapper.GetMethodWrapper("", "()V", false); + var basector = arfuTypeWrapper.GetMethodWrapper("", "()V", false); basector.Link(); basector.EmitCall(ctorilgen); ctorilgen.Emit(OpCodes.Ret); ctorilgen.DoEmit(); RegisterNestedTypeBuilder(tb); } + return cb; } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs index ea6793966e..d4eb4c2595 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.DelegateConstructorMethodWrapper.cs @@ -39,7 +39,7 @@ private sealed partial class JavaTypeImpl sealed class DelegateConstructorMethodWrapper : RuntimeJavaMethod { - IMethodSymbolBuilder constructor; + IConstructorSymbolBuilder constructor; IMethodSymbol invoke; /// diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index af8b03ae0d..0f287ff2ce 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -282,7 +282,7 @@ internal void CreateStep2() bool cantNest = false; bool setModifiers = false; - TypeBuilder enclosing = null; + ITypeSymbolBuilder enclosing = null; string enclosingClassName = null; // we only compile inner classes as nested types in the static compiler, because it has a higher cost // and doesn't buy us anything in dynamic mode (and if fact, due to an FXBUG it would make handling @@ -623,17 +623,18 @@ void AddCliEnum() while (!ccl.ReserveName(classFile.Name + "$" + name)) name += "_"; - enumBuilder = typeBuilder.DefineNestedType(name, TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.NestedPublic | TypeAttributes.Serializable, wrapper.Context.Types.Enum.AsReflection()); + enumBuilder = typeBuilder.DefineNestedType(name, TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.NestedPublic | TypeAttributes.Serializable, wrapper.Context.Types.Enum); wrapper.Context.AttributeHelper.HideFromJava(enumBuilder); - enumBuilder.DefineField("value__", wrapper.Context.Types.Int32.AsReflection(), FieldAttributes.Public | FieldAttributes.SpecialName | FieldAttributes.RTSpecialName); + enumBuilder.DefineField("value__", wrapper.Context.Types.Int32, FieldAttributes.Public | FieldAttributes.SpecialName | FieldAttributes.RTSpecialName); for (int i = 0; i < classFile.Fields.Length; i++) { if (classFile.Fields[i].IsEnum) { - FieldBuilder fieldBuilder = enumBuilder.DefineField(classFile.Fields[i].Name, enumBuilder, FieldAttributes.Public | FieldAttributes.Static | FieldAttributes.Literal); + var fieldBuilder = enumBuilder.DefineField(classFile.Fields[i].Name, enumBuilder, FieldAttributes.Public | FieldAttributes.Static | FieldAttributes.Literal); fieldBuilder.SetConstant(i); } } + wrapper.SetEnumType(enumBuilder); } #endif @@ -648,7 +649,7 @@ void AddClinitTrigger() var hasfields = false; // If we have any public static fields, the cctor trigger must (and may) be public as well - foreach (ClassFile.Field fld in classFile.Fields) + foreach (var fld in classFile.Fields) { if (fld.IsPublic && fld.IsStatic) { @@ -685,29 +686,25 @@ private static bool HasStructLayoutAttributeAnnotation(ClassFile c) } #if IMPORTER - private ClassFile.InnerClass getOuterClass() + ClassFile.InnerClass getOuterClass() { - ClassFile.InnerClass[] innerClasses = classFile.InnerClasses; + var innerClasses = classFile.InnerClasses; if (innerClasses != null) - { for (int j = 0; j < innerClasses.Length; j++) - { if (innerClasses[j].innerClass.IsNotNil && classFile.GetConstantPoolClass(innerClasses[j].innerClass) == classFile.Name) - { return innerClasses[j]; - } - } - } + return new ClassFile.InnerClass(); } - private bool IsSideEffectFreeStaticInitializerOrNoop(ClassFile.Method m, out bool noop) + bool IsSideEffectFreeStaticInitializerOrNoop(ClassFile.Method m, out bool noop) { if (m.ExceptionTable.Length != 0) { noop = false; return false; } + noop = true; for (int i = 0; i < m.Instructions.Length; i++) { @@ -725,14 +722,16 @@ private bool IsSideEffectFreeStaticInitializerOrNoop(ClassFile.Method m, out boo // uses a goto to remove the (now unused) code i = target; } + if (bc == NormalizedByteCode.__getstatic || bc == NormalizedByteCode.__putstatic) { - ClassFile.ConstantPoolItemFieldref fld = classFile.SafeGetFieldref(m.Instructions[i].Arg1); + var fld = classFile.SafeGetFieldref(m.Instructions[i].Arg1); if (fld == null || fld.Class != classFile.Name) { noop = false; return false; } + // don't allow getstatic to load non-primitive fields, because that would // cause the verifier to try to load the type if (bc == NormalizedByteCode.__getstatic && "L[".IndexOf(fld.Signature[0]) != -1) @@ -740,12 +739,14 @@ private bool IsSideEffectFreeStaticInitializerOrNoop(ClassFile.Method m, out boo noop = false; return false; } - ClassFile.Field field = classFile.GetField(fld.Name, fld.Signature); + + var field = classFile.GetField(fld.Name, fld.Signature); if (field == null) { noop = false; return false; } + if (bc == NormalizedByteCode.__putstatic) { if (field.IsProperty && field.PropertySetter != null) @@ -791,11 +792,11 @@ private bool IsSideEffectFreeStaticInitializerOrNoop(ClassFile.Method m, out boo } #endif // IMPORTER - private RuntimeJavaMethod GetMethodWrapperDuringCtor(RuntimeJavaType lookup, IList methods, string name, string sig) + RuntimeJavaMethod GetMethodWrapperDuringCtor(RuntimeJavaType lookup, IList methods, string name, string sig) { if (lookup == wrapper) { - foreach (RuntimeJavaMethod mw in methods) + foreach (var mw in methods) { if (mw.Name == name && mw.Signature == sig) { @@ -817,17 +818,19 @@ private RuntimeJavaMethod GetMethodWrapperDuringCtor(RuntimeJavaType lookup, ILi } } - private void AddMirandaMethods(List methods, List baseMethods, RuntimeJavaType tw) + void AddMirandaMethods(List methods, List baseMethods, RuntimeJavaType tw) { - foreach (RuntimeJavaType iface in tw.Interfaces) + foreach (var iface in tw.Interfaces) { if (iface.IsPublic && this.wrapper.IsInterface) { // for interfaces, we only need miranda methods for non-public interfaces that we extend continue; } + AddMirandaMethods(methods, baseMethods, iface); - foreach (RuntimeJavaMethod ifmethod in iface.GetMethods()) + + foreach (var ifmethod in iface.GetMethods()) { // skip and non-virtual interface methods introduced in Java 8 if (ifmethod.IsVirtual) @@ -835,23 +838,26 @@ private void AddMirandaMethods(List methods, List methods, List outer.Length + 1 && inner[outer.Length] == '$' && inner.StartsWith(outer, StringComparison.Ordinal); } - private string AllocNestedTypeName(string outer, string inner) + string AllocNestedTypeName(string outer, string inner) { Debug.Assert(CheckInnerOuterNames(inner, outer)); nestedTypeNames ??= new ConcurrentDictionary(); @@ -892,20 +899,16 @@ private string AllocNestedTypeName(string outer, string inner) #endif - private int GetMethodIndex(RuntimeJavaMethod mw) + int GetMethodIndex(RuntimeJavaMethod mw) { for (int i = 0; i < methods.Length; i++) - { if (methods[i] == mw) - { return i; - } - } throw new InvalidOperationException(); } - private static void CheckLoaderConstraints(RuntimeJavaMethod mw, RuntimeJavaMethod baseMethod) + static void CheckLoaderConstraints(RuntimeJavaMethod mw, RuntimeJavaMethod baseMethod) { if (mw.ReturnType != baseMethod.ReturnType) { @@ -913,9 +916,7 @@ private static void CheckLoaderConstraints(RuntimeJavaMethod mw, RuntimeJavaMeth { // unloadable types can never cause a loader constraint violation if (mw.ReturnType.IsUnloadable && baseMethod.ReturnType.IsUnloadable) - { ((RuntimeUnloadableJavaType)mw.ReturnType).SetCustomModifier(((RuntimeUnloadableJavaType)baseMethod.ReturnType).CustomModifier); - } } else { @@ -926,8 +927,9 @@ private static void CheckLoaderConstraints(RuntimeJavaMethod mw, RuntimeJavaMeth #endif } } - RuntimeJavaType[] here = mw.GetParameters(); - RuntimeJavaType[] there = baseMethod.GetParameters(); + + var here = mw.GetParameters(); + var there = baseMethod.GetParameters(); for (int i = 0; i < here.Length; i++) { if (here[i] != there[i]) @@ -1034,7 +1036,7 @@ internal override IFieldSymbol LinkField(RuntimeJavaField fw) var methodAttribs = MethodAttributes.HideBySig; #if IMPORTER - bool setModifiers = fld.IsInternal || (fld.Modifiers & (Modifiers.Synthetic | Modifiers.Enum)) != 0; + var setModifiers = fld.IsInternal || (fld.Modifiers & (Modifiers.Synthetic | Modifiers.Enum)) != 0; #endif if (fld.IsPrivate) @@ -1090,19 +1092,13 @@ internal override IFieldSymbol LinkField(RuntimeJavaField fw) else if (fld.IsFinal) { if (wrapper.IsInterface || wrapper.classLoader.StrictFinalFieldSemantics) - { attribs |= FieldAttributes.InitOnly; - } else - { setModifiers = true; - } } #else if (fld.IsFinal && wrapper.IsInterface) - { attribs |= FieldAttributes.InitOnly; - } #endif field = DefineField(realFieldName, fw.FieldTypeWrapper, attribs, fld.IsVolatile); @@ -1270,7 +1266,7 @@ FinishedTypeImpl FinishCore() if (annotationBuilder != null) { - var cab = new CustomAttributeBuilder(wrapper.Context.Resolver.ResolveRuntimeType(typeof(AnnotationAttributeAttribute).FullName).AsReflection().GetConstructor(new Type[] { wrapper.Context.Types.String }), new object[] { UnicodeUtil.EscapeInvalidSurrogates(annotationBuilder.AttributeTypeName) }); + var cab = wrapper.Context.Resolver.Symbols.CreateCustomAttribute(wrapper.Context.Resolver.ResolveRuntimeType(typeof(AnnotationAttributeAttribute).FullName).GetConstructor([wrapper.Context.Types.String]), [UnicodeUtil.EscapeInvalidSurrogates(annotationBuilder.AttributeTypeName)]); typeBuilder.SetCustomAttribute(cab); } @@ -1293,11 +1289,11 @@ FinishedTypeImpl FinishCore() } if (enumBuilder != null) { - enumBuilder.CreateType(); + enumBuilder.Complete(); } if (privateInterfaceMethods != null) { - privateInterfaceMethods.CreateType(); + privateInterfaceMethods.Complete(); } #endif var finishedClinitMethod = (IMethodSymbol)clinitMethod; @@ -1383,7 +1379,7 @@ sealed class AnnotationBuilder : Annotation ITypeSymbolBuilder outer; ITypeSymbolBuilder annotationTypeBuilder; ITypeSymbolBuilder attributeTypeBuilder; - IMethodSymbolBuilder defineConstructor; + IConstructorSymbolBuilder defineConstructor; /// /// Initializes a new instance. @@ -1471,11 +1467,11 @@ internal void Link() int dotindex = o.classFile.Name.LastIndexOf('.') + 1; context.AttributeHelper.SetInnerClass(attributeTypeBuilder, o.classFile.Name.Substring(0, dotindex) + "$Proxy" + o.classFile.Name.Substring(dotindex), Modifiers.Final); attributeTypeBuilder.AddInterfaceImplementation(o.typeBuilder); - context.AttributeHelper.SetImplementsAttribute(attributeTypeBuilder, new RuntimeJavaType[] { o.wrapper }); + context.AttributeHelper.SetImplementsAttribute(attributeTypeBuilder, [o.wrapper]); if (o.classFile.Annotations != null) { - CustomAttributeBuilder attributeUsageAttribute = null; + ICustomAttributeBuilder attributeUsageAttribute = null; bool hasAttributeUsageAttribute = false; foreach (object[] def in o.classFile.Annotations) { @@ -1528,7 +1524,7 @@ internal void Link() } } - attributeUsageAttribute = new CustomAttributeBuilder(context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName).GetConstructor([context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName)]).AsReflection(), [targets]); + attributeUsageAttribute = context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName).GetConstructor([context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName)]), [targets]); } } } @@ -1551,7 +1547,7 @@ internal void Link() } } - defineConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, [context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType()]); + defineConstructor = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, [context.Types.Object.MakeArrayType()]); context.AttributeHelper.SetEditorBrowsableNever(defineConstructor); } @@ -1590,7 +1586,7 @@ static ITypeSymbol TypeWrapperToAnnotationParameterType(RuntimeJavaType tw) } if (isArray) - argType = RuntimeArrayJavaType.MakeArrayType(argType, 1); + argType = argType.MakeArrayType(); return argType; } @@ -1608,7 +1604,7 @@ internal string AttributeTypeName Link(); if (attributeTypeBuilder != null) - return attributeTypeBuilder.Symbol.FullName; + return attributeTypeBuilder.FullName; return null; } @@ -1694,7 +1690,7 @@ internal void Finish(JavaTypeImpl o) context.AttributeHelper.HideFromJava(reqArgConstructor); ilgen = context.CodeEmitterFactory.Create(reqArgConstructor); ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Call, defaultConstructor.Symbol); + ilgen.Emit(OpCodes.Call, defaultConstructor); for (int i = 0, j = 0; i < o.methods.Length; i++) { @@ -1716,10 +1712,10 @@ internal void Finish(JavaTypeImpl o) // We don't have any required parameters, but we do have an optional "value" parameter, // so we create an additional constructor (the default constructor will be public in this case) // that accepts the value parameter. - Type argType = TypeWrapperToAnnotationParameterType(o.methods[valueArg].ReturnType); + var argType = TypeWrapperToAnnotationParameterType(o.methods[valueArg].ReturnType); if (argType != null) { - MethodBuilder cb = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, new Type[] { argType }); + var cb = ReflectUtil.DefineConstructor(attributeTypeBuilder, MethodAttributes.Public, [argType]); context.AttributeHelper.HideFromJava(cb); cb.DefineParameter(1, ParameterAttributes.None, "value"); ilgen = context.CodeEmitterFactory.Create(cb); @@ -1762,8 +1758,8 @@ internal void Finish(JavaTypeImpl o) // skip and non-virtual interface methods introduced in Java 8 if (o.methods[i].IsVirtual) { - MethodBuilder mb = o.methods[i].GetDefineMethodHelper().DefineMethod(o.wrapper, attributeTypeBuilder, o.methods[i].Name, MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.Final | MethodAttributes.NewSlot); - attributeTypeBuilder.DefineMethodOverride(mb, (MethodInfo)o.methods[i].GetMethod()); + var mb = o.methods[i].GetDefineMethodHelper().DefineMethod(o.wrapper, attributeTypeBuilder, o.methods[i].Name, MethodAttributes.Private | MethodAttributes.Virtual | MethodAttributes.Final | MethodAttributes.NewSlot); + attributeTypeBuilder.DefineMethodOverride(mb, (IMethodSymbol)o.methods[i].GetMethod()); ilgen = context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ldstr, o.methods[i].Name); @@ -1818,7 +1814,7 @@ internal void Finish(JavaTypeImpl o) && !(o.methods[i].Name == "value" && requiredArgCount == 0)) { // now add a .NET property for this annotation optional parameter - Type argType = TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType); + var argType = TypeWrapperToAnnotationParameterType(o.methods[i].ReturnType); if (argType != null) { var pb = attributeTypeBuilder.DefineProperty(o.methods[i].Name, PropertyAttributes.None, argType, []); @@ -1835,22 +1831,21 @@ internal void Finish(JavaTypeImpl o) pb.SetGetMethod(getter); // TODO implement the getter method ilgen = context.CodeEmitterFactory.Create(getter); - ilgen.ThrowException(context.Resolver.ResolveCoreType(typeof(NotImplementedException).FullName).AsReflection()); + ilgen.ThrowException(context.Resolver.ResolveCoreType(typeof(NotImplementedException).FullName)); ilgen.DoEmit(); } } } } - attributeTypeBuilder.CreateType(); + attributeTypeBuilder.Complete(); } - private CustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) + ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { Link(); - var ctor = defineConstructor != null - ? defineConstructor.__AsConstructorInfo() - : context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").GetConstructor(new [] { context.Types.Object.MakeArrayType() }); - return new CustomAttributeBuilder(ctor, new object[] { AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation)) }); + + var ctor = defineConstructor != null ? defineConstructor : context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").GetConstructor([context.Types.Object.MakeArrayType()]); + return context.Resolver.Symbols.CreateCustomAttribute(ctor, new object[] { AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation)) }); } internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) @@ -2287,7 +2282,7 @@ static IMethodSymbol GetBaseFinalizeMethod(RuntimeJavaType wrapper) } var type = wrapper.TypeAsBaseType; - var baseFinalize = type.GetMethod("__", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, []); + var baseFinalize = type.GetMethod("__", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, []); if (baseFinalize != null) return baseFinalize; @@ -2860,7 +2855,7 @@ IMethodSymbolBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setM #if IMPORTER if (classFile.Methods[index].AnnotationDefault != null) { - var cab = new CustomAttributeBuilder(wrapper.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.AnnotationDefaultAttribute").GetConstructor([wrapper.Context.Types.Object]), [AnnotationDefaultAttribute.Escape(classFile.Methods[index].AnnotationDefault)]); + var cab = wrapper.Context.Resolver.Symbols.CreateCustomAttribute(wrapper.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.AnnotationDefaultAttribute").GetConstructor([wrapper.Context.Types.Object]), [AnnotationDefaultAttribute.Escape(classFile.Methods[index].AnnotationDefault)]); mb.SetCustomAttribute(cab); } #endif diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index f58a1df740..0375c0dfea 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -633,13 +633,13 @@ private static string GetParameterName(string type) protected abstract void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, ClassFile classFile, RuntimeJavaField[] fields, RuntimeJavaMethod[] methods); - protected abstract MethodBuilder DefineGhostMethod(ITypeSymbolBuilder typeBuilder, string name, System.Reflection.MethodAttributes attribs, RuntimeJavaMethod mw); + protected abstract IMethodSymbolBuilder DefineGhostMethod(ITypeSymbolBuilder typeBuilder, string name, System.Reflection.MethodAttributes attribs, RuntimeJavaMethod mw); protected abstract void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaMethod[] methods); protected abstract void FinishGhostStep2(); - protected abstract TypeBuilder DefineGhostType(string mangledTypeName, System.Reflection.TypeAttributes typeAttribs); + protected abstract ITypeSymbolBuilder DefineGhostType(string mangledTypeName, System.Reflection.TypeAttributes typeAttribs); #endif // IMPORTER @@ -657,7 +657,7 @@ private bool IsPInvokeMethod(ClassFile.Method m) { if (method.Attributes != null) foreach (IKVM.Tools.Importer.MapXml.Attribute attr in method.Attributes) - if (Context.StaticCompiler.GetType(classLoader, attr.Type) == Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.DllImportAttribute).FullName).AsReflection()) + if (Context.StaticCompiler.GetType(classLoader, attr.Type) == Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.DllImportAttribute).FullName)) return true; break; diff --git a/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs b/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs index 877505558a..cf22e1ba95 100644 --- a/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs +++ b/src/IKVM.Runtime/RuntimeByteCodePropertyJavaField.cs @@ -21,17 +21,10 @@ Jeroen Frijters jeroen@frijters.net */ -using IKVM.CoreLib.Symbols.Emit; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else using System.Reflection; using System.Reflection.Emit; -#endif + +using IKVM.CoreLib.Symbols.Emit; #if IMPORTER using IKVM.Tools.Importer; diff --git a/src/IKVM.Runtime/RuntimeConstantJavaField.cs b/src/IKVM.Runtime/RuntimeConstantJavaField.cs index 178e1a693a..8403202e46 100644 --- a/src/IKVM.Runtime/RuntimeConstantJavaField.cs +++ b/src/IKVM.Runtime/RuntimeConstantJavaField.cs @@ -23,21 +23,11 @@ Jeroen Frijters */ using System; using System.Diagnostics; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { @@ -151,7 +141,7 @@ protected override void EmitSetImpl(CodeEmitter ilgen) internal override object GetValue(object obj) { var field = GetField(); - return FieldTypeWrapper.IsPrimitive || field == null ? GetConstantValue() : field.GetValue(null); + return FieldTypeWrapper.IsPrimitive || field == null ? GetConstantValue() : field.AsReflection().GetValue(null); } internal override void SetValue(object obj, object value) diff --git a/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs b/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs index 3eb7ca57da..0092b8e3d0 100644 --- a/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeConstructorAccessStubJavaMethod.cs @@ -21,15 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs b/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs index 3350b11ea0..fb43872cac 100644 --- a/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeDefaultInterfaceJavaMethod.cs @@ -21,15 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs b/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs index e986d08224..c24377024d 100644 --- a/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeGhostJavaMethod.cs @@ -27,14 +27,6 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { @@ -83,7 +75,7 @@ protected override void CallvirtImpl(CodeEmitter ilgen) [HideFromJava] internal override object Invoke(object obj, object[] args) { - return InvokeAndUnwrapException(ghostMethod.AsReflection(), DeclaringType.GhostWrap(obj), args); + return InvokeAndUnwrapException(ghostMethod, DeclaringType.GhostWrap(obj), args); } #endif @@ -102,12 +94,12 @@ internal IMethodSymbol GetDefaultImpl() internal void SetGhostMethod(IMethodSymbolBuilder mb) { - this.ghostMethod = mb.Symbol; + this.ghostMethod = mb; } internal IMethodSymbolBuilder GetGhostMethod() { - return ghostMethod.Builder; + return (IMethodSymbolBuilder)ghostMethod; } #endif diff --git a/src/IKVM.Runtime/RuntimeJavaMethod.cs b/src/IKVM.Runtime/RuntimeJavaMethod.cs index 2456f18eea..d416dc4516 100644 --- a/src/IKVM.Runtime/RuntimeJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeJavaMethod.cs @@ -23,24 +23,12 @@ Jeroen Frijters */ using System; using System.Diagnostics; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; - -using System.Linq; - using IKVM.CoreLib.Symbols; - - - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.Runtime { @@ -238,7 +226,7 @@ java.lang.Class[] GetExceptions() // NOTE if method is a MethodBuilder, GetCustomAttributes doesn't work (and if // the method had any declared exceptions, the declaredExceptions field would have // been set) - if (method != null && method.AsReflection() is not MethodBuilder) + if (method != null && method is not IMethodSymbolBuilder) { var attr = DeclaringType.Context.AttributeHelper.GetThrows(method); if (attr != null) @@ -479,49 +467,7 @@ internal ITypeSymbol GetDelegateType() /// internal void ResolveMethod() { -#if FIRST_PASS - throw new NotImplementedException(); -#else - // if we've still got the builder object, we need to replace it with the real thing before we can call it - var mb = method.AsReflection() as MethodBuilder; - if (mb != null) - { -#if NETFRAMEWORK - method = mb.Module.ResolveMethod(mb.GetToken().Token); -#else - // though ResolveMethod exists, Core 3.1 does not provide a stable way to obtain the resulting metadata token - // instead we have to scan the methods for the one that matches the signature using the runtime type instances - // FIXME .NET 6 - - var parameters = GetParameters(); - var typeLength = parameters.Length; - if (HasCallerID) - typeLength++; - - var types = new Type[typeLength]; - for (int i = 0; i < parameters.Length; i++) - { - parameters[i].Finish(); - types[i] = parameters[i].TypeAsSignatureType; - } - - if (HasCallerID) - types[typeLength - 1] = DeclaringType.Context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType; - - if (ReturnType != null) - ReturnType.Finish(); - - var flags = BindingFlags.DeclaredOnly; - flags |= mb.IsPublic ? BindingFlags.Public : BindingFlags.NonPublic; - flags |= mb.IsStatic ? BindingFlags.Static : BindingFlags.Instance; - method = DeclaringType.TypeAsTBD.GetMethods(flags).FirstOrDefault(i => i.Name == mb.Name && i.GetParameters().Select(j => j.ParameterType).SequenceEqual(types) && i.ReturnType.Equals(ReturnType.TypeAsSignatureType)); - if (method == null) - method = DeclaringType.TypeAsTBD.GetConstructor(flags, null, types, null); - if (method == null) - throw new InternalException("Could not resolve method against runtime type."); -#endif - } -#endif + // should not require anything since Symbols should preserve method } [HideFromJava] diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 70d6189dd8..4908a8d3eb 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -24,22 +24,13 @@ Jeroen Frijters using System; using System.Diagnostics; using System.Linq; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; - -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - #if IMPORTER using IKVM.Tools.Importer; #endif diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs index 624b90831a..3b965b99ae 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs @@ -21,20 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { @@ -117,16 +108,16 @@ protected override void EmitSetImpl(CodeEmitter ilgen) internal override object GetValue(object obj) { // we can only be invoked on type 2 access stubs (because type 1 access stubs are HideFromReflection), so we know we have a field - return GetField().GetValue(obj); + return GetField().AsReflection().GetValue(obj); } internal override void SetValue(object obj, object value) { // we can only be invoked on type 2 access stubs (because type 1 access stubs are HideFromReflection), so we know we have a field - GetField().SetValue(obj, value); + GetField().AsReflection().SetValue(obj, value); } -#endif +#endif } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs index da72483acf..c00004b8ce 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.DelegateConstructorJavaMethod.cs @@ -21,17 +21,9 @@ Jeroen Frijters jeroen@frijters.net */ -using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; using System.Reflection.Emit; -#endif + +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs index 6202c75115..dc6311ad04 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs @@ -22,16 +22,11 @@ Jeroen Frijters */ using System.Diagnostics; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index dc1156c110..c0cda24789 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -180,7 +180,7 @@ public RuntimeManagedByteCodeJavaType(RuntimeContext context, ExModifiers exmod, public RuntimeManagedByteCodeJavaType(RuntimeContext context, string name, ITypeSymbol type) : this(context, GetModifiers(context, type), name) { - Debug.Assert(!(type.AsReflection() is TypeBuilder)); + Debug.Assert(!(type is ITypeSymbolBuilder)); Debug.Assert(!type.Name.EndsWith("[]")); this.type = type; @@ -241,7 +241,7 @@ internal override bool HasStaticInitializer { try { - clinitMethod = type.GetMethod("__", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic); + clinitMethod = type.GetMethod("__", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic); } #if IMPORTER catch (IKVM.Reflection.MissingMemberException) @@ -325,10 +325,10 @@ private RuntimeJavaType[] GetInterfaces() private bool IsNestedTypeAnonymousOrLocalClass(ITypeSymbol type) { - switch (type.Attributes & (System.Reflection.TypeAttributes.SpecialName | System.Reflection.TypeAttributes.VisibilityMask)) + switch (type.Attributes & (TypeAttributes.SpecialName | TypeAttributes.VisibilityMask)) { - case System.Reflection.TypeAttributes.SpecialName | System.Reflection.TypeAttributes.NestedPublic: - case System.Reflection.TypeAttributes.SpecialName | System.Reflection.TypeAttributes.NestedAssembly: + case TypeAttributes.SpecialName | TypeAttributes.NestedPublic: + case TypeAttributes.SpecialName | TypeAttributes.NestedAssembly: return Context.AttributeHelper.HasEnclosingMethodAttribute(type); default: return false; @@ -346,7 +346,7 @@ internal override RuntimeJavaType[] InnerClasses { var wrappers = new List(); - foreach (var nested in type.GetNestedTypes(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.DeclaredOnly)) + foreach (var nested in type.GetNestedTypes(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.DeclaredOnly)) { if (IsAnnotationAttribute(nested)) { @@ -652,7 +652,7 @@ void GetNameSigFromMethodBase(IMethodBaseSymbol method, out string name, out str protected override void LazyPublishMethods() { - const System.Reflection.BindingFlags flags = System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance; + const BindingFlags flags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance; var isDelegate = type.BaseType == Context.Types.MulticastDelegate; var methods = new List(); @@ -670,7 +670,7 @@ protected override void LazyPublishMethods() if (type.IsInterface && (type.IsPublic || type.IsNestedPublic)) { - var privateInterfaceMethods = type.GetNestedType(NestedTypeName.PrivateInterfaceMethods, System.Reflection.BindingFlags.NonPublic); + var privateInterfaceMethods = type.GetNestedType(NestedTypeName.PrivateInterfaceMethods, BindingFlags.NonPublic); if (privateInterfaceMethods != null) AddMethods(privateInterfaceMethods.GetMethods(flags), methods); } @@ -714,7 +714,7 @@ private void AddMethodOrConstructor(IMethodBaseSymbol method, HideFromJavaFlags name = name.Substring(name.IndexOf('|', NamePrefix.AccessStub.Length) + 1); flags |= MemberFlags.AccessStub; - var nonvirt = type.GetMethod(NamePrefix.NonVirtual + id, System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Instance); + var nonvirt = type.GetMethod(NamePrefix.NonVirtual + id, BindingFlags.NonPublic | BindingFlags.DeclaredOnly | BindingFlags.Instance); methods.Add(new RuntimeAccessStubJavaMethod(this, name, sig, mi, mi, nonvirt ?? mi, retType, paramTypes, mods.Modifiers & ~Modifiers.Final, flags)); return; } @@ -770,7 +770,7 @@ private void AddMethodOrConstructor(IMethodBaseSymbol method, HideFromJavaFlags IMethodSymbol GetDefaultInterfaceMethodImpl(IMethodSymbol method, string expectedSig) { - foreach (var candidate in method.DeclaringType.GetMethods(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.DeclaredOnly)) + foreach (var candidate in method.DeclaringType.GetMethods(BindingFlags.Public | BindingFlags.Static | BindingFlags.DeclaredOnly)) { if (candidate.IsSpecialName && candidate.Name.StartsWith(NamePrefix.DefaultMethod, StringComparison.Ordinal) && @@ -789,12 +789,12 @@ IMethodSymbol GetDefaultInterfaceMethodImpl(IMethodSymbol method, string expecte bool GetType2AccessStubs(string name, string sig, out IMethodSymbol stubVirt, out IMethodSymbol stubNonVirt) { - const System.Reflection.BindingFlags flags = - System.Reflection.BindingFlags.DeclaredOnly | - System.Reflection.BindingFlags.Public | - System.Reflection.BindingFlags.NonPublic | - System.Reflection.BindingFlags.Static | - System.Reflection.BindingFlags.Instance; + const BindingFlags flags = + BindingFlags.DeclaredOnly | + BindingFlags.Public | + BindingFlags.NonPublic | + BindingFlags.Static | + BindingFlags.Instance; stubVirt = null; stubNonVirt = null; @@ -818,11 +818,11 @@ bool GetType2AccessStubs(string name, string sig, out IMethodSymbol stubVirt, ou bool GetType2AccessStub(string sig, out IConstructorSymbol stub) { - const System.Reflection.BindingFlags flags = - System.Reflection.BindingFlags.DeclaredOnly | - System.Reflection.BindingFlags.Public | - System.Reflection.BindingFlags.NonPublic | - System.Reflection.BindingFlags.Instance; + const BindingFlags flags = + BindingFlags.DeclaredOnly | + BindingFlags.Public | + BindingFlags.NonPublic | + BindingFlags.Instance; stub = null; foreach (var ctor in type.GetConstructors(flags)) @@ -845,12 +845,12 @@ static int SortFieldByToken(IFieldSymbol field1, IFieldSymbol field2) protected override void LazyPublishFields() { - const System.Reflection.BindingFlags flags = - System.Reflection.BindingFlags.DeclaredOnly | - System.Reflection.BindingFlags.Public | - System.Reflection.BindingFlags.NonPublic | - System.Reflection.BindingFlags.Static | - System.Reflection.BindingFlags.Instance; + const BindingFlags flags = + BindingFlags.DeclaredOnly | + BindingFlags.Public | + BindingFlags.NonPublic | + BindingFlags.Static | + BindingFlags.Instance; var fields = new List(); var rawfields = type.GetFields(flags); @@ -1022,9 +1022,7 @@ RuntimeJavaField CreateFieldWrapper(IFieldSymbol field, HideFromJavaFlags hideFr internal override void EmitRunClassConstructor(CodeEmitter ilgen) { if (HasStaticInitializer) - { ilgen.Emit(OpCodes.Call, clinitMethod); - } } #endif // EMITTERS diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs b/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs index 87f276f303..0f1222e26c 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs @@ -21,17 +21,9 @@ Jeroen Frijters jeroen@frijters.net */ -using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; using System.Reflection.Emit; -#endif + +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs index de5ed4d6d6..c27ed2d7ee 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumValueJavaField.cs @@ -21,21 +21,12 @@ Jeroen Frijters jeroen@frijters.net */ -using System; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.FinalizeJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.FinalizeJavaMethod.cs index 719def4df3..b356c8267f 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.FinalizeJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.FinalizeJavaMethod.cs @@ -22,15 +22,10 @@ Jeroen Frijters */ using System; +using System.Reflection.Emit; using IKVM.Attributes; -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs index b81eccfa33..730a30941b 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs @@ -22,15 +22,10 @@ Jeroen Frijters */ using System; +using System.Reflection.Emit; using IKVM.Attributes; -#if IMPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { @@ -70,7 +65,7 @@ internal override void EmitCall(CodeEmitter ilgen) internal override object CreateInstance(object[] args) { - return Activator.CreateInstance(DeclaringType.TypeAsTBD); + return Activator.CreateInstance(DeclaringType.TypeAsTBD.AsReflection()); } #endif diff --git a/src/IKVM.Runtime/RuntimeMirandaJavaMethod.cs b/src/IKVM.Runtime/RuntimeMirandaJavaMethod.cs index 20b759a37e..0cedcd20b2 100644 --- a/src/IKVM.Runtime/RuntimeMirandaJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeMirandaJavaMethod.cs @@ -21,13 +21,9 @@ Jeroen Frijters jeroen@frijters.net */ -using IKVM.Attributes; - -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else using System.Reflection.Emit; -#endif + +using IKVM.Attributes; namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs b/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs index d0e2256a54..dad64f765b 100644 --- a/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs +++ b/src/IKVM.Runtime/RuntimePrimitiveJavaType.cs @@ -22,21 +22,11 @@ Jeroen Frijters */ using System; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs b/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs index e7535f9f79..d02d381139 100644 --- a/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimePrivateInterfaceJavaMethod.cs @@ -21,15 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection.Emit; -#else -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs b/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs index 424a8ac14a..335307cd0c 100644 --- a/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeSimpleCallJavaMethod.cs @@ -24,12 +24,6 @@ Jeroen Frijters using IKVM.Attributes; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -#else -using System.Reflection; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeSimpleJavaField.cs b/src/IKVM.Runtime/RuntimeSimpleJavaField.cs index bba30138f1..4045ad61d3 100644 --- a/src/IKVM.Runtime/RuntimeSimpleJavaField.cs +++ b/src/IKVM.Runtime/RuntimeSimpleJavaField.cs @@ -22,22 +22,10 @@ Jeroen Frijters */ using System.Diagnostics; -using System.Runtime.CompilerServices; -using IKVM.CoreLib.Symbols; - - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; -#else -using System.Reflection; using System.Reflection.Emit; -using System.Threading; -#endif +using System.Runtime.CompilerServices; -#if IMPORTER -using IKVM.Tools.Importer; -#endif +using IKVM.CoreLib.Symbols; namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs b/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs index e2a384afa6..fc1963a95a 100644 --- a/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeTypicalJavaMethod.cs @@ -21,20 +21,11 @@ Jeroen Frijters jeroen@frijters.net */ +using System.Reflection.Emit; + using IKVM.Attributes; using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Type = IKVM.Reflection.Type; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs b/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs index e2c161e133..3b4dc7fba2 100644 --- a/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs +++ b/src/IKVM.Runtime/RuntimeVolatileLongDoubleJavaField.cs @@ -22,17 +22,10 @@ Jeroen Frijters */ using System; +using System.Reflection.Emit; using IKVM.CoreLib.Symbols; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/Serialization.cs b/src/IKVM.Runtime/Serialization.cs index c11630dbbf..a2dfffbfbb 100644 --- a/src/IKVM.Runtime/Serialization.cs +++ b/src/IKVM.Runtime/Serialization.cs @@ -89,9 +89,9 @@ bool IsSafeForAutomagicSerialization(RuntimeJavaType wrapper) return true; } - internal IMethodSymbolBuilder AddAutomagicSerialization(RuntimeByteCodeJavaType wrapper, ITypeSymbolBuilder typeBuilder) + internal IConstructorSymbolBuilder AddAutomagicSerialization(RuntimeByteCodeJavaType wrapper, ITypeSymbolBuilder typeBuilder) { - IMethodSymbolBuilder serializationCtor = null; + IConstructorSymbolBuilder serializationCtor = null; if ((wrapper.Modifiers & IKVM.Attributes.Modifiers.Enum) != 0) { MarkSerializable(typeBuilder); @@ -148,7 +148,7 @@ internal IMethodSymbolBuilder AddAutomagicSerialization(RuntimeByteCodeJavaType return serializationCtor; } - internal IMethodSymbolBuilder AddAutomagicSerializationToWorkaroundBaseClass(ITypeSymbolBuilder typeBuilderWorkaroundBaseClass, IMethodBaseSymbol baseCtor) + internal IConstructorSymbolBuilder AddAutomagicSerializationToWorkaroundBaseClass(ITypeSymbolBuilder typeBuilderWorkaroundBaseClass, IMethodBaseSymbol baseCtor) { if (typeBuilderWorkaroundBaseClass.BaseType.IsSerializable) { @@ -187,7 +187,7 @@ internal void AddGetObjectData(ITypeSymbolBuilder tb) ilgen.DoEmit(); } - IMethodSymbolBuilder AddConstructor(ITypeSymbolBuilder tb, RuntimeJavaMethod defaultConstructor, IMethodBaseSymbol serializationConstructor, bool callReadObject) + IConstructorSymbolBuilder AddConstructor(ITypeSymbolBuilder tb, RuntimeJavaMethod defaultConstructor, IMethodBaseSymbol serializationConstructor, bool callReadObject) { var ctor = ReflectUtil.DefineConstructor(tb, MethodAttributes.Family, [context.Resolver.ResolveCoreType(typeof(SerializationInfo).FullName), context.Resolver.ResolveCoreType(typeof(StreamingContext).FullName)]); context.AttributeHelper.HideFromJava(ctor); diff --git a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs index 111b284f64..35d106fc81 100644 --- a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs +++ b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs @@ -3,8 +3,10 @@ using System; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols.IkvmReflection; using IKVM.Reflection; +using IKVM.Reflection.Emit; using IKVM.Runtime; using Type = IKVM.Reflection.Type; @@ -34,30 +36,19 @@ public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, StaticCompiler c /// public ISymbolContext Symbols => symbols; - /// - /// Attempts to resolve the base Java assembly. - /// - /// + /// public IAssemblySymbol? ResolveBaseAssembly() { return ResolveAssembly(baseAssembly); } - /// - /// Attempts to resolve an assembly from one of the assembly sources. - /// - /// - /// + /// public IAssemblySymbol? ResolveAssembly(string assemblyName) { return ResolveAssembly(compiler.Load(assemblyName)); } - /// - /// Attempts to resolve a type from one of the assembly sources. - /// - /// - /// + /// public ITypeSymbol? ResolveCoreType(string typeName) { foreach (var assembly in compiler.Universe.GetAssemblies()) @@ -67,11 +58,7 @@ public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, StaticCompiler c return null; } - /// - /// Attempts to resolve a type from the IKVM runtime assembly. - /// - /// - /// + /// public ITypeSymbol? ResolveRuntimeType(string typeName) { return ResolveType(compiler.GetRuntimeType(typeName)); @@ -83,18 +70,42 @@ public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, StaticCompiler c return assembly != null ? symbols.GetOrCreateAssemblySymbol(assembly) : null; } + /// + public IAssemblySymbolBuilder? ResolveAssembly(AssemblyBuilder? assembly) + { + return assembly != null ? symbols.GetOrCreateAssemblySymbol(assembly) : null; + } + /// public IModuleSymbol? ResolveModule(Module? module) { return module != null ? symbols.GetOrCreateModuleSymbol(module) : null; } + /// + public IModuleSymbolBuilder? ResolveModule(ModuleBuilder? module) + { + return module != null ? symbols.GetOrCreateModuleSymbol(module) : null; + } + /// public ITypeSymbol? ResolveType(Type? type) { return type != null ? symbols.GetOrCreateTypeSymbol(type) : null; } + /// + public ITypeSymbolBuilder? ResolveType(TypeBuilder? type) + { + return type != null ? symbols.GetOrCreateTypeSymbol(type) : null; + } + + /// + public IMemberSymbol? ResolveMember(MemberInfo? module) + { + return module != null ? symbols.GetOrCreateMemberSymbol(module) : null; + } + /// public IMethodBaseSymbol? ResolveMethodBase(MethodBase? method) { @@ -107,12 +118,24 @@ public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, StaticCompiler c return ctor != null ? symbols.GetOrCreateConstructorSymbol(ctor) : null; } + /// + public IConstructorSymbolBuilder? ResolveConstructor(ConstructorBuilder? ctor) + { + return ctor != null ? symbols.GetOrCreateConstructorSymbol(ctor) : null; + } + /// public IMethodSymbol? ResolveMethod(MethodInfo? method) { return method != null ? symbols.GetOrCreateMethodSymbol(method) : null; } + /// + public IMethodSymbolBuilder? ResolveMethod(MethodBuilder? method) + { + return method != null ? symbols.GetOrCreateMethodSymbol(method) : null; + } + } } diff --git a/src/IKVM.Tools.Importer/AssemblyResolver.cs b/src/IKVM.Tools.Importer/AssemblyResolver.cs index a6209afaf4..2608e2c371 100644 --- a/src/IKVM.Tools.Importer/AssemblyResolver.cs +++ b/src/IKVM.Tools.Importer/AssemblyResolver.cs @@ -1,25 +1,25 @@ /* - Copyright (C) 2010-2013 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - + Copyright (C) 2010-2013 Jeroen Frijters + + This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. + + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jeroen Frijters + jeroen@frijters.net + */ using System; using System.Collections.Generic; @@ -385,4 +385,4 @@ IEnumerable FindAssemblyPath(string file) } -} +} \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/FakeTypes.cs b/src/IKVM.Tools.Importer/FakeTypes.cs index 61bf501de3..677d65f0ad 100644 --- a/src/IKVM.Tools.Importer/FakeTypes.cs +++ b/src/IKVM.Tools.Importer/FakeTypes.cs @@ -22,10 +22,10 @@ Jeroen Frijters */ using System; +using System.Reflection; using IKVM.CoreLib.Symbols; -using IKVM.Reflection; -using IKVM.Reflection.Emit; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer @@ -76,12 +76,13 @@ internal ITypeSymbol GetAttributeReturnValueType(ITypeSymbol attributeType) return genericAttributeAnnotationReturnValueType.MakeGenericType(attributeType); } - internal void Create(ModuleBuilder modb, RuntimeClassLoader loader) + internal void Create(IModuleSymbolBuilder modb, RuntimeClassLoader loader) { - var tb = modb.DefineType(RuntimeManagedJavaType.GenericDelegateInterfaceTypeName, TypeAttributes.Interface | TypeAttributes.Abstract | TypeAttributes.Public); - tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.MulticastDelegate.AsReflection()); - genericDelegateInterfaceType = context.Resolver.ResolveType(tb.CreateType()); + var tb = modb.DefineType(RuntimeManagedJavaType.GenericDelegateInterfaceTypeName, TypeAttributes.Interface | System.Reflection.TypeAttributes.Abstract | System.Reflection.TypeAttributes.Public); + tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.MulticastDelegate); + tb.Complete(); + genericDelegateInterfaceType = tb; genericAttributeAnnotationType = CreateAnnotationType(modb, RuntimeManagedJavaType.GenericAttributeAnnotationTypeName); genericAttributeAnnotationMultipleType = CreateAnnotationType(modb, RuntimeManagedJavaType.GenericAttributeAnnotationMultipleTypeName); genericAttributeAnnotationReturnValueType = CreateAnnotationType(modb, RuntimeManagedJavaType.GenericAttributeAnnotationReturnValueTypeName); @@ -90,33 +91,39 @@ internal void Create(ModuleBuilder modb, RuntimeClassLoader loader) internal void Finish(RuntimeClassLoader loader) { - var tb = (TypeBuilder)genericEnumEnumType.AsReflection(); + var tb = (ITypeSymbolBuilder)genericEnumEnumType; var enumTypeWrapper = loader.LoadClassByName("java.lang.Enum"); enumTypeWrapper.Finish(); - tb.SetParent(enumTypeWrapper.TypeAsBaseType.AsReflection()); - var ilgen = context.CodeEmitterFactory.Create(ReflectUtil.DefineConstructor(tb, MethodAttributes.Private, [context.Types.String.AsReflection(), context.Types.Int32.AsReflection()])); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Ldarg_2); + tb.SetParent(enumTypeWrapper.TypeAsBaseType); + var ilgen = context.CodeEmitterFactory.Create(ReflectUtil.DefineConstructor(tb, MethodAttributes.Private, [context.Types.String, context.Types.Int32])); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_2); enumTypeWrapper.GetMethodWrapper("", "(Ljava.lang.String;I)V", false).EmitCall(ilgen); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); - genericEnumEnumType = context.Resolver.ResolveType(tb.CreateType()); + tb.Complete(); + + genericEnumEnumType = tb; } - void CreateEnumEnum(ModuleBuilder modb, RuntimeClassLoader loader) + void CreateEnumEnum(IModuleSymbolBuilder modb, RuntimeClassLoader loader) { var tb = modb.DefineType(RuntimeManagedJavaType.GenericEnumEnumTypeName, TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.Public); var gtpb = tb.DefineGenericParameters("T")[0]; - gtpb.SetBaseTypeConstraint(context.Types.Enum.AsReflection()); - genericEnumEnumType = context.Resolver.ResolveType(tb); + gtpb.SetBaseTypeConstraint(context.Types.Enum); + tb.Complete(); + + genericEnumEnumType = tb; } - ITypeSymbol CreateAnnotationType(ModuleBuilder modb, string name) + ITypeSymbol CreateAnnotationType(IModuleSymbolBuilder modb, string name) { var tb = modb.DefineType(name, TypeAttributes.Interface | TypeAttributes.Abstract | TypeAttributes.Public); - tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.Attribute.AsReflection()); - return context.Resolver.ResolveType(tb.CreateType()); + tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.Attribute); + tb.Complete(); + + return tb; } internal void Load(IAssemblySymbol assembly) diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index a535a19578..ffcb94172f 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -61,7 +61,7 @@ sealed class ImportClassLoader : RuntimeClassLoader string assemblyFile; string assemblyDir; bool targetIsModule; - AssemblyBuilder assemblyBuilder; + IAssemblySymbolBuilder assemblyBuilder; MapXml.Attribute[] assemblyAttributes; ImportState state; private readonly StaticCompiler compiler; @@ -138,16 +138,7 @@ internal void AddReference(ImportClassLoader ccl) internal System.Reflection.AssemblyName GetAssemblyName() { - var src = assemblyBuilder.GetName(); - return new System.Reflection.AssemblyName - { - Name = src.Name, - Version = src.Version, - CultureName = src.CultureName, - HashAlgorithm = (System.Configuration.Assemblies.AssemblyHashAlgorithm)src.HashAlgorithm, - Flags = (System.Reflection.AssemblyNameFlags)src.Flags, - ContentType = (System.Reflection.AssemblyContentType)src.ContentType, - }; + return assemblyBuilder.GetName(); } private static PermissionSet Combine(PermissionSet p1, PermissionSet p2) @@ -163,7 +154,7 @@ private static PermissionSet Combine(PermissionSet p1, PermissionSet p2) return p1.Union(p2); } - internal ModuleBuilder CreateModuleBuilder() + internal IModuleSymbolBuilder CreateModuleBuilder() { var name = new AssemblyName(); name.Name = assemblyName; @@ -175,8 +166,8 @@ internal ModuleBuilder CreateModuleBuilder() name.Version = state.version; // define a dynamic assembly and module - assemblyBuilder = Context.StaticCompiler.Universe.DefineDynamicAssembly(name, AssemblyBuilderAccess.ReflectionOnly, assemblyDir); - var moduleBuilder = assemblyBuilder.DefineDynamicModule(assemblyName, assemblyFile, EmitSymbols); + assemblyBuilder = Context.Resolver.ResolveAssembly(Context.StaticCompiler.Universe.DefineDynamicAssembly(name, AssemblyBuilderAccess.ReflectionOnly, assemblyDir)); + var moduleBuilder = assemblyBuilder.DefineModule(assemblyName, assemblyFile, EmitSymbols); // if configured to emit stack trace info set source file if (EmitStackTraceInfo) @@ -195,11 +186,11 @@ internal ModuleBuilder CreateModuleBuilder() Context.AttributeHelper.SetRuntimeCompatibilityAttribute(assemblyBuilder); if (state.baseAddress != 0) - moduleBuilder.__ImageBase = state.baseAddress; + moduleBuilder.ImageBase = state.baseAddress; if (state.fileAlignment != 0) - moduleBuilder.__FileAlignment = state.fileAlignment; + moduleBuilder.FileAlignment = state.fileAlignment; if (state.highentropyva) - moduleBuilder.__DllCharacteristics |= DllCharacteristics.HighEntropyVA; + moduleBuilder.DllCharacteristics |= System.Reflection.PortableExecutable.DllCharacteristics.HighEntropyVirtualAddressSpace; // allow the runtime to "inject" dynamic classes into the assembly var mainAssemblyName = state.sharedclassloader != null && state.sharedclassloader[0] != this @@ -495,17 +486,17 @@ internal override bool InternalsVisibleToImpl(RuntimeJavaType wrapper, RuntimeJa private void AddInternalsVisibleToAttribute(ImportClassLoader ccl) { internalsVisibleTo.Add(ccl); - AssemblyBuilder asm = ccl.assemblyBuilder; - AssemblyName asmName = asm.GetName(); - string name = asmName.Name; - byte[] pubkey = asmName.GetPublicKey(); + var asm = ccl.assemblyBuilder; + var asmName = asm.GetName(); + var name = asmName.Name; + var pubkey = asmName.GetPublicKey(); + if (pubkey == null && asmName.KeyPair != null) - { pubkey = asmName.KeyPair.PublicKey; - } + if (pubkey != null && pubkey.Length != 0) { - StringBuilder sb = new StringBuilder(name); + var sb = new StringBuilder(name); sb.Append(", PublicKey="); foreach (byte b in pubkey) { @@ -513,6 +504,7 @@ private void AddInternalsVisibleToAttribute(ImportClassLoader ccl) } name = sb.ToString(); } + Context.AttributeHelper.SetInternalsVisibleToAttribute(this.assemblyBuilder, name); } @@ -524,7 +516,7 @@ private void AddInternalsVisibleToAttribute(ImportClassLoader ccl) /// /// /// - void SetMain(RuntimeJavaType type, PEFileKinds target, IDictionary properties, bool noglobbing, Type apartmentAttributeType) + void SetMain(RuntimeJavaType type, IKVM.CoreLib.Symbols.Emit.PEFileKinds target, IDictionary properties, bool noglobbing, ITypeSymbol apartmentAttributeType) { if (type is null) throw new ArgumentNullException(nameof(type)); @@ -532,63 +524,63 @@ void SetMain(RuntimeJavaType type, PEFileKinds target, IDictionary())); + mainMethodProxy.SetCustomAttribute(Context.Resolver.Symbols.CreateCustomAttribute(apartmentAttributeType.GetConstructor([]), [])); var ilgen = Context.CodeEmitterFactory.Create(mainMethodProxy); // first argument to Launch (assembly) - ilgen.Emit(OpCodes.Ldtoken, type.TypeAsTBD); - ilgen.Emit(OpCodes.Call, Context.CompilerFactory.GetTypeFromHandleMethod); - ilgen.Emit(OpCodes.Callvirt, Context.Types.Type.GetProperty(nameof(System.Type.Assembly)).GetGetMethod()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldtoken, type.TypeAsTBD); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, Context.CompilerFactory.GetTypeFromHandleMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, Context.Types.Type.GetProperty(nameof(System.Type.Assembly)).GetGetMethod()); // second argument to Launch (type name) - ilgen.Emit(OpCodes.Ldstr, type.Name); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, type.Name); // third argument: is this a jar - ilgen.Emit(OpCodes.Ldc_I4_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldc_I4_0); // fourth argument: args - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); // fifth argument, runtime prefix - ilgen.Emit(OpCodes.Ldstr, DEFAULT_RUNTIME_ARGS_PREFIX); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, DEFAULT_RUNTIME_ARGS_PREFIX); // sixth argument, property set to initialize JVM if (properties.Count > 0) { - var environmentType = Context.Resolver.ResolveCoreType(typeof(Environment).FullName).AsReflection(); + var environmentType = Context.Resolver.ResolveCoreType(typeof(Environment).FullName); var environmentExpandMethod = environmentType.GetMethod(nameof(Environment.ExpandEnvironmentVariables), [Context.Types.String]); - var dictionaryType = Context.Resolver.ResolveCoreType(typeof(Dictionary<,>).FullName).AsReflection().MakeGenericType(Context.Types.String, Context.Types.String); + var dictionaryType = Context.Resolver.ResolveCoreType(typeof(Dictionary<,>).FullName).MakeGenericType(Context.Types.String, Context.Types.String); var dictionaryAddMethod = dictionaryType.GetMethod("Add", [Context.Types.String, Context.Types.String]); ilgen.EmitLdc_I4(properties.Count); - ilgen.Emit(OpCodes.Newobj, dictionaryType.GetConstructor([Context.Types.Int32])); + ilgen.Emit(System.Reflection.Emit.OpCodes.Newobj, dictionaryType.GetConstructor([Context.Types.Int32])); foreach (var kvp in properties) { - ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Ldstr, kvp.Key); - ilgen.Emit(OpCodes.Ldstr, kvp.Value); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, kvp.Key); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldstr, kvp.Value); // property value can reference an environmental variable (reassess the requirment for this) if (kvp.Value.IndexOf('%') < kvp.Value.LastIndexOf('%')) - ilgen.Emit(OpCodes.Call, environmentExpandMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, environmentExpandMethod); // add to properties dictionary - ilgen.Emit(OpCodes.Callvirt, dictionaryAddMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, dictionaryAddMethod); } } else { - ilgen.Emit(OpCodes.Ldnull); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldnull); } // invoke the launcher main method - var launchMethod = Context.Resolver.ResolveRuntimeType(typeof(IKVM.Runtime.Launcher).FullName).GetMethod(nameof(IKVM.Runtime.Launcher.Run)).AsReflection(); - ilgen.Emit(OpCodes.Call, launchMethod); - ilgen.Emit(OpCodes.Ret); + var launchMethod = Context.Resolver.ResolveRuntimeType(typeof(IKVM.Runtime.Launcher).FullName).GetMethod(nameof(IKVM.Runtime.Launcher.Run)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, launchMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); // generate entry point ilgen.DoEmit(); @@ -602,7 +594,7 @@ void PrepareSave() void Save() { - ModuleBuilder mb = GetTypeWrapperFactory().ModuleBuilder; + var mb = GetTypeWrapperFactory().ModuleBuilder; if (targetIsModule) { // HACK force all referenced assemblies to end up as references in the assembly @@ -611,26 +603,21 @@ void Save() // NOTE now we only do this for modules, when we're an assembly we store the exported // assemblies in the ikvm.exports resource. for (int i = 0; i < referencedAssemblies.Length; i++) - { - Type[] types = referencedAssemblies[i].MainAssembly.GetExportedTypes(); - if (types.Length > 0) - { - mb.GetTypeToken(types[0]); - } - } + mb.AddReference(referencedAssemblies[i].MainAssembly); } - mb.CreateGlobalFunctions(); + + mb.Complete(); AddJavaModuleAttribute(mb); // add a package list and export map if (state.sharedclassloader == null || state.sharedclassloader[0] == this) { - var packageListAttributeCtor = Context.Resolver.ResolveRuntimeType(typeof(PackageListAttribute).FullName).AsReflection().GetConstructor([Context.Types.String, Context.Types.String.MakeArrayType()]); + var packageListAttributeCtor = Context.Resolver.ResolveRuntimeType(typeof(PackageListAttribute).FullName).GetConstructor([Context.Types.String, Context.Types.String.MakeArrayType()]); foreach (object[] args in packages.ToArray()) { args[1] = UnicodeUtil.EscapeInvalidSurrogates((string[])args[1]); - mb.SetCustomAttribute(new CustomAttributeBuilder(packageListAttributeCtor, args)); + mb.SetCustomAttribute(Context.Resolver.Symbols.CreateCustomAttribute(packageListAttributeCtor, args)); } // We can't add the resource when we're a module, because a multi-module assembly has a single resource namespace // and since you cannot combine -target:module with -sharedclassloader we don't need an export map @@ -647,7 +634,7 @@ void Save() try { - GetTypeWrapperFactory().ModuleBuilder.__Save(state.pekind, state.imageFileMachine); + GetTypeWrapperFactory().ModuleBuilder.Save(state.pekind, state.imageFileMachine); } catch (IOException x) { @@ -677,9 +664,9 @@ void Save() } } - void AddJavaModuleAttribute(ModuleBuilder mb) + void AddJavaModuleAttribute(IModuleSymbolBuilder mb) { - var typeofJavaModuleAttribute = Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName).AsReflection(); + var typeofJavaModuleAttribute = Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName); var propInfos = new[] { typeofJavaModuleAttribute.GetProperty("Jars") }; var propValues = new object[] { jarList.ToArray() }; @@ -694,12 +681,12 @@ void AddJavaModuleAttribute(ModuleBuilder mb) } list = UnicodeUtil.EscapeInvalidSurrogates(list); - var cab = new CustomAttributeBuilder(typeofJavaModuleAttribute.GetConstructor([Context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType().AsReflection()]), [list], propInfos, propValues); + var cab = Context.Resolver.Symbols.CreateCustomAttribute(typeofJavaModuleAttribute.GetConstructor([Context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]), [list], propInfos, propValues); mb.SetCustomAttribute(cab); } else { - var cab = new CustomAttributeBuilder(typeofJavaModuleAttribute.GetConstructor([]), [], propInfos, propValues); + var cab = Context.Resolver.Symbols.CreateCustomAttribute(typeofJavaModuleAttribute.GetConstructor([]), [], propInfos, propValues); mb.SetCustomAttribute(cab); } } @@ -777,7 +764,7 @@ void WriteExportMap() } } ms.Position = 0; - GetTypeWrapperFactory().ModuleBuilder.DefineManifestResource("ikvm.exports", ms, ResourceAttributes.Public); + GetTypeWrapperFactory().ModuleBuilder.DefineManifestResource("ikvm.exports", ms, System.Reflection.ResourceAttributes.Public); } void WriteResources() @@ -839,49 +826,49 @@ void WriteResources() name = Path.GetFileNameWithoutExtension(name) + "-" + moduleBuilder.ModuleVersionId.ToString("N") + Path.GetExtension(name); jarList.Add(name); - moduleBuilder.DefineManifestResource(name, mem, ResourceAttributes.Public); + moduleBuilder.DefineManifestResource(name, mem, System.Reflection.ResourceAttributes.Public); } } } - private static MethodAttributes MapMethodAccessModifiers(IKVM.Tools.Importer.MapXml.MapModifiers mod) + private static System.Reflection.MethodAttributes MapMethodAccessModifiers(IKVM.Tools.Importer.MapXml.MapModifiers mod) { const IKVM.Tools.Importer.MapXml.MapModifiers access = IKVM.Tools.Importer.MapXml.MapModifiers.Public | IKVM.Tools.Importer.MapXml.MapModifiers.Protected | IKVM.Tools.Importer.MapXml.MapModifiers.Private; switch (mod & access) { case IKVM.Tools.Importer.MapXml.MapModifiers.Public: - return MethodAttributes.Public; + return System.Reflection.MethodAttributes.Public; case IKVM.Tools.Importer.MapXml.MapModifiers.Protected: - return MethodAttributes.FamORAssem; + return System.Reflection.MethodAttributes.FamORAssem; case IKVM.Tools.Importer.MapXml.MapModifiers.Private: - return MethodAttributes.Private; + return System.Reflection.MethodAttributes.Private; default: - return MethodAttributes.Assembly; + return System.Reflection.MethodAttributes.Assembly; } } - private static FieldAttributes MapFieldAccessModifiers(IKVM.Tools.Importer.MapXml.MapModifiers mod) + private static System.Reflection.FieldAttributes MapFieldAccessModifiers(IKVM.Tools.Importer.MapXml.MapModifiers mod) { const IKVM.Tools.Importer.MapXml.MapModifiers access = IKVM.Tools.Importer.MapXml.MapModifiers.Public | IKVM.Tools.Importer.MapXml.MapModifiers.Protected | IKVM.Tools.Importer.MapXml.MapModifiers.Private; switch (mod & access) { case IKVM.Tools.Importer.MapXml.MapModifiers.Public: - return FieldAttributes.Public; + return System.Reflection.FieldAttributes.Public; case IKVM.Tools.Importer.MapXml.MapModifiers.Protected: - return FieldAttributes.FamORAssem; + return System.Reflection.FieldAttributes.FamORAssem; case IKVM.Tools.Importer.MapXml.MapModifiers.Private: - return FieldAttributes.Private; + return System.Reflection.FieldAttributes.Private; default: - return FieldAttributes.Assembly; + return System.Reflection.FieldAttributes.Assembly; } } private sealed class RemapperTypeWrapper : RuntimeJavaType { private ImportClassLoader classLoader; - private TypeBuilder typeBuilder; - private TypeBuilder helperTypeBuilder; - private Type shadowType; + private ITypeSymbolBuilder typeBuilder; + private ITypeSymbolBuilder helperTypeBuilder; + private ITypeSymbol shadowType; private IKVM.Tools.Importer.MapXml.Class classDef; private RuntimeJavaType baseTypeWrapper; private RuntimeJavaType[] interfaceWrappers; @@ -917,32 +904,32 @@ internal RemapperTypeWrapper(RuntimeContext context, ImportClassLoader classLoad this.baseTypeWrapper = GetBaseWrapper(context, c); classDef = c; bool baseIsSealed = false; - shadowType = context.StaticCompiler.Universe.GetType(c.Shadows, true); + shadowType = context.Resolver.ResolveType(context.StaticCompiler.Universe.GetType(c.Shadows, true)); classLoader.SetRemappedType(shadowType, this); - Type baseType = shadowType; - Type baseInterface = null; + var baseType = shadowType; + ITypeSymbol baseInterface = null; if (baseType.IsInterface) { baseInterface = baseType; } - TypeAttributes attrs = TypeAttributes.Public; + var attrs = System.Reflection.TypeAttributes.Public; if ((c.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Interface) == 0) { - attrs |= TypeAttributes.Class; + attrs |= System.Reflection.TypeAttributes.Class; if (baseType.IsSealed) { baseIsSealed = true; - attrs |= TypeAttributes.Abstract | TypeAttributes.Sealed; + attrs |= System.Reflection.TypeAttributes.Abstract | System.Reflection.TypeAttributes.Sealed; } } else { - attrs |= TypeAttributes.Interface | TypeAttributes.Abstract; + attrs |= System.Reflection.TypeAttributes.Interface | System.Reflection.TypeAttributes.Abstract; baseType = null; } if ((c.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Abstract) != 0) { - attrs |= TypeAttributes.Abstract; + attrs |= System.Reflection.TypeAttributes.Abstract; } string name = c.Name.Replace('/', '.'); typeBuilder = classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(name, attrs, baseIsSealed ? Context.Types.Object : baseType); @@ -1068,7 +1055,7 @@ internal RemappedMethodBaseWrapper(RemapperTypeWrapper typeWrapper, string name, } - internal abstract MethodBase DoLink(); + internal abstract IMethodBaseSymbol DoLink(); internal abstract void Finish(); @@ -1078,7 +1065,7 @@ sealed class RemappedConstructorWrapper : RemappedMethodBaseWrapper { private IKVM.Tools.Importer.MapXml.Constructor m; - private MethodBuilder mbHelper; + private IMethodSymbolBuilder mbHelper; internal RemappedConstructorWrapper(RemapperTypeWrapper typeWrapper, IKVM.Tools.Importer.MapXml.Constructor m) : base(typeWrapper, "", m.Sig, (Modifiers)m.Modifiers) @@ -1088,32 +1075,32 @@ internal RemappedConstructorWrapper(RemapperTypeWrapper typeWrapper, IKVM.Tools. internal override void EmitCall(CodeEmitter ilgen) { - ilgen.Emit(OpCodes.Call, GetMethod()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, GetMethod()); } internal override void EmitNewobj(CodeEmitter ilgen) { if (mbHelper != null) { - ilgen.Emit(OpCodes.Call, mbHelper); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mbHelper); } else { - ilgen.Emit(OpCodes.Newobj, GetMethod()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Newobj, GetMethod()); } } - internal override MethodBase DoLink() + internal override IMethodBaseSymbol DoLink() { - MethodAttributes attr = MapMethodAccessModifiers(m.Modifiers); - RemapperTypeWrapper typeWrapper = (RemapperTypeWrapper)DeclaringType; - Type[] paramTypes = typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig); + var attr = MapMethodAccessModifiers(m.Modifiers); + var typeWrapper = (RemapperTypeWrapper)DeclaringType; + var paramTypes = typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig); - MethodBuilder cbCore = null; + IConstructorSymbolBuilder cbCore = null; if (typeWrapper.shadowType.IsSealed) { - mbHelper = typeWrapper.typeBuilder.DefineMethod("newhelper", attr | MethodAttributes.Static, CallingConventions.Standard, typeWrapper.shadowType, paramTypes); + mbHelper = typeWrapper.typeBuilder.DefineMethod("newhelper", attr | System.Reflection.MethodAttributes.Static, System.Reflection.CallingConventions.Standard, typeWrapper.shadowType, paramTypes); if (m.Attributes != null) { foreach (IKVM.Tools.Importer.MapXml.Attribute custattr in m.Attributes) @@ -1121,6 +1108,7 @@ internal override MethodBase DoLink() DeclaringType.Context.AttributeHelper.SetCustomAttribute(DeclaringType.ClassLoader, mbHelper, custattr); } } + SetParameters(DeclaringType.ClassLoader, mbHelper, m.Parameters); DeclaringType.Context.AttributeHelper.SetModifiers(mbHelper, (Modifiers)m.Modifiers, false); DeclaringType.Context.AttributeHelper.SetNameSig(mbHelper, "", m.Sig); @@ -1136,9 +1124,11 @@ internal override MethodBase DoLink() DeclaringType.Context.AttributeHelper.SetCustomAttribute(DeclaringType.ClassLoader, cbCore, custattr); } } + SetParameters(DeclaringType.ClassLoader, cbCore, m.Parameters); AddDeclaredExceptions(DeclaringType.Context, cbCore, m.Throws); } + return cbCore; } @@ -1146,9 +1136,9 @@ internal override void Finish() { // TODO we should insert method tracing (if enabled) - Type[] paramTypes = this.GetParametersForDefineMethod(); + var paramTypes = this.GetParametersForDefineMethod(); - MethodBuilder cbCore = GetMethod() as MethodBuilder; + var cbCore = GetMethod() as IMethodSymbolBuilder; if (cbCore != null) { @@ -1161,7 +1151,7 @@ internal override void Finish() } else { - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); for (int i = 0; i < paramTypes.Length; i++) { ilgen.EmitLdarg(i + 1); @@ -1172,15 +1162,15 @@ internal override void Finish() } else { - ConstructorInfo baseCon = DeclaringType.TypeAsTBD.GetConstructor(paramTypes); + var baseCon = DeclaringType.TypeAsTBD.GetConstructor(paramTypes); if (baseCon == null) { // TODO better error handling throw new InvalidOperationException("base class constructor not found: " + DeclaringType.Name + "." + m.Sig); } - ilgen.Emit(OpCodes.Call, baseCon); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, baseCon); } - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } ilgen.DoEmit(); if (this.DeclaringType.ClassLoader.EmitStackTraceInfo) @@ -1191,7 +1181,7 @@ internal override void Finish() if (mbHelper != null) { - CodeEmitter ilgen = DeclaringType.Context.CodeEmitterFactory.Create(mbHelper); + var ilgen = DeclaringType.Context.CodeEmitterFactory.Create(mbHelper); if (m.Redirect != null) { m.Redirect.Emit(DeclaringType.ClassLoader, ilgen); @@ -1207,7 +1197,7 @@ internal override void Finish() } else { - ConstructorInfo baseCon = DeclaringType.TypeAsTBD.GetConstructor(paramTypes); + var baseCon = DeclaringType.TypeAsTBD.GetConstructor(paramTypes); if (baseCon == null) { // TODO better error handling @@ -1217,8 +1207,8 @@ internal override void Finish() { ilgen.EmitLdarg(i); } - ilgen.Emit(OpCodes.Newobj, baseCon); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Newobj, baseCon); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } ilgen.DoEmit(); if (this.DeclaringType.ClassLoader.EmitStackTraceInfo) @@ -1234,7 +1224,7 @@ sealed class RemappedMethodWrapper : RemappedMethodBaseWrapper private IKVM.Tools.Importer.MapXml.Method m; private IKVM.Tools.Importer.MapXml.Root map; - private MethodBuilder mbHelper; + private IMethodSymbolBuilder mbHelper; private List overriders = new List(); private bool inherited; @@ -1265,7 +1255,7 @@ internal override void EmitCall(CodeEmitter ilgen) } else { - ilgen.Emit(OpCodes.Call, (MethodInfo)GetMethod()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, (IMethodSymbol)GetMethod()); } } @@ -1278,17 +1268,17 @@ private void EmitCallvirtImpl(CodeEmitter ilgen, bool cloneOrFinalizeHack) { if (mbHelper != null && !cloneOrFinalizeHack) { - ilgen.Emit(OpCodes.Call, mbHelper); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mbHelper); } else { - ilgen.Emit(OpCodes.Callvirt, (MethodInfo)GetMethod()); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, (IMethodSymbol)GetMethod()); } } - internal override MethodBase DoLink() + internal override IMethodBaseSymbol DoLink() { - RemapperTypeWrapper typeWrapper = (RemapperTypeWrapper)DeclaringType; + var typeWrapper = (RemapperTypeWrapper)DeclaringType; if (typeWrapper.IsInterface) { @@ -1296,11 +1286,13 @@ internal override MethodBase DoLink() { throw new InvalidOperationException(typeWrapper.Name + "." + m.Name + m.Sig); } - MethodInfo interfaceMethod = typeWrapper.shadowType.GetMethod(m.Override.Name, typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig)); + + var interfaceMethod = typeWrapper.shadowType.GetMethod(m.Override.Name, typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig)); if (interfaceMethod == null) { throw new InvalidOperationException(typeWrapper.Name + "." + m.Name + m.Sig); } + // if any of the remapped types has a body for this interface method, we need a helper method // to special invocation through this interface for that type List specialCases = null; @@ -1336,17 +1328,17 @@ internal override MethodBase DoLink() } } DeclaringType.Context.AttributeHelper.SetRemappedInterfaceMethod(typeWrapper.typeBuilder, m.Name, m.Override.Name, throws); - MethodBuilder helper = null; + IMethodSymbolBuilder helper = null; if (specialCases != null) { CodeEmitter ilgen; - Type[] argTypes = ArrayUtil.Concat(typeWrapper.shadowType, typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig)); + var argTypes = ArrayUtil.Concat(typeWrapper.shadowType, typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig)); if (typeWrapper.helperTypeBuilder == null) { - typeWrapper.helperTypeBuilder = typeWrapper.typeBuilder.DefineNestedType("__Helper", TypeAttributes.NestedPublic | TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.Abstract); + typeWrapper.helperTypeBuilder = typeWrapper.typeBuilder.DefineNestedType("__Helper", System.Reflection.TypeAttributes.NestedPublic | System.Reflection.TypeAttributes.Class | System.Reflection.TypeAttributes.Sealed | System.Reflection.TypeAttributes.Abstract); DeclaringType.Context.AttributeHelper.HideFromJava(typeWrapper.helperTypeBuilder); } - helper = typeWrapper.helperTypeBuilder.DefineMethod(m.Name, MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, typeWrapper.ClassLoader.RetTypeWrapperFromSig(m.Sig, LoadMode.LoadOrThrow).TypeAsSignatureType, argTypes); + helper = typeWrapper.helperTypeBuilder.DefineMethod(m.Name, System.Reflection.MethodAttributes.HideBySig | System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static, typeWrapper.ClassLoader.RetTypeWrapperFromSig(m.Sig, LoadMode.LoadOrThrow).TypeAsSignatureType, argTypes); if (m.Attributes != null) { foreach (IKVM.Tools.Importer.MapXml.Attribute custattr in m.Attributes) @@ -1359,9 +1351,9 @@ internal override MethodBase DoLink() foreach (IKVM.Tools.Importer.MapXml.Class c in specialCases) { var tw = typeWrapper.ClassLoader.LoadClassByName(c.Name); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, tw.TypeAsTBD); - ilgen.Emit(OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, tw.TypeAsTBD); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); CodeEmitterLabel label = ilgen.DefineLabel(); ilgen.EmitBrfalse(label); for (int i = 1; i < argTypes.Length; i++) @@ -1371,16 +1363,16 @@ internal override MethodBase DoLink() var mw = tw.GetMethodWrapper(m.Name, m.Sig, false); mw.Link(); mw.EmitCallvirt(ilgen); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.MarkLabel(label); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); } for (int i = 0; i < argTypes.Length; i++) { ilgen.EmitLdarg(i); } - ilgen.Emit(OpCodes.Callvirt, interfaceMethod); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, interfaceMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); } mbHelper = helper; @@ -1388,9 +1380,9 @@ internal override MethodBase DoLink() } else { - MethodBuilder mbCore = null; - Type[] paramTypes = typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig); - Type retType = typeWrapper.ClassLoader.RetTypeWrapperFromSig(m.Sig, LoadMode.LoadOrThrow).TypeAsSignatureType; + IMethodSymbolBuilder mbCore = null; + var paramTypes = typeWrapper.ClassLoader.ArgTypeListFromSig(m.Sig); + var retType = typeWrapper.ClassLoader.RetTypeWrapperFromSig(m.Sig, LoadMode.LoadOrThrow).TypeAsSignatureType; if (typeWrapper.shadowType.IsSealed && (m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Static) == 0) { @@ -1412,33 +1404,35 @@ internal override MethodBase DoLink() } else { - MethodInfo overrideMethod = null; - MethodAttributes attr = m.MethodAttributes | MapMethodAccessModifiers(m.Modifiers) | MethodAttributes.HideBySig; + IMethodSymbol overrideMethod = null; + var attr = m.MethodAttributes | MapMethodAccessModifiers(m.Modifiers) | System.Reflection.MethodAttributes.HideBySig; if ((m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Static) != 0) { - attr |= MethodAttributes.Static; + attr |= System.Reflection.MethodAttributes.Static; } else if ((m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Private) == 0 && (m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Final) == 0) { - attr |= MethodAttributes.Virtual | MethodAttributes.NewSlot | MethodAttributes.CheckAccessOnOverride; + attr |= System.Reflection.MethodAttributes.Virtual | System.Reflection.MethodAttributes.NewSlot | System.Reflection.MethodAttributes.CheckAccessOnOverride; + if (!typeWrapper.shadowType.IsSealed) { - MethodInfo autoOverride = typeWrapper.shadowType.GetMethod(m.Name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, paramTypes, null); + var autoOverride = typeWrapper.shadowType.GetMethod(m.Name, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic, paramTypes); if (autoOverride != null && autoOverride.ReturnType == retType && !autoOverride.IsFinal) { // the method we're processing is overriding a method in its shadowType (which is the actual base type) - attr &= ~MethodAttributes.NewSlot; + attr &= ~System.Reflection.MethodAttributes.NewSlot; } } + if (typeWrapper.BaseTypeWrapper != null) { - RemappedMethodWrapper baseMethod = typeWrapper.BaseTypeWrapper.GetMethodWrapper(m.Name, m.Sig, true) as RemappedMethodWrapper; + var baseMethod = typeWrapper.BaseTypeWrapper.GetMethodWrapper(m.Name, m.Sig, true) as RemappedMethodWrapper; if (baseMethod != null) { baseMethod.overriders.Add(typeWrapper); if (baseMethod.m.Override != null) { - overrideMethod = typeWrapper.BaseTypeWrapper.TypeAsTBD.GetMethod(baseMethod.m.Override.Name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, paramTypes, null); + overrideMethod = typeWrapper.BaseTypeWrapper.TypeAsTBD.GetMethod(baseMethod.m.Override.Name, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic, paramTypes); if (overrideMethod == null) { throw new InvalidOperationException(); @@ -1470,15 +1464,15 @@ internal override MethodBase DoLink() if ((m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Static) == 0 && !IsHideFromJava(m)) { // instance methods must have an instancehelper method - MethodAttributes attr = MapMethodAccessModifiers(m.Modifiers) | MethodAttributes.HideBySig | MethodAttributes.Static; + var attr = MapMethodAccessModifiers(m.Modifiers) | System.Reflection.MethodAttributes.HideBySig | System.Reflection.MethodAttributes.Static; // NOTE instancehelpers for protected methods are made internal // and special cased in DotNetTypeWrapper.LazyPublishMembers if ((m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Protected) != 0) { - attr &= ~MethodAttributes.MemberAccessMask; - attr |= MethodAttributes.Assembly; + attr &= ~System.Reflection.MethodAttributes.MemberAccessMask; + attr |= System.Reflection.MethodAttributes.Assembly; } - mbHelper = typeWrapper.typeBuilder.DefineMethod("instancehelper_" + m.Name, attr, CallingConventions.Standard, retType, ArrayUtil.Concat(typeWrapper.shadowType, paramTypes)); + mbHelper = typeWrapper.typeBuilder.DefineMethod("instancehelper_" + m.Name, attr, System.Reflection.CallingConventions.Standard, retType, ArrayUtil.Concat(typeWrapper.shadowType, paramTypes)); if (m.Attributes != null) { foreach (IKVM.Tools.Importer.MapXml.Attribute custattr in m.Attributes) @@ -1503,10 +1497,11 @@ internal override MethodBase DoLink() { DeclaringType.Context.AttributeHelper.SetEditorBrowsableNever(mbHelper); } + DeclaringType.Context.AttributeHelper.SetModifiers(mbHelper, (Modifiers)m.Modifiers, false); DeclaringType.Context.AttributeHelper.SetNameSig(mbHelper, m.Name, m.Sig); AddDeclaredExceptions(DeclaringType.Context, mbHelper, m.Throws); - mbHelper.SetCustomAttribute(new CustomAttributeBuilder(DeclaringType.Context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).AsReflection().GetConstructor([DeclaringType.Context.Types.String]), ["This function will be removed from future versions. Please use extension methods from ikvm.extensions namespace instead."])); + mbHelper.SetCustomAttribute(DeclaringType.Context.Resolver.Symbols.CreateCustomAttribute(DeclaringType.Context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([DeclaringType.Context.Types.String]), ["This function will be removed from future versions. Please use extension methods from ikvm.extensions namespace instead."])); } return mbCore; } @@ -1530,23 +1525,22 @@ private static bool IsHideFromJava(IKVM.Tools.Importer.MapXml.Method m) internal override void Finish() { // TODO we should insert method tracing (if enabled) - Type[] paramTypes = this.GetParametersForDefineMethod(); + var paramTypes = this.GetParametersForDefineMethod(); - MethodBuilder mbCore = GetMethod() as MethodBuilder; + var mbCore = GetMethod() as IMethodSymbolBuilder; // NOTE sealed types don't have instance methods (only instancehelpers) if (mbCore != null) { - CodeEmitter ilgen = DeclaringType.Context.CodeEmitterFactory.Create(mbCore); - MethodInfo baseMethod = null; + var ilgen = DeclaringType.Context.CodeEmitterFactory.Create(mbCore); + IMethodSymbol baseMethod = null; if (m.Override != null) { - baseMethod = DeclaringType.TypeAsTBD.GetMethod(m.Override.Name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, paramTypes, null); + baseMethod = DeclaringType.TypeAsTBD.GetMethod(m.Override.Name, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic, paramTypes); if (baseMethod == null) - { throw new InvalidOperationException(); - } - ((TypeBuilder)DeclaringType.TypeAsBaseType).DefineMethodOverride(mbCore, baseMethod); + + ((ITypeSymbolBuilder)DeclaringType.TypeAsBaseType).DefineMethodOverride(mbCore, baseMethod); } // TODO we need to support ghost (and other funky?) parameter types if (m.Body != null) @@ -1571,7 +1565,7 @@ internal override void Finish() if ((m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Static) == 0) { thisOffset = 1; - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); } for (int i = 0; i < paramTypes.Length; i++) { @@ -1587,10 +1581,10 @@ internal override void Finish() { throw new InvalidOperationException(DeclaringType.Name + "." + m.Name + m.Sig); } - ilgen.Emit(OpCodes.Call, baseMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, baseMethod); } this.ReturnType.EmitConvStackTypeToSignatureType(ilgen, null); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } ilgen.DoEmit(); if (this.DeclaringType.ClassLoader.EmitStackTraceInfo) @@ -1613,7 +1607,7 @@ internal override void Finish() } else if (!m.NoNullCheck) { - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); ilgen.EmitNullCheck(); } if (mbCore != null && @@ -1621,20 +1615,20 @@ internal override void Finish() (m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Private) == 0 && (m.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Final) == 0) { // TODO we should have a way to supress this for overridden methods - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, DeclaringType.TypeAsBaseType); - ilgen.Emit(OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, DeclaringType.TypeAsBaseType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); CodeEmitterLabel skip = ilgen.DefineLabel(); ilgen.EmitBrfalse(skip); for (int i = 0; i < paramTypes.Length; i++) { ilgen.EmitLdarg(i + 1); } - ilgen.Emit(OpCodes.Callvirt, mbCore); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, mbCore); this.ReturnType.EmitConvStackTypeToSignatureType(ilgen, null); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.MarkLabel(skip); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); } foreach (RemapperTypeWrapper overrider in overriders) { @@ -1646,9 +1640,9 @@ internal override void Finish() } else { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, overrider.TypeAsTBD); - ilgen.Emit(OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, overrider.TypeAsTBD); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); CodeEmitterLabel skip = ilgen.DefineLabel(); ilgen.EmitBrfalse(skip); for (int i = 0; i < paramTypes.Length; i++) @@ -1658,9 +1652,9 @@ internal override void Finish() mw.Link(); mw.EmitCallvirtImpl(ilgen, false); this.ReturnType.EmitConvStackTypeToSignatureType(ilgen, null); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.MarkLabel(skip); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); } } if (m.Body != null || m.AlternateBody != null) @@ -1694,11 +1688,11 @@ internal override void Finish() } else if (m.Override != null) { - var baseMethod = shadowType.GetMethod(m.Override.Name, BindingFlags.Instance | BindingFlags.Public, null, paramTypes, null); + var baseMethod = shadowType.GetMethod(m.Override.Name, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public, paramTypes); if (baseMethod == null) throw new InvalidOperationException(DeclaringType.Name + "." + m.Name + m.Sig); - ilgen.Emit(OpCodes.Callvirt, baseMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, baseMethod); } else { @@ -1706,15 +1700,15 @@ internal override void Finish() if (baseMethod == null || baseMethod.m.Override == null) throw new InvalidOperationException(DeclaringType.Name + "." + m.Name + m.Sig); - var overrideMethod = shadowType.GetMethod(baseMethod.m.Override.Name, BindingFlags.Instance | BindingFlags.Public, null, paramTypes, null); + var overrideMethod = shadowType.GetMethod(baseMethod.m.Override.Name, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public, paramTypes); if (overrideMethod == null) throw new InvalidOperationException(DeclaringType.Name + "." + m.Name + m.Sig); - ilgen.Emit(OpCodes.Callvirt, overrideMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, overrideMethod); } ReturnType.EmitConvStackTypeToSignatureType(ilgen, null); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } ilgen.DoEmit(); @@ -1727,7 +1721,7 @@ internal override void Finish() if (m.NonVirtualAlternateBody != null || (m.Override != null && overriders.Count > 0)) { var tw = (RemapperTypeWrapper)DeclaringType; - var mb = tw.typeBuilder.DefineMethod("nonvirtualhelper/" + Name, MethodAttributes.Private | MethodAttributes.Static, ReturnTypeForDefineMethod, ArrayUtil.Concat(tw.TypeAsSignatureType, GetParametersForDefineMethod())); + var mb = tw.typeBuilder.DefineMethod("nonvirtualhelper/" + Name, System.Reflection.MethodAttributes.Private | System.Reflection.MethodAttributes.Static, ReturnTypeForDefineMethod, ArrayUtil.Concat(tw.TypeAsSignatureType, GetParametersForDefineMethod())); // apply custom attributes from map XML if (m.Attributes != null) @@ -1745,23 +1739,23 @@ internal override void Finish() else { var shadowType = ((RemapperTypeWrapper)DeclaringType).shadowType; - var baseMethod = shadowType.GetMethod(m.Override.Name, BindingFlags.Instance | BindingFlags.Public, null, paramTypes, null); + var baseMethod = shadowType.GetMethod(m.Override.Name, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public, paramTypes); if (baseMethod == null) throw new InvalidOperationException(DeclaringType.Name + "." + m.Name + m.Sig); - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); for (int i = 0; i < paramTypes.Length; i++) ilgen.EmitLdarg(i + 1); - ilgen.Emit(OpCodes.Call, baseMethod); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, baseMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } ilgen.DoEmit(); } } - private void EmitRedirect(Type baseType, CodeEmitter ilgen) + private void EmitRedirect(ITypeSymbol baseType, CodeEmitter ilgen) { var redirName = m.Redirect.Name ?? m.Name; var redirSig = m.Redirect.Sig ?? m.Sig; @@ -1770,10 +1764,10 @@ private void EmitRedirect(Type baseType, CodeEmitter ilgen) // type specified, or class missing, assume loading .NET type if (m.Redirect.Type != null || m.Redirect.Class == null) { - var type = m.Redirect.Type != null ? DeclaringType.Context.StaticCompiler.Universe.GetType(m.Redirect.Type, true) : baseType; + var type = m.Redirect.Type != null ? DeclaringType.Context.Resolver.ResolveType(DeclaringType.Context.StaticCompiler.Universe.GetType(m.Redirect.Type, true)) : baseType; var redirParamTypes = classLoader.ArgTypeListFromSig(redirSig); var mi = type.GetMethod(m.Redirect.Name, redirParamTypes) ?? throw new InvalidOperationException(); - ilgen.Emit(OpCodes.Call, mi); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); } else { @@ -1785,13 +1779,31 @@ private void EmitRedirect(Type baseType, CodeEmitter ilgen) } } - private static void SetParameters(RuntimeClassLoader loader, MethodBuilder mb, IKVM.Tools.Importer.MapXml.Parameter[] parameters) + static void SetParameters(RuntimeClassLoader loader, IConstructorSymbolBuilder mb, IKVM.Tools.Importer.MapXml.Parameter[] parameters) + { + if (parameters != null) + { + for (int i = 0; i < parameters.Length; i++) + { + var pb = mb.DefineParameter(i + 1, System.Reflection.ParameterAttributes.None, parameters[i].Name); + if (parameters[i].Attributes != null) + { + for (int j = 0; j < parameters[i].Attributes.Length; j++) + { + loader.Context.AttributeHelper.SetCustomAttribute(loader, pb, parameters[i].Attributes[j]); + } + } + } + } + } + + static void SetParameters(RuntimeClassLoader loader, IMethodSymbolBuilder mb, IKVM.Tools.Importer.MapXml.Parameter[] parameters) { if (parameters != null) { for (int i = 0; i < parameters.Length; i++) { - ParameterBuilder pb = mb.DefineParameter(i + 1, ParameterAttributes.None, parameters[i].Name); + var pb = mb.DefineParameter(i + 1, System.Reflection.ParameterAttributes.None, parameters[i].Name); if (parameters[i].Attributes != null) { for (int j = 0; j < parameters[i].Attributes.Length; j++) @@ -1828,20 +1840,21 @@ internal void Process2ndPassStep2(IKVM.Tools.Importer.MapXml.Root map) foreach (IKVM.Tools.Importer.MapXml.Field f in c.Fields) { { - FieldAttributes attr = MapFieldAccessModifiers(f.Modifiers); + var attr = MapFieldAccessModifiers(f.Modifiers); if (f.Constant != null) { - attr |= FieldAttributes.Literal; + attr |= System.Reflection.FieldAttributes.Literal; } else if ((f.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Final) != 0) { - attr |= FieldAttributes.InitOnly; + attr |= System.Reflection.FieldAttributes.InitOnly; } if ((f.Modifiers & IKVM.Tools.Importer.MapXml.MapModifiers.Static) != 0) { - attr |= FieldAttributes.Static; + attr |= System.Reflection.FieldAttributes.Static; } - FieldBuilder fb = tb.DefineField(f.Name, ClassLoader.FieldTypeWrapperFromSig(f.Sig, LoadMode.LoadOrThrow).TypeAsSignatureType, attr); + + var fb = tb.DefineField(f.Name, ClassLoader.FieldTypeWrapperFromSig(f.Sig, LoadMode.LoadOrThrow).TypeAsSignatureType, attr); if (f.Attributes != null) { foreach (IKVM.Tools.Importer.MapXml.Attribute custattr in f.Attributes) @@ -1849,6 +1862,7 @@ internal void Process2ndPassStep2(IKVM.Tools.Importer.MapXml.Root map) Context.AttributeHelper.SetCustomAttribute(classLoader, fb, custattr); } } + object constant; if (f.Constant != null) { @@ -1891,8 +1905,8 @@ internal void Process4thPass(ICollection remappedTypes) if (classDef.Clinit != null) { - MethodBuilder cb = ReflectUtil.DefineTypeInitializer(typeBuilder, classLoader); - CodeEmitter ilgen = Context.CodeEmitterFactory.Create(cb); + var cb = ReflectUtil.DefineTypeInitializer(typeBuilder, classLoader); + var ilgen = Context.CodeEmitterFactory.Create(cb); // TODO emit code to make sure super class is initialized classDef.Clinit.Body.Emit(classLoader, ilgen); ilgen.DoEmit(); @@ -1916,57 +1930,56 @@ internal void Process4thPass(ICollection remappedTypes) // For all inherited methods, we emit a method that hides the inherited method and // annotate it with EditorBrowsableAttribute(EditorBrowsableState.Never) to make // sure the inherited methods don't show up in Intellisense. - var methods = new Dictionary(); + var methods = new Dictionary(); foreach (var mw in GetMethods()) { - var mb = mw.GetMethod() as MethodBuilder; + var mb = mw.GetMethod() as IMethodSymbolBuilder; if (mb != null) methods.Add(MakeMethodKey(mb), mb); } - foreach (var mi in typeBuilder.BaseType.GetMethods(BindingFlags.Public | BindingFlags.Instance | BindingFlags.Static | BindingFlags.FlattenHierarchy)) + foreach (var mi in typeBuilder.BaseType.GetMethods(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.FlattenHierarchy)) { - string key = MakeMethodKey(mi); + var key = MakeMethodKey(mi); if (!methods.ContainsKey(key)) { - ParameterInfo[] paramInfo = mi.GetParameters(); - Type[] paramTypes = new Type[paramInfo.Length]; + var paramInfo = mi.GetParameters(); + var paramTypes = new ITypeSymbol[paramInfo.Length]; for (int i = 0; i < paramInfo.Length; i++) - { paramTypes[i] = paramInfo[i].ParameterType; - } - MethodBuilder mb = typeBuilder.DefineMethod(mi.Name, mi.Attributes & (MethodAttributes.MemberAccessMask | MethodAttributes.SpecialName | MethodAttributes.Static), mi.ReturnType, paramTypes); + + var mb = typeBuilder.DefineMethod(mi.Name, mi.Attributes & (System.Reflection.MethodAttributes.MemberAccessMask | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.Static), mi.ReturnType, paramTypes); Context.AttributeHelper.HideFromJava(mb); Context.AttributeHelper.SetEditorBrowsableNever(mb); - CodeEmitter ilgen = Context.CodeEmitterFactory.Create(mb); + + var ilgen = Context.CodeEmitterFactory.Create(mb); for (int i = 0; i < paramTypes.Length; i++) - { ilgen.EmitLdarg(i); - } + if (!mi.IsStatic) { ilgen.EmitLdarg(paramTypes.Length); - ilgen.Emit(OpCodes.Callvirt, mi); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, mi); } else { - ilgen.Emit(OpCodes.Call, mi); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); } - ilgen.Emit(OpCodes.Ret); + + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); methods[key] = mb; } } - foreach (var pi in typeBuilder.BaseType.GetProperties(BindingFlags.Public | BindingFlags.Instance | BindingFlags.Static)) + foreach (var pi in typeBuilder.BaseType.GetProperties(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Static)) { - ParameterInfo[] paramInfo = pi.GetIndexParameters(); - Type[] paramTypes = new Type[paramInfo.Length]; + var paramInfo = pi.GetIndexParameters(); + var paramTypes = new ITypeSymbol[paramInfo.Length]; for (int i = 0; i < paramInfo.Length; i++) - { paramTypes[i] = paramInfo[i].ParameterType; - } - PropertyBuilder pb = typeBuilder.DefineProperty(pi.Name, PropertyAttributes.None, pi.PropertyType, paramTypes); + + var pb = typeBuilder.DefineProperty(pi.Name, System.Reflection.PropertyAttributes.None, pi.PropertyType, paramTypes); if (pi.GetGetMethod() != null) { pb.SetGetMethod(methods[MakeMethodKey(pi.GetGetMethod())]); @@ -1979,17 +1992,17 @@ internal void Process4thPass(ICollection remappedTypes) } } - typeBuilder.CreateType(); + typeBuilder.Complete(); if (helperTypeBuilder != null) - helperTypeBuilder.CreateType(); + helperTypeBuilder.Complete(); } - private static string MakeMethodKey(MethodInfo method) + private static string MakeMethodKey(IMethodSymbol method) { var sb = new StringBuilder(); sb.Append(method.ReturnType.AssemblyQualifiedName).Append(":").Append(method.Name); var paramInfo = method.GetParameters(); - var paramTypes = new Type[paramInfo.Length]; + var paramTypes = new ITypeSymbol[paramInfo.Length]; for (int i = 0; i < paramInfo.Length; i++) { paramTypes[i] = paramInfo[i].ParameterType; @@ -2005,28 +2018,28 @@ private void CreateShadowInstanceOf(ICollection remappedTyp if (typeBuilder.IsInterface) return; - MethodAttributes attr = MethodAttributes.SpecialName | MethodAttributes.Public | MethodAttributes.Static; - MethodBuilder mb = typeBuilder.DefineMethod("__", attr, Context.Types.Boolean, new Type[] { Context.Types.Object }); + var attr = System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static; + var mb = typeBuilder.DefineMethod("__", attr, Context.Types.Boolean, new[] { Context.Types.Object }); Context.AttributeHelper.HideFromJava(mb); Context.AttributeHelper.SetEditorBrowsableNever(mb); - CodeEmitter ilgen = Context.CodeEmitterFactory.Create(mb); + var ilgen = Context.CodeEmitterFactory.Create(mb); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, shadowType); - CodeEmitterLabel retFalse = ilgen.DefineLabel(); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, shadowType); + var retFalse = ilgen.DefineLabel(); ilgen.EmitBrfalse(retFalse); if (!shadowType.IsSealed) { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, typeBuilder); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, typeBuilder); ilgen.EmitBrtrue(retFalse); } if (shadowType == Context.Types.Object) { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, Context.Types.Array); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, Context.Types.Array); ilgen.EmitBrtrue(retFalse); } @@ -2034,17 +2047,17 @@ private void CreateShadowInstanceOf(ICollection remappedTyp { if (!r.shadowType.IsInterface && r.shadowType.IsSubclassOf(shadowType)) { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, r.shadowType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, r.shadowType); ilgen.EmitBrtrue(retFalse); } } - ilgen.Emit(OpCodes.Ldc_I4_1); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldc_I4_1); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.MarkLabel(retFalse); - ilgen.Emit(OpCodes.Ldc_I4_0); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldc_I4_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); } @@ -2056,27 +2069,28 @@ private void CreateShadowCheckCast(ICollection remappedType { return; } - MethodAttributes attr = MethodAttributes.SpecialName | MethodAttributes.Public | MethodAttributes.Static; - MethodBuilder mb = typeBuilder.DefineMethod("__", attr, shadowType, new Type[] { Context.Types.Object }); + + var attr = System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static; + var mb = typeBuilder.DefineMethod("__", attr, shadowType, [Context.Types.Object]); Context.AttributeHelper.HideFromJava(mb); Context.AttributeHelper.SetEditorBrowsableNever(mb); - CodeEmitter ilgen = Context.CodeEmitterFactory.Create(mb); + var ilgen = Context.CodeEmitterFactory.Create(mb); - CodeEmitterLabel fail = ilgen.DefineLabel(); + var fail = ilgen.DefineLabel(); bool hasfail = false; if (!shadowType.IsSealed) { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, typeBuilder); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, typeBuilder); ilgen.EmitBrtrue(fail); hasfail = true; } if (shadowType == Context.Types.Object) { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, Context.Types.Array); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, Context.Types.Array); ilgen.EmitBrtrue(fail); hasfail = true; } @@ -2085,26 +2099,26 @@ private void CreateShadowCheckCast(ICollection remappedType { if (!r.shadowType.IsInterface && r.shadowType.IsSubclassOf(shadowType)) { - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Isinst, r.shadowType); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Isinst, r.shadowType); ilgen.EmitBrtrue(fail); hasfail = true; } } - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); ilgen.EmitCastclass(shadowType); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); if (hasfail) { ilgen.MarkLabel(fail); - ilgen.ThrowException(Context.Resolver.ResolveCoreType(typeof(InvalidCastException).FullName).AsReflection()); + ilgen.ThrowException(Context.Resolver.ResolveCoreType(typeof(InvalidCastException).FullName)); } ilgen.DoEmit(); } - internal override MethodBase LinkMethod(RuntimeJavaMethod mw) + internal override IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) { return ((RemappedMethodBaseWrapper)mw).DoLink(); } @@ -2148,15 +2162,26 @@ internal override bool IsFastClassLiteralSafe } } + internal static void AddDeclaredExceptions(RuntimeContext context, IConstructorSymbolBuilder cb, IKVM.Tools.Importer.MapXml.Throws[] throws) + { + if (throws != null) + { + var exceptions = new string[throws.Length]; + for (int i = 0; i < exceptions.Length; i++) + exceptions[i] = throws[i].Class; + + context.AttributeHelper.SetThrowsAttribute(cb, exceptions); + } + } + internal static void AddDeclaredExceptions(RuntimeContext context, IMethodSymbolBuilder mb, IKVM.Tools.Importer.MapXml.Throws[] throws) { if (throws != null) { - string[] exceptions = new string[throws.Length]; + var exceptions = new string[throws.Length]; for (int i = 0; i < exceptions.Length; i++) - { exceptions[i] = throws[i].Class; - } + context.AttributeHelper.SetThrowsAttribute(mb, exceptions); } } @@ -2282,21 +2307,21 @@ internal void Emit(MapXml.CodeGenContext context, CodeEmitter ilgen) { var mwSuppressFillInStackTrace = rcontext.JavaBase.TypeOfjavaLangThrowable.GetMethodWrapper("__", "()V", false); mwSuppressFillInStackTrace.Link(); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Callvirt, rcontext.CompilerFactory.GetTypeMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Callvirt, rcontext.CompilerFactory.GetTypeMethod); for (int i = 0; i < map.Length; i++) { - ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Ldtoken, rcontext.Resolver.ResolveCoreType(map[i].Source).AsReflection()); - ilgen.Emit(OpCodes.Call, rcontext.CompilerFactory.GetTypeFromHandleMethod); - ilgen.Emit(OpCodes.Ceq); + ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldtoken, rcontext.Resolver.ResolveCoreType(map[i].Source)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, rcontext.CompilerFactory.GetTypeFromHandleMethod); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ceq); var label = ilgen.DefineLabel(); ilgen.EmitBrfalse(label); - ilgen.Emit(OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); if (map[i].Code != null) { - ilgen.Emit(OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); if (map[i].Code.Instructions.Length > 0) { @@ -2310,7 +2335,7 @@ internal void Emit(MapXml.CodeGenContext context, CodeEmitter ilgen) } } - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } else { @@ -2319,15 +2344,15 @@ internal void Emit(MapXml.CodeGenContext context, CodeEmitter ilgen) mw.Link(); mwSuppressFillInStackTrace.EmitCall(ilgen); mw.EmitNewobj(ilgen); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } ilgen.MarkLabel(label); } - ilgen.Emit(OpCodes.Pop); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ret); + ilgen.Emit(System.Reflection.Emit.OpCodes.Pop); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } } @@ -2493,7 +2518,7 @@ internal void FinishRemappedTypes() Context.AttributeHelper.SetCustomAttribute(this, assemblyBuilder, attr); } - private static bool IsSigned(Assembly asm) + private static bool IsSigned(IAssemblySymbol asm) { byte[] key = asm.GetName().GetPublicKey(); return key != null && key.Length != 0; @@ -2536,21 +2561,23 @@ internal static int Compile(ImportContext importer, RuntimeContext context, Stat foreach (var loader in loaders) loader.CompilePass0(); - var mainAssemblyTypes = new Dictionary(); + var mainAssemblyTypes = new Dictionary(); foreach (var loader in loaders) { if (loader.state.sharedclassloader != null) { if (!mainAssemblyTypes.TryGetValue(loader.state.sharedclassloader[0], out var mainAssemblyType)) { - var tb = loader.state.sharedclassloader[0].GetTypeWrapperFactory().ModuleBuilder.DefineType("__", TypeAttributes.NotPublic | TypeAttributes.Abstract | TypeAttributes.SpecialName); + var tb = loader.state.sharedclassloader[0].GetTypeWrapperFactory().ModuleBuilder.DefineType("__", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Abstract | System.Reflection.TypeAttributes.SpecialName); loader.Context.AttributeHelper.HideFromJava(tb); - mainAssemblyType = tb.CreateType(); + tb.Complete(); + + mainAssemblyType = tb; mainAssemblyTypes.Add(loader.state.sharedclassloader[0], mainAssemblyType); } if (loader.state.sharedclassloader[0] != loader) { - ((AssemblyBuilder)loader.GetTypeWrapperFactory().ModuleBuilder.Assembly).__AddTypeForwarder(mainAssemblyType); + ((IAssemblySymbolBuilder)loader.GetTypeWrapperFactory().ModuleBuilder.Assembly).AddTypeForwarder(mainAssemblyType); } } @@ -2591,13 +2618,13 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag { diagnostics.GenericCompilerInfo($"JVM.Compile path: {options.path}, assembly: {options.assembly}"); - AssemblyName runtimeAssemblyName = compiler.runtimeAssembly.GetName(); + var runtimeAssemblyName = compiler.runtimeAssembly.GetName(); bool allReferencesAreStrongNamed = IsSigned(compiler.runtimeAssembly); List references = new List(); - foreach (Assembly reference in options.references ?? new Assembly[0]) + foreach (var reference in options.references ?? []) { references.Add(reference); - allReferencesAreStrongNamed &= IsSigned(reference); + allReferencesAreStrongNamed &= IsSigned(context.Resolver.ResolveAssembly(reference)); diagnostics.GenericCompilerInfo($"Loaded reference assembly: {reference.FullName}"); // if it's an IKVM compiled assembly, make sure that it was compiled @@ -2699,7 +2726,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag } // now look for a main method - if (options.mainClass == null && (options.guessFileKind || options.target != PEFileKinds.Dll)) + if (options.mainClass == null && (options.guessFileKind || options.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll)) { foreach (string className in classNames) { @@ -2729,22 +2756,22 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag if (options.guessFileKind && options.mainClass == null) { - options.target = PEFileKinds.Dll; + options.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; } - if (options.target != PEFileKinds.Dll && options.mainClass == null) + if (options.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && options.mainClass == null) { throw new FatalCompilerErrorException(DiagnosticEvent.ExeRequiresMainClass()); } - if (options.target == PEFileKinds.Dll && options.props.Count != 0) + if (options.target == IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && options.props.Count != 0) { throw new FatalCompilerErrorException(DiagnosticEvent.PropertiesRequireExe()); } if (options.path == null) { - if (options.target == PEFileKinds.Dll) + if (options.target == IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll) { if (options.targetIsModule) { @@ -2778,10 +2805,10 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag for (int i = 0; i < references.Count; i++) { // if reference is to base assembly, set it explicitly for resolution - if (compiler.baseAssembly == null && options.bootstrap == false && IsBaseAssembly(context, references[i])) - compiler.baseAssembly = references[i]; + if (compiler.baseAssembly == null && options.bootstrap == false && IsBaseAssembly(context, context.Resolver.ResolveAssembly(references[i]))) + compiler.baseAssembly = context.Resolver.ResolveAssembly(references[i]); - var acl = context.AssemblyClassLoaderFactory.FromAssembly(references[i]); + var acl = context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveAssembly(references[i])); if (referencedAssemblies.Contains(acl)) diagnostics.DuplicateAssemblyReference(acl.MainAssembly.FullName); @@ -2837,7 +2864,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag { foreach (var name in compiler.runtimeAssembly.GetReferencedAssemblies()) { - Assembly asm = null; + IAssemblySymbol asm = null; try { @@ -2869,8 +2896,8 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag if (options.bootstrap == false) { - allReferencesAreStrongNamed &= IsSigned(context.Resolver.ResolveBaseAssembly().AsReflection()); - loader.AddReference(context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveBaseAssembly().AsReflection())); + allReferencesAreStrongNamed &= IsSigned(context.Resolver.ResolveBaseAssembly()); + loader.AddReference(context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveBaseAssembly())); } if ((options.keyPair != null || options.publicKey != null) && !allReferencesAreStrongNamed) @@ -2886,21 +2913,20 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag if (options.bootstrap == false) { loader.fakeTypes = context.FakeTypes; - loader.fakeTypes.Load(context.Resolver.ResolveBaseAssembly().AsReflection()); + loader.fakeTypes.Load(context.Resolver.ResolveBaseAssembly()); } return 0; } - static bool IsBaseAssembly(RuntimeContext context, Assembly asm) + static bool IsBaseAssembly(RuntimeContext context, IAssemblySymbol asm) { - return asm.IsDefined(context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.RemappedClassAttribute).FullName).AsReflection(), false); + return asm.IsDefined(context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.RemappedClassAttribute).FullName), false); } - private static Assembly LoadReferencedAssembly(StaticCompiler compiler, string r) + private static IAssemblySymbol LoadReferencedAssembly(StaticCompiler compiler, string r) { - Assembly asm = compiler.LoadFile(r); - return asm; + return compiler.LoadFile(r); } private void CompilePass0() @@ -2971,7 +2997,7 @@ int CompilePass3() Diagnostics.GenericCompilerInfo("Compiling class files (3)"); // emits the IL required for module initialization - var moduleInitBuilders = new List>(); + var moduleInitBuilders = new List>(); // bootstrap mode introduces fake types if (map != null && state.bootstrap) @@ -3008,7 +3034,7 @@ int CompilePass3() mw.Link(); - var method = mw.GetMethod() as MethodInfo; + var method = mw.GetMethod() as IMethodSymbol; if (method == null) throw new FatalCompilerErrorException(DiagnosticEvent.UnsupportedMainMethod()); @@ -3025,7 +3051,7 @@ int CompilePass3() _ => throw new NotImplementedException(), }; - SetMain(wrapper, state.target, state.props, state.noglobbing, apartmentAttributeType.AsReflection()); + SetMain(wrapper, state.target, state.props, state.noglobbing, apartmentAttributeType); } // complete map @@ -3040,7 +3066,7 @@ int CompilePass3() } catch (IKVM.Reflection.MissingMemberException x) { - Context.StaticCompiler.IssueMissingTypeMessage((Type)x.MemberInfo); + Context.StaticCompiler.IssueMissingTypeMessage((ITypeSymbol)Context.Resolver.ResolveMember(x.MemberInfo)); return 1; } } @@ -3056,7 +3082,7 @@ int CompilePass3() // configure Win32 file version if (state.fileversion != null) { - var filever = new CustomAttributeBuilder(Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyFileVersionAttribute).FullName).AsReflection().GetConstructor([Context.Types.String]), [state.fileversion]); + var filever = Context.Resolver.Symbols.CreateCustomAttribute(Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyFileVersionAttribute).FullName).GetConstructor([Context.Types.String]), [state.fileversion]); assemblyBuilder.SetCustomAttribute(filever); } @@ -3101,8 +3127,8 @@ int CompilePass3() throw new FatalCompilerErrorException(DiagnosticEvent.ClassLoaderConstructorMissing()); // apply custom attribute specifying custom class loader - var ci = Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName).AsReflection().GetConstructor(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new[] { Context.Types.Type }, null); - assemblyBuilder.SetCustomAttribute(new CustomAttributeBuilder(ci, new object[] { classLoaderType.TypeAsTBD })); + var ci = Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName).GetConstructor(System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic, new[] { Context.Types.Type }); + assemblyBuilder.SetCustomAttribute(Context.Resolver.Symbols.CreateCustomAttribute(ci, new object[] { classLoaderType.TypeAsTBD })); // the class loader type defines a module initialize method, ensure we call it upon module load var mwModuleInit = classLoaderType.GetMethodWrapper("InitializeModule", "(Lcli.System.Reflection.Module;)V", false); @@ -3110,22 +3136,22 @@ int CompilePass3() { moduleInitBuilders.Add((mb, il) => { - il.Emit(OpCodes.Ldtoken, mb); - il.Emit(OpCodes.Call, Context.Resolver.ResolveCoreType(typeof(System.Reflection.MethodBase).FullName).GetMethod("GetMethodFromHandle", new[] { Context.Resolver.ResolveCoreType(typeof(RuntimeMethodHandle).FullName) }).AsReflection()); - il.Emit(OpCodes.Callvirt, Context.Resolver.ResolveCoreType(typeof(System.Reflection.MemberInfo).FullName).GetProperty("Module").GetGetMethod().AsReflection()); - il.Emit(OpCodes.Call, Context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper").GetMethod("InitializeModule").AsReflection()); + il.Emit(System.Reflection.Emit.OpCodes.Ldtoken, mb); + il.Emit(System.Reflection.Emit.OpCodes.Call, Context.Resolver.ResolveCoreType(typeof(System.Reflection.MethodBase).FullName).GetMethod("GetMethodFromHandle", new[] { Context.Resolver.ResolveCoreType(typeof(RuntimeMethodHandle).FullName) })); + il.Emit(System.Reflection.Emit.OpCodes.Callvirt, Context.Resolver.ResolveCoreType(typeof(System.Reflection.MemberInfo).FullName).GetProperty("Module").GetGetMethod()); + il.Emit(System.Reflection.Emit.OpCodes.Call, Context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper").GetMethod("InitializeModule")); }); } } if (state.iconfile != null) { - assemblyBuilder.__DefineIconResource(ImportContext.ReadAllBytes(state.iconfile)); + assemblyBuilder.DefineIconResource(ImportContext.ReadAllBytes(state.iconfile)); } if (state.manifestFile != null) { - assemblyBuilder.__DefineManifestResource(ImportContext.ReadAllBytes(state.manifestFile)); + assemblyBuilder.DefineManifestResource(ImportContext.ReadAllBytes(state.manifestFile)); } assemblyBuilder.DefineVersionInfoResource(); @@ -3141,7 +3167,7 @@ int CompilePass3() if (moduleInitBuilders.Count > 0) { // begin a module initializer - var moduleInit = GetTypeWrapperFactory().ModuleBuilder.DefineGlobalMethod(".cctor", MethodAttributes.Private | MethodAttributes.Static | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName, null, Type.EmptyTypes); + var moduleInit = GetTypeWrapperFactory().ModuleBuilder.DefineGlobalMethod(".cctor", System.Reflection.MethodAttributes.Private | System.Reflection.MethodAttributes.Static | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName, null, []); var moduleInitIL = Context.CodeEmitterFactory.Create(moduleInit); // allow builders to append IL @@ -3149,7 +3175,7 @@ int CompilePass3() moduleInitBuilder(moduleInit, moduleInitIL); // finish method - moduleInitIL.Emit(OpCodes.Ret); + moduleInitIL.Emit(System.Reflection.Emit.OpCodes.Ret); moduleInitIL.DoEmit(); } @@ -3243,16 +3269,17 @@ static bool IsValidSig(string sig, bool field) return sig != null && (field ? IKVM.Runtime.ClassFile.IsValidFieldSig(sig) : IKVM.Runtime.ClassFile.IsValidMethodSig(sig)); } - internal Type GetTypeFromReferencedAssembly(string name) + internal ITypeSymbol GetTypeFromReferencedAssembly(string name) { foreach (RuntimeAssemblyClassLoader acl in referencedAssemblies) { - Type type = acl.MainAssembly.GetType(name, false); + var type = acl.MainAssembly.GetType(name, false); if (type != null) { return type; } } + return null; } @@ -3273,6 +3300,7 @@ protected override void CheckProhibitedPackage(string className) base.CheckProhibitedPackage(className); } } + } -} +} \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportContext.cs b/src/IKVM.Tools.Importer/ImportContext.cs index 1ef1ea8e7a..b8d0f8f5b8 100644 --- a/src/IKVM.Tools.Importer/ImportContext.cs +++ b/src/IKVM.Tools.Importer/ImportContext.cs @@ -26,14 +26,15 @@ Jeroen Frijters using System.IO; using System.IO.Compression; using System.Linq; +using System.Reflection.Metadata; +using System.Reflection.PortableExecutable; using System.Text.RegularExpressions; using System.Threading; using IKVM.ByteCode; using IKVM.CoreLib.Diagnostics; -using IKVM.CoreLib.Symbols; using IKVM.Reflection; -using IKVM.Reflection.Emit; +using IKVM.Reflection.Diagnostics; using IKVM.Runtime; using IKVM.Tools.Core.Diagnostics; @@ -100,6 +101,7 @@ public override void Report(in DiagnosticEvent @event) } readonly ImportOptions _options; + static readonly AssemblyResolver resolver = new AssemblyResolver(); string manifestMainClass; string defaultAssemblyName; static bool time; @@ -108,7 +110,6 @@ public override void Report(in DiagnosticEvent @event) static bool nonDeterministicOutput; static DebugMode debugMode; static readonly List libpaths = new List(); - internal static readonly AssemblyResolver resolver = new AssemblyResolver(); public static int Execute(ImportOptions options) { @@ -179,27 +180,58 @@ static IDiagnosticHandler GetDiagnostics(IServiceProvider services, ImportState return ActivatorUtilities.CreateInstance(services, options, spec); } + /// + /// Initiates a compilation with the given options. + /// + /// + /// + /// + /// static int Compile(ImportOptions options) { + // use a service collection to initialize core services var rootTarget = new ImportState(); var services = new ServiceCollection(); services.AddToolsDiagnostics(); services.AddSingleton(p => GetDiagnostics(p, rootTarget, options.Log)); - services.AddSingleton(); + services.AddSingleton(); services.AddSingleton(); using var provider = services.BuildServiceProvider(); var diagnostics = provider.GetRequiredService(); var compiler = provider.GetRequiredService(); var targets = new List(); - var context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, provider.GetRequiredService(), options.Bootstrap, compiler); + var context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, provider.GetRequiredService(), options.Bootstrap, compiler); + + // discover the core lib from the references + var coreLibName = FindCoreLibName(rootTarget.unresolvedReferences, libpaths); + if (coreLibName == null) + { + diagnostics.CoreClassesMissing(); + throw new Exception(); + } + + var universeOptions = UniverseOptions.ResolveMissingMembers | UniverseOptions.EnableFunctionPointers; + if (nonDeterministicOutput == false) + universeOptions |= UniverseOptions.DeterministicOutput; + + // configure the universe of types + var universe = new Universe(universeOptions, coreLibName); + universe.ResolvedMissingMember += (requestingModule, member) => + { + if (requestingModule != null && member is IKVM.Reflection.Type type) + diagnostics.UnableToResolveType(requestingModule.Name, type.FullName, member.Module.FullyQualifiedName); + }; + + // enable embedded symbol writer if debug mode is enabled + if (rootTarget.debugMode == DebugMode.Portable) + universe.SetSymbolWriterFactory(module => new PortablePdbSymbolWriter(module)); compiler.rootTarget = rootTarget; var importer = new ImportContext(); importer.ParseCommandLine(context, compiler, diagnostics, options, targets, rootTarget); - compiler.Init(nonDeterministicOutput, rootTarget.debugMode, libpaths); resolver.Warning += (warning, message, parameters) => loader_Warning(compiler, diagnostics, warning, message, parameters); - resolver.Init(compiler.Universe, nostdlib, rootTarget.unresolvedReferences, libpaths); + resolver.Init(universe, nostdlib, rootTarget.unresolvedReferences, libpaths); ResolveReferences(compiler, diagnostics, targets); ResolveStrongNameKeys(targets); @@ -219,6 +251,64 @@ static int Compile(ImportOptions options) } } + /// + /// Finds the first potential core library in the reference set. + /// + /// + /// + /// + static string FindCoreLibName(IList references, IList libpaths) + { + if (references != null) + foreach (var reference in references) + if (GetAssemblyNameIfCoreLib(reference) is string coreLibName) + return coreLibName; + + if (libpaths != null) + foreach (var libpath in libpaths) + foreach (var dll in Directory.GetFiles(libpath, "*.dll")) + if (GetAssemblyNameIfCoreLib(dll) is string coreLibName) + return coreLibName; + + return null; + } + + /// + /// Returns true if the given assembly is a core library. + /// + /// + /// + static string GetAssemblyNameIfCoreLib(string path) + { + if (File.Exists(path) == false) + return null; + + using var st = File.OpenRead(path); + using var pe = new PEReader(st); + var mr = pe.GetMetadataReader(); + + foreach (var handle in mr.TypeDefinitions) + if (IsSystemObject(mr, handle)) + return mr.GetString(mr.GetAssemblyDefinition().Name); + + return null; + } + + /// + /// Returns true if the given type definition handle refers to "System.Object". + /// + /// + /// + /// + static bool IsSystemObject(MetadataReader reader, TypeDefinitionHandle th) + { + var td = reader.GetTypeDefinition(th); + var ns = reader.GetString(td.Namespace); + var nm = reader.GetString(td.Name); + + return ns == "System" && nm == "Object"; + } + static void loader_Warning(StaticCompiler compiler, IDiagnosticHandler diagnostics, AssemblyResolver.WarningId warning, string message, string[] parameters) { switch (warning) @@ -302,7 +392,7 @@ internal static byte[] ReadAllBytes(FileInfo path) void ParseCommandLine(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, ImportOptions options, List targets, ImportState compilerOptions) { - compilerOptions.target = PEFileKinds.ConsoleApplication; + compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.ConsoleApplication; compilerOptions.guessFileKind = true; compilerOptions.version = new Version(0, 0, 0, 0); compilerOptions.apartment = ApartmentState.STA; @@ -321,21 +411,21 @@ void ContinueParseCommandLine(RuntimeContext context, StaticCompiler compiler, I switch (options.Target) { case ImportTarget.Exe: - compilerOptions.target = PEFileKinds.ConsoleApplication; + compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.ConsoleApplication; compilerOptions.guessFileKind = false; break; case ImportTarget.WinExe: - compilerOptions.target = PEFileKinds.WindowApplication; + compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.WindowApplication; compilerOptions.guessFileKind = false; break; case ImportTarget.Module: compilerOptions.targetIsModule = true; - compilerOptions.target = PEFileKinds.Dll; + compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; compilerOptions.guessFileKind = false; nonDeterministicOutput = true; break; case ImportTarget.Library: - compilerOptions.target = PEFileKinds.Dll; + compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; compilerOptions.guessFileKind = false; break; default: @@ -345,28 +435,28 @@ void ContinueParseCommandLine(RuntimeContext context, StaticCompiler compiler, I switch (options.Platform) { case ImportPlatform.X86: - compilerOptions.pekind = PortableExecutableKinds.ILOnly | PortableExecutableKinds.Required32Bit; - compilerOptions.imageFileMachine = ImageFileMachine.I386; + compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.Required32Bit; + compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.I386; break; case ImportPlatform.X64: - compilerOptions.pekind = PortableExecutableKinds.ILOnly | PortableExecutableKinds.PE32Plus; - compilerOptions.imageFileMachine = ImageFileMachine.AMD64; + compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.PE32Plus; + compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.AMD64; break; case ImportPlatform.ARM: - compilerOptions.pekind = PortableExecutableKinds.ILOnly; - compilerOptions.imageFileMachine = ImageFileMachine.ARM; + compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly; + compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.ARM; break; case ImportPlatform.ARM64: - compilerOptions.pekind = PortableExecutableKinds.ILOnly; - compilerOptions.imageFileMachine = ImageFileMachine.ARM64; + compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly; + compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.ARM64; break; case ImportPlatform.AnyCpu32BitPreferred: - compilerOptions.pekind = PortableExecutableKinds.ILOnly | PortableExecutableKinds.Preferred32Bit; - compilerOptions.imageFileMachine = ImageFileMachine.UNKNOWN; + compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.Preferred32Bit; + compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.Unknown; break; case ImportPlatform.AnyCpu: - compilerOptions.pekind = PortableExecutableKinds.ILOnly; - compilerOptions.imageFileMachine = ImageFileMachine.UNKNOWN; + compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly; + compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.Unknown; break; default: throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedPlatform(options.Platform.ToString())); @@ -698,12 +788,12 @@ void ContinueParseCommandLine(RuntimeContext context, StaticCompiler compiler, I if (compilerOptions.path != null && compilerOptions.guessFileKind) { if (compilerOptions.path.Extension.Equals(".dll", StringComparison.OrdinalIgnoreCase)) - compilerOptions.target = PEFileKinds.Dll; + compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; compilerOptions.guessFileKind = false; } - if (compilerOptions.mainClass == null && manifestMainClass != null && (compilerOptions.guessFileKind || compilerOptions.target != PEFileKinds.Dll)) + if (compilerOptions.mainClass == null && manifestMainClass != null && (compilerOptions.guessFileKind || compilerOptions.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll)) { diagnostics.MainMethodFromManifest(manifestMainClass); compilerOptions.mainClass = manifestMainClass; @@ -857,7 +947,7 @@ static void SetStrongNameKeyPair(ref StrongNameKeyPair strongNameKeyPair, FileIn static void ResolveReferences(StaticCompiler compiler, IDiagnosticHandler diagnostics, List targets) { - var cache = new Dictionary(); + var cache = new Dictionary(); foreach (var target in targets) { @@ -873,6 +963,7 @@ static void ResolveReferences(StaticCompiler compiler, IDiagnosticHandler diagno goto next_reference; } } + if (!resolver.ResolveReference(cache, ref target.references, reference)) { throw new FatalCompilerErrorException(DiagnosticEvent.ReferenceNotFound(reference)); @@ -905,10 +996,10 @@ static void ResolveReferences(StaticCompiler compiler, IDiagnosticHandler diagno foreach (var target in targets) if (target.references != null) foreach (var asm in target.references) - RuntimeAssemblyClassLoader.PreloadExportedAssemblies(compiler, asm); + RuntimeAssemblyClassLoader.PreloadExportedAssemblies(compiler, compiler.Symbols.GetOrCreateAssemblySymbol(asm)); } - private static void ArrayAppend(ref T[] array, T element) + static void ArrayAppend(ref T[] array, T element) { if (array == null) array = [element]; @@ -916,7 +1007,7 @@ private static void ArrayAppend(ref T[] array, T element) array = ArrayUtil.Concat(array, element); } - private static void ArrayAppend(ref T[] array, T[] append) + static void ArrayAppend(ref T[] array, T[] append) { if (array == null) { diff --git a/src/IKVM.Tools.Importer/ImportOptions.cs b/src/IKVM.Tools.Importer/ImportOptions.cs index 7967508d4d..9ad497ff95 100644 --- a/src/IKVM.Tools.Importer/ImportOptions.cs +++ b/src/IKVM.Tools.Importer/ImportOptions.cs @@ -268,4 +268,4 @@ object ICloneable.Clone() } -} +} \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs new file mode 100644 index 0000000000..7f3eeecb84 --- /dev/null +++ b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs @@ -0,0 +1,141 @@ +/* + Copyright (C) 2002-2014 Jeroen Frijters + + This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. + + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jeroen Frijters + jeroen@frijters.net + +*/ +using System; + +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.IkvmReflection; +using IKVM.Reflection; +using IKVM.Reflection.Emit; +using IKVM.Runtime; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.Tools.Importer +{ + + class ImportRuntimeSymbolResolver : IRuntimeSymbolResolver + { + + readonly StaticCompiler compiler; + readonly IkvmReflectionSymbolContext context; + + /// + public ISymbolContext Symbols => context; + + /// + /// Initializes a new instance. + /// + /// + public ImportRuntimeSymbolResolver(StaticCompiler compiler) + { + this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); + this.context = new IkvmReflectionSymbolContext(compiler.Universe); + } + + /// + public IAssemblySymbol ResolveBaseAssembly() + { + return compiler.baseAssembly; + } + + /// + public IAssemblySymbol ResolveAssembly(string assemblyName) + { + return compiler.Universe.Load(assemblyName) is { } a ? context.GetOrCreateAssemblySymbol(a) : null; + } + + /// + public ITypeSymbol ResolveCoreType(string typeName) + { + foreach (var assembly in compiler.Universe.GetAssemblies()) + if (assembly.GetType(typeName) is Type t) + return context.GetOrCreateTypeSymbol(t); + + return null; + } + + /// + public ITypeSymbol ResolveRuntimeType(string typeName) + { + return compiler.GetRuntimeType(typeName); + } + + /// + public IAssemblySymbol ResolveAssembly(Assembly assembly) + { + return context.GetOrCreateAssemblySymbol(assembly); + } + + /// + public IAssemblySymbolBuilder ResolveAssembly(AssemblyBuilder assembly) + { + return context.GetOrCreateAssemblySymbol(assembly); + } + + /// + public IModuleSymbol ResolveModule(Module module) + { + return context.GetOrCreateModuleSymbol(module); + } + + /// + public IModuleSymbolBuilder ResolveModule(ModuleBuilder module) + { + return context.GetOrCreateModuleSymbol(module); + } + + /// + public ITypeSymbol ResolveType(Type type) + { + return context.GetOrCreateTypeSymbol(type); + } + + /// + public IMemberSymbol ResolveMember(MemberInfo memberInfo) + { + return context.GetOrCreateMemberSymbol(memberInfo); + } + + /// + public IMethodBaseSymbol ResolveMethodBase(MethodBase type) + { + return context.GetOrCreateMethodBaseSymbol(type); + } + + /// + public IConstructorSymbol ResolveConstructor(ConstructorInfo ctor) + { + return context.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IMethodSymbol ResolveMethod(MethodInfo method) + { + return context.GetOrCreateMethodSymbol(method); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportState.cs b/src/IKVM.Tools.Importer/ImportState.cs index fd8a2ceaad..38ef6f3687 100644 --- a/src/IKVM.Tools.Importer/ImportState.cs +++ b/src/IKVM.Tools.Importer/ImportState.cs @@ -1,25 +1,25 @@ /* - Copyright (C) 2002-2014 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - + Copyright (C) 2002-2014 Jeroen Frijters + + This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. + + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jeroen Frijters + jeroen@frijters.net + */ using System; using System.Collections.Generic; @@ -59,7 +59,7 @@ sealed class ImportState internal string assembly; internal string mainClass; internal ApartmentState apartment; - internal PEFileKinds target; + internal IKVM.CoreLib.Symbols.Emit.PEFileKinds target; internal bool guessFileKind; internal string[] unresolvedReferences; // only used during command line parsing internal Dictionary legacyStubReferences = new Dictionary(); // only used during command line parsing @@ -79,8 +79,8 @@ sealed class ImportState internal string sourcepath; internal Dictionary externalResources; internal string classLoader; - internal PortableExecutableKinds pekind = PortableExecutableKinds.ILOnly; - internal ImageFileMachine imageFileMachine = ImageFileMachine.I386; + internal System.Reflection.PortableExecutableKinds pekind = System.Reflection.PortableExecutableKinds.ILOnly; + internal IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.I386; internal ulong baseAddress; internal uint fileAlignment; internal bool highentropyva; @@ -195,4 +195,4 @@ internal bool IsExcludedClass(string className) } -} +} \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportTarget.cs b/src/IKVM.Tools.Importer/ImportTarget.cs index 475c272a72..a2eae1b97a 100644 --- a/src/IKVM.Tools.Importer/ImportTarget.cs +++ b/src/IKVM.Tools.Importer/ImportTarget.cs @@ -12,4 +12,4 @@ enum ImportTarget } -} \ No newline at end of file +} diff --git a/src/IKVM.Tools.Importer/ManagedResolver.cs b/src/IKVM.Tools.Importer/ManagedResolver.cs deleted file mode 100644 index 2b6ec0e4e6..0000000000 --- a/src/IKVM.Tools.Importer/ManagedResolver.cs +++ /dev/null @@ -1,75 +0,0 @@ -/* - Copyright (C) 2002-2014 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - -*/ -using System; - -using IKVM.CoreLib.Symbols; -using IKVM.CoreLib.Symbols.IkvmReflection; - -using Type = IKVM.Reflection.Type; - -namespace IKVM.Tools.Importer -{ - - class ManagedResolver : ISymbolResolver - { - - readonly StaticCompiler compiler; - readonly IkvmReflectionSymbolContext context = new(); - - /// - /// Initializes a new instance. - /// - /// - public ManagedResolver(StaticCompiler compiler) - { - this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); - } - - public IAssemblySymbol ResolveBaseAssembly() - { - return compiler.baseAssembly != null ? context.GetOrCreateAssemblySymbol(compiler.baseAssembly) : null; - } - - public IAssemblySymbol ResolveAssembly(string assemblyName) - { - return compiler.Universe.Load(assemblyName) is { } a ? context.GetOrCreateAssemblySymbol(a) : null; - } - - public ITypeSymbol ResolveCoreType(string typeName) - { - foreach (var assembly in compiler.Universe.GetAssemblies()) - if (assembly.GetType(typeName) is Type t) - return context.GetOrCreateTypeSymbol(t); - - return null; - } - - public ITypeSymbol ResolveRuntimeType(string typeName) - { - return compiler.GetRuntimeType(typeName) is { } t ? context.GetOrCreateTypeSymbol(t) : null; - } - - } - -} diff --git a/src/IKVM.Tools.Importer/MapXml/Add.cs b/src/IKVM.Tools.Importer/MapXml/Add.cs index 8d16993d07..7541d6ad8b 100644 --- a/src/IKVM.Tools.Importer/MapXml/Add.cs +++ b/src/IKVM.Tools.Importer/MapXml/Add.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/And.cs b/src/IKVM.Tools.Importer/MapXml/And.cs index e0b869ce61..4829dedbfe 100644 --- a/src/IKVM.Tools.Importer/MapXml/And.cs +++ b/src/IKVM.Tools.Importer/MapXml/And.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Box.cs b/src/IKVM.Tools.Importer/MapXml/Box.cs index 989b8a28d3..6c11c315a6 100644 --- a/src/IKVM.Tools.Importer/MapXml/Box.cs +++ b/src/IKVM.Tools.Importer/MapXml/Box.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Call.cs b/src/IKVM.Tools.Importer/MapXml/Call.cs index f0f135ef52..b2049a1018 100644 --- a/src/IKVM.Tools.Importer/MapXml/Call.cs +++ b/src/IKVM.Tools.Importer/MapXml/Call.cs @@ -25,14 +25,13 @@ Jeroen Frijters using System; using System.Diagnostics; using System.Linq; +using System.Reflection; +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection; -using IKVM.Reflection.Emit; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer.MapXml { @@ -102,11 +101,10 @@ internal sealed override void Generate(CodeGenContext context, CodeEmitter ilgen Debug.Assert(Class == null && Type != null); var argTypes = context.ClassLoader.ArgTypeListFromSig(Sig); - var ci = context.ClassLoader.Context.Resolver.ResolveCoreType(Type).AsReflection().GetConstructor(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance, null, CallingConventions.Standard, argTypes, null); + var ci = context.ClassLoader.Context.Resolver.ResolveCoreType(Type).GetConstructor(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance, argTypes); if (ci == null) - { throw new InvalidOperationException("Missing .ctor: " + Type + "..ctor" + Sig); - } + ilgen.Emit(opcode, ci); } else @@ -176,37 +174,37 @@ internal sealed override void Generate(CodeGenContext context, CodeEmitter ilgen else { // ldftn or ldvirtftn - ilgen.Emit(opcode, (MethodInfo)method.GetMethod()); + ilgen.Emit(opcode, (IMethodSymbol)method.GetMethod()); } } else { - Type[] argTypes; + ITypeSymbol[] argTypes; if (Sig.StartsWith("(")) { argTypes = context.ClassLoader.ArgTypeListFromSig(Sig); } else if (Sig == "") { - argTypes = Reflection.Type.EmptyTypes; + argTypes = []; } else { - string[] types = Sig.Split(';'); - argTypes = new Type[types.Length]; + var types = Sig.Split(';'); + argTypes = new ITypeSymbol[types.Length]; for (int i = 0; i < types.Length; i++) { - argTypes[i] = context.ClassLoader.Context.Resolver.ResolveCoreType(types[i]).AsReflection(); + argTypes[i] = context.ClassLoader.Context.Resolver.ResolveCoreType(types[i]); } } - var ti = context.ClassLoader.Context.Resolver.ResolveCoreType(Type).AsReflection(); + var ti = context.ClassLoader.Context.Resolver.ResolveCoreType(Type); if (ti == null) { throw new InvalidOperationException("Missing type: " + Type); } - var mi = ti.GetMethod(Name, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static, null, argTypes, null); + var mi = ti.GetMethod(Name, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static, argTypes); if (mi == null) { var ta = argTypes.Select(i => i.AssemblyQualifiedName).ToArray(); diff --git a/src/IKVM.Tools.Importer/MapXml/Callvirt.cs b/src/IKVM.Tools.Importer/MapXml/Callvirt.cs index 3e235dceef..7070bb7dab 100644 --- a/src/IKVM.Tools.Importer/MapXml/Callvirt.cs +++ b/src/IKVM.Tools.Importer/MapXml/Callvirt.cs @@ -22,10 +22,8 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using System.Xml.Serialization; - -using IKVM.Reflection.Emit; namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Castclass.cs b/src/IKVM.Tools.Importer/MapXml/Castclass.cs index d7f3ff7fc1..c318013a67 100644 --- a/src/IKVM.Tools.Importer/MapXml/Castclass.cs +++ b/src/IKVM.Tools.Importer/MapXml/Castclass.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Castclass_impl.cs b/src/IKVM.Tools.Importer/MapXml/Castclass_impl.cs index e2c5d65a29..a7a2a6e7b3 100644 --- a/src/IKVM.Tools.Importer/MapXml/Castclass_impl.cs +++ b/src/IKVM.Tools.Importer/MapXml/Castclass_impl.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Ceq.cs b/src/IKVM.Tools.Importer/MapXml/Ceq.cs index 8c6e1708a2..79f4881022 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ceq.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ceq.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_I.cs b/src/IKVM.Tools.Importer/MapXml/Conv_I.cs index 73749adda5..a7a8234bf3 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_I.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_I.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_I1.cs b/src/IKVM.Tools.Importer/MapXml/Conv_I1.cs index 856a49a398..e21e58b930 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_I1.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_I1.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_I2.cs b/src/IKVM.Tools.Importer/MapXml/Conv_I2.cs index 29c660e99d..d3ae5cd466 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_I2.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_I2.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_I4.cs b/src/IKVM.Tools.Importer/MapXml/Conv_I4.cs index c0dbd48d2e..e17b6f0d04 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_I4.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_I4.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_I8.cs b/src/IKVM.Tools.Importer/MapXml/Conv_I8.cs index 0072cb2e99..45dd0baf85 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_I8.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_I8.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_U1.cs b/src/IKVM.Tools.Importer/MapXml/Conv_U1.cs index 83d6dd75b7..4d773cd861 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_U1.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_U1.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_U2.cs b/src/IKVM.Tools.Importer/MapXml/Conv_U2.cs index 6299552b21..be9d0ef066 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_U2.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_U2.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_U4.cs b/src/IKVM.Tools.Importer/MapXml/Conv_U4.cs index e91580b721..bb57703b7f 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_U4.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_U4.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Conv_U8.cs b/src/IKVM.Tools.Importer/MapXml/Conv_U8.cs index 37626248f2..39a80a5282 100644 --- a/src/IKVM.Tools.Importer/MapXml/Conv_U8.cs +++ b/src/IKVM.Tools.Importer/MapXml/Conv_U8.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Cpblk.cs b/src/IKVM.Tools.Importer/MapXml/Cpblk.cs index f10e19ea49..91e7600755 100644 --- a/src/IKVM.Tools.Importer/MapXml/Cpblk.cs +++ b/src/IKVM.Tools.Importer/MapXml/Cpblk.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Div_Un.cs b/src/IKVM.Tools.Importer/MapXml/Div_Un.cs index b625ecc836..9b19f11eca 100644 --- a/src/IKVM.Tools.Importer/MapXml/Div_Un.cs +++ b/src/IKVM.Tools.Importer/MapXml/Div_Un.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Dup.cs b/src/IKVM.Tools.Importer/MapXml/Dup.cs index 2b6760e048..00b4bb568f 100644 --- a/src/IKVM.Tools.Importer/MapXml/Dup.cs +++ b/src/IKVM.Tools.Importer/MapXml/Dup.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Endfinally.cs b/src/IKVM.Tools.Importer/MapXml/Endfinally.cs index fac18f2ee6..996c163d9a 100644 --- a/src/IKVM.Tools.Importer/MapXml/Endfinally.cs +++ b/src/IKVM.Tools.Importer/MapXml/Endfinally.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/ExceptionBlock.cs b/src/IKVM.Tools.Importer/MapXml/ExceptionBlock.cs index 3658898d64..5f212b237b 100644 --- a/src/IKVM.Tools.Importer/MapXml/ExceptionBlock.cs +++ b/src/IKVM.Tools.Importer/MapXml/ExceptionBlock.cs @@ -25,10 +25,9 @@ Jeroen Frijters using System.Linq; using System.Xml.Linq; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer.MapXml { @@ -75,7 +74,7 @@ internal override void Generate(CodeGenContext context, CodeEmitter ilgen) if (Catch != null) { - Type type; + ITypeSymbol type; if (Catch.Type != null) { type = context.ClassLoader.Context.StaticCompiler.GetTypeForMapXml(context.ClassLoader, Catch.Type); diff --git a/src/IKVM.Tools.Importer/MapXml/IsInst.cs b/src/IKVM.Tools.Importer/MapXml/IsInst.cs index feecfa389b..0f870a6410 100644 --- a/src/IKVM.Tools.Importer/MapXml/IsInst.cs +++ b/src/IKVM.Tools.Importer/MapXml/IsInst.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/LdArg_0.cs b/src/IKVM.Tools.Importer/MapXml/LdArg_0.cs index 5aa356dff4..2b5b1d6f68 100644 --- a/src/IKVM.Tools.Importer/MapXml/LdArg_0.cs +++ b/src/IKVM.Tools.Importer/MapXml/LdArg_0.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/LdArg_1.cs b/src/IKVM.Tools.Importer/MapXml/LdArg_1.cs index 598cc5153a..5ee7231e4b 100644 --- a/src/IKVM.Tools.Importer/MapXml/LdArg_1.cs +++ b/src/IKVM.Tools.Importer/MapXml/LdArg_1.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/LdArg_2.cs b/src/IKVM.Tools.Importer/MapXml/LdArg_2.cs index 7997962de8..248938108c 100644 --- a/src/IKVM.Tools.Importer/MapXml/LdArg_2.cs +++ b/src/IKVM.Tools.Importer/MapXml/LdArg_2.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/LdArg_3.cs b/src/IKVM.Tools.Importer/MapXml/LdArg_3.cs index b93ca145da..1e956278f7 100644 --- a/src/IKVM.Tools.Importer/MapXml/LdArg_3.cs +++ b/src/IKVM.Tools.Importer/MapXml/LdArg_3.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/LdLoc.cs b/src/IKVM.Tools.Importer/MapXml/LdLoc.cs index 566a143103..d6b3970690 100644 --- a/src/IKVM.Tools.Importer/MapXml/LdLoc.cs +++ b/src/IKVM.Tools.Importer/MapXml/LdLoc.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Ldc_I4_0.cs b/src/IKVM.Tools.Importer/MapXml/Ldc_I4_0.cs index afe746b5e8..331f7c3b1d 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldc_I4_0.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldc_I4_0.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldc_I4_1.cs b/src/IKVM.Tools.Importer/MapXml/Ldc_I4_1.cs index 2e055bd77e..3d7e060e42 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldc_I4_1.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldc_I4_1.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldc_I4_M1.cs b/src/IKVM.Tools.Importer/MapXml/Ldc_I4_M1.cs index c9cb248b5c..408ef06510 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldc_I4_M1.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldc_I4_M1.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldelema.cs b/src/IKVM.Tools.Importer/MapXml/Ldelema.cs index 1b4688cdaa..90b99fccba 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldelema.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldelema.cs @@ -22,10 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using IKVM.Runtime; -using IKVM.Reflection.Emit; namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldfld.cs b/src/IKVM.Tools.Importer/MapXml/Ldfld.cs index 5a8869a548..d3659e7b7e 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldfld.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldfld.cs @@ -22,10 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using IKVM.Runtime; -using IKVM.Reflection.Emit; namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldflda.cs b/src/IKVM.Tools.Importer/MapXml/Ldflda.cs index b8b7bbc10e..fded0165d2 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldflda.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldflda.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Ldftn.cs b/src/IKVM.Tools.Importer/MapXml/Ldftn.cs index 0c3395bae8..f415d93a01 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldftn.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldftn.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldind_i1.cs b/src/IKVM.Tools.Importer/MapXml/Ldind_i1.cs index 5ee93d4cb1..3e0e9dd4a1 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldind_i1.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldind_i1.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldind_i2.cs b/src/IKVM.Tools.Importer/MapXml/Ldind_i2.cs index 02f96718c6..d45bf0908c 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldind_i2.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldind_i2.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldind_i4.cs b/src/IKVM.Tools.Importer/MapXml/Ldind_i4.cs index d2631f1a85..19c9dfcf62 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldind_i4.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldind_i4.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldind_i8.cs b/src/IKVM.Tools.Importer/MapXml/Ldind_i8.cs index 4dc7dee7d7..2eb4c82af5 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldind_i8.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldind_i8.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldind_r4.cs b/src/IKVM.Tools.Importer/MapXml/Ldind_r4.cs index 9e9194e722..d6b32a66c8 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldind_r4.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldind_r4.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldind_r8.cs b/src/IKVM.Tools.Importer/MapXml/Ldind_r8.cs index 638c8254da..e7edaee8e0 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldind_r8.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldind_r8.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldind_ref.cs b/src/IKVM.Tools.Importer/MapXml/Ldind_ref.cs index 2e1e048784..3efc3151df 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldind_ref.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldind_ref.cs @@ -22,10 +22,8 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using System.Xml.Serialization; - -using IKVM.Reflection.Emit; namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldlen.cs b/src/IKVM.Tools.Importer/MapXml/Ldlen.cs index e134943bf2..d1453c6ed7 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldlen.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldlen.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldnull.cs b/src/IKVM.Tools.Importer/MapXml/Ldnull.cs index 6034da1d3e..3f6a098310 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldnull.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldnull.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldobj.cs b/src/IKVM.Tools.Importer/MapXml/Ldobj.cs index 6977dbbe71..0342abe9f9 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldobj.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldobj.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ldsfld.cs b/src/IKVM.Tools.Importer/MapXml/Ldsfld.cs index e656ad8b24..6b5e24425f 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldsfld.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldsfld.cs @@ -22,10 +22,10 @@ Jeroen Frijters */ +using System.Reflection; +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Ldstr.cs b/src/IKVM.Tools.Importer/MapXml/Ldstr.cs index 3cc6e13ce8..31652d7bf5 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldstr.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldstr.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Ldtoken.cs b/src/IKVM.Tools.Importer/MapXml/Ldtoken.cs index 57aa18b150..ede00503df 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldtoken.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldtoken.cs @@ -23,15 +23,12 @@ Jeroen Frijters */ using System; +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.CoreLib.Diagnostics; -using IKVM.Reflection; -using IKVM.Reflection.Emit; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer.MapXml { @@ -79,15 +76,13 @@ public static void Load(Ldtoken inst, XElement element) internal override void Generate(CodeGenContext context, CodeEmitter ilgen) { if (!Validate(context)) - { return; - } - MemberInfo member = Resolve(context); - Type type = member as Type; - MethodInfo method = member as MethodInfo; - ConstructorInfo constructor = member as ConstructorInfo; - FieldInfo field = member as FieldInfo; + var member = Resolve(context); + var type = member as ITypeSymbol; + var method = member as IMethodSymbol; + var constructor = member as IConstructorSymbol; + var field = member as IFieldSymbol; if (type != null) { @@ -146,14 +141,13 @@ private bool Validate(CodeGenContext context) } } - private MemberInfo Resolve(CodeGenContext context) + private IMemberSymbol Resolve(CodeGenContext context) { if (Type != null) { if (Class != null || Method != null || Field != null || Sig != null) - { throw new NotImplementedException(); - } + return context.ClassLoader.Context.StaticCompiler.GetTypeForMapXml(context.ClassLoader, Type); } else if (Class != null) @@ -167,18 +161,16 @@ private MemberInfo Resolve(CodeGenContext context) { var mw = tw.GetMethodWrapper(Method, Sig, false); if (mw == null) - { return null; - } + return mw.GetMethod(); } else if (Field != null) { var fw = tw.GetFieldWrapper(Field, Sig); if (fw == null) - { return null; - } + return fw.GetField(); } else diff --git a/src/IKVM.Tools.Importer/MapXml/Ldvirtftn.cs b/src/IKVM.Tools.Importer/MapXml/Ldvirtftn.cs index 27737ce64d..32c1479313 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ldvirtftn.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ldvirtftn.cs @@ -21,11 +21,8 @@ Jeroen Frijters jeroen@frijters.net */ - +using System.Reflection.Emit; using System.Xml.Linq; -using System.Xml.Serialization; - -using IKVM.Reflection.Emit; namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/MapXmlSerializer.cs b/src/IKVM.Tools.Importer/MapXml/MapXmlSerializer.cs index 865777f230..46e178106a 100644 --- a/src/IKVM.Tools.Importer/MapXml/MapXmlSerializer.cs +++ b/src/IKVM.Tools.Importer/MapXml/MapXmlSerializer.cs @@ -1,9 +1,8 @@ using System; using System.Linq; +using System.Reflection; using System.Xml.Linq; -using IKVM.Reflection; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/MethodBase.cs b/src/IKVM.Tools.Importer/MapXml/MethodBase.cs index fb710de508..407a70a649 100644 --- a/src/IKVM.Tools.Importer/MapXml/MethodBase.cs +++ b/src/IKVM.Tools.Importer/MapXml/MethodBase.cs @@ -23,9 +23,9 @@ Jeroen Frijters */ using System.Linq; +using System.Reflection; using System.Xml.Linq; -using IKVM.Reflection; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Mul.cs b/src/IKVM.Tools.Importer/MapXml/Mul.cs index dabdba1069..666aaa5a8a 100644 --- a/src/IKVM.Tools.Importer/MapXml/Mul.cs +++ b/src/IKVM.Tools.Importer/MapXml/Mul.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/NewObj.cs b/src/IKVM.Tools.Importer/MapXml/NewObj.cs index 3cea26ab55..68db92fbfd 100644 --- a/src/IKVM.Tools.Importer/MapXml/NewObj.cs +++ b/src/IKVM.Tools.Importer/MapXml/NewObj.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Newarr.cs b/src/IKVM.Tools.Importer/MapXml/Newarr.cs index 5b3223adef..d517252abb 100644 --- a/src/IKVM.Tools.Importer/MapXml/Newarr.cs +++ b/src/IKVM.Tools.Importer/MapXml/Newarr.cs @@ -22,10 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using IKVM.Runtime; -using IKVM.Reflection.Emit; namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Not.cs b/src/IKVM.Tools.Importer/MapXml/Not.cs index 1890f95e33..674875372e 100644 --- a/src/IKVM.Tools.Importer/MapXml/Not.cs +++ b/src/IKVM.Tools.Importer/MapXml/Not.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Or.cs b/src/IKVM.Tools.Importer/MapXml/Or.cs index 9f397086ef..13c6de5fd3 100644 --- a/src/IKVM.Tools.Importer/MapXml/Or.cs +++ b/src/IKVM.Tools.Importer/MapXml/Or.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Pop.cs b/src/IKVM.Tools.Importer/MapXml/Pop.cs index 9a6ac80925..cd275e7b08 100644 --- a/src/IKVM.Tools.Importer/MapXml/Pop.cs +++ b/src/IKVM.Tools.Importer/MapXml/Pop.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Redirect.cs b/src/IKVM.Tools.Importer/MapXml/Redirect.cs index 57951eaef6..18096da63c 100644 --- a/src/IKVM.Tools.Importer/MapXml/Redirect.cs +++ b/src/IKVM.Tools.Importer/MapXml/Redirect.cs @@ -23,14 +23,11 @@ Jeroen Frijters */ using System; +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer.MapXml { @@ -85,12 +82,11 @@ internal void Emit(RuntimeClassLoader loader, CodeEmitter ilgen) // HACK if the class name contains a comma, we assume it is a .NET type if (Type != null) { - var type = loader.Context.Resolver.ResolveCoreType(Type).AsReflection(); + var type = loader.Context.Resolver.ResolveCoreType(Type); var mi = type.GetMethod(Name, redirParamTypes); if (mi == null) - { throw new InvalidOperationException(); - } + ilgen.Emit(OpCodes.Call, mi); } else diff --git a/src/IKVM.Tools.Importer/MapXml/Rem_Un.cs b/src/IKVM.Tools.Importer/MapXml/Rem_Un.cs index 8b6a21f6c3..6ece91caa3 100644 --- a/src/IKVM.Tools.Importer/MapXml/Rem_Un.cs +++ b/src/IKVM.Tools.Importer/MapXml/Rem_Un.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Ret.cs b/src/IKVM.Tools.Importer/MapXml/Ret.cs index 5241e3283c..37fb3e5e55 100644 --- a/src/IKVM.Tools.Importer/MapXml/Ret.cs +++ b/src/IKVM.Tools.Importer/MapXml/Ret.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Simple.cs b/src/IKVM.Tools.Importer/MapXml/Simple.cs index 7d2a9db171..bcaba124d1 100644 --- a/src/IKVM.Tools.Importer/MapXml/Simple.cs +++ b/src/IKVM.Tools.Importer/MapXml/Simple.cs @@ -21,10 +21,9 @@ Jeroen Frijters jeroen@frijters.net */ - +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/StLoc.cs b/src/IKVM.Tools.Importer/MapXml/StLoc.cs index d2fb668509..b97b89d44f 100644 --- a/src/IKVM.Tools.Importer/MapXml/StLoc.cs +++ b/src/IKVM.Tools.Importer/MapXml/StLoc.cs @@ -23,13 +23,12 @@ Jeroen Frijters */ using System.Diagnostics; +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer.MapXml { @@ -63,7 +62,7 @@ public static void Load(StLoc inst, XElement element) } RuntimeJavaType typeWrapper; - Type typeType; + ITypeSymbol typeType; public string Name { get; set; } diff --git a/src/IKVM.Tools.Importer/MapXml/Stfld.cs b/src/IKVM.Tools.Importer/MapXml/Stfld.cs index 2f658147e8..4f5a26019e 100644 --- a/src/IKVM.Tools.Importer/MapXml/Stfld.cs +++ b/src/IKVM.Tools.Importer/MapXml/Stfld.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Stind_i1.cs b/src/IKVM.Tools.Importer/MapXml/Stind_i1.cs index a58f813dbe..bcefaa6dca 100644 --- a/src/IKVM.Tools.Importer/MapXml/Stind_i1.cs +++ b/src/IKVM.Tools.Importer/MapXml/Stind_i1.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Stind_i2.cs b/src/IKVM.Tools.Importer/MapXml/Stind_i2.cs index dc1bb863a3..a4b7858bbb 100644 --- a/src/IKVM.Tools.Importer/MapXml/Stind_i2.cs +++ b/src/IKVM.Tools.Importer/MapXml/Stind_i2.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Stind_i4.cs b/src/IKVM.Tools.Importer/MapXml/Stind_i4.cs index 67f4231535..d5e61f8859 100644 --- a/src/IKVM.Tools.Importer/MapXml/Stind_i4.cs +++ b/src/IKVM.Tools.Importer/MapXml/Stind_i4.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Stind_i8.cs b/src/IKVM.Tools.Importer/MapXml/Stind_i8.cs index 36fb4abec9..c0de5001da 100644 --- a/src/IKVM.Tools.Importer/MapXml/Stind_i8.cs +++ b/src/IKVM.Tools.Importer/MapXml/Stind_i8.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Stind_ref.cs b/src/IKVM.Tools.Importer/MapXml/Stind_ref.cs index 1d653482b2..b30e8b40b1 100644 --- a/src/IKVM.Tools.Importer/MapXml/Stind_ref.cs +++ b/src/IKVM.Tools.Importer/MapXml/Stind_ref.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Stsfld.cs b/src/IKVM.Tools.Importer/MapXml/Stsfld.cs index 9d95d93e90..0233b8cd5b 100644 --- a/src/IKVM.Tools.Importer/MapXml/Stsfld.cs +++ b/src/IKVM.Tools.Importer/MapXml/Stsfld.cs @@ -22,9 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer.MapXml diff --git a/src/IKVM.Tools.Importer/MapXml/Sub.cs b/src/IKVM.Tools.Importer/MapXml/Sub.cs index 1c2af5ec3a..a5080691c0 100644 --- a/src/IKVM.Tools.Importer/MapXml/Sub.cs +++ b/src/IKVM.Tools.Importer/MapXml/Sub.cs @@ -22,11 +22,10 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; using System.Xml.Serialization; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Throw.cs b/src/IKVM.Tools.Importer/MapXml/Throw.cs index 0f384cf827..8995e5b901 100644 --- a/src/IKVM.Tools.Importer/MapXml/Throw.cs +++ b/src/IKVM.Tools.Importer/MapXml/Throw.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/TypeInstruction.cs b/src/IKVM.Tools.Importer/MapXml/TypeInstruction.cs index 5da986a1c9..3c39e1fe91 100644 --- a/src/IKVM.Tools.Importer/MapXml/TypeInstruction.cs +++ b/src/IKVM.Tools.Importer/MapXml/TypeInstruction.cs @@ -23,13 +23,12 @@ Jeroen Frijters */ using System.Diagnostics; +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer.MapXml { @@ -42,7 +41,7 @@ public static void Load(TypeInstruction inst, XElement element) } readonly OpCode opcode; - Type typeType; + ITypeSymbol typeType; public string Type { get; set; } diff --git a/src/IKVM.Tools.Importer/MapXml/TypeOrTypeWrapperInstruction.cs b/src/IKVM.Tools.Importer/MapXml/TypeOrTypeWrapperInstruction.cs index 0357223567..7e1fcdcbcd 100644 --- a/src/IKVM.Tools.Importer/MapXml/TypeOrTypeWrapperInstruction.cs +++ b/src/IKVM.Tools.Importer/MapXml/TypeOrTypeWrapperInstruction.cs @@ -25,10 +25,9 @@ Jeroen Frijters using System.Diagnostics; using System.Xml.Linq; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer.MapXml { @@ -49,7 +48,7 @@ public static void Load(TypeOrTypeWrapperInstruction inst, XElement element) } internal RuntimeJavaType typeWrapper; - internal Type typeType; + internal ITypeSymbol typeType; public string Class { get; set; } diff --git a/src/IKVM.Tools.Importer/MapXml/Unbox.cs b/src/IKVM.Tools.Importer/MapXml/Unbox.cs index cdf4c43bc9..a23f7c0a74 100644 --- a/src/IKVM.Tools.Importer/MapXml/Unbox.cs +++ b/src/IKVM.Tools.Importer/MapXml/Unbox.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Volatile.cs b/src/IKVM.Tools.Importer/MapXml/Volatile.cs index e27751f585..77492c13c4 100644 --- a/src/IKVM.Tools.Importer/MapXml/Volatile.cs +++ b/src/IKVM.Tools.Importer/MapXml/Volatile.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/MapXml/Xor.cs b/src/IKVM.Tools.Importer/MapXml/Xor.cs index 07087346a9..d014fdb123 100644 --- a/src/IKVM.Tools.Importer/MapXml/Xor.cs +++ b/src/IKVM.Tools.Importer/MapXml/Xor.cs @@ -22,10 +22,9 @@ Jeroen Frijters */ +using System.Reflection.Emit; using System.Xml.Linq; -using IKVM.Reflection.Emit; - namespace IKVM.Tools.Importer.MapXml { diff --git a/src/IKVM.Tools.Importer/Proxy.cs b/src/IKVM.Tools.Importer/Proxy.cs index e1cd970955..2c1717e7e3 100644 --- a/src/IKVM.Tools.Importer/Proxy.cs +++ b/src/IKVM.Tools.Importer/Proxy.cs @@ -23,14 +23,14 @@ Jeroen Frijters */ using System; using System.Collections.Generic; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; -using IKVM.Reflection; -using IKVM.Reflection.Emit; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer { @@ -230,7 +230,7 @@ static RuntimeJavaType[] Merge(RuntimeJavaType[] newExceptionTypes, RuntimeJavaT void CreateNoFail(ImportClassLoader loader, RuntimeJavaType[] interfaces, List methods) { var ispublic = true; - var interfaceTypes = new Type[interfaces.Length]; + var interfaceTypes = new ITypeSymbol[interfaces.Length]; for (int i = 0; i < interfaceTypes.Length; i++) { ispublic &= interfaces[i].IsPublic; @@ -253,9 +253,9 @@ void CreateNoFail(ImportClassLoader loader, RuntimeJavaType[] interfaces, List

(); @@ -358,14 +358,15 @@ void CreateMethod(ImportClassLoader loader, TypeBuilder tb, ProxyMethod pm) ilgen.DoEmit(); } - void CreateStaticInitializer(TypeBuilder tb, List methods, ImportClassLoader loader) + void CreateStaticInitializer(ITypeSymbolBuilder tb, List methods, ImportClassLoader loader) { var ilgen = loader.Context.CodeEmitterFactory.Create(ReflectUtil.DefineTypeInitializer(tb, loader)); var callerID = ilgen.DeclareLocal(loader.Context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType); var tbCallerID = RuntimeByteCodeJavaType.FinishContext.EmitCreateCallerID(loader.Context, tb, ilgen); ilgen.Emit(OpCodes.Stloc, callerID); // HACK we shouldn't create the nested type here (the outer type must be created first) - tbCallerID.CreateType(); + tbCallerID.Complete(); + ilgen.BeginExceptionBlock(); foreach (ProxyMethod method in methods) { @@ -405,7 +406,7 @@ sealed class ProxyMethod internal readonly RuntimeJavaMethod mw; internal readonly RuntimeJavaType[] exceptions; - internal FieldBuilder fb; + internal IFieldSymbolBuilder fb; internal ProxyMethod(RuntimeJavaMethod mw, RuntimeJavaType[] exceptions) { diff --git a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs index 9712f24ac8..f6b342afd5 100644 --- a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs +++ b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs @@ -24,18 +24,16 @@ Jeroen Frijters using System; using System.Collections.Generic; +using System.Reflection; +using System.Reflection.Emit; using IKVM.Attributes; using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Runtime; using IKVM.Tools.Importer.MapXml; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer { @@ -131,7 +129,7 @@ internal void GetParameterNamesFromXml(string methodName, string methodSig, stri parameterNames[i] = parameters[i].Name; } - internal void AddXmlMapParameterAttributes(IMethodSymbolBuilder method, string className, string methodName, string methodSig, ref ParameterBuilder[] parameterBuilders) + internal void AddXmlMapParameterAttributes(IMethodSymbolBuilder method, string className, string methodName, string methodSig, ref IParameterSymbolBuilder[] parameterBuilders) { var parameters = classLoader.GetXmlMapParameters(className, methodName, methodSig); if (parameters != null) @@ -149,7 +147,7 @@ internal void AddXmlMapParameterAttributes(IMethodSymbolBuilder method, string c private void AddParameterMetadata(IMethodSymbolBuilder method, RuntimeJavaMethod mw) { - ParameterBuilder[] pbs; + IParameterSymbolBuilder[] pbs; if ((mw.DeclaringType.IsPublic && (mw.IsPublic || mw.IsProtected)) || classLoader.EmitSymbols) { string[] parameterNames = new string[mw.GetParameters().Length]; @@ -323,16 +321,14 @@ private void PublishProperties(ITypeSymbolBuilder typeBuilder, Class clazz) if (m == null || m.DeclaringType != typeBuilder || (!m.IsFinal && final)) { var mb = typeBuilder.DefineMethod("get_" + prop.Name, GetPropertyMethodAttributes(mw, final), typeWrapper.TypeAsSignatureType, indexer); - m = mb.Symbol; Context.AttributeHelper.HideFromJava(mb); var ilgen = Context.CodeEmitterFactory.Create(mb); if (mw.IsStatic) { for (int i = 0; i < indexer.Length; i++) - { ilgen.EmitLdarg(i); - } + mw.EmitCall(ilgen); } else @@ -363,7 +359,6 @@ private void PublishProperties(ITypeSymbolBuilder typeBuilder, Class clazz) if (m == null || m.DeclaringType != typeBuilder || (!m.IsFinal && final)) { var mb = typeBuilder.DefineMethod("set_" + prop.Name, GetPropertyMethodAttributes(mw, final), mw.ReturnTypeForDefineMethod, args); - m = mb.Symbol; Context.AttributeHelper.HideFromJava(mb); var ilgen = Context.CodeEmitterFactory.Create(mb); @@ -371,6 +366,7 @@ private void PublishProperties(ITypeSymbolBuilder typeBuilder, Class clazz) { for (int i = 0; i <= indexer.Length; i++) ilgen.EmitLdarg(i); + mw.EmitCall(ilgen); } else @@ -378,6 +374,7 @@ private void PublishProperties(ITypeSymbolBuilder typeBuilder, Class clazz) ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); for (int i = 0; i <= indexer.Length; i++) ilgen.EmitLdarg(i + 1); + mw.EmitCallvirt(ilgen); } @@ -489,7 +486,7 @@ protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, Class { if (fw.Name == field.Name && fw.Signature == field.Sig) { - var fb = fw.GetField() as FieldBuilder; + var fb = fw.GetField() as IFieldSymbolBuilder; if (fb != null) foreach (var attr in field.Attributes) Context.AttributeHelper.SetCustomAttribute(classLoader, fb, attr); @@ -537,7 +534,7 @@ protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, Class { if (mw.Name == "" && mw.Signature == constructor.Sig) { - var mb = mw.GetMethod() as MethodBuilder; + var mb = mw.GetMethod() as IMethodSymbolBuilder; if (mb != null) foreach (var attr in constructor.Attributes) Context.AttributeHelper.SetCustomAttribute(classLoader, mb, attr); @@ -573,7 +570,7 @@ protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, Class { var mw = ClassLoader.LoadClassByName(method.Override.Class).GetMethodWrapper(method.Override.Name, method.Sig, true); mw.Link(); - typeBuilder.DefineMethodOverride(mb, (MethodInfo)mw.GetMethod()); + typeBuilder.DefineMethodOverride(mb, (IMethodSymbol)mw.GetMethod()); } ImportClassLoader.AddDeclaredExceptions(Context, mb, method.Throws); @@ -598,7 +595,7 @@ protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, Class { if (mw.Name == method.Name && mw.Signature == method.Sig) { - MethodBuilder mb = mw.GetMethod() as MethodBuilder; + var mb = mw.GetMethod() as IMethodSymbolBuilder; if (mb != null) { foreach (IKVM.Tools.Importer.MapXml.Attribute attr in method.Attributes) @@ -611,6 +608,7 @@ protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, Class } } } + if (clazz.Interfaces != null) { foreach (var iface in clazz.Interfaces) @@ -631,7 +629,7 @@ protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, Class var mb = mw.GetDefineMethodHelper().DefineMethod(this, typeBuilder, tw.Name + "/" + m.Name, System.Reflection.MethodAttributes.Private | System.Reflection.MethodAttributes.NewSlot | System.Reflection.MethodAttributes.Virtual | System.Reflection.MethodAttributes.Final | System.Reflection.MethodAttributes.CheckAccessOnOverride); Context.AttributeHelper.HideFromJava(mb); typeBuilder.DefineMethodOverride(mb, (IMethodSymbol)mw.GetMethod()); - CodeEmitter ilgen = Context.CodeEmitterFactory.Create(mb); + var ilgen = Context.CodeEmitterFactory.Create(mb); m.Emit(classLoader, ilgen); ilgen.DoEmit(); } @@ -642,7 +640,7 @@ protected override void EmitMapXmlMetadata(ITypeSymbolBuilder typeBuilder, Class } } - protected override MethodBuilder DefineGhostMethod(ITypeSymbolBuilder typeBuilder, string name, System.Reflection.MethodAttributes attribs, RuntimeJavaMethod mw) + protected override IMethodSymbolBuilder DefineGhostMethod(ITypeSymbolBuilder typeBuilder, string name, System.Reflection.MethodAttributes attribs, RuntimeJavaMethod mw) { if (typeBuilderGhostInterface != null && mw.IsVirtual) { @@ -733,14 +731,14 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM // HACK create a scope to enable reuse of "implementers" name if (true) { - MethodBuilder mb; + IMethodSymbolBuilder mb; CodeEmitter ilgen; CodeEmitterLocal local; // add implicit conversions for all the ghost implementers var implementers = classLoader.GetGhostImplementers(this); for (int i = 0; i < implementers.Length; i++) { - mb = typeBuilder.DefineMethod("op_Implicit", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, TypeAsSignatureType, new Type[] { implementers[i].TypeAsSignatureType }); + mb = typeBuilder.DefineMethod("op_Implicit", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, TypeAsSignatureType, new[] { implementers[i].TypeAsSignatureType }); Context.AttributeHelper.HideFromJava(mb); ilgen = Context.CodeEmitterFactory.Create(mb); local = ilgen.DeclareLocal(TypeAsSignatureType); @@ -752,21 +750,23 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); } + // Implement the "IsInstance" method mb = ghostIsInstanceMethod; Context.AttributeHelper.HideFromJava(mb); ilgen = Context.CodeEmitterFactory.Create(mb); - CodeEmitterLabel end = ilgen.DefineLabel(); + var end = ilgen.DefineLabel(); for (int i = 0; i < implementers.Length; i++) { ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Isinst, implementers[i].TypeAsTBD); - CodeEmitterLabel label = ilgen.DefineLabel(); + var label = ilgen.DefineLabel(); ilgen.EmitBrfalse(label); ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.EmitBr(end); ilgen.MarkLabel(label); } + ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Isinst, typeBuilderGhostInterface); ilgen.Emit(OpCodes.Ldnull); @@ -774,6 +774,7 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM ilgen.MarkLabel(end); ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); + // Implement the "IsInstanceArray" method mb = ghostIsInstanceArrayMethod; Context.AttributeHelper.HideFromJava(mb); @@ -864,7 +865,7 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); // Add "ToObject" methods - mb = typeBuilder.DefineMethod("ToObject", MethodAttributes.HideBySig | MethodAttributes.Public, Context.Types.Object, Type.EmptyTypes); + mb = typeBuilder.DefineMethod("ToObject", MethodAttributes.HideBySig | MethodAttributes.Public, Context.Types.Object, []); Context.AttributeHelper.HideFromJava(mb); ilgen = Context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldarg_0); @@ -889,13 +890,13 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM ilgen.Emit(OpCodes.Ldarg_0); ilgen.Emit(OpCodes.Ldtoken, typeBuilder); ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Call, Context.Resolver.ResolveRuntimeType(typeof(IKVM.Runtime.GhostTag).FullName).AsReflection().GetMethod("ThrowClassCastException", BindingFlags.NonPublic | BindingFlags.Static)); + ilgen.Emit(OpCodes.Call, Context.Resolver.ResolveRuntimeType(typeof(IKVM.Runtime.GhostTag).FullName).GetMethod("ThrowClassCastException", BindingFlags.NonPublic | BindingFlags.Static)); ilgen.MarkLabel(end); ilgen.Emit(OpCodes.Ret); ilgen.DoEmit(); // Implement the "Equals" method - mb = typeBuilder.DefineMethod("Equals", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Virtual, Context.Types.Boolean, new Type[] { Context.Types.Object }); + mb = typeBuilder.DefineMethod("Equals", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Virtual, Context.Types.Boolean, [Context.Types.Object]); Context.AttributeHelper.HideFromJava(mb); ilgen = Context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldarg_0); @@ -906,7 +907,7 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM ilgen.DoEmit(); // Implement the "GetHashCode" method - mb = typeBuilder.DefineMethod("GetHashCode", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Virtual, Context.Types.Int32, Type.EmptyTypes); + mb = typeBuilder.DefineMethod("GetHashCode", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Virtual, Context.Types.Int32, []); Context.AttributeHelper.HideFromJava(mb); ilgen = Context.CodeEmitterFactory.Create(mb); ilgen.Emit(OpCodes.Ldarg_0); @@ -916,7 +917,7 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM ilgen.DoEmit(); // Implement the "op_Equality" method - mb = typeBuilder.DefineMethod("op_Equality", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, Context.Types.Boolean, new Type[] { typeBuilder, typeBuilder }); + mb = typeBuilder.DefineMethod("op_Equality", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, Context.Types.Boolean, [typeBuilder, typeBuilder]); Context.AttributeHelper.HideFromJava(mb); ilgen = Context.CodeEmitterFactory.Create(mb); ilgen.EmitLdarga(0); @@ -928,7 +929,7 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM ilgen.DoEmit(); // Implement the "op_Inequality" method - mb = typeBuilder.DefineMethod("op_Inequality", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, Context.Types.Boolean, new Type[] { typeBuilder, typeBuilder }); + mb = typeBuilder.DefineMethod("op_Inequality", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static | MethodAttributes.SpecialName, Context.Types.Boolean, [typeBuilder, typeBuilder]); Context.AttributeHelper.HideFromJava(mb); ilgen = Context.CodeEmitterFactory.Create(mb); ilgen.EmitLdarga(0); @@ -946,27 +947,27 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM protected override void FinishGhostStep2() { - typeBuilderGhostInterface?.CreateType(); + typeBuilderGhostInterface?.Complete(); } - protected override TypeBuilder DefineGhostType(string mangledTypeName, TypeAttributes typeAttribs) + protected override ITypeSymbolBuilder DefineGhostType(string mangledTypeName, TypeAttributes typeAttribs) { typeAttribs &= ~(TypeAttributes.Interface | TypeAttributes.Abstract); typeAttribs |= TypeAttributes.Class | TypeAttributes.Sealed; - TypeBuilder typeBuilder = classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(mangledTypeName, typeAttribs, Context.Types.ValueType); + var typeBuilder = classLoader.GetTypeWrapperFactory().ModuleBuilder.DefineType(mangledTypeName, typeAttribs, Context.Types.ValueType); Context.AttributeHelper.SetGhostInterface(typeBuilder); Context.AttributeHelper.SetModifiers(typeBuilder, Modifiers, IsInternal); ghostRefField = typeBuilder.DefineField("__", Context.Types.Object, FieldAttributes.Public | FieldAttributes.SpecialName); typeBuilderGhostInterface = typeBuilder.DefineNestedType("__Interface", TypeAttributes.Interface | TypeAttributes.Abstract | TypeAttributes.NestedPublic); Context.AttributeHelper.HideFromJava(typeBuilderGhostInterface); - ghostIsInstanceMethod = typeBuilder.DefineMethod("IsInstance", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, Context.Types.Boolean, new Type[] { Context.Types.Object }); + ghostIsInstanceMethod = typeBuilder.DefineMethod("IsInstance", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, Context.Types.Boolean, [Context.Types.Object]); ghostIsInstanceMethod.DefineParameter(1, ParameterAttributes.None, "obj"); - ghostIsInstanceArrayMethod = typeBuilder.DefineMethod("IsInstanceArray", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, Context.Types.Boolean, new Type[] { Context.Types.Object, Context.Types.Int32 }); + ghostIsInstanceArrayMethod = typeBuilder.DefineMethod("IsInstanceArray", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, Context.Types.Boolean, [Context.Types.Object, Context.Types.Int32]); ghostIsInstanceArrayMethod.DefineParameter(1, ParameterAttributes.None, "obj"); ghostIsInstanceArrayMethod.DefineParameter(2, ParameterAttributes.None, "rank"); - ghostCastMethod = typeBuilder.DefineMethod("Cast", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, typeBuilder, new Type[] { Context.Types.Object }); + ghostCastMethod = typeBuilder.DefineMethod("Cast", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, typeBuilder, [Context.Types.Object]); ghostCastMethod.DefineParameter(1, ParameterAttributes.None, "obj"); - ghostCastArrayMethod = typeBuilder.DefineMethod("CastArray", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, Context.Types.Void, new Type[] { Context.Types.Object, Context.Types.Int32 }); + ghostCastArrayMethod = typeBuilder.DefineMethod("CastArray", MethodAttributes.HideBySig | MethodAttributes.Public | MethodAttributes.Static, Context.Types.Void, [Context.Types.Object, Context.Types.Int32]); ghostCastArrayMethod.DefineParameter(1, ParameterAttributes.None, "obj"); ghostCastArrayMethod.DefineParameter(2, ParameterAttributes.None, "rank"); return typeBuilder; @@ -994,7 +995,7 @@ internal override void EmitCheckcast(CodeEmitter ilgen) } ilgen.EmitLdc_I4(rank); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ghostCastArrayMethod); - ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(Context.Types.Object, rank)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, rank == 1 ? Context.Types.Object.MakeArrayType() : Context.Types.Object.MakeArrayType(rank)); } else { diff --git a/src/IKVM.Tools.Importer/StaticCompiler.cs b/src/IKVM.Tools.Importer/StaticCompiler.cs index f5e3f7cb74..795568db50 100644 --- a/src/IKVM.Tools.Importer/StaticCompiler.cs +++ b/src/IKVM.Tools.Importer/StaticCompiler.cs @@ -1,25 +1,25 @@ /* - Copyright (C) 2002-2014 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - + Copyright (C) 2002-2014 Jeroen Frijters + + This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. + + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jeroen Frijters + jeroen@frijters.net + */ using System; @@ -31,6 +31,7 @@ Jeroen Frijters using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.IkvmReflection; using IKVM.Reflection; using IKVM.Reflection.Diagnostics; using IKVM.Runtime; @@ -43,24 +44,29 @@ namespace IKVM.Tools.Importer class StaticCompiler { - readonly ConcurrentDictionary runtimeTypeCache = new(); + readonly ConcurrentDictionary runtimeTypeCache = new(); readonly IDiagnosticHandler diagnostics; + readonly IkvmReflectionSymbolContext symbols; internal Universe universe; - internal Assembly runtimeAssembly; - internal Assembly baseAssembly; + internal IAssemblySymbol runtimeAssembly; + internal IAssemblySymbol baseAssembly; internal ImportState rootTarget; internal int errorCount; internal Universe Universe => universe; + internal IkvmReflectionSymbolContext Symbols => symbols; + ///

/// Initializes a new instance. /// /// - public StaticCompiler(IDiagnosticHandler diagnostics) + /// + public StaticCompiler(IDiagnosticHandler diagnostics, IkvmReflectionSymbolContext symbols) { this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); + this.symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); } /// @@ -167,17 +173,17 @@ internal Assembly Load(string assemblyString) return asm; } - internal Assembly LoadFile(string path) + internal IAssemblySymbol LoadFile(string path) { - return universe.LoadFile(path); + return symbols.GetOrCreateAssemblySymbol( universe.LoadFile(path)); } - internal Type GetRuntimeType(string name) + internal ITypeSymbol GetRuntimeType(string name) { return runtimeTypeCache.GetOrAdd(name, runtimeAssembly.GetType); } - internal Type GetTypeForMapXml(RuntimeClassLoader loader, string name) + internal ITypeSymbol GetTypeForMapXml(RuntimeClassLoader loader, string name) { return GetType(loader, name) ?? throw new FatalCompilerErrorException(DiagnosticEvent.MapFileTypeNotFound(name)); } @@ -197,7 +203,7 @@ internal RuntimeJavaField GetFieldForMapXml(RuntimeClassLoader loader, string cl return fw; } - internal Type GetType(RuntimeClassLoader loader, string name) + internal ITypeSymbol GetType(RuntimeClassLoader loader, string name) { var ccl = (ImportClassLoader)loader; return ccl.GetTypeFromReferencedAssembly(name); @@ -205,14 +211,15 @@ internal Type GetType(RuntimeClassLoader loader, string name) internal static void LinkageError(string msg, RuntimeJavaType actualType, RuntimeJavaType expectedType, params object[] values) { - var args = new object[values.Length + 2]; + object[] args = new object[values.Length + 2]; values.CopyTo(args, 2); args[0] = AssemblyQualifiedName(actualType); args[1] = AssemblyQualifiedName(expectedType); - - var str = string.Format(msg, args); + string str = string.Format(msg, args); if (actualType is RuntimeUnloadableJavaType && (expectedType is RuntimeManagedByteCodeJavaType || expectedType is RuntimeManagedJavaType)) - str += string.Format("\n\t(Please add a reference to {0})", expectedType.TypeAsBaseType.Assembly.AsReflection().Location); + { + str += string.Format("\n\t(Please add a reference to {0})", expectedType.TypeAsBaseType.Assembly.Location); + } throw new FatalCompilerErrorException(DiagnosticEvent.LinkageError(str)); } @@ -247,4 +254,4 @@ internal void SuppressWarning(ImportState options, Diagnostic diagnostic, string } -} +} \ No newline at end of file From 2f8e098f878d053ff62bed094755d30f12c0f299 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Thu, 26 Sep 2024 13:41:11 -0500 Subject: [PATCH 13/59] Almost. --- src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs | 11 + src/IKVM.CoreLib/Diagnostics/Diagnostic.json | 15 + .../Diagnostics/DiagnosticEvent.g.cs | 8 + .../Diagnostics/DiagnosticEventHandler.g.cs | 12 + .../Diagnostics/IDiagnosticHandler.g.cs | 8 + .../Diagnostics/NullDiagnosticHandler.g.cs | 11 + .../Tracing/DiagnosticEventSource.g.cs | 10 + .../Tracing/DiagnosticEventSource.g.tt | 2 + .../Reflection/ReflectionExtensions.cs | 14 + .../Symbols/AssemblyNameFormatter.cs | 146 ++ src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs | 159 ++ .../Symbols/Emit/IConstructorSymbolBuilder.cs | 43 +- .../Symbols/Emit/IMethodBaseSymbolBuilder.cs | 43 +- .../Symbols/Emit/IMethodSymbolBuilder.cs | 41 - .../Symbols/Emit/IModuleSymbolBuilder.cs | 6 +- src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs | 17 +- src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 4 +- src/IKVM.CoreLib/Symbols/ISymbolResolver.cs | 20 +- .../IIkvmReflectionMemberSymbolBuilder.cs | 1 + .../IIkvmReflectionModuleSymbolBuilder.cs | 3 +- .../IIkvmReflectionPropertySymbolBuilder.cs | 7 + .../Emit/IIkvmReflectionSymbolBuilder.cs | 8 - .../IkvmReflectionAssemblySymbolBuilder.cs | 10 +- .../IkvmReflectionConstructorSymbolBuilder.cs | 18 +- .../Emit/IkvmReflectionEventSymbolBuilder.cs | 1 - .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 1 - ...ectionGenericTypeParameterSymbolBuilder.cs | 2 +- .../Emit/IkvmReflectionILGenerator.cs | 1 + .../Emit/IkvmReflectionMemberSymbolBuilder.cs | 21 +- .../IkvmReflectionMethodBaseSymbolBuilder.cs | 29 +- .../Emit/IkvmReflectionMethodSymbolBuilder.cs | 65 +- .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 26 +- .../IkvmReflectionParameterBuilderInfo.cs | 10 +- .../IkvmReflectionParameterSymbolBuilder.cs | 20 +- .../IkvmReflectionPropertySymbolBuilder.cs | 16 +- .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 31 +- .../IIkvmReflectionMethodSymbol.cs | 7 + .../IkvmReflectionAssemblySymbol.cs | 10 +- ...IkvmReflectionGenericTypeParameterTable.cs | 6 +- .../IkvmReflectionMemberSymbol.cs | 46 +- .../IkvmReflectionMethodSpecTable.cs | 6 +- .../IkvmReflectionMethodSymbol.cs | 9 + .../IkvmReflectionMethodTable.cs | 10 +- .../IkvmReflectionParameterTable.cs | 9 +- .../IkvmReflection/IkvmReflectionSymbol.cs | 34 +- .../IkvmReflectionSymbolContext.cs | 55 +- .../IkvmReflectionTypeSymbol.cs | 12 +- .../IkvmReflection/IkvmReflectionUtil.cs | 45 +- .../Emit/ReflectionAssemblySymbolBuilder.cs | 20 +- .../ReflectionConstructorSymbolBuilder.cs | 18 +- .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 22 + .../Emit/ReflectionMethodSymbolBuilder.cs | 56 +- .../Emit/ReflectionModuleSymbolBuilder.cs | 12 +- .../Reflection/ReflectionAssemblySymbol.cs | 20 +- .../Reflection/ReflectionSymbolContext.cs | 8 +- .../Symbols/Reflection/ReflectionUtil.cs | 44 + src/IKVM.CoreLib/Text/HexConverter.cs | 443 ++++++ src/IKVM.CoreLib/Text/ValueStringBuilder.cs | 339 ++++ src/IKVM.Reflection/Universe.cs | 2 +- src/IKVM.Runtime/Annotation.cs | 8 +- src/IKVM.Runtime/AttributeHelper.cs | 168 +- .../CustomAssemblyClassLoaderAttribute.cs | 4 - src/IKVM.Runtime/ByteCodeHelper.cs | 33 +- src/IKVM.Runtime/CodeEmitter.cs | 23 +- src/IKVM.Runtime/DefineMethodHelper.cs | 37 +- src/IKVM.Runtime/DynamicClassLoader.cs | 26 +- src/IKVM.Runtime/DynamicMethodUtil.cs | 2 +- src/IKVM.Runtime/ExceptionHelper.cs | 4 +- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 44 +- src/IKVM.Runtime/JVM.Resolver.cs | 2 +- .../Java/Externs/ikvm/runtime/Util.cs | 8 +- .../Java/Externs/java/lang/Class.cs | 2 +- src/IKVM.Runtime/ReflectUtil.cs | 27 +- .../RuntimeAssemblyClassLoader.cs | 14 +- .../RuntimeAssemblyClassLoaderFactory.cs | 5 +- .../RuntimeByteCodeJavaType.FinishContext.cs | 49 +- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 6 +- src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 7 +- src/IKVM.Runtime/RuntimeClassLoaderFactory.cs | 10 +- src/IKVM.Runtime/RuntimeContext.cs | 17 +- src/IKVM.Runtime/RuntimeContextOptions.cs | 10 +- src/IKVM.Runtime/RuntimeJavaType.cs | 2 +- ...anagedByteCodeJavaType.RemappedJavaType.cs | 2 +- .../RuntimeManagedByteCodeJavaType.cs | 10 +- ...tionJavaType.MultipleAnnotationJavaType.cs | 2 +- ...nJavaType.ReturnValueAnnotationJavaType.cs | 4 +- ...gedJavaType.AttributeAnnotationJavaType.cs | 6 +- ...agedJavaType.DelegateInnerClassJavaType.cs | 2 +- ...RuntimeManagedJavaType.EnumEnumJavaType.cs | 2 +- src/IKVM.Runtime/RuntimeManagedJavaType.cs | 2 +- src/IKVM.Runtime/StubGen/StubGenerator.cs | 2 +- src/IKVM.Runtime/atomic.cs | 2 +- .../AssemblyResolver.cs | 8 +- src/IKVM.Tools.Exporter/ExportImpl.cs | 9 +- .../IKVM.Tools.Exporter.csproj | 4 - .../ManagedTypeResolver.cs | 98 +- src/IKVM.Tools.Exporter/StaticCompiler.cs | 1 - .../ExecutionContext.NetFramework.cs | 2 +- src/IKVM.Tools.Importer/FakeTypes.cs | 4 - .../ImportAssemblyResolver.cs | 359 +++++ src/IKVM.Tools.Importer/ImportClassLoader.cs | 295 ++-- src/IKVM.Tools.Importer/ImportContext.cs | 1391 ++--------------- .../ImportContextFactory.cs | 1096 +++++++++++++ .../ImportRuntimeSymbolResolver.cs | 149 +- src/IKVM.Tools.Importer/ImportState.cs | 198 --- src/IKVM.Tools.Importer/ImportTool.cs | 159 +- src/IKVM.Tools.Importer/MapXml/Call.cs | 13 +- .../RuntimeImportByteCodeJavaType.cs | 4 +- src/IKVM.Tools.Importer/StaticCompiler.cs | 120 +- 109 files changed, 3977 insertions(+), 2548 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs create mode 100644 src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs create mode 100644 src/IKVM.CoreLib/Text/HexConverter.cs create mode 100644 src/IKVM.CoreLib/Text/ValueStringBuilder.cs rename src/{IKVM.Tools.Importer => IKVM.Tools.Exporter}/AssemblyResolver.cs (98%) create mode 100644 src/IKVM.Tools.Importer/ImportAssemblyResolver.cs create mode 100644 src/IKVM.Tools.Importer/ImportContextFactory.cs delete mode 100644 src/IKVM.Tools.Importer/ImportState.cs diff --git a/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs b/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs index 9f7f9e73d2..36c9374bf6 100644 --- a/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs @@ -285,6 +285,8 @@ partial record class Diagnostic return ModuleInitializerMethodRequirements; case 5060: return InvalidZip; + case 5061: + return CoreAssemblyVersionMismatch; case 6000: return GenericRuntimeTrace; case 6001: @@ -1396,6 +1398,15 @@ partial record class Diagnostic /// public static readonly Diagnostic InvalidZip = new Diagnostic(5060, nameof(InvalidZip), "Invalid zip: {0}.", DiagnosticLevel.Fatal); + /// + /// The 'CoreAssemblyVersionMismatch' diagnostic. + /// + /// +/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. + /// + public static readonly Diagnostic CoreAssemblyVersionMismatch = new Diagnostic(5061, nameof(CoreAssemblyVersionMismatch), "Unable to load assembly \'{-1}\' as it depends on a higher version of {-1} than the" + + " one currently loaded.", DiagnosticLevel.Fatal); + /// /// The 'GenericRuntimeTrace' diagnostic. /// diff --git a/src/IKVM.CoreLib/Diagnostics/Diagnostic.json b/src/IKVM.CoreLib/Diagnostics/Diagnostic.json index 3979a699a0..833477aefe 100644 --- a/src/IKVM.CoreLib/Diagnostics/Diagnostic.json +++ b/src/IKVM.CoreLib/Diagnostics/Diagnostic.json @@ -1631,6 +1631,21 @@ } ] }, + "CoreAssemblyVersionMismatch": { + "id": 5061, + "level": "Fatal", + "message": "Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded.", + "args": [ + { + "name": "arg0", + "type": "string" + }, + { + "name": "arg1", + "type": "string" + } + ] + }, "GenericRuntimeTrace": { "id": 6000, "level": "Trace", diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs index 1b84ae7019..3dde983f23 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs @@ -1096,6 +1096,14 @@ readonly partial struct DiagnosticEvent /// public static DiagnosticEvent InvalidZip(string name, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidZip.Event([name], exception, location); + /// + /// The 'CoreAssemblyVersionMismatch' diagnostic. + /// + /// +/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. + /// + public static DiagnosticEvent CoreAssemblyVersionMismatch(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.CoreAssemblyVersionMismatch.Event([arg0, arg1], exception, location); + /// /// The 'GenericRuntimeTrace' diagnostic. /// diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs index 3e9ecb9d1a..53fc27600f 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs @@ -1638,6 +1638,18 @@ public void InvalidZip(string name) Report(Diagnostic.InvalidZip.Event([name])); } + /// + /// The 'CoreAssemblyVersionMismatch' diagnostic. + /// + /// +/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. + /// + public void CoreAssemblyVersionMismatch(string arg0, string arg1) + { + if (IsEnabled(Diagnostic.CoreAssemblyVersionMismatch)) + Report(Diagnostic.CoreAssemblyVersionMismatch.Event([arg0, arg1])); + } + /// /// The 'GenericRuntimeTrace' diagnostic. /// diff --git a/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs b/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs index bfa84e1165..1bac0acbc8 100644 --- a/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs @@ -1094,6 +1094,14 @@ partial interface IDiagnosticHandler /// void InvalidZip(string name); + /// + /// The 'CoreAssemblyVersionMismatch' diagnostic. + /// + /// +/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. + /// + void CoreAssemblyVersionMismatch(string arg0, string arg1); + /// /// The 'GenericRuntimeTrace' diagnostic. /// diff --git a/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs b/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs index 8a20d769a1..1283a95575 100644 --- a/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs @@ -1502,6 +1502,17 @@ public void InvalidZip(string name) } + /// + /// The 'CoreAssemblyVersionMismatch' diagnostic. + /// + /// +/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. + /// + public void CoreAssemblyVersionMismatch(string arg0, string arg1) + { + + } + /// /// The 'GenericRuntimeTrace' diagnostic. /// diff --git a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs index f6559bc13d..8d447587b1 100644 --- a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs @@ -1244,6 +1244,16 @@ partial class DiagnosticEventSource [Event(5060, Message = "Invalid zip: {0}.", Level = EventLevel.Critical)] public void InvalidZip(string name) => WriteEvent(5060, name); + /// + /// The 'CoreAssemblyVersionMismatch' diagnostic. + /// + /// +/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. + /// + [Event(5061, Message = "Unable to load assembly \'{-1}\' as it depends on a higher version of {-1} than the" + + " one currently loaded.", Level = EventLevel.Critical)] + public void CoreAssemblyVersionMismatch(string arg0, string arg1) => WriteEvent(5061, arg0, arg1); + /// /// The 'GenericRuntimeTrace' diagnostic. /// diff --git a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt index 8bf9d174f4..3e266cf33e 100644 --- a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt +++ b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt @@ -38,6 +38,8 @@ foreach (var kvp in DiagnosticFile.Read(Host.ResolvePath(Path.Combine("..", "Dia var level = kvp.Value.Level; if (level == "Fatal") level = "Critical"; + if (level == "Info") + level = "Informational"; if (level == "Trace") level = "Verbose"; diff --git a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs index 0defa18ab2..7ce0795da3 100644 --- a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs +++ b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs @@ -576,6 +576,20 @@ public static MethodBuilder GetMethodBuilder(this ParameterBuilder parameter) return _getParameterMethodBuilderFunc(parameter); } + /// + /// Returns true if the is a SZArray. + /// + /// + /// + public static bool IsSZArray(this Type type) + { +#if NET + return type.IsSZArray; +#else + return type.IsArray && type.Name.EndsWith("[]"); +#endif + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs b/src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs new file mode 100644 index 0000000000..08c41a9c6d --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs @@ -0,0 +1,146 @@ +using System; +using System.Diagnostics; +using System.Reflection; + +using IKVM.CoreLib.Text; + +namespace IKVM.CoreLib.Symbols +{ + + internal static class AssemblyNameFormatter + { + + public static string ComputeDisplayName(string name, Version? version, string? cultureName, byte[]? pkt, AssemblyNameFlags flags = 0, AssemblyContentType contentType = 0, byte[]? pk = null) + { + const int PUBLIC_KEY_TOKEN_LEN = 8; + Debug.Assert(name.Length != 0); + + var vsb = new ValueStringBuilder(stackalloc char[256]); + vsb.AppendQuoted(name); + + if (version != null) + { + ushort major = (ushort)version.Major; + if (major != ushort.MaxValue) + { + vsb.Append(", Version="); + vsb.AppendSpanFormattable(major); + + ushort minor = (ushort)version.Minor; + if (minor != ushort.MaxValue) + { + vsb.Append('.'); + vsb.AppendSpanFormattable(minor); + + ushort build = (ushort)version.Build; + if (build != ushort.MaxValue) + { + vsb.Append('.'); + vsb.AppendSpanFormattable(build); + + ushort revision = (ushort)version.Revision; + if (revision != ushort.MaxValue) + { + vsb.Append('.'); + vsb.AppendSpanFormattable(revision); + } + } + } + } + } + + if (cultureName != null) + { + if (cultureName.Length == 0) + cultureName = "neutral"; + vsb.Append(", Culture="); + vsb.AppendQuoted(cultureName); + } + + byte[]? keyOrToken = pkt ?? pk; + if (keyOrToken != null) + { + if (pkt != null) + { + if (pkt.Length > PUBLIC_KEY_TOKEN_LEN) + throw new ArgumentException(); + + vsb.Append(", PublicKeyToken="); + } + else + { + vsb.Append(", PublicKey="); + } + + if (keyOrToken.Length == 0) + { + vsb.Append("null"); + } + else + { + HexConverter.EncodeToUtf16(keyOrToken, vsb.AppendSpan(keyOrToken.Length * 2), HexConverter.Casing.Lower); + } + } + + if (0 != (flags & AssemblyNameFlags.Retargetable)) + vsb.Append(", Retargetable=Yes"); + + if (contentType == AssemblyContentType.WindowsRuntime) + vsb.Append(", ContentType=WindowsRuntime"); + + // NOTE: By design (desktop compat) AssemblyName.FullName and ToString() do not include ProcessorArchitecture. + + return vsb.ToString(); + } + + private static void AppendQuoted(this ref ValueStringBuilder vsb, string s) + { + bool needsQuoting = false; + const char quoteChar = '\"'; + + // App-compat: You can use double or single quotes to quote a name, and Fusion (or rather the IdentityAuthority) picks one + // by some algorithm. Rather than guess at it, we use double quotes consistently. + ReadOnlySpan span = s.AsSpan(); + if (s.Length != span.Trim().Length || span.IndexOfAny('\"', '\'') >= 0) + needsQuoting = true; + + if (needsQuoting) + vsb.Append(quoteChar); + + for (int i = 0; i < s.Length; i++) + { + switch (s[i]) + { + case '\\': + case ',': + case '=': + case '\'': + case '"': + vsb.Append('\\'); + break; + case '\t': + vsb.Append("\\t"); + continue; + case '\r': + vsb.Append("\\r"); + continue; + case '\n': + vsb.Append("\\n"); + continue; + } + + vsb.Append(s[i]); + } + + if (needsQuoting) + vsb.Append(quoteChar); + } + + private static void AppendSpanFormattable(this ref ValueStringBuilder vsb, ushort value) + { + vsb.Append(value.ToString()); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs b/src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs new file mode 100644 index 0000000000..b92ecd28f3 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs @@ -0,0 +1,159 @@ +using System; +using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; +using System.Linq; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class AssemblyNameInfo + { + + readonly AssemblyNameFlags _flags; + string? _fullName; + + /// + /// Initializes a new instance of the AssemblyNameInfo class. + /// + /// The simple name of the assembly. + /// The version of the assembly. + /// The name of the culture associated with the assembly. + /// The attributes of the assembly. + /// The public key or its token. Set to when it's public key. + /// is null. + public AssemblyNameInfo(string name, Version? version = null, string? cultureName = null, AssemblyNameFlags flags = AssemblyNameFlags.None, ImmutableArray publicKeyOrToken = default) + { + Name = name ?? throw new ArgumentNullException(nameof(name)); + Version = version; + CultureName = cultureName; + _flags = flags; + PublicKeyOrToken = publicKeyOrToken; + } + + /// + /// Gets the simple name of the assembly. + /// + public string Name { get; } + + /// + /// Gets the version of the assembly. + /// + public Version? Version { get; } + + /// + /// Gets the name of the culture associated with the assembly. + /// + /// + /// Do not create a instance from this string unless + /// you know the string has originated from a trustworthy source. + /// + public string? CultureName { get; } + + /// + /// Gets the attributes of the assembly. + /// + public AssemblyNameFlags Flags => _flags; + + /// + /// Gets the public key or the public key token of the assembly. + /// + /// Check for flag to see whether it's public key or its token. +#if SYSTEM_PRIVATE_CORELIB + public byte[]? PublicKeyOrToken { get; } +#else + public ImmutableArray PublicKeyOrToken { get; } +#endif + + + /// + /// Gets the full name of the assembly, also known as the display name. + /// + /// In contrary to it does not validate public key token neither computes it based on the provided public key. + public string FullName + { + get + { + if (_fullName is null) + { + bool isPublicKey = (Flags & AssemblyNameFlags.PublicKey) != 0; + + byte[]? publicKeyOrToken = +#if SYSTEM_PRIVATE_CORELIB + PublicKeyOrToken; +#elif NET8_0_OR_GREATER + !PublicKeyOrToken.IsDefault ? System.Runtime.InteropServices.ImmutableCollectionsMarshal.AsArray(PublicKeyOrToken) : null; +#else + !PublicKeyOrToken.IsDefault ? PublicKeyOrToken.ToArray() : null; +#endif + _fullName = AssemblyNameFormatter.ComputeDisplayName(Name, Version, CultureName, + pkt: isPublicKey ? null : publicKeyOrToken, + ExtractAssemblyNameFlags(_flags), ExtractAssemblyContentType(_flags), + pk: isPublicKey ? publicKeyOrToken : null); + } + + return _fullName; + } + } + + /// + /// Initializes a new instance of the class based on the stored information. + /// + /// + /// Do not create an instance with string unless + /// you know the string has originated from a trustworthy source. + /// + public AssemblyName ToAssemblyName() + { + AssemblyName assemblyName = new(); + assemblyName.Name = Name; + assemblyName.CultureName = CultureName; + assemblyName.Version = Version; + assemblyName.Flags = Flags; + assemblyName.ContentType = ExtractAssemblyContentType(_flags); +#pragma warning disable SYSLIB0037 // Type or member is obsolete + assemblyName.ProcessorArchitecture = ExtractProcessorArchitecture(_flags); +#pragma warning restore SYSLIB0037 // Type or member is obsolete + +#if SYSTEM_PRIVATE_CORELIB + if (PublicKeyOrToken is not null) + { + if ((Flags & AssemblyNameFlags.PublicKey) != 0) + { + assemblyName.SetPublicKey(PublicKeyOrToken); + } + else + { + assemblyName.SetPublicKeyToken(PublicKeyOrToken); + } + } +#else + if (!PublicKeyOrToken.IsDefault) + { + // A copy of the array needs to be created, as AssemblyName allows for the mutation of provided array. + if ((Flags & AssemblyNameFlags.PublicKey) != 0) + { + assemblyName.SetPublicKey(PublicKeyOrToken.ToArray()); + } + else + { + assemblyName.SetPublicKeyToken(PublicKeyOrToken.ToArray()); + } + } +#endif + + return assemblyName; + } + + internal static AssemblyNameFlags ExtractAssemblyNameFlags(AssemblyNameFlags combinedFlags) + => combinedFlags & unchecked((AssemblyNameFlags)0xFFFFF10F); + + internal static AssemblyContentType ExtractAssemblyContentType(AssemblyNameFlags flags) + => (AssemblyContentType)((((int)flags) >> 9) & 0x7); + + internal static ProcessorArchitecture ExtractProcessorArchitecture(AssemblyNameFlags flags) + => (ProcessorArchitecture)((((int)flags) >> 4) & 0x7); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs index e3ca768853..a099d7d060 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs @@ -1,51 +1,10 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Emit +namespace IKVM.CoreLib.Symbols.Emit { interface IConstructorSymbolBuilder : ISymbolBuilder, IMethodBaseSymbolBuilder, IConstructorSymbol { - /// - /// Sets the method implementation flags for this constructor. - /// - /// - void SetImplementationFlags(MethodImplAttributes attributes); - - /// - /// Defines a parameter of this constructor. - /// - /// - /// - /// - /// - IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName); - - /// - /// Gets an ILGenerator object, with the specified MSIL stream size, that can be used to build a method body for this constructor. - /// - /// - /// - IILGenerator GetILGenerator(int streamSize); - - /// - /// Gets an ILGenerator for this constructor. - /// - /// - IILGenerator GetILGenerator(); - - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs index 894c8e9b12..c3173daf10 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs @@ -1,10 +1,51 @@ -namespace IKVM.CoreLib.Symbols.Emit +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit { interface IMethodBaseSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IMethodBaseSymbol { + /// + /// Sets the implementation flags for this method. + /// + /// + void SetImplementationFlags(MethodImplAttributes attributes); + + /// + /// Defines a parameter of this method. + /// + /// + /// + /// + /// + IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName); + + /// + /// Gets an ILGenerator object, with the specified MSIL stream size, that can be used to build a method body for this method. + /// + /// + /// + IILGenerator GetILGenerator(int streamSize); + + /// + /// Gets an ILGenerator for this method. + /// + /// + IILGenerator GetILGenerator(); + + /// + /// Set a custom attribute using a custom attribute builder. + /// + /// + void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + /// + /// Sets a custom attribute using a specified custom attribute blob. + /// + /// + /// + void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs index 8220de2960..8ae9770eb6 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs @@ -4,12 +4,6 @@ interface IMethodSymbolBuilder : ISymbolBuilder, IMethodBaseSymbolBuilder, IMethodSymbol { - /// - /// Sets the implementation flags for this method. - /// - /// - void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes); - /// /// Sets the number and types of parameters for a method. /// @@ -40,41 +34,6 @@ interface IMethodSymbolBuilder : ISymbolBuilder, IMethodBaseSymbo /// IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names); - /// - /// Sets the parameter attributes and the name of a parameter of this method, or of the return value of this method. Returns a ParameterBuilder that can be used to apply custom attributes. - /// - /// - /// - /// - /// - IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName); - - /// - /// Returns an ILGenerator for this method with a default Microsoft intermediate language (MSIL) stream size of 64 bytes. - /// - /// - IILGenerator GetILGenerator(); - - /// - /// Returns an ILGenerator for this method with the specified Microsoft intermediate language (MSIL) stream size. - /// - /// - /// - IILGenerator GetILGenerator(int size); - - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index 79737a1767..f030d9e2ed 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -71,7 +71,7 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] parameterTypes); + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); /// /// Defines a global method with the specified name, attributes, calling convention, return type, custom modifiers for the return type, parameter types, and custom modifiers for the parameter types. @@ -86,7 +86,7 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] requiredReturnTypeCustomModifiers, ITypeSymbol[] optionalReturnTypeCustomModifiers, ITypeSymbol[] parameterTypes, ITypeSymbol[][] requiredParameterTypeCustomModifiers, ITypeSymbol[][] optionalParameterTypeCustomModifiers); + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? requiredReturnTypeCustomModifiers, ITypeSymbol[]? optionalReturnTypeCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredParameterTypeCustomModifiers, ITypeSymbol[][]? optionalParameterTypeCustomModifiers); /// /// Defines a global method with the specified name, attributes, return type, and parameter types. @@ -96,7 +96,7 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol returnType, ITypeSymbol[] parameterTypes); + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); /// /// Constructs a TypeBuilder for a private type with the specified name in this module. diff --git a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs index 4e14036aba..17fecec182 100644 --- a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs @@ -1,8 +1,5 @@ using System.Collections.Generic; using System.IO; -using System.Reflection; - -using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols { @@ -68,11 +65,17 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider IModuleSymbol[] GetModules(bool getResourceModules); - AssemblyName GetName(); - - AssemblyName GetName(bool copiedName); + /// + /// Gets an for this assembly. + /// + /// + AssemblyNameInfo GetName(); - AssemblyName[] GetReferencedAssemblies(); + /// + /// Gets the objects for all the assemblies referenced by this assembly. + /// + /// + AssemblyNameInfo[] GetReferencedAssemblies(); ITypeSymbol? GetType(string name, bool throwOnError); diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index 47a832f043..37440c21b5 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -14,14 +14,14 @@ interface ISymbolContext /// /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyName name); + IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name); /// /// Defines a dynamic assembly that has the specified name and access rights. /// /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyName name, ICustomAttributeBuilder[]? assemblyAttributes); + IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttributeBuilder[]? assemblyAttributes); /// /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. diff --git a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs index 2976d5bbb9..fab9546036 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs @@ -2,17 +2,23 @@ { /// - /// Provides an interface to resolve a managed type symbols. + /// Provides an interface to resolve managed type symbols. /// interface ISymbolResolver { /// - /// Resolves the named type from the IKVM runtime assembly. + /// Gets the known core assembly. + /// + /// + IAssemblySymbol ResolveCoreAssembly(); + + /// + /// Resolves the named type from the core assembly. /// /// /// - ITypeSymbol? ResolveRuntimeType(string typeName); + ITypeSymbol ResolveCoreType(string typeName); /// /// Resolves the named assembly from any reference source. @@ -26,13 +32,7 @@ interface ISymbolResolver /// /// /// - ITypeSymbol? ResolveCoreType(string typeName); - - /// - /// Resolves the known Java base assembly. - /// - /// - IAssemblySymbol? ResolveBaseAssembly(); + ITypeSymbol? ResolveType(string typeName); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs index 7e936c5290..3008c8e063 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs @@ -1,4 +1,5 @@ using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs index fc5f3eb9db..a572d60bba 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs @@ -57,9 +57,10 @@ interface IIkvmReflectionModuleSymbolBuilder : IIkvmReflectionSymbolBuilder, IMo /// /// Gets or creates a for the specified . /// + /// /// /// - IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IIkvmReflectionMemberSymbolBuilder member, ParameterBuilder parameter); /// /// Gets or creates a for the specified . diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs index 723fc6ca04..a4fc28e00f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs @@ -13,6 +13,13 @@ interface IIkvmReflectionPropertySymbolBuilder : IIkvmReflectionSymbolBuilder, I /// PropertyBuilder UnderlyingPropertyBuilder { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs index c19769466f..9d57604e49 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs @@ -73,14 +73,6 @@ interface IIkvmReflectionSymbolBuilder : ISymbolBuilder [return: NotNullIfNotNull(nameof(@event))] IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - [return: NotNullIfNotNull(nameof(parameter))] - IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(ParameterBuilder parameter); - /// /// Resolves the symbol for the specified generic type parameter. /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs index bafa374cf0..73594ea8c1 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -190,19 +190,13 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public System.Reflection.AssemblyName GetName() + public AssemblyNameInfo GetName() { return UnderlyingAssembly.GetName().Pack(); } /// - public System.Reflection.AssemblyName GetName(bool copiedName) - { - return UnderlyingAssembly.GetName(copiedName).Pack(); - } - - /// - public System.Reflection.AssemblyName[] GetReferencedAssemblies() + public AssemblyNameInfo[] GetReferencedAssemblies() { return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs index 66e1ef64d2..8c776fbff4 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs @@ -42,37 +42,40 @@ public IkvmReflectionConstructorSymbolBuilder(IkvmReflectionSymbolContext contex #region IConstructorSymbolBuilder /// - public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + public override void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) { UnderlyingConstructorBuilder.SetImplementationFlags((MethodImplAttributes)attributes); } /// - public IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection.ParameterAttributes attributes, string? strParamName) + public override IParameterSymbolBuilder DefineParameter(int iSequence, System.Reflection.ParameterAttributes attributes, string? strParamName) { - return ResolveParameterSymbol(UnderlyingConstructorBuilder.DefineParameter(iSequence, (ParameterAttributes)attributes, strParamName)); + if (iSequence <= 0) + throw new ArgumentOutOfRangeException(nameof(iSequence)); + + return ResolveParameterSymbol(this, UnderlyingConstructorBuilder.DefineParameter(iSequence, (ParameterAttributes)attributes, strParamName)); } /// - public IILGenerator GetILGenerator() + public override IILGenerator GetILGenerator() { return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator()); } /// - public IILGenerator GetILGenerator(int streamSize) + public override IILGenerator GetILGenerator(int streamSize) { return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator(streamSize)); } /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { UnderlyingConstructorBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { UnderlyingConstructorBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } @@ -89,7 +92,6 @@ public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) /// public override void OnComplete() { - _ctor = (ConstructorInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs index b7c2ca9c35..4f388a3b2c 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs @@ -153,7 +153,6 @@ public IMethodSymbol[] GetOtherMethods(bool nonPublic) /// public override void OnComplete() { - _event = (EventInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs index 342d6bce41..8472497807 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs @@ -135,7 +135,6 @@ public ITypeSymbol[] GetRequiredCustomModifiers() /// public override void OnComplete() { - _field = ResolvingModule.UnderlyingModule.ResolveField(MetadataToken) ?? throw new InvalidOperationException(); _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs index 12c2606df5..5e318922e5 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -699,7 +699,7 @@ public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) /// public override void OnComplete() { - throw new NotImplementedException(); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs index f83e7c3904..dcfdb68ad0 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs @@ -490,6 +490,7 @@ OpCode Convert(System.Reflection.Emit.OpCode opcode) 0xfe1a => OpCodes.Rethrow, 0xfe1c => OpCodes.Sizeof, 0xfe1d => OpCodes.Refanytype, + 0xfe13 => OpCodes.Volatile, _ => throw new NotImplementedException(), }; } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs index 58ac56a0fd..456507620d 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs @@ -145,15 +145,28 @@ public override IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilde /// [return: NotNullIfNotNull(nameof(parameter))] - public override IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + public override IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(IIkvmReflectionMethodBaseSymbolBuilder method, ParameterBuilder parameter) { if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + return null; if (parameter.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); + return _resolvingModule.GetOrCreateParameterSymbol(method, parameter); - return base.ResolveParameterSymbol(parameter); + return base.ResolveParameterSymbol(method, parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(IIkvmReflectionPropertySymbolBuilder property, ParameterBuilder parameter) + { + if (parameter is null) + return null; + + if (parameter.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(property, parameter); + + return base.ResolveParameterSymbol(property, parameter); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs index 573c98183f..60499625ab 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs @@ -1,4 +1,5 @@ -using IKVM.Reflection; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.Reflection; using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit @@ -27,20 +28,38 @@ public IkvmReflectionMethodBaseSymbolBuilder(IkvmReflectionSymbolContext context /// public override MemberInfo UnderlyingMember => UnderlyingMethodBase; - #region IIkvmReflectionMethodBaseSymbolBuilder + #region IIkvmReflectionMethodBaseSymbol /// - public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { return _parameterTable.GetOrCreateParameterSymbol(parameter); } #endregion - #region IIkvmReflectionMethodBaseSymbol + #region IMethodBaseSymbolBuilder /// - public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + public abstract void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes); + + /// + public abstract IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName); + + /// + public abstract IILGenerator GetILGenerator(); + + /// + public abstract IILGenerator GetILGenerator(int streamSize); + + /// + public abstract void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + /// + public abstract void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) { return _parameterTable.GetOrCreateParameterSymbol(parameter); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs index 23b82a6387..2b5270b6d4 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs @@ -16,6 +16,7 @@ class IkvmReflectionMethodSymbolBuilder : IkvmReflectionMethodBaseSymbolBuilder, MethodInfo _method; IkvmReflectionGenericTypeParameterTable _genericTypeParameterTable; + IkvmReflectionMethodSpecTable _specTable; IkvmReflectionILGenerator? _il; @@ -33,6 +34,7 @@ public IkvmReflectionMethodSymbolBuilder(IkvmReflectionSymbolContext context, II _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _method = _builder; _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, resolvingModule, this); + _specTable = new IkvmReflectionMethodSpecTable(context, resolvingModule, resolvingType, this); } /// @@ -62,6 +64,12 @@ public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type gene return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); } + /// + public IIkvmReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) + { + return _specTable.GetOrCreateGenericMethodSymbol(method.GetGenericArguments()); + } + #endregion #region IIkvmReflectionMethodBaseSymbol @@ -72,70 +80,74 @@ public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type gene #endregion - #region IMethodSymbolBuilder + #region IMethodBaseSymbolBuilder /// - public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + public override void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) { UnderlyingMethodBuilder.SetImplementationFlags((MethodImplAttributes)attributes); } /// - public void SetParameters(params ITypeSymbol[] parameterTypes) + public override IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) { - UnderlyingMethodBuilder.SetParameters(parameterTypes.Unpack()); + return ResolveParameterSymbol(this, UnderlyingMethodBuilder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); } /// - public void SetReturnType(ITypeSymbol? returnType) + public override IILGenerator GetILGenerator() { - UnderlyingMethodBuilder.SetReturnType(returnType?.Unpack()); + return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator()); } /// - public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + public override IILGenerator GetILGenerator(int streamSize) { - UnderlyingMethodBuilder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); + return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); } - public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) + /// + public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - var l = UnderlyingMethodBuilder.DefineGenericParameters(names); - var a = new IGenericTypeParameterSymbolBuilder[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = ResolveGenericTypeParameterSymbol(l[i]); - - return a; + UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// - public IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) + public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - return ResolveParameterSymbol(UnderlyingMethodBuilder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); + UnderlyingMethodBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } + #endregion + + #region IMethodSymbolBuilder + /// - public IILGenerator GetILGenerator() + public void SetParameters(params ITypeSymbol[] parameterTypes) { - return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator()); + UnderlyingMethodBuilder.SetParameters(parameterTypes.Unpack()); } /// - public IILGenerator GetILGenerator(int streamSize) + public void SetReturnType(ITypeSymbol? returnType) { - return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); + UnderlyingMethodBuilder.SetReturnType(returnType?.Unpack()); } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingMethodBuilder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); } - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) { - UnderlyingMethodBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + var l = UnderlyingMethodBuilder.DefineGenericParameters(names); + var a = new IGenericTypeParameterSymbolBuilder[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = ResolveGenericTypeParameterSymbol(l[i]); + + return a; } #endregion @@ -177,7 +189,6 @@ public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) /// public override void OnComplete() { - _method = (MethodInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs index 1ac802ff40..752ef4f3ec 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -23,7 +23,6 @@ class IkvmReflectionModuleSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmRefl IkvmReflectionMethodTable _methodTable; IkvmReflectionFieldTable _fieldTable; - /// /// Initializes a new instance. /// @@ -68,6 +67,10 @@ public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) return ResolveTypeSymbol(type.GetElementType()).GetOrCreatePointerTypeSymbol(); else if (type.IsByRef) return ResolveTypeSymbol(type.GetElementType()).GetOrCreateByRefTypeSymbol(); + else if (type.IsGenericParameter && type.DeclaringMethod is MethodInfo dm) + return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(type); + else if (type.IsGenericParameter) + return ResolveTypeSymbol(type.DeclaringType).GetOrCreateGenericTypeParameterSymbol(type); else throw new InvalidOperationException(); } @@ -171,9 +174,14 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p } /// - public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IIkvmReflectionMemberSymbolBuilder member, ParameterBuilder parameter) { - return ResolveMethodSymbol((MethodBuilder)parameter.Method).GetOrCreateParameterSymbol(parameter); + return member switch + { + IIkvmReflectionMethodBaseSymbolBuilder method => method.GetOrCreateParameterSymbol(parameter), + IIkvmReflectionPropertySymbolBuilder property => property.GetOrCreateParameterSymbol(parameter), + _ => throw new InvalidOperationException(), + }; } /// @@ -214,21 +222,21 @@ public IResourceWriter DefineResource(string name, string description, System.Re } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), parameterTypes.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] requiredReturnTypeCustomModifiers, ITypeSymbol[] optionalReturnTypeCustomModifiers, ITypeSymbol[] parameterTypes, ITypeSymbol[][] requiredParameterTypeCustomModifiers, ITypeSymbol[][] optionalParameterTypeCustomModifiers) + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? requiredReturnTypeCustomModifiers, ITypeSymbol[]? optionalReturnTypeCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredParameterTypeCustomModifiers, ITypeSymbol[][]? optionalParameterTypeCustomModifiers) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), requiredReturnTypeCustomModifiers.Unpack(), optionalReturnTypeCustomModifiers.Unpack(), parameterTypes.Unpack(), requiredParameterTypeCustomModifiers.Unpack(), optionalParameterTypeCustomModifiers.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), requiredReturnTypeCustomModifiers?.Unpack(), optionalReturnTypeCustomModifiers?.Unpack(), parameterTypes?.Unpack(), requiredParameterTypeCustomModifiers?.Unpack(), optionalParameterTypeCustomModifiers?.Unpack())); } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, returnType.Unpack(), parameterTypes.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs index ea7a2a744f..441b991f5c 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs @@ -14,18 +14,20 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit class IkvmReflectionParameterBuilderInfo : ParameterInfo { + readonly IIkvmReflectionMemberSymbol _member; readonly ParameterBuilder _builder; readonly Func _getDefaultValue; /// /// Initialies a new instance. /// + /// /// - /// /// /// - public IkvmReflectionParameterBuilderInfo(ParameterBuilder builder, Func getDefaultValue) + public IkvmReflectionParameterBuilderInfo(IIkvmReflectionMemberSymbol member, ParameterBuilder builder, Func getDefaultValue) { + _member = member ?? throw new ArgumentNullException(nameof(member)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _getDefaultValue = getDefaultValue ?? throw new ArgumentNullException(nameof(getDefaultValue)); } @@ -34,7 +36,7 @@ public IkvmReflectionParameterBuilderInfo(ParameterBuilder builder, Func (ParameterAttributes)_builder.Attributes; /// - public override MemberInfo Member => throw new NotImplementedException(); + public override MemberInfo Member => _member.UnderlyingMember; /// public override Type ParameterType => ((MethodBase)Member).GetParameters()[Position].ParameterType; @@ -46,7 +48,7 @@ public IkvmReflectionParameterBuilderInfo(ParameterBuilder builder, Func _builder.Name; /// - public override int Position => _builder.Position; + public override int Position => _builder.Position - 1; /// public override int MetadataToken => throw new NotImplementedException(); diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs index e49827c7dd..461d75db79 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs @@ -11,8 +11,8 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit class IkvmReflectionParameterSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmReflectionParameterSymbolBuilder { - readonly IIkvmReflectionModuleSymbol _resolvingModule; - readonly IIkvmReflectionMemberSymbol _resolvingMethod; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionMemberSymbol _member; ParameterBuilder? _builder; ParameterInfo _parameter; @@ -23,23 +23,23 @@ class IkvmReflectionParameterSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmR /// Initializes a new instance. /// /// - /// - /// + /// + /// /// - public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionMemberSymbol resolvingMethod, ParameterBuilder builder) : + public IkvmReflectionParameterSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionMemberSymbol member, ParameterBuilder builder) : base(context) { - _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _member = member ?? throw new ArgumentNullException(nameof(member)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _parameter = new IkvmReflectionParameterBuilderInfo(_builder, () => _constant); + _parameter = new IkvmReflectionParameterBuilderInfo(member, _builder, () => _constant); } /// - public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingMethod.ResolvingModule; + public IIkvmReflectionModuleSymbol ResolvingModule => _module; /// - public IIkvmReflectionMemberSymbol ResolvingMember => _resolvingMethod; + public IIkvmReflectionMemberSymbol ResolvingMember => _member; /// public ParameterInfo UnderlyingParameter => _parameter; diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs index 731828bd75..f4416773b7 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs @@ -40,8 +40,19 @@ public IkvmReflectionPropertySymbolBuilder(IkvmReflectionSymbolContext context, /// public override MemberInfo UnderlyingMember => UnderlyingProperty; - #region IIkvmPropertySymbol + #region IIkvmReflectionPropertySymbolBuilder + /// + public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + + #region IIkvmReflectionPropertySymbol + + /// public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { return _parameterTable.GetOrCreateParameterSymbol(parameter); @@ -49,7 +60,7 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p #endregion - #region IPropertySymbol + #region IPropertySymbolBuilder /// public void SetConstant(object? defaultValue) @@ -186,7 +197,6 @@ public ITypeSymbol[] GetRequiredCustomModifiers() /// public override void OnComplete() { - _property = (PropertyInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index f392d45025..3ec41457e8 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -27,18 +27,19 @@ class IkvmReflectionTypeSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvm /// Initializes a new instance. /// /// - /// + /// /// - public IkvmReflectionTypeSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, TypeBuilder builder) : - base(context, resolvingModule, null) + public IkvmReflectionTypeSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder module, TypeBuilder builder) : + base(context, module, null) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _type = _builder; - _methodTable = new IkvmReflectionMethodTable(context, resolvingModule, this); - _fieldTable = new IkvmReflectionFieldTable(context, resolvingModule, this); - _propertyTable = new IkvmReflectionPropertyTable(context, resolvingModule, this); - _eventTable = new IkvmReflectionEventTable(context, resolvingModule, this); - _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, resolvingModule, this); + _methodTable = new IkvmReflectionMethodTable(context, module, this); + _fieldTable = new IkvmReflectionFieldTable(context, module, this); + _propertyTable = new IkvmReflectionPropertyTable(context, module, this); + _eventTable = new IkvmReflectionEventTable(context, module, this); + _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, module, this); + _specTable = new IkvmReflectionTypeSpecTable(context, module, this); } /// @@ -164,12 +165,6 @@ public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @ev return _eventTable.GetOrCreateEventSymbol(@event); } - /// - public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return ResolveMethodSymbol((MethodBuilder)parameter.Method).GetOrCreateParameterSymbol(parameter); - } - #endregion #region ITypeSymbolBuilder @@ -899,7 +894,10 @@ public void Complete() { // complete type if (_builder.IsCreated() == false) - _builder.CreateType(); + { + _type = _builder.CreateType(); + _builder = null; + } // force module to reresolve Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); @@ -912,9 +910,6 @@ public override void OnComplete() { const System.Reflection.BindingFlags DefaultBindingFlags = System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Static; - _type = ResolvingModule.UnderlyingModule.ResolveType(MetadataToken); - _builder = null; - foreach (var i in GetGenericArguments()) if (i is IIkvmReflectionGenericTypeParameterSymbolBuilder b) b.OnComplete(); diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs index 8e64ccaa46..5a0068973c 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs @@ -18,6 +18,13 @@ interface IIkvmReflectionMethodSymbol : IIkvmReflectionMethodBaseSymbol, IMethod /// IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); + /// + /// Gets or creates a for the given generic version of this method definition. + /// + /// + /// + IIkvmReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 61b83f6297..73163f1ba9 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -93,19 +93,13 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public System.Reflection.AssemblyName GetName() + public AssemblyNameInfo GetName() { return UnderlyingAssembly.GetName().Pack(); } /// - public System.Reflection.AssemblyName GetName(bool copiedName) - { - return UnderlyingAssembly.GetName().Pack(); - } - - /// - public System.Reflection.AssemblyName[] GetReferencedAssemblies() + public AssemblyNameInfo[] GetReferencedAssemblies() { return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs index 7caf5453c1..9bff410a3d 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs @@ -60,10 +60,8 @@ public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type gene return _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionMemberSymbolBuilder)_member, builder); else return _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbol(_context, _module, _member, genericTypeParameter); - else - { - return _table[pos] ?? throw new InvalidOperationException(); - } + + return _table[pos] ?? throw new InvalidOperationException(); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index 69abb71899..c74eafbf30 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -2,9 +2,7 @@ using System.Diagnostics.CodeAnalysis; using System.Linq; -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; using IKVM.Reflection; -using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; @@ -17,8 +15,8 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection abstract class IkvmReflectionMemberSymbol : IkvmReflectionSymbol, IIkvmReflectionMemberSymbol { - readonly IIkvmReflectionModuleSymbol _resolvingModule; - readonly IIkvmReflectionTypeSymbol? _resolvingType; + readonly IIkvmReflectionModuleSymbol _module; + readonly IIkvmReflectionTypeSymbol? _type; /// /// Initializes a new instance. @@ -30,8 +28,8 @@ abstract class IkvmReflectionMemberSymbol : IkvmReflectionSymbol, IIkvmReflectio public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol resolvingModule, IIkvmReflectionTypeSymbol? resolvingType) : base(context) { - _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingType = resolvingType; + _module = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _type = resolvingType; } /// @@ -40,12 +38,12 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl /// /// Gets the which contains the metadata of this member. /// - public IIkvmReflectionModuleSymbol ResolvingModule => _resolvingModule; + public IIkvmReflectionModuleSymbol ResolvingModule => _module; /// /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. /// - public IIkvmReflectionTypeSymbol? ResolvingType => _resolvingType; + public IIkvmReflectionTypeSymbol? ResolvingType => _type; /// [return: NotNullIfNotNull(nameof(type))] @@ -57,11 +55,11 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl if (type == UnderlyingMember) return (IIkvmReflectionTypeSymbol)this; - if (_resolvingType != null && type == _resolvingType.UnderlyingType) - return _resolvingType; + if (_type != null && type == _type.UnderlyingType) + return _type; - if (type.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateTypeSymbol(type); + if (type.Module == _module.UnderlyingModule) + return _module.GetOrCreateTypeSymbol(type); return base.ResolveTypeSymbol(type); } @@ -76,8 +74,8 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl if (ctor == UnderlyingMember) return (IIkvmReflectionConstructorSymbol)this; - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + if (ctor.Module == _module.UnderlyingModule) + return _module.GetOrCreateConstructorSymbol(ctor); return base.ResolveConstructorSymbol(ctor); } @@ -92,8 +90,8 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl if (method == UnderlyingMember) return (IIkvmReflectionMethodSymbol)this; - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); + if (method.Module == _module.UnderlyingModule) + return _module.GetOrCreateMethodSymbol(method); return base.ResolveMethodSymbol(method); } @@ -108,8 +106,8 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl if (field == UnderlyingMember) return (IIkvmReflectionFieldSymbol)this; - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); + if (field.Module == _module.UnderlyingModule) + return _module.GetOrCreateFieldSymbol(field); return base.ResolveFieldSymbol(field); } @@ -124,8 +122,8 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl if (property == UnderlyingMember) return (IIkvmReflectionPropertySymbol)this; - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); + if (property.Module == _module.UnderlyingModule) + return _module.GetOrCreatePropertySymbol(property); return base.ResolvePropertySymbol(property); } @@ -140,8 +138,8 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl if (@event == UnderlyingMember) return (IIkvmReflectionEventSymbol)this; - if (@event.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); + if (@event.Module == _module.UnderlyingModule) + return _module.GetOrCreateEventSymbol(@event); return base.ResolveEventSymbol(@event); } @@ -153,8 +151,8 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl if (parameter is null) throw new ArgumentNullException(nameof(parameter)); - if (parameter.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); + if (parameter.Module == _module.UnderlyingModule) + return _module.GetOrCreateParameterSymbol(parameter); return base.ResolveParameterSymbol(parameter); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs index 1a94625e77..5c0c70607c 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs @@ -12,7 +12,7 @@ struct IkvmReflectionMethodSpecTable readonly IkvmReflectionSymbolContext _context; readonly IIkvmReflectionModuleSymbol _module; - readonly IIkvmReflectionTypeSymbol _type; + readonly IIkvmReflectionTypeSymbol? _type; readonly IIkvmReflectionMethodSymbol _method; ConcurrentDictionary? _genericMethodSymbols; @@ -25,11 +25,11 @@ struct IkvmReflectionMethodSpecTable /// /// /// - public IkvmReflectionMethodSpecTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol type, IIkvmReflectionMethodSymbol method) + public IkvmReflectionMethodSpecTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type, IIkvmReflectionMethodSymbol method) { _context = context ?? throw new ArgumentNullException(nameof(context)); _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type ?? throw new ArgumentNullException(nameof(type)); + _type = type; _method = method ?? throw new ArgumentNullException(nameof(method)); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs index e0c8b8e3e6..50efe60e8f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSymbol.cs @@ -1,4 +1,5 @@ using System; +using System.Threading; using IKVM.Reflection; @@ -13,6 +14,7 @@ class IkvmReflectionMethodSymbol : IkvmReflectionMethodBaseSymbol, IIkvmReflecti readonly MethodInfo _method; IkvmReflectionGenericTypeParameterTable _genericTypeParameterTable; + IkvmReflectionMethodSpecTable _specTable; /// /// Initializes a new instance. @@ -26,6 +28,7 @@ public IkvmReflectionMethodSymbol(IkvmReflectionSymbolContext context, IIkvmRefl { _method = method ?? throw new ArgumentNullException(nameof(method)); _genericTypeParameterTable = new IkvmReflectionGenericTypeParameterTable(context, module, this); + _specTable = new IkvmReflectionMethodSpecTable(context, module, type, this); } /// @@ -42,6 +45,12 @@ public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type gene return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); } + /// + public IIkvmReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) + { + return _specTable.GetOrCreateGenericMethodSymbol(method.GetGenericArguments()); + } + #endregion #region IMethodSymbol diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs index cd1781c83a..479dda6ac6 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs @@ -53,8 +53,8 @@ public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase me if (method is MethodInfo m_ && m_.IsMethodDefinition() == false) throw new ArgumentException(nameof(method)); - var row = MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(method.MetadataToken)); - if (row == 0) + var token = method.MetadataToken; + if (token <= 0) { // we fall back to lookup by name if there is no valid metadata token if (_byName == null) @@ -73,11 +73,11 @@ public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase me using (_lock.CreateUpgradeableReadLock()) { - if (_table[row] == null) + if (_table[token] == null) using (_lock.CreateWriteLock()) - return _table[row] ??= CreateMethodBaseSymbol(_context, _module, _type, method); + return _table[token] ??= CreateMethodBaseSymbol(_context, _module, _type, method); - return _table[row] ?? throw new InvalidOperationException(); + return _table[token] ?? throw new InvalidOperationException(); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs index 452c861a43..9f4452ec4f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs @@ -19,6 +19,7 @@ struct IkvmReflectionParameterTable IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; + IIkvmReflectionParameterSymbol? _returnParameter; /// /// Initializes a new instance. @@ -54,6 +55,9 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p using (_lock.CreateUpgradeableReadLock()) { var position = parameter.Position; + if (position == -1) + return _returnParameter ??= new IkvmReflectionParameterSymbol(_context, _module, _member, parameter); + if (_table[position] == null) using (_lock.CreateWriteLock()) return _table[position] ??= new IkvmReflectionParameterSymbol(_context, _module, _member, parameter); @@ -80,7 +84,10 @@ public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(Paramete using (_lock.CreateUpgradeableReadLock()) { - var position = parameter.Position; + var position = parameter.Position - 1; + if (position == -1) + return (IIkvmReflectionParameterSymbolBuilder)(_returnParameter ??= new IkvmReflectionParameterSymbolBuilder(_context, _module, (IIkvmReflectionMethodBaseSymbol)_member, parameter)); + if (_table[position] == null) using (_lock.CreateWriteLock()) return (IIkvmReflectionParameterSymbolBuilder)(_table[position] ??= new IkvmReflectionParameterSymbolBuilder(_context, _module, (IIkvmReflectionMethodBaseSymbol)_member, parameter)); diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index 9780e79974..68f30b47dd 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -349,12 +349,15 @@ public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Proper [return: NotNullIfNotNull(nameof(@event))] public virtual IIkvmReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) { - return @event == null ? null : _context.GetOrCreateEventSymbol(@event); + if (@event is null) + return null; + + return _context.GetOrCreateEventSymbol(@event); } /// [return: NotNullIfNotNull(nameof(@event))] - public virtual IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + public virtual IIkvmReflectionEventSymbolBuilder? ResolveEventSymbol(EventBuilder @event) { if (@event is null) throw new ArgumentNullException(nameof(@event)); @@ -383,17 +386,36 @@ public virtual IIkvmReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder [return: NotNullIfNotNull(nameof(parameter))] public virtual IIkvmReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) { - return parameter == null ? null : _context.GetOrCreateParameterSymbol(parameter); + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + return _context.GetOrCreateParameterSymbol(parameter); } /// [return: NotNullIfNotNull(nameof(parameter))] - public virtual IIkvmReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + public virtual IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(IIkvmReflectionMethodBaseSymbolBuilder method, ParameterBuilder parameter) { + if (method is null) + throw new ArgumentNullException(nameof(method)); + if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + return null; - return _context.GetOrCreateParameterSymbol(parameter); + return method.GetOrCreateParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public virtual IIkvmReflectionParameterSymbolBuilder? ResolveParameterSymbol(IIkvmReflectionPropertySymbolBuilder property, ParameterBuilder parameter) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (parameter is null) + return null; + + return property.GetOrCreateParameterSymbol(parameter); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs index c7a1c06ee5..4cc41b20b4 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -32,7 +32,7 @@ public IkvmReflectionSymbolContext(Universe universe) } /// - public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name) + public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name) { if (name is null) throw new ArgumentNullException(nameof(name)); @@ -41,7 +41,7 @@ public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name } /// - public IAssemblySymbolBuilder DefineAssembly(System.Reflection.AssemblyName name, ICustomAttributeBuilder[]? assemblyAttributes) + public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttributeBuilder[]? assemblyAttributes) { if (name is null) throw new ArgumentNullException(nameof(name)); @@ -245,16 +245,6 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p return GetOrCreateModuleSymbol(parameter.Module).GetOrCreateParameterSymbol(parameter); } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return GetOrCreateModuleSymbol((ModuleBuilder)parameter.Module).GetOrCreateParameterSymbol(parameter); - } - /// /// Gets or creates a for the specified . /// @@ -262,11 +252,7 @@ public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(Paramete /// public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - return field switch - { - FieldBuilder builder => GetOrCreateFieldSymbol(builder), - _ => GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field) - }; + return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); } /// @@ -340,25 +326,52 @@ public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypePa /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs) { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs)); + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs))); } /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedFields.Unpack(), fieldValues)); + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedFields.Unpack(), UnpackArguments(fieldValues))); } /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues)); + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues))); } /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues, namedFields.Unpack(), fieldValues)); + return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues), namedFields.Unpack(), UnpackArguments(fieldValues))); + } + + /// + /// Unpacks a single constructor argument. + /// + /// + /// + object? UnpackArgument(object? constructorArg) + { + if (constructorArg is ITypeSymbol type) + return type.Unpack(); + + return constructorArg; + } + + /// + /// Unpacks a set of constructor arguments. + /// + /// + /// + object?[] UnpackArguments(object?[] constructorArgs) + { + var l = new object?[constructorArgs.Length]; + for (int i = 0; i < constructorArgs.Length; i++) + l[i] = UnpackArgument(constructorArgs[i]); + + return l; } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index cad0ca9129..b99a9ef220 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -55,13 +55,19 @@ public IIkvmReflectionConstructorSymbol GetOrCreateConstructorSymbol(Constructor /// public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) { - return _methodTable.GetOrCreateMethodBaseSymbol(method); + if (method is ConstructorInfo ctor) + return GetOrCreateConstructorSymbol(ctor); + else + return GetOrCreateMethodSymbol((MethodInfo)method); } /// public IIkvmReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { - return _methodTable.GetOrCreateMethodSymbol(method); + if (method.IsMethodDefinition()) + return _methodTable.GetOrCreateMethodSymbol(method); + else + return ResolveMethodSymbol(method.GetGenericMethodDefinition()).GetOrCreateGenericMethodSymbol(method); } /// @@ -433,7 +439,7 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) if (inherit) return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); else - throw new NotImplementedException(); + return ResolveTypeSymbols(UnderlyingType.__GetDeclaredInterfaces()); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs index 7a7d30082c..7239bb3f36 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Immutable; using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols.IkvmReflection.Emit; @@ -13,83 +14,55 @@ namespace IKVM.CoreLib.Symbols.IkvmReflection static class IkvmReflectionUtil { -#pragma warning disable SYSLIB0017 // Type or member is obsolete -#pragma warning disable SYSLIB0037 // Type or member is obsolete - /// /// Converts a to a . /// /// /// - public static System.Reflection.AssemblyName Pack(this AssemblyName n) + public static AssemblyNameInfo Pack(this AssemblyName n) { - return new System.Reflection.AssemblyName() - { - Name = n.Name, - Version = n.Version, - CultureInfo = n.CultureInfo, - CultureName = n.CultureName, - ProcessorArchitecture = (System.Reflection.ProcessorArchitecture)n.ProcessorArchitecture, - Flags = (System.Reflection.AssemblyNameFlags)n.Flags, - HashAlgorithm = (System.Configuration.Assemblies.AssemblyHashAlgorithm)n.HashAlgorithm, - ContentType = (System.Reflection.AssemblyContentType)n.ContentType, - VersionCompatibility = (System.Configuration.Assemblies.AssemblyVersionCompatibility)n.VersionCompatibility, - }; + return new AssemblyNameInfo(n.Name, n.Version, n.CultureName, (System.Reflection.AssemblyNameFlags)n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? ImmutableArray.Empty); } -#pragma warning restore SYSLIB0037 // Type or member is obsolete -#pragma warning restore SYSLIB0017 // Type or member is obsolete - /// /// Converts a set of to a set of . /// /// /// - public static System.Reflection.AssemblyName[] Pack(this AssemblyName[] n) + public static AssemblyNameInfo[] Pack(this AssemblyName[] n) { if (n.Length == 0) return []; - var a = new System.Reflection.AssemblyName[n.Length]; + var a = new AssemblyNameInfo[n.Length]; for (int i = 0; i < n.Length; i++) a[i] = n[i].Pack(); return a; } -#pragma warning disable SYSLIB0017 // Type or member is obsolete -#pragma warning disable SYSLIB0037 // Type or member is obsolete - /// - /// Converts a to a . + /// Converts a to a . /// /// /// - public static AssemblyName Unpack(this System.Reflection.AssemblyName n) + public static AssemblyName Unpack(this AssemblyNameInfo n) { return new AssemblyName() { Name = n.Name, Version = n.Version, - CultureInfo = n.CultureInfo, CultureName = n.CultureName, - ProcessorArchitecture = (ProcessorArchitecture)n.ProcessorArchitecture, Flags = (AssemblyNameFlags)n.Flags, - HashAlgorithm = (AssemblyHashAlgorithm)n.HashAlgorithm, - ContentType = (AssemblyContentType)n.ContentType, - VersionCompatibility = (AssemblyVersionCompatibility)n.VersionCompatibility, }; } -#pragma warning restore SYSLIB0037 // Type or member is obsolete -#pragma warning restore SYSLIB0017 // Type or member is obsolete - /// /// Converts a set of to a set of . /// /// /// - public static AssemblyName[] Unpack(this System.Reflection.AssemblyName[] n) + public static AssemblyName[] Unpack(this AssemblyNameInfo[] n) { if (n.Length == 0) return []; @@ -454,7 +427,7 @@ public static bool IsMethodDefinition(this MethodBase method) if (method is null) throw new ArgumentNullException(nameof(method)); - return method.IsGenericMethod == false || (method.IsGenericMethod && method.IsGenericMethodDefinition == true); + return method.IsGenericMethod == false || method.IsGenericMethodDefinition; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index 941d04e53d..b421a94c6e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.IO; using System.Linq; using System.Reflection; @@ -187,21 +188,26 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public AssemblyName GetName() + public AssemblyNameInfo GetName() { - return UnderlyingAssembly.GetName(); + return ToAssemblyName(UnderlyingAssembly.GetName()); } /// - public AssemblyName GetName(bool copiedName) + public AssemblyNameInfo[] GetReferencedAssemblies() { - return UnderlyingAssembly.GetName(copiedName); + return UnderlyingAssembly.GetReferencedAssemblies().Select(i => ToAssemblyName(i)).ToArray(); } - /// - public AssemblyName[] GetReferencedAssemblies() + /// + /// Transforms the to a . + /// + /// + /// + /// + AssemblyNameInfo ToAssemblyName(AssemblyName n) { - return UnderlyingAssembly.GetReferencedAssemblies(); + return new AssemblyNameInfo(n.Name ?? throw new InvalidOperationException(), n.Version, n.CultureName, n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? []); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index 1dcb3c58d7..a80569f593 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -39,46 +39,50 @@ public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, IRefl /// public ConstructorBuilder UnderlyingConstructorBuilder => _builder ?? throw new InvalidOperationException(); - #region IConstructorSymbolBuilder + #region IMethodBaseSymbolBuilder /// - public void SetImplementationFlags(MethodImplAttributes attributes) + public override void SetImplementationFlags(MethodImplAttributes attributes) { UnderlyingConstructorBuilder.SetImplementationFlags(attributes); } /// - public IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) + public override IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) { return ResolveParameterSymbol(UnderlyingConstructorBuilder.DefineParameter(iSequence, attributes, strParamName)); } /// - public IILGenerator GetILGenerator() + public override IILGenerator GetILGenerator() { return _il ??= new ReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator()); } /// - public IILGenerator GetILGenerator(int streamSize) + public override IILGenerator GetILGenerator(int streamSize) { return _il ??= new ReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator(streamSize)); } /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { UnderlyingConstructorBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { UnderlyingConstructorBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } #endregion + #region IConstructorSymbolBuilder + + #endregion + #region IConstructorSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs index b662e1a597..d9d2833276 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs @@ -26,6 +26,28 @@ public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IRefle /// public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + #region IMethodBaseSymbolBuilder + + /// + public abstract void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes); + + /// + public abstract IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName); + + /// + public abstract IILGenerator GetILGenerator(); + + /// + public abstract IILGenerator GetILGenerator(int streamSize); + + /// + public abstract void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); + + /// + public abstract void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + + #endregion + #region IMethodBaseSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index 7fba722c59..9336237402 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -39,70 +39,74 @@ public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectio /// public MethodBuilder UnderlyingMethodBuilder => _builder ?? throw new InvalidOperationException(); - #region IMethodSymbolBuilder + #region IMethodBaseSymbolBuilder /// - public void SetImplementationFlags(MethodImplAttributes attributes) + public override void SetImplementationFlags(MethodImplAttributes attributes) { UnderlyingMethodBuilder.SetImplementationFlags(attributes); } /// - public void SetParameters(params ITypeSymbol[] parameterTypes) + public override IParameterSymbolBuilder DefineParameter(int position, ParameterAttributes attributes, string? strParamName) { - UnderlyingMethodBuilder.SetParameters(parameterTypes.Unpack()); + return ResolveParameterSymbol(UnderlyingMethodBuilder.DefineParameter(position, attributes, strParamName)); } /// - public void SetReturnType(ITypeSymbol? returnType) + public override IILGenerator GetILGenerator() { - UnderlyingMethodBuilder.SetReturnType(returnType?.Unpack()); + return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator()); } /// - public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + public override IILGenerator GetILGenerator(int streamSize) { - UnderlyingMethodBuilder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); + return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); } - public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) + /// + public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - var l = UnderlyingMethodBuilder.DefineGenericParameters(names); - var a = new IGenericTypeParameterSymbolBuilder[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = (IGenericTypeParameterSymbolBuilder)ResolveTypeSymbol(l[i]); - - return a; + UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// - public IParameterSymbolBuilder DefineParameter(int position, ParameterAttributes attributes, string? strParamName) + public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - return ResolveParameterSymbol(UnderlyingMethodBuilder.DefineParameter(position, attributes, strParamName)); + UnderlyingMethodBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } + #endregion + + #region IMethodSymbolBuilder + /// - public IILGenerator GetILGenerator() + public void SetParameters(params ITypeSymbol[] parameterTypes) { - return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator()); + UnderlyingMethodBuilder.SetParameters(parameterTypes.Unpack()); } /// - public IILGenerator GetILGenerator(int streamSize) + public void SetReturnType(ITypeSymbol? returnType) { - return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); + UnderlyingMethodBuilder.SetReturnType(returnType?.Unpack()); } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingMethodBuilder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); } - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) { - UnderlyingMethodBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + var l = UnderlyingMethodBuilder.DefineGenericParameters(names); + var a = new IGenericTypeParameterSymbolBuilder[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = (IGenericTypeParameterSymbolBuilder)ResolveTypeSymbol(l[i]); + + return a; } #endregion diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index 0c6e91d2f0..42fdb989d9 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -87,21 +87,21 @@ public IResourceWriter DefineResource(string name, string description, ResourceA } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType.Unpack(), parameterTypes.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[] requiredReturnTypeCustomModifiers, ITypeSymbol[] optionalReturnTypeCustomModifiers, ITypeSymbol[] parameterTypes, ITypeSymbol[][] requiredParameterTypeCustomModifiers, ITypeSymbol[][] optionalParameterTypeCustomModifiers) + public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? requiredReturnTypeCustomModifiers, ITypeSymbol[]? optionalReturnTypeCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredParameterTypeCustomModifiers, ITypeSymbol[][]? optionalParameterTypeCustomModifiers) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType.Unpack(), requiredReturnTypeCustomModifiers.Unpack(), optionalReturnTypeCustomModifiers.Unpack(), parameterTypes.Unpack(), requiredParameterTypeCustomModifiers.Unpack(), optionalParameterTypeCustomModifiers.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType?.Unpack(), requiredReturnTypeCustomModifiers?.Unpack(), optionalReturnTypeCustomModifiers?.Unpack(), parameterTypes?.Unpack(), requiredParameterTypeCustomModifiers?.Unpack(), optionalParameterTypeCustomModifiers?.Unpack())); } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol returnType, ITypeSymbol[] parameterTypes) + public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, returnType.Unpack(), parameterTypes.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, returnType?.Unpack(), parameterTypes?.Unpack())); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index 951f0c2430..df2d48527c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.IO; using System.Linq; using System.Reflection; @@ -84,21 +85,26 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public AssemblyName GetName() + public AssemblyNameInfo GetName() { - return _assembly.GetName(); + return ToAssemblyNameInfo(_assembly.GetName()); } /// - public AssemblyName GetName(bool copiedName) + public AssemblyNameInfo[] GetReferencedAssemblies() { - return _assembly.GetName(copiedName); + return _assembly.GetReferencedAssemblies().Select(i => ToAssemblyNameInfo(i)).ToArray(); } - /// - public AssemblyName[] GetReferencedAssemblies() + /// + /// Transforms the to a . + /// + /// + /// + /// + AssemblyNameInfo ToAssemblyNameInfo(AssemblyName n) { - return _assembly.GetReferencedAssemblies(); + return new AssemblyNameInfo(n.Name ?? throw new InvalidOperationException(), n.Version, n.CultureName, n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? []); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index 369833fb7a..8b57fc2b6e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -34,12 +34,12 @@ public ReflectionSymbolContext() /// /// /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyName name) + public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name) { if (name is null) throw new ArgumentNullException(nameof(name)); - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, AssemblyBuilderAccess.RunAndCollect)); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect)); } /// @@ -48,12 +48,12 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyName name) /// /// /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyName name, ICustomAttributeBuilder[]? assemblyAttributes) + public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttributeBuilder[]? assemblyAttributes) { if (name is null) throw new ArgumentNullException(nameof(name)); - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name, AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index 10f77d1848..26c53e8989 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Immutable; using System.Reflection; using System.Reflection.Emit; @@ -11,6 +12,49 @@ namespace IKVM.CoreLib.Symbols.Reflection static class ReflectionUtil { + /// + /// Converts a to a . + /// + /// + /// + public static AssemblyNameInfo Pack(this AssemblyName n) + { + return new AssemblyNameInfo(n.Name ?? throw new InvalidOperationException(), n.Version, n.CultureName, n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? ImmutableArray.Empty); + } + + /// + /// Converts a set of to a set of . + /// + /// + /// + public static AssemblyNameInfo[] Pack(this AssemblyName[] n) + { + if (n.Length == 0) + return []; + + var a = new AssemblyNameInfo[n.Length]; + for (int i = 0; i < n.Length; i++) + a[i] = n[i].Pack(); + + return a; + } + + /// + /// Converts a to a . + /// + /// + /// + public static AssemblyName Unpack(this AssemblyNameInfo n) + { + return new AssemblyName() + { + Name = n.Name, + Version = n.Version, + CultureName = n.CultureName, + Flags = n.Flags, + }; + } + /// /// Unpacks the symbol into their original type. /// diff --git a/src/IKVM.CoreLib/Text/HexConverter.cs b/src/IKVM.CoreLib/Text/HexConverter.cs new file mode 100644 index 0000000000..504f432382 --- /dev/null +++ b/src/IKVM.CoreLib/Text/HexConverter.cs @@ -0,0 +1,443 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System; +using System.Diagnostics; +using System.Runtime.CompilerServices; + +namespace IKVM.CoreLib.Text +{ + + internal static class HexConverter + { + + public enum Casing : uint + { + // Output [ '0' .. '9' ] and [ 'A' .. 'F' ]. + Upper = 0, + + // Output [ '0' .. '9' ] and [ 'a' .. 'f' ]. + // This works because values in the range [ 0x30 .. 0x39 ] ([ '0' .. '9' ]) + // already have the 0x20 bit set, so ORing them with 0x20 is a no-op, + // while outputs in the range [ 0x41 .. 0x46 ] ([ 'A' .. 'F' ]) + // don't have the 0x20 bit set, so ORing them maps to + // [ 0x61 .. 0x66 ] ([ 'a' .. 'f' ]), which is what we want. + Lower = 0x2020U, + } + + // We want to pack the incoming byte into a single integer [ 0000 HHHH 0000 LLLL ], + // where HHHH and LLLL are the high and low nibbles of the incoming byte. Then + // subtract this integer from a constant minuend as shown below. + // + // [ 1000 1001 1000 1001 ] + // - [ 0000 HHHH 0000 LLLL ] + // ========================= + // [ *YYY **** *ZZZ **** ] + // + // The end result of this is that YYY is 0b000 if HHHH <= 9, and YYY is 0b111 if HHHH >= 10. + // Similarly, ZZZ is 0b000 if LLLL <= 9, and ZZZ is 0b111 if LLLL >= 10. + // (We don't care about the value of asterisked bits.) + // + // To turn a nibble in the range [ 0 .. 9 ] into hex, we calculate hex := nibble + 48 (ascii '0'). + // To turn a nibble in the range [ 10 .. 15 ] into hex, we calculate hex := nibble - 10 + 65 (ascii 'A'). + // => hex := nibble + 55. + // The difference in the starting ASCII offset is (55 - 48) = 7, depending on whether the nibble is <= 9 or >= 10. + // Since 7 is 0b111, this conveniently matches the YYY or ZZZ value computed during the earlier subtraction. + + // The commented out code below is code that directly implements the logic described above. + + // uint packedOriginalValues = (((uint)value & 0xF0U) << 4) + ((uint)value & 0x0FU); + // uint difference = 0x8989U - packedOriginalValues; + // uint add7Mask = (difference & 0x7070U) >> 4; // line YYY and ZZZ back up with the packed values + // uint packedResult = packedOriginalValues + add7Mask + 0x3030U /* ascii '0' */; + + // The code below is equivalent to the commented out code above but has been tweaked + // to allow codegen to make some extra optimizations. + + // The low byte of the packed result contains the hex representation of the incoming byte's low nibble. + // The adjacent byte of the packed result contains the hex representation of the incoming byte's high nibble. + + // Finally, write to the output buffer starting with the *highest* index so that codegen can + // elide all but the first bounds check. (This only works if 'startingIndex' is a compile-time constant.) + + // The JIT can elide bounds checks if 'startingIndex' is constant and if the caller is + // writing to a span of known length (or the caller has already checked the bounds of the + // furthest access). + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static void ToBytesBuffer(byte value, Span buffer, int startingIndex = 0, Casing casing = Casing.Upper) + { + uint difference = (((uint)value & 0xF0U) << 4) + ((uint)value & 0x0FU) - 0x8989U; + uint packedResult = ((((uint)(-(int)difference) & 0x7070U) >> 4) + difference + 0xB9B9U) | (uint)casing; + + buffer[startingIndex + 1] = (byte)packedResult; + buffer[startingIndex] = (byte)(packedResult >> 8); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static void ToCharsBuffer(byte value, Span buffer, int startingIndex = 0, Casing casing = Casing.Upper) + { + uint difference = (((uint)value & 0xF0U) << 4) + ((uint)value & 0x0FU) - 0x8989U; + uint packedResult = ((((uint)(-(int)difference) & 0x7070U) >> 4) + difference + 0xB9B9U) | (uint)casing; + + buffer[startingIndex + 1] = (char)(packedResult & 0xFF); + buffer[startingIndex] = (char)(packedResult >> 8); + } + +#if SYSTEM_PRIVATE_CORELIB + // Converts Vector128 into 2xVector128 ASCII Hex representation + [MethodImpl(MethodImplOptions.AggressiveInlining)] + [CompExactlyDependsOn(typeof(Ssse3))] + [CompExactlyDependsOn(typeof(AdvSimd.Arm64))] + internal static (Vector128, Vector128) AsciiToHexVector128(Vector128 src, Vector128 hexMap) + { + Debug.Assert(Ssse3.IsSupported || AdvSimd.Arm64.IsSupported); + // The algorithm is simple: a single srcVec (contains the whole 16b Guid) is converted + // into nibbles and then, via hexMap, converted into a HEX representation via + // Shuffle(nibbles, srcVec). ASCII is then expanded to UTF-16. + Vector128 shiftedSrc = Vector128.ShiftRightLogical(src.AsUInt64(), 4).AsByte(); + Vector128 lowNibbles = Vector128.UnpackLow(shiftedSrc, src); + Vector128 highNibbles = Vector128.UnpackHigh(shiftedSrc, src); + + return (Vector128.ShuffleUnsafe(hexMap, lowNibbles & Vector128.Create((byte)0xF)), + Vector128.ShuffleUnsafe(hexMap, highNibbles & Vector128.Create((byte)0xF))); + } + + [CompExactlyDependsOn(typeof(Ssse3))] + [CompExactlyDependsOn(typeof(AdvSimd.Arm64))] + private static void EncodeToUtf16_Vector128(ReadOnlySpan bytes, Span chars, Casing casing) + { + Debug.Assert(bytes.Length >= Vector128.Count); + + ref byte srcRef = ref MemoryMarshal.GetReference(bytes); + ref ushort destRef = ref Unsafe.As(ref MemoryMarshal.GetReference(chars)); + + Vector128 hexMap = casing == Casing.Upper ? + Vector128.Create((byte)'0', (byte)'1', (byte)'2', (byte)'3', + (byte)'4', (byte)'5', (byte)'6', (byte)'7', + (byte)'8', (byte)'9', (byte)'A', (byte)'B', + (byte)'C', (byte)'D', (byte)'E', (byte)'F') : + Vector128.Create((byte)'0', (byte)'1', (byte)'2', (byte)'3', + (byte)'4', (byte)'5', (byte)'6', (byte)'7', + (byte)'8', (byte)'9', (byte)'a', (byte)'b', + (byte)'c', (byte)'d', (byte)'e', (byte)'f'); + + nuint pos = 0; + nuint lengthSubVector128 = (nuint)bytes.Length - (nuint)Vector128.Count; + do + { + // This implementation processes 4 bytes of input at once, it can be easily modified + // to support 16 bytes at once, but that didn't demonstrate noticeable wins + // for Converter.ToHexString (around 8% faster for large inputs) so + // it focuses on small inputs instead. + + uint i32 = Unsafe.ReadUnaligned(ref Unsafe.Add(ref srcRef, pos)); + Vector128 vec = Vector128.CreateScalar(i32).AsByte(); + + // JIT is expected to eliminate all unused calculations + (Vector128 hexLow, _) = AsciiToHexVector128(vec, hexMap); + (Vector128 v0, _) = Vector128.Widen(hexLow); + + v0.StoreUnsafe(ref destRef, pos * 2); + + pos += (nuint)Vector128.Count; + if (pos == (nuint)bytes.Length) + { + return; + } + + // Overlap with the current chunk for trailing elements + if (pos > lengthSubVector128) + { + pos = lengthSubVector128; + } + + } while (true); + } +#endif + + public static void EncodeToUtf16(ReadOnlySpan bytes, Span chars, Casing casing = Casing.Upper) + { + Debug.Assert(chars.Length >= bytes.Length * 2); + +#if SYSTEM_PRIVATE_CORELIB + if ((AdvSimd.Arm64.IsSupported || Ssse3.IsSupported) && bytes.Length >= 4) + { + EncodeToUtf16_Vector128(bytes, chars, casing); + return; + } +#endif + for (int pos = 0; pos < bytes.Length; pos++) + { + ToCharsBuffer(bytes[pos], chars, pos * 2, casing); + } + } + + public static unsafe string ToString(ReadOnlySpan bytes, Casing casing = Casing.Upper) + { +#if NETFRAMEWORK || NETSTANDARD2_0 + Span result = bytes.Length > 16 ? + new char[bytes.Length * 2].AsSpan() : + stackalloc char[bytes.Length * 2]; + + int pos = 0; + foreach (byte b in bytes) + { + ToCharsBuffer(b, result, pos, casing); + pos += 2; + } + return result.ToString(); +#else + return string.Create(bytes.Length * 2, (RosPtr: (IntPtr)(&bytes), casing), static (chars, args) => + EncodeToUtf16(*(ReadOnlySpan*)args.RosPtr, chars, args.casing)); +#endif + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static char ToCharUpper(int value) + { + value &= 0xF; + value += '0'; + + if (value > '9') + { + value += ('A' - ('9' + 1)); + } + + return (char)value; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static char ToCharLower(int value) + { + value &= 0xF; + value += '0'; + + if (value > '9') + { + value += ('a' - ('9' + 1)); + } + + return (char)value; + } + + public static bool TryDecodeFromUtf16(ReadOnlySpan chars, Span bytes, out int charsProcessed) + { +#if SYSTEM_PRIVATE_CORELIB + if (BitConverter.IsLittleEndian && (Ssse3.IsSupported || AdvSimd.Arm64.IsSupported) && + chars.Length >= Vector128.Count * 2) + { + return TryDecodeFromUtf16_Vector128(chars, bytes, out charsProcessed); + } +#endif + return TryDecodeFromUtf16_Scalar(chars, bytes, out charsProcessed); + } + +#if SYSTEM_PRIVATE_CORELIB + [CompExactlyDependsOn(typeof(AdvSimd.Arm64))] + [CompExactlyDependsOn(typeof(Ssse3))] + public static bool TryDecodeFromUtf16_Vector128(ReadOnlySpan chars, Span bytes, out int charsProcessed) + { + Debug.Assert(Ssse3.IsSupported || AdvSimd.Arm64.IsSupported); + Debug.Assert(chars.Length <= bytes.Length * 2); + Debug.Assert(chars.Length % 2 == 0); + Debug.Assert(chars.Length >= Vector128.Count * 2); + + nuint offset = 0; + nuint lengthSubTwoVector128 = (nuint)chars.Length - ((nuint)Vector128.Count * 2); + + ref ushort srcRef = ref Unsafe.As(ref MemoryMarshal.GetReference(chars)); + ref byte destRef = ref MemoryMarshal.GetReference(bytes); + + do + { + // The algorithm is UTF8 so we'll be loading two UTF-16 vectors to narrow them into a + // single UTF8 ASCII vector - the implementation can be shared with UTF8 paths. + Vector128 vec1 = Vector128.LoadUnsafe(ref srcRef, offset); + Vector128 vec2 = Vector128.LoadUnsafe(ref srcRef, offset + (nuint)Vector128.Count); + Vector128 vec = Ascii.ExtractAsciiVector(vec1, vec2); + + // Based on "Algorithm #3" https://github.com/WojciechMula/toys/blob/master/simd-parse-hex/geoff_algorithm.cpp + // by Geoff Langdale and Wojciech Mula + // Move digits '0'..'9' into range 0xf6..0xff. + Vector128 t1 = vec + Vector128.Create((byte)(0xFF - '9')); + // And then correct the range to 0xf0..0xf9. + // All other bytes become less than 0xf0. + Vector128 t2 = Vector128.SubtractSaturate(t1, Vector128.Create((byte)6)); + // Convert into uppercase 'a'..'f' => 'A'..'F' and + // move hex letter 'A'..'F' into range 0..5. + Vector128 t3 = (vec & Vector128.Create((byte)0xDF)) - Vector128.Create((byte)'A'); + // And correct the range into 10..15. + // The non-hex letters bytes become greater than 0x0f. + Vector128 t4 = Vector128.AddSaturate(t3, Vector128.Create((byte)10)); + // Convert '0'..'9' into nibbles 0..9. Non-digit bytes become + // greater than 0x0f. Finally choose the result: either valid nibble (0..9/10..15) + // or some byte greater than 0x0f. + Vector128 nibbles = Vector128.Min(t2 - Vector128.Create((byte)0xF0), t4); + // Any high bit is a sign that input is not a valid hex data + if (!Utf16Utility.AllCharsInVectorAreAscii(vec1 | vec2) || + Vector128.AddSaturate(nibbles, Vector128.Create((byte)(127 - 15))).ExtractMostSignificantBits() != 0) + { + // Input is either non-ASCII or invalid hex data + break; + } + Vector128 output; + if (Ssse3.IsSupported) + { + output = Ssse3.MultiplyAddAdjacent(nibbles, + Vector128.Create((short)0x0110).AsSByte()).AsByte(); + } + else + { + // Workaround for missing MultiplyAddAdjacent on ARM + Vector128 even = AdvSimd.Arm64.TransposeEven(nibbles, Vector128.Zero).AsInt16(); + Vector128 odd = AdvSimd.Arm64.TransposeOdd(nibbles, Vector128.Zero).AsInt16(); + even = AdvSimd.ShiftLeftLogical(even, 4).AsInt16(); + output = AdvSimd.AddSaturate(even, odd).AsByte(); + } + // Accumulate output in lower INT64 half and take care about endianness + output = Vector128.Shuffle(output, Vector128.Create((byte)0, 2, 4, 6, 8, 10, 12, 14, 0, 0, 0, 0, 0, 0, 0, 0)); + // Store 8 bytes in dest by given offset + Unsafe.WriteUnaligned(ref Unsafe.Add(ref destRef, offset / 2), output.AsUInt64().ToScalar()); + + offset += (nuint)Vector128.Count * 2; + if (offset == (nuint)chars.Length) + { + charsProcessed = chars.Length; + return true; + } + // Overlap with the current chunk for trailing elements + if (offset > lengthSubTwoVector128) + { + offset = lengthSubTwoVector128; + } + } + while (true); + + // Fall back to the scalar routine in case of invalid input. + bool fallbackResult = TryDecodeFromUtf16_Scalar(chars.Slice((int)offset), bytes.Slice((int)(offset / 2)), out int fallbackProcessed); + charsProcessed = (int)offset + fallbackProcessed; + return fallbackResult; + } +#endif + + private static bool TryDecodeFromUtf16_Scalar(ReadOnlySpan chars, Span bytes, out int charsProcessed) + { + Debug.Assert(chars.Length % 2 == 0, "Un-even number of characters provided"); + Debug.Assert(chars.Length / 2 == bytes.Length, "Target buffer not right-sized for provided characters"); + + int i = 0; + int j = 0; + int byteLo = 0; + int byteHi = 0; + while (j < bytes.Length) + { + byteLo = FromChar(chars[i + 1]); + byteHi = FromChar(chars[i]); + + // byteHi hasn't been shifted to the high half yet, so the only way the bitwise or produces this pattern + // is if either byteHi or byteLo was not a hex character. + if ((byteLo | byteHi) == 0xFF) + break; + + bytes[j++] = (byte)((byteHi << 4) | byteLo); + i += 2; + } + + if (byteLo == 0xFF) + i++; + + charsProcessed = i; + return (byteLo | byteHi) != 0xFF; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static int FromChar(int c) + { + return c >= CharToHexLookup.Length ? 0xFF : CharToHexLookup[c]; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static int FromUpperChar(int c) + { + return c > 71 ? 0xFF : CharToHexLookup[c]; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static int FromLowerChar(int c) + { + if ((uint)(c - '0') <= '9' - '0') + return c - '0'; + + if ((uint)(c - 'a') <= 'f' - 'a') + return c - 'a' + 10; + + return 0xFF; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static bool IsHexChar(int c) + { + if (IntPtr.Size == 8) + { + // This code path, when used, has no branches and doesn't depend on cache hits, + // so it's faster and does not vary in speed depending on input data distribution. + // We only use this logic on 64-bit systems, as using 64 bit values would otherwise + // be much slower than just using the lookup table anyway (no hardware support). + // The magic constant 18428868213665201664 is a 64 bit value containing 1s at the + // indices corresponding to all the valid hex characters (ie. "0123456789ABCDEFabcdef") + // minus 48 (ie. '0'), and backwards (so from the most significant bit and downwards). + // The offset of 48 for each bit is necessary so that the entire range fits in 64 bits. + // First, we subtract '0' to the input digit (after casting to uint to account for any + // negative inputs). Note that even if this subtraction underflows, this happens before + // the result is zero-extended to ulong, meaning that `i` will always have upper 32 bits + // equal to 0. We then left shift the constant with this offset, and apply a bitmask that + // has the highest bit set (the sign bit) if and only if `c` is in the ['0', '0' + 64) range. + // Then we only need to check whether this final result is less than 0: this will only be + // the case if both `i` was in fact the index of a set bit in the magic constant, and also + // `c` was in the allowed range (this ensures that false positive bit shifts are ignored). + ulong i = (uint)c - '0'; + ulong shift = 18428868213665201664UL << (int)i; + ulong mask = i - 64; + + return (long)(shift & mask) < 0 ? true : false; + } + + return FromChar(c) != 0xFF; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static bool IsHexUpperChar(int c) + { + return (uint)(c - '0') <= 9 || (uint)(c - 'A') <= ('F' - 'A'); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static bool IsHexLowerChar(int c) + { + return (uint)(c - '0') <= 9 || (uint)(c - 'a') <= ('f' - 'a'); + } + + /// Map from an ASCII char to its hex value, e.g. arr['b'] == 11. 0xFF means it's not a hex digit. + public static ReadOnlySpan CharToHexLookup => + [ + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 15 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 31 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 47 + 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x8, 0x9, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 63 + 0xFF, 0xA, 0xB, 0xC, 0xD, 0xE, 0xF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 79 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 95 + 0xFF, 0xa, 0xb, 0xc, 0xd, 0xe, 0xf, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 111 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 127 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 143 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 159 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 175 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 191 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 207 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 223 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, // 239 + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF // 255 + ]; + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Text/ValueStringBuilder.cs b/src/IKVM.CoreLib/Text/ValueStringBuilder.cs new file mode 100644 index 0000000000..4418936736 --- /dev/null +++ b/src/IKVM.CoreLib/Text/ValueStringBuilder.cs @@ -0,0 +1,339 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System; +using System.Buffers; +using System.Diagnostics; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +namespace IKVM.CoreLib.Text +{ + + /// + /// Stolen from dotnet/runtime. + /// + internal ref partial struct ValueStringBuilder + { + + private char[]? _arrayToReturnToPool; + private Span _chars; + private int _pos; + + public ValueStringBuilder(Span initialBuffer) + { + _arrayToReturnToPool = null; + _chars = initialBuffer; + _pos = 0; + } + + public ValueStringBuilder(int initialCapacity) + { + _arrayToReturnToPool = ArrayPool.Shared.Rent(initialCapacity); + _chars = _arrayToReturnToPool; + _pos = 0; + } + + public int Length + { + get => _pos; + set + { + Debug.Assert(value >= 0); + Debug.Assert(value <= _chars.Length); + _pos = value; + } + } + + public int Capacity => _chars.Length; + + public void EnsureCapacity(int capacity) + { + // This is not expected to be called this with negative capacity + Debug.Assert(capacity >= 0); + + // If the caller has a bug and calls this with negative capacity, make sure to call Grow to throw an exception. + if ((uint)capacity > (uint)_chars.Length) + Grow(capacity - _pos); + } + + /// + /// Get a pinnable reference to the builder. + /// Does not ensure there is a null char after + /// This overload is pattern matched in the C# 7.3+ compiler so you can omit + /// the explicit method call, and write eg "fixed (char* c = builder)" + /// + public ref char GetPinnableReference() + { + return ref MemoryMarshal.GetReference(_chars); + } + + /// + /// Get a pinnable reference to the builder. + /// + /// Ensures that the builder has a null char after + public ref char GetPinnableReference(bool terminate) + { + if (terminate) + { + EnsureCapacity(Length + 1); + _chars[Length] = '\0'; + } + return ref MemoryMarshal.GetReference(_chars); + } + + public ref char this[int index] + { + get + { + Debug.Assert(index < _pos); + return ref _chars[index]; + } + } + + public override string ToString() + { + string s = _chars.Slice(0, _pos).ToString(); + Dispose(); + return s; + } + + /// Returns the underlying storage of the builder. + public Span RawChars => _chars; + + /// + /// Returns a span around the contents of the builder. + /// + /// Ensures that the builder has a null char after + public ReadOnlySpan AsSpan(bool terminate) + { + if (terminate) + { + EnsureCapacity(Length + 1); + _chars[Length] = '\0'; + } + return _chars.Slice(0, _pos); + } + + public ReadOnlySpan AsSpan() => _chars.Slice(0, _pos); + public ReadOnlySpan AsSpan(int start) => _chars.Slice(start, _pos - start); + public ReadOnlySpan AsSpan(int start, int length) => _chars.Slice(start, length); + + public bool TryCopyTo(Span destination, out int charsWritten) + { + if (_chars.Slice(0, _pos).TryCopyTo(destination)) + { + charsWritten = _pos; + Dispose(); + return true; + } + else + { + charsWritten = 0; + Dispose(); + return false; + } + } + + public void Insert(int index, char value, int count) + { + if (_pos > _chars.Length - count) + { + Grow(count); + } + + int remaining = _pos - index; + _chars.Slice(index, remaining).CopyTo(_chars.Slice(index + count)); + _chars.Slice(index, count).Fill(value); + _pos += count; + } + + public void Insert(int index, string? s) + { + if (s == null) + { + return; + } + + int count = s.Length; + + if (_pos > (_chars.Length - count)) + { + Grow(count); + } + + int remaining = _pos - index; + _chars.Slice(index, remaining).CopyTo(_chars.Slice(index + count)); + s +#if !NET + .AsSpan() +#endif + .CopyTo(_chars.Slice(index)); + _pos += count; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public void Append(char c) + { + int pos = _pos; + Span chars = _chars; + if ((uint)pos < (uint)chars.Length) + { + chars[pos] = c; + _pos = pos + 1; + } + else + { + GrowAndAppend(c); + } + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public void Append(string? s) + { + if (s == null) + { + return; + } + + int pos = _pos; + if (s.Length == 1 && (uint)pos < (uint)_chars.Length) // very common case, e.g. appending strings from NumberFormatInfo like separators, percent symbols, etc. + { + _chars[pos] = s[0]; + _pos = pos + 1; + } + else + { + AppendSlow(s); + } + } + + private void AppendSlow(string s) + { + int pos = _pos; + if (pos > _chars.Length - s.Length) + { + Grow(s.Length); + } + + s +#if !NET + .AsSpan() +#endif + .CopyTo(_chars.Slice(pos)); + _pos += s.Length; + } + + public void Append(char c, int count) + { + if (_pos > _chars.Length - count) + { + Grow(count); + } + + Span dst = _chars.Slice(_pos, count); + for (int i = 0; i < dst.Length; i++) + { + dst[i] = c; + } + _pos += count; + } + + public unsafe void Append(char* value, int length) + { + int pos = _pos; + if (pos > _chars.Length - length) + { + Grow(length); + } + + Span dst = _chars.Slice(_pos, length); + for (int i = 0; i < dst.Length; i++) + { + dst[i] = *value++; + } + _pos += length; + } + + public void Append(scoped ReadOnlySpan value) + { + int pos = _pos; + if (pos > _chars.Length - value.Length) + { + Grow(value.Length); + } + + value.CopyTo(_chars.Slice(_pos)); + _pos += value.Length; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public Span AppendSpan(int length) + { + int origPos = _pos; + if (origPos > _chars.Length - length) + { + Grow(length); + } + + _pos = origPos + length; + return _chars.Slice(origPos, length); + } + + [MethodImpl(MethodImplOptions.NoInlining)] + private void GrowAndAppend(char c) + { + Grow(1); + Append(c); + } + + /// + /// Resize the internal buffer either by doubling current buffer size or + /// by adding to + /// whichever is greater. + /// + /// + /// Number of chars requested beyond current position. + /// + [MethodImpl(MethodImplOptions.NoInlining)] + private void Grow(int additionalCapacityBeyondPos) + { + Debug.Assert(additionalCapacityBeyondPos > 0); + Debug.Assert(_pos > _chars.Length - additionalCapacityBeyondPos, "Grow called incorrectly, no resize is needed."); + + const uint ArrayMaxLength = 0x7FFFFFC7; // same as Array.MaxLength + + // Increase to at least the required size (_pos + additionalCapacityBeyondPos), but try + // to double the size if possible, bounding the doubling to not go beyond the max array length. + int newCapacity = (int)Math.Max( + (uint)(_pos + additionalCapacityBeyondPos), + Math.Min((uint)_chars.Length * 2, ArrayMaxLength)); + + // Make sure to let Rent throw an exception if the caller has a bug and the desired capacity is negative. + // This could also go negative if the actual required length wraps around. + char[] poolArray = ArrayPool.Shared.Rent(newCapacity); + + _chars.Slice(0, _pos).CopyTo(poolArray); + + char[]? toReturn = _arrayToReturnToPool; + _chars = _arrayToReturnToPool = poolArray; + if (toReturn != null) + { + ArrayPool.Shared.Return(toReturn); + } + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public void Dispose() + { + char[]? toReturn = _arrayToReturnToPool; + this = default; // for safety, to avoid using pooled array if this instance is erroneously appended to again + if (toReturn != null) + { + ArrayPool.Shared.Return(toReturn); + } + } + + } + +} diff --git a/src/IKVM.Reflection/Universe.cs b/src/IKVM.Reflection/Universe.cs index e933bc87af..2c71d09935 100644 --- a/src/IKVM.Reflection/Universe.cs +++ b/src/IKVM.Reflection/Universe.cs @@ -204,7 +204,7 @@ static bool GetUseNativeFusion() /// /// Gets the core library. /// - internal Assembly CoreLib => Load(coreLibName); + public Assembly CoreLib => Load(coreLibName); /// /// Attempts to import the type from the core library. diff --git a/src/IKVM.Runtime/Annotation.cs b/src/IKVM.Runtime/Annotation.cs index 69d77735fa..932b6e7e8f 100644 --- a/src/IKVM.Runtime/Annotation.cs +++ b/src/IKVM.Runtime/Annotation.cs @@ -34,7 +34,7 @@ namespace IKVM.Runtime abstract class Annotation { -#if IMPORTER +#if !EXPORTER internal static Annotation LoadAssemblyCustomAttribute(RuntimeClassLoader loader, object[] def) { @@ -60,10 +60,6 @@ internal static Annotation LoadAssemblyCustomAttribute(RuntimeClassLoader loader return null; } -#endif - -#if !EXPORTER - // NOTE this method returns null if the type could not be found // or if the type is not a Custom Attribute and we're not in the static compiler internal static Annotation Load(RuntimeJavaType owner, object[] def) @@ -303,7 +299,7 @@ private static object[] ValueQualifyClassNames(RuntimeClassLoader loader, object } internal abstract void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation); - internal abstract void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation); + internal abstract void Apply(RuntimeClassLoader loader, IMethodBaseSymbolBuilder mb, object annotation); internal abstract void Apply(RuntimeClassLoader loader, IFieldSymbolBuilder fb, object annotation); internal abstract void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder pb, object annotation); internal abstract void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder ab, object annotation); diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index fd2195cb43..f510655810 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -25,21 +25,17 @@ Jeroen Frijters using System.Collections.Generic; using System.ComponentModel; using System.Diagnostics; +using System.Reflection; using System.Runtime.CompilerServices; using IKVM.Attributes; -using IKVM.CoreLib.Diagnostics; using IKVM.ByteCode.Buffers; using IKVM.ByteCode.Decoding; using IKVM.ByteCode.Encoding; +using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; -#else -using System.Reflection; -#endif +using IKVM.CoreLib.Symbols.Reflection; #if IMPORTER using IKVM.Tools.Importer; @@ -56,8 +52,6 @@ class AttributeHelper readonly RuntimeContext context; -#if IMPORTER - ICustomAttributeBuilder compilerGeneratedAttribute; ICustomAttributeBuilder ghostInterfaceAttribute; ICustomAttributeBuilder deprecatedAttribute; @@ -80,8 +74,6 @@ class AttributeHelper ITypeSymbol typeofSourceFileAttribute; ITypeSymbol typeofLineNumberTableAttribute; -#endif - ITypeSymbol typeofRemappedClassAttribute; ITypeSymbol typeofRemappedTypeAttribute; ITypeSymbol typeofModifiersAttribute; @@ -105,80 +97,69 @@ class AttributeHelper ITypeSymbol typeofRuntimeVisibleTypeAnnotationsAttribute; ITypeSymbol typeofConstantPoolAttribute; ITypeSymbol typeofDebuggableAttribute; + ITypeSymbol typeofCustomAssemblyClassLoaderAttribute; ICustomAttributeBuilder hideFromJavaAttribute; ICustomAttributeBuilder hideFromReflection; IConstructorSymbol debuggableAttribute; -#if IMPORTER - - ITypeSymbol TypeOfModifiers => typeofModifiers ??= LoadType(typeof(Modifiers)); + ITypeSymbol TypeOfModifiers => typeofModifiers ??= context.Resolver.ResolveRuntimeType(typeof(Modifiers).FullName); - ITypeSymbol TypeOfSourceFileAttribute => typeofSourceFileAttribute ??= LoadType(typeof(IKVM.Attributes.SourceFileAttribute)); + ITypeSymbol TypeOfSourceFileAttribute => typeofSourceFileAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.SourceFileAttribute).FullName); - ITypeSymbol TypeOfLineNumberTableAttribute => typeofLineNumberTableAttribute ??= LoadType(typeof(IKVM.Attributes.LineNumberTableAttribute)); + ITypeSymbol TypeOfLineNumberTableAttribute => typeofLineNumberTableAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.LineNumberTableAttribute).FullName); -#endif - - ITypeSymbol TypeOfRemappedClassAttribute => typeofRemappedClassAttribute ??= LoadType(typeof(RemappedClassAttribute)); + ITypeSymbol TypeOfRemappedClassAttribute => typeofRemappedClassAttribute ??= context.Resolver.ResolveRuntimeType(typeof(RemappedClassAttribute).FullName); - ITypeSymbol TypeOfRemappedTypeAttribute => typeofRemappedTypeAttribute ??= LoadType(typeof(RemappedTypeAttribute)); + ITypeSymbol TypeOfRemappedTypeAttribute => typeofRemappedTypeAttribute ??= context.Resolver.ResolveRuntimeType(typeof(RemappedTypeAttribute).FullName); - ITypeSymbol TypeOfModifiersAttribute => typeofModifiersAttribute ??= LoadType(typeof(ModifiersAttribute)); + ITypeSymbol TypeOfModifiersAttribute => typeofModifiersAttribute ??= context.Resolver.ResolveRuntimeType(typeof(ModifiersAttribute).FullName); - ITypeSymbol TypeOfRemappedInterfaceMethodAttribute => typeofRemappedInterfaceMethodAttribute ??= LoadType(typeof(RemappedInterfaceMethodAttribute)); + ITypeSymbol TypeOfRemappedInterfaceMethodAttribute => typeofRemappedInterfaceMethodAttribute ??= context.Resolver.ResolveRuntimeType(typeof(RemappedInterfaceMethodAttribute).FullName); - ITypeSymbol TypeOfNameSigAttribute => typeofNameSigAttribute ??= LoadType(typeof(NameSigAttribute)); + ITypeSymbol TypeOfNameSigAttribute => typeofNameSigAttribute ??= context.Resolver.ResolveRuntimeType(typeof(NameSigAttribute).FullName); - ITypeSymbol TypeOfJavaModuleAttribute => typeofJavaModuleAttribute ??= LoadType(typeof(JavaModuleAttribute)); + ITypeSymbol TypeOfJavaModuleAttribute => typeofJavaModuleAttribute ??= context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName); - ITypeSymbol TypeOfSignatureAttribute => typeofSignatureAttribute ??= LoadType(typeof(IKVM.Attributes.SignatureAttribute)); + ITypeSymbol TypeOfSignatureAttribute => typeofSignatureAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.SignatureAttribute).FullName); - ITypeSymbol TypeOfInnerClassAttribute => typeofInnerClassAttribute ??= LoadType(typeof(InnerClassAttribute)); + ITypeSymbol TypeOfInnerClassAttribute => typeofInnerClassAttribute ??= context.Resolver.ResolveRuntimeType(typeof(InnerClassAttribute).FullName); - ITypeSymbol TypeOfImplementsAttribute => typeofImplementsAttribute ??= LoadType(typeof(ImplementsAttribute)); + ITypeSymbol TypeOfImplementsAttribute => typeofImplementsAttribute ??= context.Resolver.ResolveRuntimeType(typeof(ImplementsAttribute).FullName); - ITypeSymbol TypeOfGhostInterfaceAttribute => typeofGhostInterfaceAttribute ??= LoadType(typeof(GhostInterfaceAttribute)); + ITypeSymbol TypeOfGhostInterfaceAttribute => typeofGhostInterfaceAttribute ??= context.Resolver.ResolveRuntimeType(typeof(GhostInterfaceAttribute).FullName); - ITypeSymbol TypeOfExceptionIsUnsafeForMappingAttribute => typeofExceptionIsUnsafeForMappingAttribute ??= LoadType(typeof(ExceptionIsUnsafeForMappingAttribute)); + ITypeSymbol TypeOfExceptionIsUnsafeForMappingAttribute => typeofExceptionIsUnsafeForMappingAttribute ??= context.Resolver.ResolveRuntimeType(typeof(ExceptionIsUnsafeForMappingAttribute).FullName); - ITypeSymbol TypeOfThrowsAttribute => typeofThrowsAttribute ??= LoadType(typeof(ThrowsAttribute)); + ITypeSymbol TypeOfThrowsAttribute => typeofThrowsAttribute ??= context.Resolver.ResolveRuntimeType(typeof(ThrowsAttribute).FullName); - ITypeSymbol TypeOfHideFromJavaAttribute => typeofHideFromJavaAttribute ??= LoadType(typeof(HideFromJavaAttribute)); + ITypeSymbol TypeOfHideFromJavaAttribute => typeofHideFromJavaAttribute ??= context.Resolver.ResolveRuntimeType(typeof(HideFromJavaAttribute).FullName); - ITypeSymbol TypeOfHideFromJavaFlags => typeofHideFromJavaFlags ??= LoadType(typeof(HideFromJavaFlags)); + ITypeSymbol TypeOfHideFromJavaFlags => typeofHideFromJavaFlags ??= context.Resolver.ResolveRuntimeType(typeof(HideFromJavaFlags).FullName); - ITypeSymbol TypeOfNoPackagePrefixAttribute => typeofNoPackagePrefixAttribute ??= LoadType(typeof(NoPackagePrefixAttribute)); + ITypeSymbol TypeOfNoPackagePrefixAttribute => typeofNoPackagePrefixAttribute ??= context.Resolver.ResolveRuntimeType(typeof(NoPackagePrefixAttribute).FullName); - ITypeSymbol TypeOfAnnotationAttributeAttribute => typeofAnnotationAttributeAttribute ??= LoadType(typeof(AnnotationAttributeAttribute)); + ITypeSymbol TypeOfAnnotationAttributeAttribute => typeofAnnotationAttributeAttribute ??= context.Resolver.ResolveRuntimeType(typeof(AnnotationAttributeAttribute).FullName); - ITypeSymbol TypeOfNonNestedInnerClassAttribute => typeofNonNestedInnerClassAttribute ??= LoadType(typeof(NonNestedInnerClassAttribute)); + ITypeSymbol TypeOfNonNestedInnerClassAttribute => typeofNonNestedInnerClassAttribute ??= context.Resolver.ResolveRuntimeType(typeof(NonNestedInnerClassAttribute).FullName); - ITypeSymbol TypeOfNonNestedOuterClassAttribute => typeofNonNestedOuterClassAttribute ??= LoadType(typeof(NonNestedOuterClassAttribute)); + ITypeSymbol TypeOfNonNestedOuterClassAttribute => typeofNonNestedOuterClassAttribute ??= context.Resolver.ResolveRuntimeType(typeof(NonNestedOuterClassAttribute).FullName); - ITypeSymbol TypeOfEnclosingMethodAttribute => typeofEnclosingMethodAttribute ??= LoadType(typeof(IKVM.Attributes.EnclosingMethodAttribute)); + ITypeSymbol TypeOfEnclosingMethodAttribute => typeofEnclosingMethodAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.EnclosingMethodAttribute).FullName); - ITypeSymbol TypeOfMethodParametersAttribute => typeofMethodParametersAttribute ??= LoadType(typeof(IKVM.Attributes.MethodParametersAttribute)); + ITypeSymbol TypeOfMethodParametersAttribute => typeofMethodParametersAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.MethodParametersAttribute).FullName); - ITypeSymbol TypeOfRuntimeVisibleTypeAnnotationsAttribute => typeofRuntimeVisibleTypeAnnotationsAttribute ??= LoadType(typeof(IKVM.Attributes.RuntimeVisibleTypeAnnotationsAttribute)); + ITypeSymbol TypeOfRuntimeVisibleTypeAnnotationsAttribute => typeofRuntimeVisibleTypeAnnotationsAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.RuntimeVisibleTypeAnnotationsAttribute).FullName); - ITypeSymbol TypeOfConstantPoolAttribute => typeofConstantPoolAttribute ??= LoadType(typeof(ConstantPoolAttribute)); + ITypeSymbol TypeOfConstantPoolAttribute => typeofConstantPoolAttribute ??= context.Resolver.ResolveRuntimeType(typeof(ConstantPoolAttribute).FullName); ITypeSymbol TypeOfDebuggableAttribute => typeofDebuggableAttribute ??= context.Resolver.ResolveCoreType(typeof(DebuggableAttribute).FullName); + ITypeSymbol TypeOfCustomAssemblyClassLoaderAttribute => typeofCustomAssemblyClassLoaderAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.CustomAssemblyClassLoaderAttribute).FullName); + ICustomAttributeBuilder HideFromJavaAttributeBuilder => hideFromJavaAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([]), []); ICustomAttributeBuilder HideFromReflectionBuilder => hideFromReflection ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [HideFromJavaFlags.Reflection | HideFromJavaFlags.StackTrace | HideFromJavaFlags.StackWalk]); - /// - /// Loads the given managed type from the runtime assembly. - /// - /// - /// - ITypeSymbol LoadType(System.Type t) - { - return context.Resolver.ResolveRuntimeType(t.FullName); - } - /// /// Initializes a new instance. /// @@ -320,7 +301,7 @@ ICustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.To GetAttributeArgsAndTypes(loader, attr, out var argTypes, out var args); if (attr.Type != null) { - var t = context.Resolver.ResolveCoreType(attr.Type); + var t = context.Resolver.ResolveType(attr.Type); var ci = t.GetConstructor(argTypes); if (ci == null) throw new InvalidOperationException($"Constructor missing: {attr.Type}::{attr.Sig}"); @@ -404,13 +385,13 @@ ICustomAttributeBuilder GetEditorBrowsableNever() internal void SetCompilerGenerated(ITypeSymbolBuilder tb) { - compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); + compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); tb.SetCustomAttribute(compilerGeneratedAttribute); } - internal void SetCompilerGenerated(IMethodSymbolBuilder mb) + internal void SetCompilerGenerated(IMethodBaseSymbolBuilder mb) { - compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); + compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); mb.SetCustomAttribute(compilerGeneratedAttribute); } @@ -419,12 +400,7 @@ internal void SetEditorBrowsableNever(ITypeSymbolBuilder tb) tb.SetCustomAttribute(GetEditorBrowsableNever()); } - internal void SetEditorBrowsableNever(IConstructorSymbolBuilder mb) - { - mb.SetCustomAttribute(GetEditorBrowsableNever()); - } - - internal void SetEditorBrowsableNever(IMethodSymbolBuilder mb) + internal void SetEditorBrowsableNever(IMethodBaseSymbolBuilder mb) { mb.SetCustomAttribute(GetEditorBrowsableNever()); } @@ -434,7 +410,7 @@ internal void SetEditorBrowsableNever(IPropertySymbolBuilder pb) pb.SetCustomAttribute(GetEditorBrowsableNever()); } - internal void SetDeprecatedAttribute(IMethodSymbolBuilder mb) + internal void SetDeprecatedAttribute(IMethodBaseSymbolBuilder mb) { deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); mb.SetCustomAttribute(deprecatedAttribute); @@ -458,17 +434,7 @@ internal void SetDeprecatedAttribute(IPropertySymbolBuilder pb) pb.SetCustomAttribute(deprecatedAttribute); } - internal void SetThrowsAttribute(IConstructorSymbolBuilder mb, string[] exceptions) - { - if (exceptions != null && exceptions.Length != 0) - { - throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); - exceptions = UnicodeUtil.EscapeInvalidSurrogates(exceptions); - mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(throwsAttribute, [exceptions])); - } - } - - internal void SetThrowsAttribute(IMethodSymbolBuilder mb, string[] exceptions) + internal void SetThrowsAttribute(IMethodBaseSymbolBuilder mb, string[] exceptions) { if (exceptions != null && exceptions.Length != 0) { @@ -498,7 +464,7 @@ internal void SetNonNestedOuterClass(ITypeSymbolBuilder typeBuilder, string clas #endif // IMPORTER - internal void HideFromReflection(IMethodSymbolBuilder mb) + internal void HideFromReflection(IMethodBaseSymbolBuilder mb) { mb.SetCustomAttribute(HideFromReflectionBuilder); } @@ -518,17 +484,12 @@ internal void HideFromJava(ITypeSymbolBuilder typeBuilder) typeBuilder.SetCustomAttribute(HideFromJavaAttributeBuilder); } - internal void HideFromJava(IConstructorSymbolBuilder ctor) + internal void HideFromJava(IMethodBaseSymbolBuilder ctor) { ctor.SetCustomAttribute(HideFromJavaAttributeBuilder); } - internal void HideFromJava(IMethodSymbolBuilder mb) - { - mb.SetCustomAttribute(HideFromJavaAttributeBuilder); - } - - internal void HideFromJava(IMethodSymbolBuilder mb, HideFromJavaFlags flags) + internal void HideFromJava(IMethodBaseSymbolBuilder mb, HideFromJavaFlags flags) { mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [flags])); } @@ -538,15 +499,11 @@ internal void HideFromJava(IFieldSymbolBuilder fb) fb.SetCustomAttribute(HideFromJavaAttributeBuilder); } -#if IMPORTER - internal void HideFromJava(IPropertySymbolBuilder pb) { pb.SetCustomAttribute(HideFromJavaAttributeBuilder); } -#endif - internal bool IsHideFromJava(ITypeSymbol type) { return type.IsDefined(TypeOfHideFromJavaAttribute, false) || (type.IsNested && (type.DeclaringType.IsDefined(TypeOfHideFromJavaAttribute, false) || type.Name.StartsWith("__<", StringComparison.Ordinal))); @@ -584,8 +541,6 @@ internal HideFromJavaFlags GetHideFromJavaFlags(IMemberSymbol mi) return HideFromJavaFlags.None; } -#if IMPORTER - internal void SetImplementsAttribute(ITypeSymbolBuilder typeBuilder, RuntimeJavaType[] ifaceWrappers) { var interfaces = new string[ifaceWrappers.Length]; @@ -598,8 +553,6 @@ internal void SetImplementsAttribute(ITypeSymbolBuilder typeBuilder, RuntimeJava typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(implementsAttribute, [interfaces])); } -#endif - internal bool IsGhostInterface(ITypeSymbol type) { return type.IsDefined(TypeOfGhostInterfaceAttribute, false); @@ -749,18 +702,7 @@ internal void SetDebuggingModes(IAssemblySymbolBuilder assemblyBuilder, Debuggab #if IMPORTER - internal void SetModifiers(IConstructorSymbolBuilder cb, Modifiers modifiers, bool isInternal) - { - ICustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); - else - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); - - cb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetModifiers(IMethodSymbolBuilder mb, Modifiers modifiers, bool isInternal) + internal void SetModifiers(IMethodBaseSymbolBuilder mb, Modifiers modifiers, bool isInternal) { ICustomAttributeBuilder customAttributeBuilder; if (isInternal) @@ -804,7 +746,7 @@ internal void SetModifiers(ITypeSymbolBuilder tb, Modifiers modifiers, bool isIn tb.SetCustomAttribute(customAttributeBuilder); } - internal void SetNameSig(IMethodSymbolBuilder mb, string name, string sig) + internal void SetNameSig(IMethodBaseSymbolBuilder mb, string name, string sig) { var customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfNameSigAttribute.GetConstructor([context.Types.String, context.Types.String]), [UnicodeUtil.EscapeInvalidSurrogates(name), UnicodeUtil.EscapeInvalidSurrogates(sig)]); mb.SetCustomAttribute(customAttributeBuilder); @@ -831,7 +773,7 @@ internal void SetSourceFile(IModuleSymbolBuilder moduleBuilder, string filename) moduleBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(sourceFileAttribute, [filename])); } - internal void SetLineNumberTable(IMethodSymbolBuilder mb, IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter writer) + internal void SetLineNumberTable(IMethodBaseSymbolBuilder mb, IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter writer) { object arg; IConstructorSymbol con; @@ -869,13 +811,13 @@ internal void SetSignatureAttribute(IFieldSymbolBuilder fb, string signature) fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } - internal void SetSignatureAttribute(IMethodSymbolBuilder mb, string signature) + internal void SetSignatureAttribute(IMethodBaseSymbolBuilder mb, string signature) { signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } - internal void SetMethodParametersAttribute(IMethodSymbolBuilder mb, Modifiers[] modifiers) + internal void SetMethodParametersAttribute(IMethodBaseSymbolBuilder mb, Modifiers[] modifiers) { methodParametersAttribute ??= TypeOfMethodParametersAttribute.GetConstructor([TypeOfModifiers.MakeArrayType()]); mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(methodParametersAttribute, [modifiers])); @@ -901,7 +843,7 @@ internal void SetRuntimeVisibleTypeAnnotationsAttribute(IFieldSymbolBuilder fb, fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); } - internal void SetRuntimeVisibleTypeAnnotationsAttribute(IMethodSymbolBuilder mb, ref readonly TypeAnnotationTable table) + internal void SetRuntimeVisibleTypeAnnotationsAttribute(IMethodBaseSymbolBuilder mb, ref readonly TypeAnnotationTable table) { var builder = new BlobBuilder(); var encoder = new TypeAnnotationTableEncoder(builder); @@ -1080,9 +1022,9 @@ internal string GetAnnotationAttributeType(ITypeSymbol type) return null; } - internal System.Reflection.AssemblyName[] GetInternalsVisibleToAttributes(IAssemblySymbol assembly) + internal AssemblyNameInfo[] GetInternalsVisibleToAttributes(IAssemblySymbol assembly) { - var list = new List(); + var list = new List(); foreach (var cad in assembly.GetCustomAttributes()) { @@ -1090,7 +1032,7 @@ internal System.Reflection.AssemblyName[] GetInternalsVisibleToAttributes(IAssem { try { - list.Add(new System.Reflection.AssemblyName((string)cad.ConstructorArguments[0].Value)); + list.Add(new AssemblyName((string)cad.ConstructorArguments[0].Value).Pack()); } catch { @@ -1141,8 +1083,6 @@ internal IKVM.Attributes.EnclosingMethodAttribute GetEnclosingMethodAttribute(IT return null; } -#if IMPORTER - internal void SetRemappedClass(IAssemblySymbolBuilder assemblyBuilder, string name, ITypeSymbol shadowType) { var remappedClassAttribute = TypeOfRemappedClassAttribute.GetConstructor([context.Types.String, context.Types.Type]); @@ -1167,8 +1107,6 @@ internal void SetExceptionIsUnsafeForMapping(ITypeSymbolBuilder typeBuilder) typeBuilder.SetCustomAttribute(cab); } -#endif - internal void SetRuntimeCompatibilityAttribute(IAssemblySymbolBuilder assemblyBuilder) { var runtimeCompatibilityAttribute = context.Resolver.ResolveCoreType(typeof(RuntimeCompatibilityAttribute).FullName); @@ -1182,6 +1120,12 @@ internal void SetInternalsVisibleToAttribute(IAssemblySymbolBuilder assemblyBuil assemblyBuilder.SetCustomAttribute(cab); } + internal void SetCustomAssemblyClassLoaderAttribute(IAssemblySymbolBuilder assemblyBuilder, ITypeSymbol classLoaderType) + { + var cab = context.Resolver.Symbols.CreateCustomAttribute(TypeOfCustomAssemblyClassLoaderAttribute.GetConstructor([context.Types.Type]), [classLoaderType]); + assemblyBuilder.SetCustomAttribute(cab); + } + } } diff --git a/src/IKVM.Runtime/Attributes/CustomAssemblyClassLoaderAttribute.cs b/src/IKVM.Runtime/Attributes/CustomAssemblyClassLoaderAttribute.cs index 3ae59ca9b2..9cd806a030 100644 --- a/src/IKVM.Runtime/Attributes/CustomAssemblyClassLoaderAttribute.cs +++ b/src/IKVM.Runtime/Attributes/CustomAssemblyClassLoaderAttribute.cs @@ -23,10 +23,6 @@ Jeroen Frijters */ using System; -#if IMPORTER || EXPORTER -using Type = IKVM.Reflection.Type; -#endif - namespace IKVM.Attributes { diff --git a/src/IKVM.Runtime/ByteCodeHelper.cs b/src/IKVM.Runtime/ByteCodeHelper.cs index 43f3be833b..337d16c351 100644 --- a/src/IKVM.Runtime/ByteCodeHelper.cs +++ b/src/IKVM.Runtime/ByteCodeHelper.cs @@ -27,13 +27,13 @@ Jeroen Frijters using System.Threading; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Symbols; using IKVM.Attributes; using IKVM.ByteCode; #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; -using IKVM.Tools.Importer; using Type = IKVM.Reflection.Type; #else @@ -44,6 +44,7 @@ Jeroen Frijters using IKVM.Java.Externs.java.lang.invoke; using IKVM.Runtime.Accessors.Java.Lang; +using IKVM.CoreLib.Reflection; #endif @@ -99,7 +100,7 @@ public static object multianewarray_ghost(RuntimeTypeHandle typeHandle, int[] le { var type = Type.GetTypeFromHandle(typeHandle); int rank = 0; - while (ReflectUtil.IsVector(type)) + while (type.IsSZArray()) { rank++; type = type.GetElementType(); @@ -127,7 +128,7 @@ public static object DynamicMultianewarray(int[] lengths, global::java.lang.Clas Profiler.Count("DynamicMultianewarray"); var wrapper = RuntimeJavaType.FromClass(clazz); - var obj = multianewarray(wrapper.TypeAsArrayType.TypeHandle, lengths); + var obj = multianewarray(wrapper.TypeAsArrayType.AsReflection().TypeHandle, lengths); if (wrapper.IsGhostArray) GhostTag.SetTag(obj, wrapper); @@ -146,7 +147,7 @@ public static object DynamicNewarray(int length, global::java.lang.Class clazz) throw new global::java.lang.NegativeArraySizeException(); var wrapper = RuntimeJavaType.FromClass(clazz); - var obj = Array.CreateInstance(wrapper.TypeAsArrayType, length); + var obj = Array.CreateInstance(wrapper.TypeAsArrayType.AsReflection(), length); if (wrapper.IsGhost || wrapper.IsGhostArray) GhostTag.SetTag(obj, wrapper.MakeArrayType(1)); @@ -573,8 +574,8 @@ public static void arraycopy(object src, int srcStart, object dest, int destStar } else { - object[] src1 = src as object[]; - object[] dst1 = dest as object[]; + var src1 = src as object[]; + var dst1 = dest as object[]; if (src1 != null && dst1 != null) { // for small copies, don't bother comparing the types as this is relatively expensive @@ -594,8 +595,7 @@ public static void arraycopy(object src, int srcStart, object dest, int destStar return; } } - else if (src.GetType() != dest.GetType() && - (IsPrimitiveArrayType(src.GetType()) || IsPrimitiveArrayType(dest.GetType()))) + else if (src.GetType() != dest.GetType() && (IsPrimitiveArrayType(src.GetType()) || IsPrimitiveArrayType(dest.GetType()))) { // we don't want to allow copying a primitive into an object array! throw new global::java.lang.ArrayStoreException(); @@ -616,7 +616,7 @@ public static void arraycopy(object src, int srcStart, object dest, int destStar #endif // !FIRST_PASS } - private static bool IsPrimitiveArrayType(Type type) + private static bool IsPrimitiveArrayType(ITypeSymbol type) { #if FIRST_PASS throw new NotImplementedException(); @@ -625,6 +625,15 @@ private static bool IsPrimitiveArrayType(Type type) #endif } + private static bool IsPrimitiveArrayType(Type type) + { +#if FIRST_PASS + throw new NotImplementedException(); +#else + return type.IsArray && IsPrimitiveArrayType(JVM.Context.Resolver.ImportType(type.GetElementType())); +#endif + } + [DebuggerStepThroughAttribute] public static void arraycopy_fast(Array src, int srcStart, Array dest, int destStart, int len) { @@ -1040,7 +1049,7 @@ public static void InitializeModule(Module module) throw new ArgumentOutOfRangeException(); // check for InitializeModule method present on classloader - var classLoader = JVM.Context.AssemblyClassLoaderFactory.FromAssembly(asm).GetJavaClassLoader(); + var classLoader = JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.ImportAssembly(asm)).GetJavaClassLoader(); if (classLoader != null) { var init = (Action)Delegate.CreateDelegate(typeof(Action), classLoader, "InitializeModule", false, false); @@ -1098,8 +1107,8 @@ public static Exception DynamicMapException(Exception x, MapFlags mode, global:: if (exceptionTypeWrapper.IsSubTypeOf(JVM.Context.JavaBase.TypeOfCliSystemException)) mode |= MapFlags.NoRemapping; - var exceptionType = exceptionTypeWrapper == JVM.Context.JavaBase.TypeOfjavaLangThrowable ? typeof(System.Exception) : exceptionTypeWrapper.TypeAsBaseType; - return (Exception)JVM.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(exceptionType).Invoke(null, new object[] { x, mode }); + var exceptionType = exceptionTypeWrapper == JVM.Context.JavaBase.TypeOfjavaLangThrowable ? JVM.Context.Resolver.ResolveCoreType(typeof(System.Exception).FullName) : exceptionTypeWrapper.TypeAsBaseType; + return (Exception)JVM.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(exceptionType).AsReflection().Invoke(null, [x, mode]); #endif } diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index 59f1fde78b..1df5466c44 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -61,11 +61,11 @@ public CodeEmitterFactory(RuntimeContext context) public IMethodSymbol VerboseCastFailureMethod => verboseCastFailure ??= JVM.SafeGetEnvironmentVariable("IKVM_VERBOSE_CAST") == null ? null : context.ByteCodeHelperMethods.VerboseCastFailure; - public IMethodSymbol MonitorEnterMethod => monitorEnter ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); + public IMethodSymbol MonitorEnterMethod => monitorEnter ??= context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); - public IMethodSymbol MonitorExitMethod => monitorExit ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); + public IMethodSymbol MonitorExitMethod => monitorExit ??= context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); - public IMethodSymbol MemoryBarrierMethod => memoryBarrier ??= context.Resolver.ResolveCoreType(typeof(System.Threading.Thread).FullName).GetMethod("MemoryBarrier", []); + public IMethodSymbol MemoryBarrierMethod => memoryBarrier ??= context.Resolver.ResolveType(typeof(System.Threading.Thread).FullName).GetMethod("MemoryBarrier", []); public bool ExperimentalOptimizations = JVM.SafeGetEnvironmentVariable("IKVM_EXPERIMENTAL_OPTIMIZATIONS") != null; @@ -74,21 +74,11 @@ public CodeEmitterFactory(RuntimeContext context) /// /// /// - public CodeEmitter Create(IMethodSymbolBuilder method) + public CodeEmitter Create(IMethodBaseSymbolBuilder method) { return new CodeEmitter(context, method.GetILGenerator(), method.DeclaringType); } - /// - /// Creates a new instance. - /// - /// - /// - public CodeEmitter Create(IConstructorSymbolBuilder ctor) - { - return new CodeEmitter(context, ctor.GetILGenerator(), ctor.DeclaringType); - } - #if IMPORTER == false /// @@ -338,10 +328,9 @@ private void RealEmitPseudoOpCode(int ilOffset, CodeType type, object data) break; case CodeType.SequencePoint: // MarkSequencePoint does not exist in Core, but does exist in Framework and IKVM.Reflection -#if NETFRAMEWORK || IMPORTER if (symbols != null) ilgen_real.MarkSequencePoint(symbols, (int)data, 0, (int)data + 1, 0); -#endif + // we emit a nop to make sure we always have an instruction associated with the sequence point ilgen_real.Emit(System.Reflection.Emit.OpCodes.Nop); break; @@ -2431,7 +2420,7 @@ internal byte[] GetLineNumberTable() #if IMPORTER - internal void EmitLineNumberTable(IMethodSymbolBuilder mb) + internal void EmitLineNumberTable(IMethodBaseSymbolBuilder mb) { if (linenums != null) context.AttributeHelper.SetLineNumberTable(mb, linenums); diff --git a/src/IKVM.Runtime/DefineMethodHelper.cs b/src/IKVM.Runtime/DefineMethodHelper.cs index d6e041c684..78a4731442 100644 --- a/src/IKVM.Runtime/DefineMethodHelper.cs +++ b/src/IKVM.Runtime/DefineMethodHelper.cs @@ -72,21 +72,23 @@ internal IMethodSymbolBuilder DefineMethod(RuntimeJavaTypeFactory context, IType var parameters = mw.GetParameters(); var parameterTypes = new ITypeSymbol[parameters.Length + (mw.HasCallerID ? 1 : 0) + firstParam]; var modopt = new ITypeSymbol[parameterTypes.Length][]; + if (firstParameter != null) { parameterTypes[0] = firstParameter; modopt[0] = []; } + for (int i = 0; i < parameters.Length; i++) { - parameterTypes[i + firstParam] = mustBePublic - ? parameters[i].TypeAsPublicSignatureType - : parameters[i].TypeAsSignatureType; + parameterTypes[i + firstParam] = mustBePublic ? parameters[i].TypeAsPublicSignatureType : parameters[i].TypeAsSignatureType; modopt[i + firstParam] = RuntimeByteCodeJavaType.GetModOpt(context, parameters[i], mustBePublic); } + if (mw.HasCallerID) { parameterTypes[parameterTypes.Length - 1] = mw.DeclaringType.Context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType; + modopt[parameterTypes.Length - 1] = []; } var returnType = mustBePublic ? mw.ReturnType.TypeAsPublicSignatureType : mw.ReturnType.TypeAsSignatureType; @@ -94,14 +96,35 @@ internal IMethodSymbolBuilder DefineMethod(RuntimeJavaTypeFactory context, IType return tb.DefineMethod(name, attribs, System.Reflection.CallingConventions.Standard, returnType, null, modoptReturnType, parameterTypes, null, modopt); } - internal IMethodSymbolBuilder DefineConstructor(RuntimeByteCodeJavaType context, ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs) + internal IConstructorSymbolBuilder DefineConstructor(RuntimeByteCodeJavaType context, ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs) { - return DefineConstructor(context.ClassLoader.GetTypeWrapperFactory(), tb, attribs); + return DefineConstructor(context.ClassLoader.GetTypeWrapperFactory(), tb, attribs, false); } - internal IMethodSymbolBuilder DefineConstructor(RuntimeJavaTypeFactory context, ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs) + internal IConstructorSymbolBuilder DefineConstructor(RuntimeJavaTypeFactory context, ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs) { - return DefineMethod(context, tb, ConstructorInfo.ConstructorName, attribs | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName); + return DefineConstructor(context, tb, attribs, false); + } + + internal IConstructorSymbolBuilder DefineConstructor(RuntimeJavaTypeFactory context, ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs, bool mustBePublic) + { + // we add optional modifiers to make the signature unique + var parameters = mw.GetParameters(); + var parameterTypes = new ITypeSymbol[parameters.Length + (mw.HasCallerID ? 1 : 0)]; + var modopt = new ITypeSymbol[parameterTypes.Length][]; + for (int i = 0; i < parameters.Length; i++) + { + parameterTypes[i] = mustBePublic ? parameters[i].TypeAsPublicSignatureType : parameters[i].TypeAsSignatureType; + modopt[i] = RuntimeByteCodeJavaType.GetModOpt(context, parameters[i], mustBePublic); + } + + if (mw.HasCallerID) + { + parameterTypes[parameterTypes.Length - 1] = mw.DeclaringType.Context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType; + modopt[parameterTypes.Length - 1] = []; + } + + return tb.DefineConstructor(attribs, System.Reflection.CallingConventions.Standard, parameterTypes, null, modopt); } } diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index 8a82599a4e..dff4b46568 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -32,6 +32,8 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; using static System.Diagnostics.DebuggableAttribute; +using System.Collections.Immutable; + #if IMPORTER using IKVM.Reflection; @@ -137,10 +139,12 @@ public DynamicClassLoader GetOrCreate(RuntimeClassLoader loader) { if (attr.AssemblyName == name) { - var n = new AssemblyName(name); + byte[] kp = []; #if NETFRAMEWORK - n.KeyPair = DynamicClassLoader.ForgedKeyPair.Instance; + kp = DynamicClassLoader.ForgedKeyPair.Instance.PublicKey; #endif + + var n = new AssemblyNameInfo(name, publicKeyOrToken: kp.ToImmutableArray()); return new DynamicClassLoader(context, loader.Diagnostics, DynamicClassLoader.CreateModuleBuilder(context, n), true); } } @@ -442,8 +446,7 @@ internal void FinishAll() internal static IModuleSymbolBuilder CreateJniProxyModuleBuilder(RuntimeContext context) { - var name = new AssemblyName("jniproxy"); - jniProxyAssemblyBuilder = DefineDynamicAssembly(context, name, AssemblyBuilderAccess.Run, null); + jniProxyAssemblyBuilder = DefineDynamicAssembly(context, new AssemblyNameInfo("jniproxy"), null); return jniProxyAssemblyBuilder.DefineModule("jniproxy.dll"); } @@ -515,24 +518,21 @@ private static SerializationInfo ToInfo(byte[] publicKey) public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context) { - AssemblyName name = new AssemblyName(); - name.Name = "ikvm_dynamic_assembly__" + (uint)Environment.TickCount; - return CreateModuleBuilder(context, name); + return CreateModuleBuilder(context, new AssemblyNameInfo("ikvm_dynamic_assembly__" + (uint)Environment.TickCount)); } - public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, AssemblyName name) + public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, AssemblyNameInfo name) { var now = DateTime.Now; - name.Version = new Version(now.Year, (now.Month * 100) + now.Day, (now.Hour * 100) + now.Minute, (now.Second * 1000) + now.Millisecond); + name = new AssemblyNameInfo(name.Name, new Version(now.Year, (now.Month * 100) + now.Day, (now.Hour * 100) + now.Minute, (now.Second * 1000) + now.Millisecond)); var attribs = new List(); - var access = AssemblyBuilderAccess.Run; #if NETFRAMEWORK if (!AppDomain.CurrentDomain.IsFullyTrusted) attribs.Add(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(System.Security.SecurityTransparentAttribute).FullName).GetConstructor([]), [])); #endif - var assemblyBuilder = DefineDynamicAssembly(context, name, access, attribs.ToArray()); + var assemblyBuilder = DefineDynamicAssembly(context, name, attribs.ToArray()); context.AttributeHelper.SetRuntimeCompatibilityAttribute(assemblyBuilder); // determine debugging mode @@ -548,9 +548,9 @@ public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, A return moduleBuilder; } - static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyName name, AssemblyBuilderAccess access, ICustomAttributeBuilder[] assemblyAttributes) + static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyNameInfo name, ICustomAttributeBuilder[] assemblyAttributes) { - return context.Resolver.Symbols.DefineAssembly(name, access, assemblyAttributes); + return context.Resolver.Symbols.DefineAssembly(name, assemblyAttributes); } #endif diff --git a/src/IKVM.Runtime/DynamicMethodUtil.cs b/src/IKVM.Runtime/DynamicMethodUtil.cs index 81cde41b18..aa19721171 100644 --- a/src/IKVM.Runtime/DynamicMethodUtil.cs +++ b/src/IKVM.Runtime/DynamicMethodUtil.cs @@ -87,7 +87,7 @@ static DynamicMethod CreateFramework(string name, Type owner, bool nonPublic, Ty /// static DynamicMethod CreateCore(string name, Type owner, bool nonPublic, Type returnType, Type[] paramTypes) { - if (ReflectUtil.CanOwnDynamicMethod(owner)) + if (ReflectUtil.CanOwnDynamicMethod(owner)) return new DynamicMethod(name, returnType, paramTypes, owner); else return new DynamicMethod(name, MethodAttributes.Public | MethodAttributes.Static, CallingConventions.Standard, returnType, paramTypes, owner.Module, true); diff --git a/src/IKVM.Runtime/ExceptionHelper.cs b/src/IKVM.Runtime/ExceptionHelper.cs index d9151e11a4..20ab5b79a4 100644 --- a/src/IKVM.Runtime/ExceptionHelper.cs +++ b/src/IKVM.Runtime/ExceptionHelper.cs @@ -381,7 +381,7 @@ int GetLineNumber(StackFrame frame) var mb = frame.GetMethod(); if (mb != null && mb.DeclaringType != null) { - var mbs = context.Resolver.ResolveMethodBase(mb); + var mbs = context.Resolver.ImportMethodBase(mb); if (context.ClassLoaderFactory.IsRemappedType(mbs.DeclaringType)) return -1; @@ -399,7 +399,7 @@ string GetFileName(StackFrame frame) var mb = frame.GetMethod(); if (mb != null && mb.DeclaringType != null) { - var mbs = context.Resolver.ResolveMethodBase(mb); + var mbs = context.Resolver.ImportMethodBase(mb); if (context.ClassLoaderFactory.IsRemappedType(mbs.DeclaringType)) return null; diff --git a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs index 6c48e74ad5..c3ae1c1767 100644 --- a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs +++ b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs @@ -29,68 +29,94 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// ISymbolContext Symbols { get; } + /// + /// Gets the known runtime assembly. + /// + /// + IAssemblySymbol ResolveRuntimeAssembly(); + + /// + /// Resolves the named type from the IKVM runtime assembly. + /// + /// + /// + ITypeSymbol ResolveRuntimeType(string typeName); + + /// + /// Resolves the known Java base assembly. + /// + /// + IAssemblySymbol ResolveBaseAssembly(); + + /// + /// Resolves the named type from the IKVM Java assembly. + /// + /// + /// + ITypeSymbol ResolveBaseType(string typeName); + /// /// Gets the associated with the specified assembly. /// /// /// - IAssemblySymbol? ResolveAssembly(Assembly? assembly); + IAssemblySymbol ImportAssembly(Assembly assembly); /// /// Gets the associated with the specified assembly. /// /// /// - IAssemblySymbolBuilder? ResolveAssembly(AssemblyBuilder? assembly); + IAssemblySymbolBuilder?ImportAssembly(AssemblyBuilder assembly); /// /// Gets the associated with the specified module. /// /// /// - IModuleSymbol? ResolveModule(Module? module); + IModuleSymbol ImportModule(Module module); /// /// Gets the associated with the specified module. /// /// /// - IModuleSymbolBuilder? ResolveModule(ModuleBuilder? module); + IModuleSymbolBuilder ImportModule(ModuleBuilder module); /// /// Gets the associated with the specified type. /// /// /// - ITypeSymbol? ResolveType(Type? type); + ITypeSymbol ImportType(Type type); /// /// Gets the associated with the specified member. /// /// /// - IMemberSymbol? ResolveMember(MemberInfo? memberInfo); + IMemberSymbol ImportMember(MemberInfo memberInfo); /// /// Gets the associated with the specified method. /// /// /// - IMethodBaseSymbol? ResolveMethodBase(MethodBase? type); + IMethodBaseSymbol ImportMethodBase(MethodBase type); /// /// Gets the associated with the specified method. /// /// /// - IConstructorSymbol? ResolveConstructor(ConstructorInfo? ctor); + IConstructorSymbol ImportConstructor(ConstructorInfo ctor); /// /// Gets the associated with the specified method. /// /// /// - IMethodSymbol? ResolveMethod(MethodInfo? method); + IMethodSymbol ImportMethod(MethodInfo method); } diff --git a/src/IKVM.Runtime/JVM.Resolver.cs b/src/IKVM.Runtime/JVM.Resolver.cs index 18fc01b756..6174d0a9c2 100644 --- a/src/IKVM.Runtime/JVM.Resolver.cs +++ b/src/IKVM.Runtime/JVM.Resolver.cs @@ -92,7 +92,7 @@ public ITypeSymbol ResolveRuntimeType(string typeName) } /// - public ITypeSymbol ResolveType(Type type) + public ITypeSymbol ImportType(Type type) { return type is { } t ? _context.GetOrCreateTypeSymbol(t) : null; } diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs index 98f7c118a6..b8735c4d1d 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs @@ -50,7 +50,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, return ghostType; var t = o.GetType(); - var ts = context.Resolver.ResolveType(t); + var ts = context.Resolver.ImportType(t); if (t.IsPrimitive || context.ClassLoaderFactory.IsRemappedType(ts) && !ts.IsSealed) return context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts); @@ -73,7 +73,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, throw new NotImplementedException(); #else var t = Type.GetTypeFromHandle(handle); - var ts = JVM.Context.Resolver.ResolveType(t); + var ts = JVM.Context.Resolver.ImportType(t); if (t.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || t == typeof(void)) return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).ClassObject; @@ -94,7 +94,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, throw new NotImplementedException(); #else var t = Type.GetTypeFromHandle(handle); - var ts = JVM.Context.Resolver.ResolveType(t); + var ts = JVM.Context.Resolver.ImportType(t); if (ts.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || ts == typeof(void)) return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).MakeArrayType(rank).ClassObject; @@ -114,7 +114,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, #if FIRST_PASS throw new NotImplementedException(); #else - var ts = JVM.Context.Resolver.ResolveType(type); + var ts = JVM.Context.Resolver.ImportType(type); int rank = 0; while (ReflectUtil.IsVector(ts)) diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs index ea4d8fa576..cab514262d 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs @@ -72,7 +72,7 @@ static class Class var type = Type.GetType(name); if (type != null) - tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.ResolveType(type)); + tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.ImportType(type)); if (tw == null) { diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index 86868c4bb0..96cce87e57 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -26,6 +26,9 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; +using System.Collections.Immutable; + + #if IMPORTER || EXPORTER using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -116,29 +119,19 @@ internal static bool IsDynamicMethod(IMethodSymbol method) } } - internal static IMethodSymbolBuilder DefineTypeInitializer(ITypeSymbolBuilder typeBuilder, RuntimeClassLoader loader) + internal static IConstructorSymbolBuilder DefineTypeInitializer(ITypeSymbolBuilder typeBuilder, RuntimeClassLoader loader) { - var attr = System.Reflection.MethodAttributes.Static | System.Reflection.MethodAttributes.RTSpecialName | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.Private; - return typeBuilder.DefineMethod(ConstructorInfo.TypeConstructorName, attr, null, []); + return typeBuilder.DefineTypeInitializer(); } - internal static bool MatchNameAndPublicKeyToken(System.Reflection.AssemblyName name1, System.Reflection.AssemblyName name2) + internal static bool MatchNameAndPublicKeyToken(AssemblyNameInfo name1, AssemblyNameInfo name2) { - return name1.Name.Equals(name2.Name, StringComparison.OrdinalIgnoreCase) && CompareKeys(name1.GetPublicKeyToken(), name2.GetPublicKeyToken()); + return name1.Name.Equals(name2.Name, StringComparison.OrdinalIgnoreCase) && CompareKeys(name1.PublicKeyOrToken, name2.PublicKeyOrToken); } - static bool CompareKeys(byte[] b1, byte[] b2) + static bool CompareKeys(ImmutableArray b1, ImmutableArray b2) { - int len1 = b1 == null ? 0 : b1.Length; - int len2 = b2 == null ? 0 : b2.Length; - if (len1 != len2) - return false; - - for (int i = 0; i < len1; i++) - if (b1[i] != b2[i]) - return false; - - return true; + return b1.AsSpan().SequenceEqual(b2.AsSpan()); } internal static bool IsConstructor(IMethodBaseSymbol method) @@ -156,7 +149,7 @@ internal static IConstructorSymbolBuilder DefineConstructor(ITypeSymbolBuilder t /// /// /// - internal static bool CanOwnDynamicMethod(ITypeSymbol type) + internal static bool CanOwnDynamicMethod(Type type) { return type != null && !type.IsInterface && !type.HasElementType && !type.IsGenericTypeDefinition && !type.IsGenericParameter; } diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index e44241a4a3..9869a856ed 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -75,7 +75,7 @@ sealed class AssemblyLoader IModuleSymbol[] modules; Dictionary nameMap; bool hasDotNetModule; - System.Reflection.AssemblyName[] internalsVisibleTo; + AssemblyNameInfo[] internalsVisibleTo; string[] jarList; #if !IMPORTER && !EXPORTER && !FIRST_PASS sun.misc.URLClassPath urlClassPath; @@ -384,7 +384,7 @@ internal RuntimeJavaType CreateJavaTypeForAssemblyType(ITypeSymbol type) } } - internal bool InternalsVisibleTo(System.Reflection.AssemblyName otherName) + internal bool InternalsVisibleTo(AssemblyNameInfo otherName) { if (internalsVisibleTo == null) Interlocked.CompareExchange(ref internalsVisibleTo, loader.Context.AttributeHelper.GetInternalsVisibleToAttributes(assembly), null); @@ -394,9 +394,7 @@ internal bool InternalsVisibleTo(System.Reflection.AssemblyName otherName) // we match the simple name and PublicKeyToken (because the AssemblyName constructor used // by GetInternalsVisibleToAttributes() only sets the PublicKeyToken, even if a PublicKey is specified) if (ReflectUtil.MatchNameAndPublicKeyToken(name, otherName)) - { return true; - } } return false; @@ -1176,7 +1174,7 @@ Type GetCustomClassLoaderType() var attribs = assembly.GetCustomAttribute(Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName), false); if (attribs is not null) - return new CustomAssemblyClassLoaderAttribute((System.Type)attribs.Value.ConstructorArguments[0].Value); + return ((ITypeSymbol)attribs.Value.ConstructorArguments[0].Value).AsReflection(); return null; } @@ -1286,7 +1284,7 @@ sealed class CustomClassLoaderCtorCaller : java.security.PrivilegedAction readonly ConstructorInfo ctor; readonly object classLoader; - readonly Assembly assembly; + readonly IAssemblySymbol assembly; /// /// Initializes a new instance. @@ -1294,7 +1292,7 @@ sealed class CustomClassLoaderCtorCaller : java.security.PrivilegedAction /// /// /// - internal CustomClassLoaderCtorCaller(ConstructorInfo ctor, object classLoader, Assembly assembly) + internal CustomClassLoaderCtorCaller(ConstructorInfo ctor, object classLoader, IAssemblySymbol assembly) { this.ctor = ctor ?? throw new ArgumentNullException(nameof(ctor)); this.classLoader = classLoader ?? throw new ArgumentNullException(nameof(classLoader)); @@ -1303,7 +1301,7 @@ internal CustomClassLoaderCtorCaller(ConstructorInfo ctor, object classLoader, A public object run() { - ctor.Invoke(classLoader, new object[] { assembly }); + ctor.Invoke(classLoader, [assembly.AsReflection()]); return null; } } diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs index 5b50ef6619..c0b9bf7283 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs @@ -107,13 +107,12 @@ RuntimeAssemblyClassLoader Create(IAssemblySymbol assembly) return FromAssembly(mainAssembly); } - var baseAssembly = context.Resolver.ResolveBaseAssembly(); #if IMPORTER - if (baseAssembly != null && assembly.IsDefined(context.Resolver.ResolveRuntimeType("IKVM.Attributes.RemappedClassAttribute"), false)) + if (context.Options.Bootstrap == false && assembly.IsDefined(context.Resolver.ResolveRuntimeType("IKVM.Attributes.RemappedClassAttribute"), false)) context.ClassLoaderFactory.LoadRemappedTypes(); #endif - if (baseAssembly == assembly) + if (assembly.IsDefined(context.Resolver.ResolveRuntimeType("IKVM.Attributes.RemappedClassAttribute"), false)) { // This cast is necessary for ikvmc and a no-op for the runtime. // Note that the cast cannot fail, because ikvmc will only return a non AssemblyClassLoader diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index c884f801a6..6c26b41fc3 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -291,20 +291,19 @@ internal ITypeSymbol FinishImpl() #if IMPORTER ITypeSymbolBuilder tbDefaultMethods = null; #endif - bool basehasclinit = wrapper.BaseTypeWrapper != null && wrapper.BaseTypeWrapper.HasStaticInitializer; + var basehasclinit = wrapper.BaseTypeWrapper != null && wrapper.BaseTypeWrapper.HasStaticInitializer; int clinitIndex = -1; - bool hasConstructor = false; + var hasConstructor = false; for (int i = 0; i < classFile.Methods.Length; i++) { var m = classFile.Methods[i]; - var mb = (IMethodSymbolBuilder)methods[i].GetMethod(); + var mb = (IMethodBaseSymbolBuilder)methods[i].GetMethod(); if (mb == null) { // method doesn't really exist (e.g. delegate constructor or that is optimized away) if (m.IsConstructor) - { hasConstructor = true; - } + } else if (m.IsClassInitializer) { @@ -435,32 +434,27 @@ internal ITypeSymbol FinishImpl() if (field == null) { wrapper.Context.Diagnostics.GenericCompilerError($"Error: Native method field binding not found: {classFile.Name}.{param[j].Name}{fieldTypeWrapper.SigName}"); - wrapper.Context.StaticCompiler.errorCount++; continue; } if (m.IsStatic && !field.IsStatic) { wrapper.Context.Diagnostics.GenericCompilerError($"Error: Native method field binding cannot access instance field from static method: {classFile.Name}.{param[j].Name}{fieldTypeWrapper.SigName}"); - wrapper.Context.StaticCompiler.errorCount++; continue; } if (!field.IsAccessibleFrom(wrapper, wrapper, wrapper)) { wrapper.Context.Diagnostics.GenericCompilerError($"Error: Native method field binding not accessible: {classFile.Name}.{param[j].Name}{fieldTypeWrapper.SigName}"); - wrapper.Context.StaticCompiler.errorCount++; continue; } if (paramType.IsByRef && field.IsFinal) { wrapper.Context.Diagnostics.GenericCompilerError($"Error: Native method field binding cannot use ByRef for final field: {classFile.Name}.{param[j].Name}{fieldTypeWrapper.SigName}"); - wrapper.Context.StaticCompiler.errorCount++; continue; } field.Link(); if (paramType.IsByRef && field.GetField() == null) { wrapper.Context.Diagnostics.GenericCompilerError($"Error: Native method field binding cannot use ByRef on field without backing field: {classFile.Name}.{param[j].Name}{fieldTypeWrapper.SigName}"); - wrapper.Context.StaticCompiler.errorCount++; continue; } if (!field.IsStatic) @@ -509,9 +503,9 @@ internal ITypeSymbol FinishImpl() { if (m.IsVirtual && classFile.IsInterface) { - mb = (IMethodSymbolBuilder)RuntimeDefaultInterfaceJavaMethod.GetImpl(methods[i]); + mb = (IMethodBaseSymbolBuilder)RuntimeDefaultInterfaceJavaMethod.GetImpl(methods[i]); #if IMPORTER - CreateDefaultMethodInterop(ref tbDefaultMethods, mb, methods[i]); + CreateDefaultMethodInterop(ref tbDefaultMethods, (IMethodSymbolBuilder)mb, methods[i]); #endif } @@ -558,10 +552,10 @@ internal ITypeSymbol FinishImpl() if (clinitIndex != -1 || (basehasclinit && !classFile.IsInterface) || classFile.HasInitializedFields) { - IMethodSymbolBuilder cb; + IConstructorSymbolBuilder cb; if (clinitIndex != -1) { - cb = (IMethodSymbolBuilder)methods[clinitIndex].GetMethod(); + cb = (IConstructorSymbolBuilder)methods[clinitIndex].GetMethod(); } else { @@ -659,7 +653,7 @@ internal ITypeSymbol FinishImpl() for (int i = 0; i < classFile.Methods.Length; i++) { var m = classFile.Methods[i]; - var mb = (IMethodSymbolBuilder)methods[i].GetMethod(); + var mb = (IMethodBaseSymbolBuilder)methods[i].GetMethod(); if (mb == null) continue; @@ -672,7 +666,10 @@ internal ITypeSymbol FinishImpl() if (annotation != null) { annotation.Apply(wrapper.ClassLoader, mb, def); - annotation.ApplyReturnValue(wrapper.ClassLoader, mb, ref returnParameter, def); + + // constructors have no return value + if (mb is IMethodSymbolBuilder ms) + annotation.ApplyReturnValue(wrapper.ClassLoader, ms, ref returnParameter, def); } } } @@ -1001,7 +998,7 @@ private bool EmitInterlockedCompareAndSet(RuntimeJavaMethod method, string field } #endif - private void AddMethodParameterInfo(ClassFile.Method m, RuntimeJavaMethod mw, IMethodSymbolBuilder mb, out string[] parameterNames) + private void AddMethodParameterInfo(ClassFile.Method m, RuntimeJavaMethod mw, IMethodBaseSymbolBuilder mb, out string[] parameterNames) { parameterNames = null; IParameterSymbolBuilder[] parameterBuilders = null; @@ -1396,18 +1393,18 @@ void GenerateAccessStub(int id, RuntimeJavaMethod mw, bool virt, bool type1) var returnType = mw.ReturnType.TypeAsPublicSignatureType; var modoptReturnType = ArrayUtil.Concat(wrapper.GetModOpt(mw.ReturnType, true), context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.AccessStub).FullName)); - string name; + IMethodBaseSymbolBuilder mb; if (mw.Name == StringConstants.INIT) { - name = ConstructorInfo.ConstructorName; stubattribs |= MethodAttributes.SpecialName | MethodAttributes.RTSpecialName; + mb = typeBuilder.DefineConstructor(stubattribs, CallingConventions.Standard, parameterTypes, null, modopt); } else { - name = virt ? (mw.Modifiers & Modifiers.Bridge) == 0 ? mw.Name : NamePrefix.Bridge + mw.Name : NamePrefix.NonVirtual + id; + var name = virt ? (mw.Modifiers & Modifiers.Bridge) == 0 ? mw.Name : NamePrefix.Bridge + mw.Name : NamePrefix.NonVirtual + id; + mb = typeBuilder.DefineMethod(name, stubattribs, CallingConventions.Standard, returnType, null, modoptReturnType, parameterTypes, null, modopt); } - var mb = typeBuilder.DefineMethod(name, stubattribs, CallingConventions.Standard, returnType, null, modoptReturnType, parameterTypes, null, modopt); if (virt && type1) { context.AttributeHelper.HideFromReflection(mb); @@ -1664,11 +1661,11 @@ public JniBuilder(RuntimeContext context) IMethodSymbol UnwrapLocalRefMethod => LocalRefStructType.GetMethod("UnwrapLocalRef"); - IMethodSymbol WriteLineMethod => context.Resolver.ResolveCoreType(typeof(Console).FullName).GetMethod("WriteLine", [context.Types.Object]); + IMethodSymbol WriteLineMethod => context.Resolver.ResolveType(typeof(Console).FullName).GetMethod("WriteLine", [context.Types.Object]); - IMethodSymbol MonitorEnterMethod => context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", [context.Types.Object]); + IMethodSymbol MonitorEnterMethod => context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", [context.Types.Object]); - IMethodSymbol MonitorExitMethod => context.Resolver.ResolveCoreType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", [context.Types.Object]); + IMethodSymbol MonitorExitMethod => context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", [context.Types.Object]); internal void Generate(RuntimeByteCodeJavaType.FinishContext context, CodeEmitter ilGenerator, RuntimeByteCodeJavaType wrapper, RuntimeJavaMethod mw, ITypeSymbolBuilder typeBuilder, ClassFile classFile, ClassFile.Method m, RuntimeJavaType[] args, bool thruProxy) { @@ -1899,7 +1896,7 @@ void EmitCallerIDStub(RuntimeJavaMethod mw, string[] parameterNames) } ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.Emit(OpCodes.Ldc_I4_0); - ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveCoreType(typeof(StackFrame).FullName).GetConstructor(new ITypeSymbol[] { context.Types.Int32, context.Types.Boolean })); + ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveType(typeof(StackFrame).FullName).GetConstructor([context.Types.Int32, context.Types.Boolean])); var callerID = context.JavaBase.TypeOfIkvmInternalCallerID.GetMethodWrapper("create", "(Lcli.System.Diagnostics.StackFrame;)Likvm.internal.CallerID;", false); callerID.Link(); callerID.EmitCall(ilgen); @@ -2057,7 +2054,7 @@ void CompileConstructorBody(FinishContext context, CodeEmitter ilGenerator, int Compiler.Compile(context, host, wrapper, methods[methodIndex], classFile, m, ilGenerator, ref nonLeaf); ilGenerator.DoEmit(); #if IMPORTER - ilGenerator.EmitLineNumberTable((IMethodSymbolBuilder)methods[methodIndex].GetMethod()); + ilGenerator.EmitLineNumberTable((IMethodBaseSymbolBuilder)methods[methodIndex].GetMethod()); #else // IMPORTER var linenumbers = ilGenerator.GetLineNumberTable(); if (linenumbers != null) diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index 0f287ff2ce..ed378f2a18 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -1853,7 +1853,7 @@ internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, o tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodBaseSymbolBuilder mb, object annotation) { mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } @@ -2461,7 +2461,7 @@ internal override IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) } var m = classFile.Methods[index]; - IMethodSymbolBuilder method; + IMethodBaseSymbolBuilder method; bool setModifiers = false; if (methods[index].HasCallerID && (m.Modifiers & Modifiers.VarArgs) != 0) @@ -2567,7 +2567,7 @@ private bool HasSerialVersionUID } } - IMethodSymbolBuilder GenerateConstructor(RuntimeJavaMethod mw) + IConstructorSymbolBuilder GenerateConstructor(RuntimeJavaMethod mw) { return mw.GetDefineMethodHelper().DefineConstructor(wrapper, typeBuilder, GetMethodAccess(mw) | MethodAttributes.HideBySig); } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index 0375c0dfea..ea1dadac63 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -575,7 +575,7 @@ protected static void GetParameterNamesFromSig(string sig, string[] parameterNam parameterNames[i] = names[i]; } - protected static IParameterSymbolBuilder[] GetParameterBuilders(IMethodSymbolBuilder mb, int parameterCount, string[] parameterNames) + protected static IParameterSymbolBuilder[] GetParameterBuilders(IMethodBaseSymbolBuilder mb, int parameterCount, string[] parameterNames) { var parameterBuilders = new IParameterSymbolBuilder[parameterCount]; Dictionary clashes = null; @@ -909,7 +909,7 @@ internal static ITypeSymbol[] GetModOpt(RuntimeJavaTypeFactory context, RuntimeJ if (tw.IsUnloadable) { if (((RuntimeUnloadableJavaType)tw).MissingType == null) - modopt = new ITypeSymbol[] { ((RuntimeUnloadableJavaType)tw).GetCustomModifier(context) }; + modopt = [((RuntimeUnloadableJavaType)tw).GetCustomModifier(context)]; } else { @@ -920,11 +920,10 @@ internal static ITypeSymbol[] GetModOpt(RuntimeJavaTypeFactory context, RuntimeJ modopt = new ITypeSymbol[tw.ArrayRank + 1]; modopt[0] = GetModOptHelper(tw1); for (int i = 1; i < modopt.Length; i++) - { modopt[i] = tw.Context.Types.Array; - } } } + return modopt; } diff --git a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs index f47f336ec6..1625345a5c 100644 --- a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs @@ -100,14 +100,14 @@ internal void SetBootstrapClassLoader(RuntimeClassLoader bootstrapClassLoader) internal void LoadRemappedTypes() { // if we're compiling the base assembly, we won't be able to resolve one - var baseAssembly = context.Resolver.ResolveBaseAssembly(); - if (baseAssembly != null && remappedTypes.Count == 0) + if (context.Options.Bootstrap == false && remappedTypes.Count == 0) { + var baseAssembly = context.Resolver.ResolveBaseAssembly(); var remapped = context.AttributeHelper.GetRemappedClasses(baseAssembly); if (remapped.Length > 0) { foreach (var r in remapped) - remappedTypes.Add(context.Resolver.ResolveType(r.RemappedType), r.Name); + remappedTypes.Add(context.Resolver.ImportType(r.RemappedType), r.Name); } else { @@ -390,9 +390,9 @@ internal RuntimeClassLoader GetAssemblyClassLoaderByName(string name) return GetGenericClassLoaderByName(name); #if NETFRAMEWORK - return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveAssembly( Assembly.Load(name))); + return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ImportAssembly( Assembly.Load(name))); #else - return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveAssembly(AssemblyLoadContext.GetLoadContext(typeof(RuntimeClassLoader).Assembly).LoadFromAssemblyName(new AssemblyName(name)))); + return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ImportAssembly(AssemblyLoadContext.GetLoadContext(typeof(RuntimeClassLoader).Assembly).LoadFromAssemblyName(new AssemblyName(name)))); #endif } diff --git a/src/IKVM.Runtime/RuntimeContext.cs b/src/IKVM.Runtime/RuntimeContext.cs index ef2ec783b4..3568a86488 100644 --- a/src/IKVM.Runtime/RuntimeContext.cs +++ b/src/IKVM.Runtime/RuntimeContext.cs @@ -30,7 +30,6 @@ class RuntimeContext readonly RuntimeContextOptions options; readonly IDiagnosticHandler diagnostics; readonly IRuntimeSymbolResolver resolver; - readonly bool bootstrap; readonly ConcurrentDictionary singletons = new(); Types types; @@ -79,14 +78,12 @@ class RuntimeContext /// /// /// - /// /// - public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, IRuntimeSymbolResolver resolver, bool bootstrap, StaticCompiler staticCompiler) + public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, IRuntimeSymbolResolver resolver, StaticCompiler staticCompiler) { this.options = options ?? throw new ArgumentNullException(nameof(options)); this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); this.resolver = resolver ?? throw new ArgumentNullException(nameof(resolver)); - this.bootstrap = bootstrap; this.staticCompiler = staticCompiler; } @@ -98,13 +95,11 @@ public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnost /// /// /// - /// - public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, IRuntimeSymbolResolver resolver, bool bootstrap) + public RuntimeContext(RuntimeContextOptions options, IDiagnosticHandler diagnostics, IRuntimeSymbolResolver resolver) { this.options = options ?? throw new ArgumentNullException(nameof(options)); this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); this.resolver = resolver ?? throw new ArgumentNullException(nameof(resolver)); - this.bootstrap = bootstrap; } #endif @@ -147,12 +142,6 @@ T GetOrCreateSingleton(ref T value, Func create) /// Gets the associated with this instance of the runtime. /// public IRuntimeSymbolResolver Resolver => resolver; - - /// - /// Gets whether or not the runtime is running in bootstrap mode; that is, we are compiling the Java base assembly itself. - /// - public bool Bootstrap => bootstrap; - /// /// Gets the associated with this instance of the runtime. /// @@ -213,7 +202,7 @@ T GetOrCreateSingleton(ref T value, Func create) /// Gets the associated with this instance of the runtime. /// /// - public CompilerFactory CompilerFactory => GetOrCreateSingleton(ref compilerFactory, () => new CompilerFactory(this, bootstrap)); + public CompilerFactory CompilerFactory => GetOrCreateSingleton(ref compilerFactory, () => new CompilerFactory(this, options.Bootstrap)); /// /// Gets the associated with this instance of the runtime. diff --git a/src/IKVM.Runtime/RuntimeContextOptions.cs b/src/IKVM.Runtime/RuntimeContextOptions.cs index c89914b558..159bef8308 100644 --- a/src/IKVM.Runtime/RuntimeContextOptions.cs +++ b/src/IKVM.Runtime/RuntimeContextOptions.cs @@ -10,17 +10,25 @@ internal class RuntimeContextOptions internal const string DefaultDynamicAssemblySuffixAndPublicKey = "-ikvm-runtime-injected"; #endif + readonly bool bootstrap; readonly string dynamicAssemblySuffixAndPublicKey; /// /// Initializes a new instance. /// + /// /// - public RuntimeContextOptions(string dynamicAssemblySuffixAndPublicKey = null) + public RuntimeContextOptions(bool bootstrap = false, string dynamicAssemblySuffixAndPublicKey = null) { + this.bootstrap = bootstrap; this.dynamicAssemblySuffixAndPublicKey = dynamicAssemblySuffixAndPublicKey ?? DefaultDynamicAssemblySuffixAndPublicKey; } + /// + /// Gets whether or not bootstrap mode is enabled. + /// + public bool Bootstrap => bootstrap; + /// /// Gets the suffix and public key to add to dynamically generated assemblies. /// diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 4908a8d3eb..6fb940ce16 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -302,7 +302,7 @@ internal static RuntimeJavaType FromClass(java.lang.Class clazz) return FromClass(clazz); } - var symbol = JVM.Context.Resolver.ResolveType(type); + var symbol = JVM.Context.Resolver.ImportType(type); if (type == typeof(void) || type.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(symbol)) tw = JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(symbol); else diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs index ed369d2fe2..ca2fb0d06d 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs @@ -58,7 +58,7 @@ internal RemappedJavaType(RuntimeContext context, string name, ITypeSymbol type) base(context, name, type) { var attr = Context.AttributeHelper.GetRemappedType(type) ?? throw new InvalidOperationException(); - remappedType = Context.Resolver.ResolveType(attr.Type); + remappedType = Context.Resolver.ImportType(attr.Type); } internal override ITypeSymbol TypeAsTBD => remappedType; diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index c0cda24789..cce2864319 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -137,7 +137,7 @@ static RuntimeJavaType GetBaseTypeWrapper(RuntimeContext context, ITypeSymbol ty var attr = context.AttributeHelper.GetRemappedType(type); if (attr != null) { - if (context.Resolver.ResolveType(attr.Type) == context.Types.Object) + if (context.Resolver.ImportType(attr.Type) == context.Types.Object) return null; else return context.JavaBase.TypeOfJavaLangObject; @@ -1196,7 +1196,7 @@ internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, o tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodBaseSymbolBuilder mb, object annotation) { mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } @@ -1254,7 +1254,7 @@ internal override ITypeSymbol EnumType internal override string GetSourceFileName() { - var attr = type.GetCustomAttribute(Context.Resolver.ResolveType(typeof(SourceFileAttribute))); + var attr = type.GetCustomAttribute(Context.Resolver.ImportType(typeof(SourceFileAttribute))); if (attr != null && attr.Value.ConstructorArguments.Length > 0) return (string)attr.Value.ConstructorArguments[0].Value; @@ -1264,7 +1264,7 @@ internal override string GetSourceFileName() if (IsNestedTypeAnonymousOrLocalClass(type)) return Context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).GetSourceFileName(); - if (type.Module.IsDefined(Context.Resolver.ResolveType(typeof(SourceFileAttribute)), false)) + if (type.Module.IsDefined(Context.Resolver.ImportType(typeof(SourceFileAttribute)), false)) return type.Name + ".java"; return null; @@ -1272,7 +1272,7 @@ internal override string GetSourceFileName() internal override int GetSourceLineNumber(IMethodBaseSymbol mb, int ilOffset) { - var attr = type.GetCustomAttribute(Context.Resolver.ResolveType(typeof(LineNumberTableAttribute))); + var attr = type.GetCustomAttribute(Context.Resolver.ImportType(typeof(LineNumberTableAttribute))); if (attr != null && attr.Value.Constructor != null) return ((LineNumberTableAttribute)attr.Value.Constructor.AsReflection().Invoke(attr.Value.ConstructorArguments.Cast().ToArray())).GetLineNumber(ilOffset); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs index d5b164b58f..c288ba1d32 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs @@ -112,7 +112,7 @@ static object[] UnwrapArray(object annotation) return []; } - internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodBaseSymbolBuilder mb, object annotation) { Annotation annot = type.Annotation; foreach (object ann in UnwrapArray(annotation)) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs index 81e268fd76..304a0bb331 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.ReturnValueAnnotationJavaType.cs @@ -66,7 +66,7 @@ internal ReturnValueAnnotationJavaType(RuntimeContext context, AttributeAnnotati #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetAttributeReturnValueType(declaringType.attributeType); #elif !FIRST_PASS - this.fakeType = typeof(ikvm.@internal.AttributeAnnotationReturnValue<>).MakeGenericType(declaringType.attributeType); + this.fakeType = context.Resolver.ResolveBaseType(typeof(ikvm.@internal.AttributeAnnotationReturnValue<>).FullName).MakeGenericType(declaringType.attributeType); #endif this.declaringType = declaringType; } @@ -138,7 +138,7 @@ internal override void ApplyReturnValue(RuntimeClassLoader loader, IMethodSymbol } } - internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodBaseSymbolBuilder mb, object annotation) { } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs index 51ee91f3b2..ae41f128c7 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs @@ -71,7 +71,7 @@ internal AttributeAnnotationJavaType(RuntimeContext context, string name, ITypeS #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetAttributeType(attributeType); #elif !FIRST_PASS - this.fakeType = context.Resolver.ResolveType(typeof(ikvm.@internal.AttributeAnnotation<>)).MakeGenericType(attributeType); + this.fakeType = context.Resolver.ImportType(typeof(ikvm.@internal.AttributeAnnotation<>)).MakeGenericType(attributeType); #endif this.attributeType = attributeType; } @@ -560,7 +560,7 @@ internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, o tb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } - internal override void Apply(RuntimeClassLoader loader, IMethodSymbolBuilder mb, object annotation) + internal override void Apply(RuntimeClassLoader loader, IMethodBaseSymbolBuilder mb, object annotation) { mb.SetCustomAttribute(MakeCustomAttributeBuilder(loader, annotation)); } @@ -593,7 +593,7 @@ internal override void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder a { string str = (string)ConvertValue(loader, loader.Context.Types.String, ((object[])annotation)[3]); Version version; - if (ImportContext.TryParseVersion(str, out version)) + if (ImportContextFactory.TryParseVersion(str, out version)) { ab.__SetAssemblyVersion(version); } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs index 7d47c90905..f3703bba64 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs @@ -53,7 +53,7 @@ internal DelegateInnerClassJavaType(RuntimeContext context, string name, ITypeSy #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetDelegateType(delegateType); #elif !FIRST_PASS - this.fakeType = context.Resolver.ResolveType(typeof(ikvm.@internal.DelegateInterface<>)).MakeGenericType(delegateType); + this.fakeType = context.Resolver.ImportType(typeof(ikvm.@internal.DelegateInterface<>)).MakeGenericType(delegateType); #endif var invoke = delegateType.GetMethod("Invoke"); var parameters = invoke.GetParameters(); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs index a3412f98ca..b9765c9522 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs @@ -56,7 +56,7 @@ internal EnumEnumJavaType(RuntimeContext context, string name, ITypeSymbol enumT #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetEnumType(enumType); #elif !FIRST_PASS - this.fakeType = context.Resolver.ResolveType(typeof(ikvm.@internal.EnumEnum<>)).MakeGenericType(enumType); + this.fakeType = context.Resolver.ImportType(typeof(ikvm.@internal.EnumEnum<>)).MakeGenericType(enumType); #endif } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index a4df662c17..758e61747f 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -541,7 +541,7 @@ protected override void LazyPublishMembers() #if !IMPORTER && !EXPORTER && !FIRST_PASS // support serializing .NET exceptions (by replacing them with a placeholder exception) - if (Context.Types.Exception.IsAssignableFrom(type) && Context.Resolver.ResolveType(typeof(java.io.Serializable.__Interface)).IsAssignableFrom(type) == false && methodsList.ContainsKey("writeReplace()Ljava.lang.Object;") == false) + if (Context.Types.Exception.IsAssignableFrom(type) && Context.Resolver.ImportType(typeof(java.io.Serializable.__Interface)).IsAssignableFrom(type) == false && methodsList.ContainsKey("writeReplace()Ljava.lang.Object;") == false) methodsList.Add("writeReplace()Ljava.lang.Object;", new ExceptionWriteReplaceJavaMethod(this)); #endif diff --git a/src/IKVM.Runtime/StubGen/StubGenerator.cs b/src/IKVM.Runtime/StubGen/StubGenerator.cs index f5a6b5fa86..51d7f48332 100644 --- a/src/IKVM.Runtime/StubGen/StubGenerator.cs +++ b/src/IKVM.Runtime/StubGen/StubGenerator.cs @@ -329,7 +329,7 @@ void AddExceptionsAttribute(ClassFileBuilder builder, RuntimeJavaType type, Runt if (throws.types != null) foreach (var ex in throws.types) - e.Class(builder.Constants.GetOrAddClass(context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveType(ex)).Name.Replace('.', '/'))); + e.Class(builder.Constants.GetOrAddClass(context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ImportType(ex)).Name.Replace('.', '/'))); }); } } diff --git a/src/IKVM.Runtime/atomic.cs b/src/IKVM.Runtime/atomic.cs index 3467e39924..42f2af31c0 100644 --- a/src/IKVM.Runtime/atomic.cs +++ b/src/IKVM.Runtime/atomic.cs @@ -143,7 +143,7 @@ public InterlockedMethods(RuntimeContext context) { this.context = context; - var type = context.Resolver.ResolveCoreType(typeof(System.Threading.Interlocked).FullName); + var type = context.Resolver.ResolveType(typeof(System.Threading.Interlocked).FullName); AddInt32 = type.GetMethod("Add", [context.Types.Int32.MakeByRefType(), context.Types.Int32]); CompareExchangeInt32 = type.GetMethod("CompareExchange", [context.Types.Int32.MakeByRefType(), context.Types.Int32, context.Types.Int32]); CompareExchangeInt64 = type.GetMethod("CompareExchange", [context.Types.Int64.MakeByRefType(), context.Types.Int64, context.Types.Int64]); diff --git a/src/IKVM.Tools.Importer/AssemblyResolver.cs b/src/IKVM.Tools.Exporter/AssemblyResolver.cs similarity index 98% rename from src/IKVM.Tools.Importer/AssemblyResolver.cs rename to src/IKVM.Tools.Exporter/AssemblyResolver.cs index 2608e2c371..5c5f582341 100644 --- a/src/IKVM.Tools.Importer/AssemblyResolver.cs +++ b/src/IKVM.Tools.Exporter/AssemblyResolver.cs @@ -28,15 +28,15 @@ Jeroen Frijters using IKVM.Reflection; using IKVM.Runtime; -namespace IKVM.Tools.Importer +namespace IKVM.Tools.Exporter { sealed class AssemblyResolver { - readonly List libpath = new List(); - Universe universe; - Version coreLibVersion; + private readonly List libpath = new List(); + private Universe universe; + private Version coreLibVersion; internal enum WarningId { diff --git a/src/IKVM.Tools.Exporter/ExportImpl.cs b/src/IKVM.Tools.Exporter/ExportImpl.cs index 149aaf0557..b7e4b327b5 100644 --- a/src/IKVM.Tools.Exporter/ExportImpl.cs +++ b/src/IKVM.Tools.Exporter/ExportImpl.cs @@ -11,7 +11,6 @@ using IKVM.CoreLib.Symbols.IkvmReflection; using IKVM.Reflection; using IKVM.Runtime; -using IKVM.Tools.Importer; using Type = IKVM.Reflection.Type; @@ -147,7 +146,7 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(symbols, compiler, null), true, compiler); + context = new RuntimeContext(new RuntimeContextOptions(true), diagnostics, new ManagedTypeResolver(symbols, universe, runtimeAssembly, null), compiler); context.ClassLoaderFactory.SetBootstrapClassLoader(new RuntimeBootstrapClassLoader(context)); } else @@ -174,10 +173,10 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(symbols, compiler, baseAssembly), false, compiler); + context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(symbols, universe, runtimeAssembly, baseAssembly), compiler); } - if (context.AttributeHelper.IsJavaModule(context.Resolver.ResolveModule(assembly.ManifestModule))) + if (context.AttributeHelper.IsJavaModule(context.Resolver.ImportModule(assembly.ManifestModule))) { diagnostics.ExportingImportsNotSupported(); return 1; @@ -369,7 +368,7 @@ bool ExportNamespace(IList namespaces, ITypeSymbol type) int ProcessTypes(RuntimeContext context, Type[] types) { int rc = 0; - foreach (var t in types.Select(context.Resolver.ResolveType)) + foreach (var t in types.Select(context.Resolver.ImportType)) { if ((t.IsPublic || options.IncludeNonPublicTypes) && ExportNamespace(options.Namespaces, t) && !t.IsGenericTypeDefinition && !context.AttributeHelper.IsHideFromJava(t) && (!t.IsGenericType || !context.AttributeHelper.IsJavaModule(t.Module))) { diff --git a/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj b/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj index d3db518a92..af1d639c72 100644 --- a/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj +++ b/src/IKVM.Tools.Exporter/IKVM.Tools.Exporter.csproj @@ -97,9 +97,5 @@ - - - - diff --git a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs index 35d106fc81..55d36cceaa 100644 --- a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs +++ b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs @@ -17,7 +17,8 @@ namespace IKVM.Tools.Exporter class ManagedTypeResolver : IRuntimeSymbolResolver { - readonly StaticCompiler compiler; + readonly Universe universe; + readonly Assembly runtimeAssembly; readonly Assembly baseAssembly; readonly IkvmReflectionSymbolContext symbols; @@ -26,10 +27,11 @@ class ManagedTypeResolver : IRuntimeSymbolResolver /// /// /// - public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, StaticCompiler compiler, Assembly baseAssembly) + public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, Universe universe, Assembly runtimeAssembly, Assembly baseAssembly) { this.symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); - this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); + this.universe = universe ?? throw new ArgumentNullException(nameof(universe)); + this.runtimeAssembly = runtimeAssembly ?? throw new ArgumentNullException(nameof(runtimeAssembly)); this.baseAssembly = baseAssembly; } @@ -37,103 +39,123 @@ public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, StaticCompiler c public ISymbolContext Symbols => symbols; /// - public IAssemblySymbol? ResolveBaseAssembly() + public IAssemblySymbol ResolveCoreAssembly() { - return ResolveAssembly(baseAssembly); + return ImportAssembly(universe.CoreLib); } /// - public IAssemblySymbol? ResolveAssembly(string assemblyName) + public ITypeSymbol ResolveCoreType(string typeName) { - return ResolveAssembly(compiler.Load(assemblyName)); + return ResolveCoreAssembly().GetType(typeName) ?? throw new InvalidOperationException(); } /// - public ITypeSymbol? ResolveCoreType(string typeName) + public IAssemblySymbol ResolveRuntimeAssembly() { - foreach (var assembly in compiler.Universe.GetAssemblies()) - if (assembly.GetType(typeName) is Type t) - return ResolveType(t); + return ImportAssembly(runtimeAssembly); + } + + /// + public ITypeSymbol ResolveRuntimeType(string typeName) + { + return ResolveRuntimeAssembly().GetType(typeName) ?? throw new InvalidOperationException(); + } - return null; + /// + public IAssemblySymbol ResolveBaseAssembly() + { + return ImportAssembly(baseAssembly); + } + + /// + public ITypeSymbol ResolveBaseType(string typeName) + { + throw new NotImplementedException(); + } + + /// + public ITypeSymbol? ResolveType(string typeName) + { + throw new NotImplementedException(); } /// - public ITypeSymbol? ResolveRuntimeType(string typeName) + public IAssemblySymbol ResolveAssembly(string assemblyName) { - return ResolveType(compiler.GetRuntimeType(typeName)); + return ImportAssembly(universe.Load(assemblyName)); } /// - public IAssemblySymbol? ResolveAssembly(Assembly? assembly) + public IAssemblySymbol ImportAssembly(Assembly assembly) { - return assembly != null ? symbols.GetOrCreateAssemblySymbol(assembly) : null; + return symbols.GetOrCreateAssemblySymbol(assembly); } /// - public IAssemblySymbolBuilder? ResolveAssembly(AssemblyBuilder? assembly) + public IAssemblySymbolBuilder ImportAssembly(AssemblyBuilder assembly) { - return assembly != null ? symbols.GetOrCreateAssemblySymbol(assembly) : null; + return symbols.GetOrCreateAssemblySymbol(assembly); } /// - public IModuleSymbol? ResolveModule(Module? module) + public IModuleSymbol ImportModule(Module module) { - return module != null ? symbols.GetOrCreateModuleSymbol(module) : null; + return symbols.GetOrCreateModuleSymbol(module); } /// - public IModuleSymbolBuilder? ResolveModule(ModuleBuilder? module) + public IModuleSymbolBuilder ImportModule(ModuleBuilder module) { - return module != null ? symbols.GetOrCreateModuleSymbol(module) : null; + return symbols.GetOrCreateModuleSymbol(module); } /// - public ITypeSymbol? ResolveType(Type? type) + public ITypeSymbol ImportType(Type type) { - return type != null ? symbols.GetOrCreateTypeSymbol(type) : null; + return symbols.GetOrCreateTypeSymbol(type) ; } /// - public ITypeSymbolBuilder? ResolveType(TypeBuilder? type) + public ITypeSymbolBuilder ResolveType(TypeBuilder type) { - return type != null ? symbols.GetOrCreateTypeSymbol(type) : null; + return symbols.GetOrCreateTypeSymbol(type); } /// - public IMemberSymbol? ResolveMember(MemberInfo? module) + public IMemberSymbol ImportMember(MemberInfo module) { - return module != null ? symbols.GetOrCreateMemberSymbol(module) : null; + return symbols.GetOrCreateMemberSymbol(module); } /// - public IMethodBaseSymbol? ResolveMethodBase(MethodBase? method) + public IMethodBaseSymbol ImportMethodBase(MethodBase method) { - return method != null ? symbols.GetOrCreateMethodBaseSymbol(method) : null; + return symbols.GetOrCreateMethodBaseSymbol(method); } /// - public IConstructorSymbol? ResolveConstructor(ConstructorInfo? ctor) + public IConstructorSymbol ImportConstructor(ConstructorInfo ctor) { - return ctor != null ? symbols.GetOrCreateConstructorSymbol(ctor) : null; + return symbols.GetOrCreateConstructorSymbol(ctor); } /// - public IConstructorSymbolBuilder? ResolveConstructor(ConstructorBuilder? ctor) + public IConstructorSymbolBuilder ResolveConstructor(ConstructorBuilder ctor) { - return ctor != null ? symbols.GetOrCreateConstructorSymbol(ctor) : null; + return symbols.GetOrCreateConstructorSymbol(ctor); } /// - public IMethodSymbol? ResolveMethod(MethodInfo? method) + public IMethodSymbol ImportMethod(MethodInfo method) { - return method != null ? symbols.GetOrCreateMethodSymbol(method) : null; + return symbols.GetOrCreateMethodSymbol(method); } /// - public IMethodSymbolBuilder? ResolveMethod(MethodBuilder? method) + public IMethodSymbolBuilder ResolveMethod(MethodBuilder method) { - return method != null ? symbols.GetOrCreateMethodSymbol(method) : null; + return symbols.GetOrCreateMethodSymbol(method); } } diff --git a/src/IKVM.Tools.Exporter/StaticCompiler.cs b/src/IKVM.Tools.Exporter/StaticCompiler.cs index 57f27fbfd1..59c8c06050 100644 --- a/src/IKVM.Tools.Exporter/StaticCompiler.cs +++ b/src/IKVM.Tools.Exporter/StaticCompiler.cs @@ -24,7 +24,6 @@ Jeroen Frijters using System; using IKVM.Reflection; -using IKVM.Tools.Importer; using Type = IKVM.Reflection.Type; diff --git a/src/IKVM.Tools.Importer/ExecutionContext.NetFramework.cs b/src/IKVM.Tools.Importer/ExecutionContext.NetFramework.cs index 74d2cb56ff..72496b06f4 100644 --- a/src/IKVM.Tools.Importer/ExecutionContext.NetFramework.cs +++ b/src/IKVM.Tools.Importer/ExecutionContext.NetFramework.cs @@ -11,7 +11,7 @@ partial class ExecutionContext { /// - /// Encapsulates a in a remote . + /// Encapsulates a in a remote . /// class ExecutionContextDispatcher : MarshalByRefObject { diff --git a/src/IKVM.Tools.Importer/FakeTypes.cs b/src/IKVM.Tools.Importer/FakeTypes.cs index 677d65f0ad..6ae6aa6389 100644 --- a/src/IKVM.Tools.Importer/FakeTypes.cs +++ b/src/IKVM.Tools.Importer/FakeTypes.cs @@ -103,7 +103,6 @@ internal void Finish(RuntimeClassLoader loader) ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); tb.Complete(); - genericEnumEnumType = tb; } @@ -112,8 +111,6 @@ void CreateEnumEnum(IModuleSymbolBuilder modb, RuntimeClassLoader loader) var tb = modb.DefineType(RuntimeManagedJavaType.GenericEnumEnumTypeName, TypeAttributes.Class | TypeAttributes.Sealed | TypeAttributes.Public); var gtpb = tb.DefineGenericParameters("T")[0]; gtpb.SetBaseTypeConstraint(context.Types.Enum); - tb.Complete(); - genericEnumEnumType = tb; } @@ -122,7 +119,6 @@ ITypeSymbol CreateAnnotationType(IModuleSymbolBuilder modb, string name) var tb = modb.DefineType(name, TypeAttributes.Interface | TypeAttributes.Abstract | TypeAttributes.Public); tb.DefineGenericParameters("T")[0].SetBaseTypeConstraint(context.Types.Attribute); tb.Complete(); - return tb; } diff --git a/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs b/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs new file mode 100644 index 0000000000..4814a786d8 --- /dev/null +++ b/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs @@ -0,0 +1,359 @@ +/* + Copyright (C) 2010-2013 Jeroen Frijters + + This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. + + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jeroen Frijters + jeroen@frijters.net + +*/ +using System; +using System.Collections.Generic; +using System.IO; + +using IKVM.CoreLib.Diagnostics; +using IKVM.Reflection; + +namespace IKVM.Tools.Importer +{ + + /// + /// Resolves assemblies from the universe of types. + /// + class ImportAssemblyResolver + { + + readonly Universe universe; + readonly ImportOptions options; + readonly IDiagnosticHandler diagnostics; + readonly List libpaths = new List(); + readonly Version coreLibVersion; + + /// + /// Initializes a new instance. + /// + /// + /// + public ImportAssemblyResolver(Universe universe, ImportOptions options, IDiagnosticHandler diagnostics) + { + this.universe = universe ?? throw new ArgumentNullException(nameof(universe)); + this.options = options ?? throw new ArgumentNullException(nameof(options)); + this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); + + // like the C# compiler, the references are loaded from: + // current directory, CLR directory, -lib: option, %LIB% environment + // (note that, unlike the C# compiler, we don't add the CLR directory if -nostdlib has been specified) + libpaths.Add(Environment.CurrentDirectory); + + // add the runtime directory + if (options.NoStdLib == false) + libpaths.Add(System.Runtime.InteropServices.RuntimeEnvironment.GetRuntimeDirectory()); + + // add user libraries + foreach (var directory in options.Libraries) + AddLibraryPaths(directory.FullName, true); + + // add LIB environmental variable + AddLibraryPaths(Environment.GetEnvironmentVariable("LIB") ?? "", false); + + // either load the corelib from the references, or from what already exists + if (options.NoStdLib) + coreLibVersion = LoadCoreLib(options.References).GetName().Version; + else + coreLibVersion = universe.Load(universe.CoreLibName).GetName().Version; + } + + /// + /// Gets the universe of types. + /// + public Universe Universe => universe; + + /// + /// Loads the assembly at the specified path. + /// + /// + /// + /// + internal Assembly LoadFile(string path) + { + string ex = null; + + try + { + using (var module = universe.OpenRawModule(path)) + { + if (coreLibVersion != null) + { + // to avoid problems (i.e. weird exceptions), we don't allow assemblies to load that reference a newer version of the corelib + foreach (var asmref in module.GetReferencedAssemblies()) + if (asmref.Name == universe.CoreLibName && asmref.Version > coreLibVersion) + throw new FatalCompilerErrorException(DiagnosticEvent.CoreAssemblyVersionMismatch(asmref.Name, universe.CoreLibName)); + } + + var asm = universe.LoadAssembly(module); + if (asm.Location != module.Location && CanonicalizePath(asm.Location) != CanonicalizePath(module.Location)) + diagnostics.AssemblyLocationIgnored(path, asm.Location, asm.FullName); + + return asm; + } + } + catch (IOException x) + { + ex = x.Message; + } + catch (UnauthorizedAccessException x) + { + ex = x.Message; + } + catch (IKVM.Reflection.BadImageFormatException x) + { + ex = x.Message; + } + + // TODO + Console.Error.WriteLine("Error: unable to load assembly '{0}'" + Environment.NewLine + " ({1})", path, ex); + Environment.Exit(1); + return null; + } + + static string CanonicalizePath(string path) + { + try + { + var fi = new System.IO.FileInfo(path); + if (fi.DirectoryName == null) + return path.Length > 1 && path[1] == ':' ? path.ToUpper() : path; + + var dir = CanonicalizePath(fi.DirectoryName); + var name = fi.Name; + try + { + var arr = System.IO.Directory.GetFileSystemEntries(dir, name); + if (arr.Length == 1) + name = arr[0]; + } + catch (System.UnauthorizedAccessException) + { + + } + catch (System.IO.IOException) + { + + } + + return System.IO.Path.Combine(dir, name); + } + catch (System.UnauthorizedAccessException) + { + + } + catch (System.IO.IOException) + { + + } + catch (System.Security.SecurityException) + { + + } + catch (System.NotSupportedException) + { + + } + + return path; + } + + internal Assembly LoadWithPartialName(string name) + { + foreach (string path in FindAssemblyPath(name + ".dll")) + return LoadFile(path); + + return null; + } + + internal bool ResolveReference(Dictionary cache, List references, string reference) + { + var files = Array.Empty(); + + try + { + var path = Path.GetDirectoryName(reference); + files = Directory.GetFiles(path == "" ? "." : path, Path.GetFileName(reference)); + } + catch (ArgumentException) + { + + } + catch (IOException) + { + + } + + if (files.Length == 0) + { + cache.TryGetValue(reference, out var asm); + + if (asm == null) + { + foreach (var found in FindAssemblyPath(reference)) + { + asm = LoadFile(found); + cache.Add(reference, asm); + break; + } + } + + if (asm == null) + return false; + + references.Add(asm); + } + else + { + foreach (string file in files) + { + if (!cache.TryGetValue(file, out var asm)) + asm = LoadFile(file); + + references.Add(asm); + } + } + + return true; + } + + /// + /// Handles the event. + /// + /// + /// + /// + public Assembly AssemblyResolve(object sender, IKVM.Reflection.ResolveEventArgs args) + { + var name = new AssemblyName(args.Name); + + foreach (var asm in universe.GetAssemblies()) + if (Match(asm.GetName(), name)) + return asm; + + if (args.RequestingAssembly != null) + return universe.CreateMissingAssembly(args.Name); + + return null; + } + + /// + /// Returs true if the two assembly names match. + /// + /// + /// + /// + bool Match(AssemblyName assemblyDef, AssemblyName assemblyRef) + { + return assemblyRef.Name == assemblyDef.Name; + } + + /// + /// Adds the library paths from the path separated string formatted string. + /// + /// + /// + void AddLibraryPaths(string env, bool option) + { + foreach (var directory in env.Split(Path.PathSeparator)) + { + if (Directory.Exists(directory)) + { + libpaths.Add(directory); + } + else if (directory != "") + { + if (option) + diagnostics.InvalidDirectoryInLibOptionPath(directory); + else + diagnostics.InvalidDirectoryInLibEnvironmentPath(directory); + } + } + } + + /// + /// Search for the CoreLib from the reference assembly set. + /// + /// + /// + Assembly LoadCoreLib(IList references) + { + // try to locate core lib from direct references + if (references != null) + { + foreach (var reference in references) + { + try + { + if (AssemblyName.GetAssemblyName(reference).Name == universe.CoreLibName) + return LoadFile(reference); + } + catch + { + + } + } + } + + // try to locate corelib from library paths + foreach (var coreLib in FindAssemblyPath(universe.CoreLibName + ".dll")) + return LoadFile(coreLib); + + Console.Error.WriteLine($"Error: unable to find '{universe.CoreLibName}.dll'."); + Environment.Exit(1); + return null; + } + + /// + /// Returns the assembly at the path, or the assemblies within the path. + /// + /// + /// + IEnumerable FindAssemblyPath(string path) + { + if (Path.IsPathRooted(path)) + { + if (File.Exists(path)) + yield return path; + } + else + { + foreach (var libpath in libpaths) + { + var p = Path.Combine(libpath, path); + if (File.Exists(p)) + yield return p; + + // for legacy compat, we try again after appending .dll + p = Path.Combine(libpath, p + ".dll"); + if (File.Exists(p)) + { + diagnostics.LegacySearchRule(p); + yield return p; + } + } + } + } + + } + +} diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index ffcb94172f..08d4327fb4 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -41,8 +41,6 @@ Jeroen Frijters using IKVM.Reflection.Emit; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer { @@ -54,7 +52,9 @@ sealed class ImportClassLoader : RuntimeClassLoader const string DEFAULT_RUNTIME_ARGS_PREFIX = "-J"; + readonly StaticCompiler compiler; readonly IDiagnosticHandler diagnostics; + Dictionary classes; Dictionary remapped = new Dictionary(); string assemblyName; @@ -63,8 +63,7 @@ sealed class ImportClassLoader : RuntimeClassLoader bool targetIsModule; IAssemblySymbolBuilder assemblyBuilder; MapXml.Attribute[] assemblyAttributes; - ImportState state; - private readonly StaticCompiler compiler; + ImportContext state; RuntimeAssemblyClassLoader[] referencedAssemblies; Dictionary nameMappings = new Dictionary(); Packages packages; @@ -98,7 +97,7 @@ sealed class ImportClassLoader : RuntimeClassLoader /// /// /// - public ImportClassLoader(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, RuntimeAssemblyClassLoader[] referencedAssemblies, ImportState options, FileInfo assemblyPath, bool targetIsModule, string assemblyName, Dictionary classes) : + public ImportClassLoader(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, RuntimeAssemblyClassLoader[] referencedAssemblies, ImportContext options, FileInfo assemblyPath, bool targetIsModule, string assemblyName, Dictionary classes) : base(context, options.codegenoptions, null) { this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); @@ -136,7 +135,7 @@ internal void AddReference(ImportClassLoader ccl) peerReferences.Add(ccl); } - internal System.Reflection.AssemblyName GetAssemblyName() + internal AssemblyNameInfo GetAssemblyName() { return assemblyBuilder.GetName(); } @@ -166,7 +165,7 @@ internal IModuleSymbolBuilder CreateModuleBuilder() name.Version = state.version; // define a dynamic assembly and module - assemblyBuilder = Context.Resolver.ResolveAssembly(Context.StaticCompiler.Universe.DefineDynamicAssembly(name, AssemblyBuilderAccess.ReflectionOnly, assemblyDir)); + assemblyBuilder = Context.Resolver.ImportAssembly(Context.StaticCompiler.Universe.DefineDynamicAssembly(name, AssemblyBuilderAccess.ReflectionOnly, assemblyDir)); var moduleBuilder = assemblyBuilder.DefineModule(assemblyName, assemblyFile, EmitSymbols); // if configured to emit stack trace info set source file @@ -483,25 +482,24 @@ internal override bool InternalsVisibleToImpl(RuntimeJavaType wrapper, RuntimeJa return false; } - private void AddInternalsVisibleToAttribute(ImportClassLoader ccl) + void AddInternalsVisibleToAttribute(ImportClassLoader ccl) { internalsVisibleTo.Add(ccl); var asm = ccl.assemblyBuilder; var asmName = asm.GetName(); var name = asmName.Name; - var pubkey = asmName.GetPublicKey(); + var pubkey = asmName.PublicKeyOrToken; - if (pubkey == null && asmName.KeyPair != null) - pubkey = asmName.KeyPair.PublicKey; + if (pubkey.IsEmpty && asmName.PublicKeyOrToken.IsEmpty == false) + pubkey = asmName.PublicKeyOrToken; if (pubkey != null && pubkey.Length != 0) { var sb = new StringBuilder(name); sb.Append(", PublicKey="); foreach (byte b in pubkey) - { sb.AppendFormat("{0:X2}", b); - } + name = sb.ToString(); } @@ -904,7 +902,7 @@ internal RemapperTypeWrapper(RuntimeContext context, ImportClassLoader classLoad this.baseTypeWrapper = GetBaseWrapper(context, c); classDef = c; bool baseIsSealed = false; - shadowType = context.Resolver.ResolveType(context.StaticCompiler.Universe.GetType(c.Shadows, true)); + shadowType = context.Resolver.ImportType(context.StaticCompiler.Universe.GetType(c.Shadows, true)); classLoader.SetRemappedType(shadowType, this); var baseType = shadowType; ITypeSymbol baseInterface = null; @@ -1064,8 +1062,8 @@ internal RemappedMethodBaseWrapper(RemapperTypeWrapper typeWrapper, string name, sealed class RemappedConstructorWrapper : RemappedMethodBaseWrapper { - private IKVM.Tools.Importer.MapXml.Constructor m; - private IMethodSymbolBuilder mbHelper; + IKVM.Tools.Importer.MapXml.Constructor m; + IMethodSymbolBuilder mbHelper; internal RemappedConstructorWrapper(RemapperTypeWrapper typeWrapper, IKVM.Tools.Importer.MapXml.Constructor m) : base(typeWrapper, "", m.Sig, (Modifiers)m.Modifiers) @@ -1764,7 +1762,7 @@ private void EmitRedirect(ITypeSymbol baseType, CodeEmitter ilgen) // type specified, or class missing, assume loading .NET type if (m.Redirect.Type != null || m.Redirect.Class == null) { - var type = m.Redirect.Type != null ? DeclaringType.Context.Resolver.ResolveType(DeclaringType.Context.StaticCompiler.Universe.GetType(m.Redirect.Type, true)) : baseType; + var type = m.Redirect.Type != null ? DeclaringType.Context.Resolver.ImportType(DeclaringType.Context.StaticCompiler.Universe.GetType(m.Redirect.Type, true)) : baseType; var redirParamTypes = classLoader.ArgTypeListFromSig(redirSig); var mi = type.GetMethod(m.Redirect.Name, redirParamTypes) ?? throw new InvalidOperationException(); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); @@ -2201,9 +2199,7 @@ internal void EmitRemappedTypes() if (c.Shadows != null) { if (classes.ContainsKey(c.Name)) - { Diagnostics.DuplicateClassName(c.Name); - } remapped.Add(c.Name, new RemapperTypeWrapper(Context, this, c, map)); hasRemappedTypes = true; @@ -2213,13 +2209,10 @@ internal void EmitRemappedTypes() if (hasRemappedTypes) { SetupGhosts(map); + foreach (IKVM.Tools.Importer.MapXml.Class c in map.Assembly.Classes) - { if (c.Shadows != null) - { remapped[c.Name].LoadInterfaces(c); - } - } } } } @@ -2485,7 +2478,7 @@ void SetupGhosts(MapXml.Root map) AddGhost("java.lang.Cloneable", array); } - private void AddGhost(string interfaceName, RuntimeJavaType implementer) + void AddGhost(string interfaceName, RuntimeJavaType implementer) { if (!ghosts.TryGetValue(interfaceName, out var list)) { @@ -2520,53 +2513,49 @@ internal void FinishRemappedTypes() private static bool IsSigned(IAssemblySymbol asm) { - byte[] key = asm.GetName().GetPublicKey(); - return key != null && key.Length != 0; + return asm.GetName().PublicKeyOrToken.IsEmpty == false; } - internal static int Compile(ImportContext importer, RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, string runtimeAssembly, List optionsList) + /// + /// Initiates a compilation of the specified imports. + /// + /// + /// + /// + /// + /// + internal static int Compile(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, List imports) { - try - { - compiler.runtimeAssembly = compiler.LoadFile(runtimeAssembly ?? Path.Combine(Path.GetDirectoryName(typeof(ImportClassLoader).Assembly.Location), "IKVM.Runtime.dll")); - } - catch (FileNotFoundException) - { - // runtime assembly is required - if (compiler.runtimeAssembly == null) - throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeNotFound()); - - // some unknown error - throw new FatalCompilerErrorException(DiagnosticEvent.FileNotFound(compiler.runtimeAssembly.FullName)); - } - - diagnostics.GenericCompilerInfo($"Loaded runtime assembly: {compiler.runtimeAssembly.FullName}"); - var loaders = new List(); - foreach (var options in optionsList) + + // create class loaders for each import + foreach (var import in imports) { - int rc = CreateCompiler(context, compiler, diagnostics, options, out var loader); + int rc = CreateCompiler(context, compiler, diagnostics, import, out var loader); if (rc != 0) return rc; loaders.Add(loader); - options.sharedclassloader?.Add(loader); + import.sharedclassloader?.Add(loader); } + // add a reference between all of the loaders. foreach (var loader1 in loaders) foreach (var loader2 in loaders) if (loader1 != loader2 && (loader1.state.crossReferenceAllPeers || (loader1.state.peerReferences != null && Array.IndexOf(loader1.state.peerReferences, loader2.state.assembly) != -1))) loader1.AddReference(loader2); + // first compilation pass foreach (var loader in loaders) loader.CompilePass0(); var mainAssemblyTypes = new Dictionary(); + foreach (var loader in loaders) { if (loader.state.sharedclassloader != null) { - if (!mainAssemblyTypes.TryGetValue(loader.state.sharedclassloader[0], out var mainAssemblyType)) + if (mainAssemblyTypes.TryGetValue(loader.state.sharedclassloader[0], out var mainAssemblyType) == false) { var tb = loader.state.sharedclassloader[0].GetTypeWrapperFactory().ModuleBuilder.DefineType("__", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Abstract | System.Reflection.TypeAttributes.SpecialName); loader.Context.AttributeHelper.HideFromJava(tb); @@ -2575,21 +2564,18 @@ internal static int Compile(ImportContext importer, RuntimeContext context, Stat mainAssemblyType = tb; mainAssemblyTypes.Add(loader.state.sharedclassloader[0], mainAssemblyType); } + if (loader.state.sharedclassloader[0] != loader) - { ((IAssemblySymbolBuilder)loader.GetTypeWrapperFactory().ModuleBuilder.Assembly).AddTypeForwarder(mainAssemblyType); - } } loader.CompilePass1(); } foreach (var loader in loaders) - { loader.CompilePass2(); - } - if (context.Bootstrap) + if (context.Options.Bootstrap) foreach (var loader in loaders) loader.EmitRemappedTypes2ndPass(); @@ -2605,48 +2591,47 @@ internal static int Compile(ImportContext importer, RuntimeContext context, Stat foreach (var loader in loaders) loader.PrepareSave(); - if (compiler.errorCount > 0) - return 1; + //if (compiler.errorCount > 0) + // return 1; - foreach (ImportClassLoader loader in loaders) + foreach (var loader in loaders) loader.Save(); - return compiler.errorCount == 0 ? 0 : 1; + return 1; } - static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, ImportState options, out ImportClassLoader loader) + static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, ImportContext import, out ImportClassLoader loader) { - diagnostics.GenericCompilerInfo($"JVM.Compile path: {options.path}, assembly: {options.assembly}"); + diagnostics.GenericCompilerInfo($"JVM.Compile path: {import.path}, assembly: {import.assembly}"); + + // locate specified runtime assembly + var runtimeAssembly = context.Resolver.ResolveRuntimeAssembly(); + var allReferencesAreStrongNamed = IsSigned(runtimeAssembly); - var runtimeAssemblyName = compiler.runtimeAssembly.GetName(); - bool allReferencesAreStrongNamed = IsSigned(compiler.runtimeAssembly); - List references = new List(); - foreach (var reference in options.references ?? []) + var references = new List(); + + foreach (var reference in import.references ?? []) { + // check that reference is signed references.Add(reference); - allReferencesAreStrongNamed &= IsSigned(context.Resolver.ResolveAssembly(reference)); + allReferencesAreStrongNamed &= IsSigned(reference); diagnostics.GenericCompilerInfo($"Loaded reference assembly: {reference.FullName}"); - // if it's an IKVM compiled assembly, make sure that it was compiled - // against same version of the runtime - foreach (AssemblyName asmref in reference.GetReferencedAssemblies()) + // if it's an IKVM compiled assembly, make sure that it was compiled against same version of the runtime + foreach (var asmref in reference.GetReferencedAssemblies()) { - if (asmref.Name == runtimeAssemblyName.Name) + if (asmref.Name == runtimeAssembly.GetName().Name) { - if (IsSigned(compiler.runtimeAssembly)) + if (IsSigned(runtimeAssembly)) { // TODO we really should support binding redirects here to allow different revisions to be mixed - if (asmref.FullName != runtimeAssemblyName.FullName) - { - throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssemblyName.FullName, asmref.FullName)); - } + if (asmref.FullName != runtimeAssembly.FullName) + throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); } else { - if (asmref.GetPublicKeyToken() != null && asmref.GetPublicKeyToken().Length != 0) - { - throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssemblyName.FullName, asmref.FullName)); - } + if (asmref.PublicKeyOrToken.IsEmpty == false) + throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); } } } @@ -2655,27 +2640,27 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag diagnostics.GenericCompilerInfo("Parsing class files"); // map the class names to jar entries - Dictionary h = new Dictionary(); - List classNames = new List(); - foreach (Jar jar in options.jars) + var h = new Dictionary(); + var classNames = new List(); + foreach (var jar in import.jars) { - if (options.IsResourcesJar(jar)) - { + if (import.IsResourcesJar(jar)) continue; - } - foreach (Jar.Item item in jar) + + foreach (var item in jar) { - string name = item.Name; - if (name.EndsWith(".class", StringComparison.Ordinal) - && name.Length > 6 - && name.IndexOf('.') == name.Length - 6) + var name = item.Name; + if (name.EndsWith(".class", StringComparison.Ordinal) && + name.Length > 6 && + name.IndexOf('.') == name.Length - 6) { - string className = name.Substring(0, name.Length - 6).Replace('/', '.'); + var className = name.Substring(0, name.Length - 6).Replace('/', '.'); if (h.ContainsKey(className)) { diagnostics.DuplicateClassName(className); - Jar.Item itemRef = h[className]; - if ((options.classesJar != -1 && itemRef.Jar == options.jars[options.classesJar]) || jar != itemRef.Jar) + + var itemRef = h[className]; + if ((import.classesJar != -1 && itemRef.Jar == import.jars[import.classesJar]) || jar != itemRef.Jar) { // the previous class stays, because it was either in an earlier jar or we're processing the classes.jar // which contains the classes loaded from the file system (where the first encountered class wins) @@ -2688,13 +2673,14 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag classNames.Remove(className); } } + h.Add(className, item); classNames.Add(className); } } } - if (options.assemblyAttributeAnnotations == null) + if (import.assemblyAttributeAnnotations.Count == 0) { // look for "assembly" type that acts as a placeholder for assembly attributes if (h.TryGetValue("assembly", out var assemblyType)) @@ -2707,7 +2693,8 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag // that acts as the placeholder for assembly attributes if (f.Name == "assembly" && f.Annotations != null) { - options.assemblyAttributeAnnotations = f.Annotations; + import.assemblyAttributeAnnotations.AddRange(f.Annotations); + // HACK remove "assembly" type that exists only as a placeholder for assembly attributes h.Remove(f.Name); assemblyType.Remove(); @@ -2726,9 +2713,9 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag } // now look for a main method - if (options.mainClass == null && (options.guessFileKind || options.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll)) + if (import.mainClass == null && (import.guessFileKind || import.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll)) { - foreach (string className in classNames) + foreach (var className in classNames) { try { @@ -2740,7 +2727,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag if (m.IsPublic && m.IsStatic && m.Name == "main" && m.Signature == "([Ljava.lang.String;)V") { diagnostics.MainMethodFound(f.Name); - options.mainClass = f.Name; + import.mainClass = f.Name; goto break_outer; } } @@ -2754,83 +2741,68 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag break_outer:; } - if (options.guessFileKind && options.mainClass == null) - { - options.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; - } + if (import.guessFileKind && import.mainClass == null) + import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; - if (options.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && options.mainClass == null) - { + if (import.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && import.mainClass == null) throw new FatalCompilerErrorException(DiagnosticEvent.ExeRequiresMainClass()); - } - if (options.target == IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && options.props.Count != 0) - { + if (import.target == IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && import.props.Count != 0) throw new FatalCompilerErrorException(DiagnosticEvent.PropertiesRequireExe()); - } - if (options.path == null) + if (import.path == null) { - if (options.target == IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll) + if (import.target == IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll) { - if (options.targetIsModule) - { - options.path = ImportContext.GetFileInfo(options.assembly + ".netmodule"); - } + if (import.targetIsModule) + import.path = ImportContextFactory.GetFileInfo(import.assembly + ".netmodule"); else - { - options.path = ImportContext.GetFileInfo(options.assembly + ".dll"); - } + import.path = ImportContextFactory.GetFileInfo(import.assembly + ".dll"); } else - { - options.path = ImportContext.GetFileInfo(options.assembly + ".exe"); - } + import.path = ImportContextFactory.GetFileInfo(import.assembly + ".exe"); - diagnostics.OutputFileIs(options.path.ToString()); + diagnostics.OutputFileIs(import.path.ToString()); } - if (options.targetIsModule) + if (import.targetIsModule) { - if (options.classLoader != null) - { + if (import.classLoader != null) throw new FatalCompilerErrorException(DiagnosticEvent.ModuleCannotHaveClassLoader()); - } + // TODO if we're overwriting a user specified assembly name, we need to emit a warning - options.assembly = options.path.Name; + import.assembly = import.path.Name; } diagnostics.GenericCompilerInfo("Constructing compiler"); + var referencedAssemblies = new List(references.Count); for (int i = 0; i < references.Count; i++) { - // if reference is to base assembly, set it explicitly for resolution - if (compiler.baseAssembly == null && options.bootstrap == false && IsBaseAssembly(context, context.Resolver.ResolveAssembly(references[i]))) - compiler.baseAssembly = context.Resolver.ResolveAssembly(references[i]); - - var acl = context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveAssembly(references[i])); + var acl = context.AssemblyClassLoaderFactory.FromAssembly(references[i]); if (referencedAssemblies.Contains(acl)) diagnostics.DuplicateAssemblyReference(acl.MainAssembly.FullName); referencedAssemblies.Add(acl); } - loader = new ImportClassLoader(context, compiler, diagnostics, referencedAssemblies.ToArray(), options, options.path, options.targetIsModule, options.assembly, h); + loader = new ImportClassLoader(context, compiler, diagnostics, referencedAssemblies.ToArray(), import, import.path, import.targetIsModule, import.assembly, h); loader.classesToCompile = new List(h.Keys); - if (options.remapfile != null) + + if (import.remapfile != null) { - diagnostics.GenericCompilerInfo($"Loading remapped types (1) from {options.remapfile}"); + diagnostics.GenericCompilerInfo($"Loading remapped types (1) from {import.remapfile}"); FileStream fs; try { // NOTE: Using FileShare.ReadWrite ensures other FileStreams (from other processes) can be opened // simultaneously on this file while we are reading it. - fs = new FileStream(options.remapfile.FullName, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); + fs = new FileStream(import.remapfile.FullName, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); } catch (Exception e) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(options.remapfile.FullName, e.Message)); + throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(import.remapfile.FullName, e.Message)); } try @@ -2843,7 +2815,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag } catch (MapXml.MapXmlException x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorParsingMapFile(options.remapfile.FullName, x.Message)); + throw new FatalCompilerErrorException(DiagnosticEvent.ErrorParsingMapFile(import.remapfile.FullName, x.Message)); } if (loader.ValidateAndSetMap(map) == false) @@ -2854,53 +2826,17 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag fs.Close(); } - if (options.bootstrap) + if (import.bootstrap) context.ClassLoaderFactory.SetBootstrapClassLoader(loader); } - // If we do not yet have a reference to the base assembly and we are not compiling the base assembly, - // try to find the base assembly by looking at the assemblies that the runtime references - if (compiler.baseAssembly == null && options.bootstrap == false) - { - foreach (var name in compiler.runtimeAssembly.GetReferencedAssemblies()) - { - IAssemblySymbol asm = null; - - try - { - var path = Path.Combine(Path.GetDirectoryName(compiler.runtimeAssembly.Location), name.Name + ".dll"); - if (File.Exists(path)) - asm = LoadReferencedAssembly(compiler, path); - } - catch (FileNotFoundException) - { - - } - - if (asm != null && IsBaseAssembly(context, asm)) - { - RuntimeAssemblyClassLoader.PreloadExportedAssemblies(context.StaticCompiler, asm); - compiler.baseAssembly = asm; - break; - } - } - - if (compiler.baseAssembly == null) - { - throw new FatalCompilerErrorException(DiagnosticEvent.BootstrapClassesMissing()); - } - - // we need to scan again for remapped types, now that we've loaded the core library - context.ClassLoaderFactory.LoadRemappedTypes(); - } - - if (options.bootstrap == false) + if (import.bootstrap == false) { allReferencesAreStrongNamed &= IsSigned(context.Resolver.ResolveBaseAssembly()); loader.AddReference(context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveBaseAssembly())); } - if ((options.keyPair != null || options.publicKey != null) && !allReferencesAreStrongNamed) + if ((import.keyPair != null || import.publicKey != null) && !allReferencesAreStrongNamed) { throw new FatalCompilerErrorException(DiagnosticEvent.StrongNameRequiresStrongNamedRefs()); } @@ -2910,7 +2846,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag loader.LoadMapXml(); } - if (options.bootstrap == false) + if (import.bootstrap == false) { loader.fakeTypes = context.FakeTypes; loader.fakeTypes.Load(context.Resolver.ResolveBaseAssembly()); @@ -3066,7 +3002,7 @@ int CompilePass3() } catch (IKVM.Reflection.MissingMemberException x) { - Context.StaticCompiler.IssueMissingTypeMessage((ITypeSymbol)Context.Resolver.ResolveMember(x.MemberInfo)); + Context.StaticCompiler.IssueMissingTypeMessage((ITypeSymbol)Context.Resolver.ImportMember(x.MemberInfo)); return 1; } } @@ -3127,8 +3063,7 @@ int CompilePass3() throw new FatalCompilerErrorException(DiagnosticEvent.ClassLoaderConstructorMissing()); // apply custom attribute specifying custom class loader - var ci = Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName).GetConstructor(System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic, new[] { Context.Types.Type }); - assemblyBuilder.SetCustomAttribute(Context.Resolver.Symbols.CreateCustomAttribute(ci, new object[] { classLoaderType.TypeAsTBD })); + Context.AttributeHelper.SetCustomAssemblyClassLoaderAttribute(assemblyBuilder, classLoaderType.TypeAsTBD); // the class loader type defines a module initialize method, ensure we call it upon module load var mwModuleInit = classLoaderType.GetMethodWrapper("InitializeModule", "(Lcli.System.Reflection.Module;)V", false); @@ -3137,7 +3072,7 @@ int CompilePass3() moduleInitBuilders.Add((mb, il) => { il.Emit(System.Reflection.Emit.OpCodes.Ldtoken, mb); - il.Emit(System.Reflection.Emit.OpCodes.Call, Context.Resolver.ResolveCoreType(typeof(System.Reflection.MethodBase).FullName).GetMethod("GetMethodFromHandle", new[] { Context.Resolver.ResolveCoreType(typeof(RuntimeMethodHandle).FullName) })); + il.Emit(System.Reflection.Emit.OpCodes.Call, Context.Resolver.ResolveCoreType(typeof(System.Reflection.MethodBase).FullName).GetMethod("GetMethodFromHandle", [Context.Resolver.ResolveCoreType(typeof(RuntimeMethodHandle).FullName)])); il.Emit(System.Reflection.Emit.OpCodes.Callvirt, Context.Resolver.ResolveCoreType(typeof(System.Reflection.MemberInfo).FullName).GetProperty("Module").GetGetMethod()); il.Emit(System.Reflection.Emit.OpCodes.Call, Context.Resolver.ResolveRuntimeType("IKVM.Runtime.ByteCodeHelper").GetMethod("InitializeModule")); }); @@ -3146,12 +3081,12 @@ int CompilePass3() if (state.iconfile != null) { - assemblyBuilder.DefineIconResource(ImportContext.ReadAllBytes(state.iconfile)); + assemblyBuilder.DefineIconResource(ImportContextFactory.ReadAllBytes(state.iconfile)); } if (state.manifestFile != null) { - assemblyBuilder.DefineManifestResource(ImportContext.ReadAllBytes(state.manifestFile)); + assemblyBuilder.DefineManifestResource(ImportContextFactory.ReadAllBytes(state.manifestFile)); } assemblyBuilder.DefineVersionInfoResource(); diff --git a/src/IKVM.Tools.Importer/ImportContext.cs b/src/IKVM.Tools.Importer/ImportContext.cs index b8d0f8f5b8..ddad70d932 100644 --- a/src/IKVM.Tools.Importer/ImportContext.cs +++ b/src/IKVM.Tools.Importer/ImportContext.cs @@ -1,1334 +1,201 @@ -/* - Copyright (C) 2002-2014 Jeroen Frijters +/* + Copyright (C) 2002-2014 Jeroen Frijters - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. + This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jeroen Frijters + jeroen@frijters.net - Jeroen Frijters - jeroen@frijters.net - */ using System; using System.Collections.Generic; using System.IO; -using System.IO.Compression; -using System.Linq; -using System.Reflection.Metadata; -using System.Reflection.PortableExecutable; using System.Text.RegularExpressions; using System.Threading; -using IKVM.ByteCode; -using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; using IKVM.Reflection; -using IKVM.Reflection.Diagnostics; +using IKVM.Reflection.Emit; using IKVM.Runtime; -using IKVM.Tools.Core.Diagnostics; - -using Microsoft.Extensions.DependencyInjection; namespace IKVM.Tools.Importer { /// - /// Represents the context of an import operation outputing a single assembly. + /// Holds some state for an instance of . /// - class ImportContext + sealed class ImportContext { - /// - /// for the importer. - /// - class CompilerOptionsDiagnosticHandler : FormattedDiagnosticHandler - { - - readonly ImportState _options; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public CompilerOptionsDiagnosticHandler(ImportState options, string spec, DiagnosticFormatterProvider formatters) : - base(spec, formatters) - { - _options = options ?? throw new ArgumentNullException(nameof(options)); - } - - /// - public override bool IsEnabled(Diagnostic diagnostic) - { - return diagnostic.Level is not DiagnosticLevel.Trace and not DiagnosticLevel.Info; - } - - /// - public override void Report(in DiagnosticEvent @event) - { - if (IsEnabled(@event.Diagnostic) == false) - return; - - var key = @event.Diagnostic.Id.ToString(); - for (int i = 0; ; i++) - { - if (_options.suppressWarnings.Contains(key)) - return; - - if (i == @event.Args.Length) - break; - - key += ":" + @event.Args[i]; - } - - _options.suppressWarnings.Add(key); - - base.Report(@event); - } - - } - - readonly ImportOptions _options; - static readonly AssemblyResolver resolver = new AssemblyResolver(); - string manifestMainClass; - string defaultAssemblyName; - static bool time; - static string runtimeAssembly; - static bool nostdlib; - static bool nonDeterministicOutput; - static DebugMode debugMode; - static readonly List libpaths = new List(); - - public static int Execute(ImportOptions options) - { - DateTime start = DateTime.Now; - Thread.CurrentThread.Name = "compiler"; - - try - { - try - { - return Compile(options); - } - catch (TypeInitializationException x) - { - if (x.InnerException is FatalCompilerErrorException) - throw x.InnerException; - - throw; - } - } - catch (FatalCompilerErrorException x) - { - Console.Error.WriteLine(x.Message); - return 1; - } - catch (Exception x) - { - Console.Error.WriteLine(); - Console.Error.WriteLine("*** COMPILER ERROR ***"); - Console.Error.WriteLine(); - Console.Error.WriteLine(System.Reflection.Assembly.GetExecutingAssembly().FullName); - Console.Error.WriteLine(System.Runtime.InteropServices.RuntimeEnvironment.GetRuntimeDirectory()); - Console.Error.WriteLine("{0} {1}-bit", Environment.Version, IntPtr.Size * 8); - Console.Error.WriteLine(); - Console.Error.WriteLine(x); - return 2; - } - finally - { - if (time) - { - Console.WriteLine("Total cpu time: {0}", System.Diagnostics.Process.GetCurrentProcess().TotalProcessorTime); - Console.WriteLine("User cpu time: {0}", System.Diagnostics.Process.GetCurrentProcess().UserProcessorTime); - Console.WriteLine("Total wall clock time: {0}", DateTime.Now - start); - Console.WriteLine("Peak virtual memory: {0}", System.Diagnostics.Process.GetCurrentProcess().PeakVirtualMemorySize64); - for (int i = 0; i <= GC.MaxGeneration; i++) - { - Console.WriteLine("GC({0}) count: {1}", i, GC.CollectionCount(i)); - } - } - } - } - - /// - /// Generates a diagnostic instance from the diagnostics options. - /// - /// - /// - /// - /// - static IDiagnosticHandler GetDiagnostics(IServiceProvider services, ImportState options, string spec) - { - if (services is null) - throw new ArgumentNullException(nameof(services)); - if (string.IsNullOrWhiteSpace(spec)) - throw new ArgumentException($"'{nameof(spec)}' cannot be null or whitespace.", nameof(spec)); - - return ActivatorUtilities.CreateInstance(services, options, spec); - } - - /// - /// Initiates a compilation with the given options. - /// - /// - /// - /// - /// - static int Compile(ImportOptions options) - { - // use a service collection to initialize core services - var rootTarget = new ImportState(); - var services = new ServiceCollection(); - services.AddToolsDiagnostics(); - services.AddSingleton(p => GetDiagnostics(p, rootTarget, options.Log)); - services.AddSingleton(); - services.AddSingleton(); - using var provider = services.BuildServiceProvider(); - - var diagnostics = provider.GetRequiredService(); - var compiler = provider.GetRequiredService(); - var targets = new List(); - var context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, provider.GetRequiredService(), options.Bootstrap, compiler); - - // discover the core lib from the references - var coreLibName = FindCoreLibName(rootTarget.unresolvedReferences, libpaths); - if (coreLibName == null) - { - diagnostics.CoreClassesMissing(); - throw new Exception(); - } - - var universeOptions = UniverseOptions.ResolveMissingMembers | UniverseOptions.EnableFunctionPointers; - if (nonDeterministicOutput == false) - universeOptions |= UniverseOptions.DeterministicOutput; - - // configure the universe of types - var universe = new Universe(universeOptions, coreLibName); - universe.ResolvedMissingMember += (requestingModule, member) => - { - if (requestingModule != null && member is IKVM.Reflection.Type type) - diagnostics.UnableToResolveType(requestingModule.Name, type.FullName, member.Module.FullyQualifiedName); - }; - - // enable embedded symbol writer if debug mode is enabled - if (rootTarget.debugMode == DebugMode.Portable) - universe.SetSymbolWriterFactory(module => new PortablePdbSymbolWriter(module)); - - compiler.rootTarget = rootTarget; - var importer = new ImportContext(); - importer.ParseCommandLine(context, compiler, diagnostics, options, targets, rootTarget); - resolver.Warning += (warning, message, parameters) => loader_Warning(compiler, diagnostics, warning, message, parameters); - resolver.Init(universe, nostdlib, rootTarget.unresolvedReferences, libpaths); - ResolveReferences(compiler, diagnostics, targets); - ResolveStrongNameKeys(targets); - - if (targets.Count == 0) - throw new FatalCompilerErrorException(DiagnosticEvent.NoTargetsFound()); - - if (compiler.errorCount != 0) - return 1; - - try - { - return ImportClassLoader.Compile(importer, context, compiler, diagnostics, runtimeAssembly, targets); - } - catch (FileFormatLimitationExceededException x) - { - throw new FatalCompilerErrorException(DiagnosticEvent.FileFormatLimitationExceeded(x.Message)); - } - } - - /// - /// Finds the first potential core library in the reference set. - /// - /// - /// - /// - static string FindCoreLibName(IList references, IList libpaths) - { - if (references != null) - foreach (var reference in references) - if (GetAssemblyNameIfCoreLib(reference) is string coreLibName) - return coreLibName; - - if (libpaths != null) - foreach (var libpath in libpaths) - foreach (var dll in Directory.GetFiles(libpath, "*.dll")) - if (GetAssemblyNameIfCoreLib(dll) is string coreLibName) - return coreLibName; - - return null; - } - - /// - /// Returns true if the given assembly is a core library. - /// - /// - /// - static string GetAssemblyNameIfCoreLib(string path) - { - if (File.Exists(path) == false) - return null; - - using var st = File.OpenRead(path); - using var pe = new PEReader(st); - var mr = pe.GetMetadataReader(); - - foreach (var handle in mr.TypeDefinitions) - if (IsSystemObject(mr, handle)) - return mr.GetString(mr.GetAssemblyDefinition().Name); - - return null; - } + internal string manifestMainClass; + internal string defaultAssemblyName; + internal List jars = new List(); + private Dictionary jarMap = new Dictionary(); + internal int classesJar = -1; + internal int resourcesJar = -1; + internal bool nojarstubs; + internal FileInfo path; + internal FileInfo keyfile; + internal string keycontainer; + internal bool delaysign; + internal byte[] publicKey; + internal StrongNameKeyPair keyPair; + internal Version version; + internal string fileversion; + internal FileInfo iconfile; + internal FileInfo manifestFile; + internal bool targetIsModule; + internal string assembly; + internal string mainClass; + internal ApartmentState apartment; + internal IKVM.CoreLib.Symbols.Emit.PEFileKinds target; + internal bool guessFileKind; + internal List unresolvedReferences = new(); + internal Dictionary legacyStubReferences = new(); // only used during command line parsing + internal List references = new(); + internal string[] peerReferences; + internal bool crossReferenceAllPeers = true; + internal string[] classesToExclude; // only used during command line parsing + internal FileInfo remapfile; + internal Dictionary props; + internal bool noglobbing; + internal CodeGenOptions codegenoptions; + internal DebugMode debugMode = DebugMode.Portable; + internal string debugFileName; + internal bool compressedResources; + internal string[] privatePackages; + internal string[] publicPackages; + internal string sourcepath; + internal Dictionary externalResources; + internal string classLoader; + internal System.Reflection.PortableExecutableKinds pekind = System.Reflection.PortableExecutableKinds.ILOnly; + internal IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.I386; + internal ulong baseAddress; + internal uint fileAlignment; + internal bool highentropyva; + internal List sharedclassloader; // should *not* be deep copied in Copy(), because we want the list of all compilers that share a class loader + internal HashSet suppressWarnings = new HashSet(StringComparer.OrdinalIgnoreCase); + internal HashSet errorWarnings = new HashSet(StringComparer.OrdinalIgnoreCase); + internal bool warnaserror; // treat all warnings as errors + internal List proxies = new(); + internal List assemblyAttributeAnnotations = new(); + internal bool warningLevelHigh; + internal bool noParameterReflection; + internal bool bootstrap; + internal string log; - /// - /// Returns true if the given type definition handle refers to "System.Object". - /// - /// - /// - /// - static bool IsSystemObject(MetadataReader reader, TypeDefinitionHandle th) + internal ImportContext Copy() { - var td = reader.GetTypeDefinition(th); - var ns = reader.GetString(td.Namespace); - var nm = reader.GetString(td.Name); - - return ns == "System" && nm == "Object"; - } - - static void loader_Warning(StaticCompiler compiler, IDiagnosticHandler diagnostics, AssemblyResolver.WarningId warning, string message, string[] parameters) - { - switch (warning) - { - case AssemblyResolver.WarningId.HigherVersion: - diagnostics.AssumeAssemblyVersionMatch(parameters[0], parameters[1]); - break; - case AssemblyResolver.WarningId.InvalidLibDirectoryOption: - diagnostics.InvalidDirectoryInLibOptionPath(parameters[0]); - break; - case AssemblyResolver.WarningId.InvalidLibDirectoryEnvironment: - diagnostics.InvalidDirectoryInLibEnvironmentPath(parameters[0]); - break; - case AssemblyResolver.WarningId.LegacySearchRule: - diagnostics.LegacySearchRule(parameters[0]); - break; - case AssemblyResolver.WarningId.LocationIgnored: - diagnostics.AssemblyLocationIgnored(parameters[0], parameters[1], parameters[2]); - break; - default: - diagnostics.UnknownWarning(string.Format(message, parameters)); - break; - } - } - - static void ResolveStrongNameKeys(List targets) - { - foreach (var options in targets) - { - if (options.keyfile != null && options.keycontainer != null) - throw new FatalCompilerErrorException(DiagnosticEvent.CannotSpecifyBothKeyFileAndContainer()); - - if (options.keyfile == null && options.keycontainer == null && options.delaysign) - throw new FatalCompilerErrorException(DiagnosticEvent.DelaySignRequiresKey()); - - if (options.keyfile != null) - { - if (options.delaysign) - { - var buf = ReadAllBytes(options.keyfile); - try - { - // maybe it is a key pair, if so we need to extract just the public key - buf = new StrongNameKeyPair(buf).PublicKey; - } - catch - { - - } - - options.publicKey = buf; - } - else - { - SetStrongNameKeyPair(ref options.keyPair, options.keyfile, null); - } - } - else if (options.keycontainer != null) - { - StrongNameKeyPair keyPair = null; - SetStrongNameKeyPair(ref keyPair, null, options.keycontainer); - if (options.delaysign) - options.publicKey = keyPair.PublicKey; - else - options.keyPair = keyPair; - } - } - } - - internal static byte[] ReadAllBytes(FileInfo path) - { - try - { - return File.ReadAllBytes(path.FullName); - } - catch (Exception x) - { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(path.ToString(), x.Message)); - } - } - - void ParseCommandLine(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, ImportOptions options, List targets, ImportState compilerOptions) - { - compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.ConsoleApplication; - compilerOptions.guessFileKind = true; - compilerOptions.version = new Version(0, 0, 0, 0); - compilerOptions.apartment = ApartmentState.STA; - compilerOptions.props = new Dictionary(); - ContinueParseCommandLine(context, compiler, diagnostics, options, targets, compilerOptions); - } - - void ContinueParseCommandLine(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, ImportOptions options, List targets, ImportState compilerOptions) - { - if (options.Output != null) - compilerOptions.path = options.Output; - - if (options.AssemblyName != null) - compilerOptions.assembly = options.AssemblyName; - - switch (options.Target) - { - case ImportTarget.Exe: - compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.ConsoleApplication; - compilerOptions.guessFileKind = false; - break; - case ImportTarget.WinExe: - compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.WindowApplication; - compilerOptions.guessFileKind = false; - break; - case ImportTarget.Module: - compilerOptions.targetIsModule = true; - compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; - compilerOptions.guessFileKind = false; - nonDeterministicOutput = true; - break; - case ImportTarget.Library: - compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; - compilerOptions.guessFileKind = false; - break; - default: - throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedTargetType(options.Target.ToString())); - } - - switch (options.Platform) - { - case ImportPlatform.X86: - compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.Required32Bit; - compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.I386; - break; - case ImportPlatform.X64: - compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.PE32Plus; - compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.AMD64; - break; - case ImportPlatform.ARM: - compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly; - compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.ARM; - break; - case ImportPlatform.ARM64: - compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly; - compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.ARM64; - break; - case ImportPlatform.AnyCpu32BitPreferred: - compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.Preferred32Bit; - compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.Unknown; - break; - case ImportPlatform.AnyCpu: - compilerOptions.pekind = System.Reflection.PortableExecutableKinds.ILOnly; - compilerOptions.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.Unknown; - break; - default: - throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedPlatform(options.Platform.ToString())); - } - - switch (options.Apartment) - { - case ImportApartment.STA: - compilerOptions.apartment = ApartmentState.STA; - break; - case ImportApartment.MTA: - compilerOptions.apartment = ApartmentState.MTA; - break; - case ImportApartment.None: - compilerOptions.apartment = ApartmentState.Unknown; - break; - default: - throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedApartment(options.Apartment.ToString())); - } - - if (options.NoGlobbing) - compilerOptions.noglobbing = true; - - if (options.Properties.Count > 0) - foreach (var kvp in options.Properties) - compilerOptions.props[kvp.Key] = kvp.Value; - - if (options.EnableAssertions != null) - { - if (options.EnableAssertions.Length == 0) - compilerOptions.props["ikvm.assert.default"] = "true"; - else - compilerOptions.props["ikvm.assert.enable"] = string.Join(";", options.EnableAssertions); - } - - if (options.DisableAssertions != null) - { - if (options.DisableAssertions.Length == 0) - compilerOptions.props["ikvm.assert.default"] = "false"; - else - compilerOptions.props["ikvm.assert.disable"] = string.Join(";", options.DisableAssertions); - } - - if (options.RemoveAssertions) - compilerOptions.codegenoptions |= CodeGenOptions.RemoveAsserts; - - if (options.Main != null) - compilerOptions.mainClass = options.Main; - - foreach (var reference in options.References) - ArrayAppend(ref compilerOptions.unresolvedReferences, reference); - - foreach (var spec in options.Recurse) - { - var exists = false; - - // MONOBUG On Mono 1.0.2, Directory.Exists throws an exception if we pass an invalid directory name - try - { - exists = Directory.Exists((string)spec); - } - catch (IOException) - { - - } - - var found = false; - if (exists) - { - var dir = new DirectoryInfo(spec); - found = Recurse(context, compiler, compilerOptions, diagnostics, dir, dir, "*"); - } - else - { - try - { - var dir = new DirectoryInfo(Path.GetDirectoryName(spec)); - if (dir.Exists) - { - found = Recurse(context, compiler, compilerOptions, diagnostics, dir, dir, Path.GetFileName(spec)); - } - else - { - found = RecurseJar(context, compiler, compilerOptions, diagnostics, spec); - } - } - catch (PathTooLongException) - { - throw new FatalCompilerErrorException(DiagnosticEvent.PathTooLong(spec)); - } - catch (DirectoryNotFoundException) - { - throw new FatalCompilerErrorException(DiagnosticEvent.PathNotFound(spec)); - } - catch (ArgumentException) - { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(spec)); - } - } - - if (!found) - throw new FatalCompilerErrorException(DiagnosticEvent.FileNotFound(spec)); - } - - foreach (var kvp in options.Resources) - { - var fileInfo = GetFileInfo(kvp.Value.FullName); - var fileName = kvp.Key.TrimStart('/').TrimEnd('/'); - compilerOptions.GetResourcesJar().Add(fileName, ReadAllBytes(fileInfo), fileInfo); - } - - foreach (var kvp in options.ExternalResources) - { - if (!File.Exists(kvp.Value.FullName)) - throw new FatalCompilerErrorException(DiagnosticEvent.ExternalResourceNotFound(kvp.Value.FullName)); - if (Path.GetFileName(kvp.Value.FullName) != kvp.Value.FullName) - throw new FatalCompilerErrorException(DiagnosticEvent.ExternalResourceNameInvalid(kvp.Value.FullName)); - - // TODO resource name clashes should be tested - compilerOptions.externalResources ??= new Dictionary(); - compilerOptions.externalResources.Add(kvp.Key, kvp.Value.FullName); - } - - if (options.NoJNI) - compilerOptions.codegenoptions |= CodeGenOptions.NoJNI; - - if (options.Exclude != null) - ProcessExclusionFile(ref compilerOptions.classesToExclude, options.Exclude.FullName); - - if (options.Version != null) - compilerOptions.version = options.Version; - - if (options.FileVersion != null) - compilerOptions.fileversion = options.FileVersion.ToString(); - - if (options.Win32Icon != null) - { - compilerOptions.iconfile = GetFileInfo(options.Win32Icon.FullName); - } - - if (options.Win32Manifest != null) - compilerOptions.manifestFile = GetFileInfo(options.Win32Manifest.FullName); - - if (options.KeyFile != null) - compilerOptions.keyfile = GetFileInfo(options.KeyFile.FullName); - - if (options.Key != null) - compilerOptions.keycontainer = options.Key; - - if (options.DelaySign) - compilerOptions.delaysign = true; - - switch (options.Debug) - { - case ImportDebug.Full: - compilerOptions.codegenoptions |= CodeGenOptions.EmitSymbols; - compilerOptions.debugMode = DebugMode.Full; - break; - case ImportDebug.Portable: - compilerOptions.codegenoptions |= CodeGenOptions.EmitSymbols; - compilerOptions.debugMode = DebugMode.Portable; - break; - case ImportDebug.Embedded: - compilerOptions.codegenoptions |= CodeGenOptions.EmitSymbols; - compilerOptions.debugMode = DebugMode.Embedded; - break; - } - - if (options.Deterministic == false) - nonDeterministicOutput = true; - - if (options.Optimize == false) - compilerOptions.codegenoptions |= CodeGenOptions.DisableOptimizations; - - if (options.SourcePath != null) - compilerOptions.sourcepath = options.SourcePath.FullName; - - if (options.Remap != null) - compilerOptions.remapfile = GetFileInfo(options.Remap.FullName); - - if (options.NoStackTraceInfo) - compilerOptions.codegenoptions |= CodeGenOptions.NoStackTraceInfo; - - if (options.RemoveUnusedPrivateFields) - compilerOptions.codegenoptions |= CodeGenOptions.RemoveUnusedFields; - - if (options.CompressResources) - compilerOptions.compressedResources = true; - - if (options.StrictFinalFieldSemantics) - compilerOptions.codegenoptions |= CodeGenOptions.StrictFinalFieldSemantics; - - if (options.PrivatePackages != null) - foreach (var prefix in options.PrivatePackages) - ArrayAppend(ref compilerOptions.privatePackages, prefix); - - if (options.PublicPackages != null) - foreach (var prefix in options.PublicPackages) - ArrayAppend(ref compilerOptions.publicPackages, prefix); - - if (options.NoWarn != null) - foreach (var diagnostic in options.NoWarn) - compilerOptions.suppressWarnings.Add($"IKVM{diagnostic.Id:D4}"); - - // TODO handle specific diagnostic IDs - if (options.WarnAsError != null) - { - if (options.WarnAsError.Length == 0) - compilerOptions.warnaserror = true; - else - foreach (var i in options.WarnAsError) - compilerOptions.errorWarnings.Add($"IKVM{i.Id:D4}"); - } - - if (options.Runtime != null) - runtimeAssembly = options.Runtime.FullName; - - if (options.Time) - time = true; - - if (options.ClassLoader != null) - compilerOptions.classLoader = options.ClassLoader; - - if (options.SharedClassLoader) - compilerOptions.sharedclassloader ??= new List(); - - if (options.BaseAddress != null) - { - var baseAddress = options.BaseAddress; - ulong baseAddressParsed; - if (baseAddress.StartsWith("0x", StringComparison.OrdinalIgnoreCase)) - baseAddressParsed = ulong.Parse(baseAddress.Substring(2), System.Globalization.NumberStyles.AllowHexSpecifier); - else - baseAddressParsed = ulong.Parse(baseAddress); // note that unlike CSC we don't support octal - - compilerOptions.baseAddress = (baseAddressParsed & 0xFFFFFFFFFFFF0000UL); - } - - if (options.FileAlign != null) - { - if (!uint.TryParse(options.FileAlign, out var filealign) || filealign < 512 || filealign > 8192 || (filealign & (filealign - 1)) != 0) - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidFileAlignment(options.FileAlign)); - - compilerOptions.fileAlignment = filealign; - } - - if (options.NoPeerCrossReference) - compilerOptions.crossReferenceAllPeers = false; - - if (options.NoStdLib) - nostdlib = true; - - if (options.Libraries != null) - foreach (var lib in options.Libraries) - libpaths.Add(lib.FullName); - - if (options.NoAutoSerialization) - compilerOptions.codegenoptions |= CodeGenOptions.NoAutomagicSerialization; - - if (options.HighEntropyVA) - { - compilerOptions.highentropyva = true; - } - - if (options.Proxies != null) + ImportContext copy = (ImportContext)MemberwiseClone(); + copy.jars = Copy(jars); + copy.jarMap = new Dictionary(jarMap); + if (props != null) { - foreach (var proxy in options.Proxies) - { - if (compilerOptions.proxies.Contains(proxy)) - diagnostics.DuplicateProxy(proxy); - - compilerOptions.proxies.Add(proxy); - } - } - - if (options.AllowNonVirtualCalls) - JVM.AllowNonVirtualCalls = true; - - if (options.Static) - { - // we abuse -static to also enable support for NoRefEmit scenarios - compilerOptions.codegenoptions |= CodeGenOptions.DisableDynamicBinding | CodeGenOptions.NoRefEmitHelpers; - } - - if (options.NoJarStubs) // undocumented temporary option to mitigate risk - { - compilerOptions.nojarstubs = true; - } - - if (options.AssemblyAttributes != null) - foreach (var i in options.AssemblyAttributes) - ProcessAttributeAnnotationsClass(context, diagnostics, ref compilerOptions.assemblyAttributeAnnotations, i.FullName); - - if (options.WarningLevel4Option) // undocumented option to always warn if a class isn't found - compilerOptions.warningLevelHigh = true; - - if (options.NoParameterReflection) // undocumented option to compile core class libraries with, to disable MethodParameter attribute - compilerOptions.noParameterReflection = true; - - if (options.Bootstrap) - compilerOptions.bootstrap = true; - - if (compilerOptions.targetIsModule && compilerOptions.sharedclassloader != null) - throw new FatalCompilerErrorException(DiagnosticEvent.SharedClassLoaderCannotBeUsedOnModuleTarget()); - - ReadFiles(context, compiler, compilerOptions, diagnostics, options.Inputs.Select(i => i.FullName).ToList()); - - foreach (var nested in options.Nested) - { - var nestedLevel = new ImportContext(); - nestedLevel.manifestMainClass = manifestMainClass; - nestedLevel.defaultAssemblyName = defaultAssemblyName; - nestedLevel.ContinueParseCommandLine(context, compiler, diagnostics, nested, targets, compilerOptions.Copy()); - } - - if (compilerOptions.assembly == null) - { - var basename = compilerOptions.path == null ? defaultAssemblyName : compilerOptions.path.Name; - if (basename == null) - throw new FatalCompilerErrorException(DiagnosticEvent.NoOutputFileSpecified()); - - int idx = basename.LastIndexOf('.'); - if (idx > 0) - compilerOptions.assembly = basename.Substring(0, idx); - else - compilerOptions.assembly = basename; - } - - if (compilerOptions.path != null && compilerOptions.guessFileKind) - { - if (compilerOptions.path.Extension.Equals(".dll", StringComparison.OrdinalIgnoreCase)) - compilerOptions.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; - - compilerOptions.guessFileKind = false; + copy.props = new Dictionary(props); } - - if (compilerOptions.mainClass == null && manifestMainClass != null && (compilerOptions.guessFileKind || compilerOptions.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll)) + if (externalResources != null) { - diagnostics.MainMethodFromManifest(manifestMainClass); - compilerOptions.mainClass = manifestMainClass; + copy.externalResources = new Dictionary(externalResources); } - - // schedule run if leaf-node - if (options.Nested == null || options.Nested.Length == 0) - targets.Add(compilerOptions); + copy.suppressWarnings = new(suppressWarnings, StringComparer.OrdinalIgnoreCase); + copy.errorWarnings = new(errorWarnings, StringComparer.OrdinalIgnoreCase); + return copy; } - internal static FileInfo GetFileInfo(string path) + private static List Copy(List jars) { - try + List newJars = new List(); + foreach (Jar jar in jars) { - FileInfo fileInfo = new FileInfo(path); - if (fileInfo.Directory == null) - { - // this happens with an incorrect unc path (e.g. "\\foo\bar") - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); - } - return fileInfo; - } - catch (ArgumentException) - { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); - } - catch (NotSupportedException) - { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); - } - catch (PathTooLongException) - { - throw new FatalCompilerErrorException(DiagnosticEvent.PathTooLong(path)); - } - catch (UnauthorizedAccessException) - { - // this exception does not appear to be possible - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + newJars.Add(jar.Copy()); } + return newJars; } - void ReadFiles(RuntimeContext context, StaticCompiler compiler, ImportState options, IDiagnosticHandler diagnostics, List fileNames) + internal Jar GetJar(string file) { - foreach (var fileName in fileNames) - { - if (defaultAssemblyName == null) - { - try - { - defaultAssemblyName = new FileInfo(Path.GetFileName(fileName)).Name; - } - catch (ArgumentException) - { - // if the filename contains a wildcard (or any other invalid character), we ignore - // it as a potential default assembly name - } - catch (NotSupportedException) - { - - } - catch (PathTooLongException) - { - - } - } - - string[] files = null; - try - { - var path = Path.GetDirectoryName(fileName); - files = Directory.GetFiles(path == "" ? "." : path, Path.GetFileName(fileName)); - } - catch - { - - } + if (jarMap.TryGetValue(file, out var existingJar)) + return jars[existingJar]; - - if (files == null || files.Length == 0) - { - diagnostics.InputFileNotFound(fileName); - } - else - { - foreach (var f in files) - { - ProcessFile(context, compiler, options, diagnostics, null, f); - } - } - } + jarMap.Add(file, jars.Count); + return CreateJar(Path.GetFileName(file)); } - internal static bool TryParseVersion(string str, out Version version) + Jar CreateJar(string jarName) { - if (str.EndsWith(".*")) + int count = 0; + var name = jarName; + retry: + foreach (var jar in jars) { - str = str.Substring(0, str.Length - 1); - int count = str.Split('.').Length; - // NOTE this is the published algorithm for generating automatic build and revision numbers - // (see AssemblyVersionAttribute constructor docs), but it turns out that the revision - // number is off an hour (on my system)... - DateTime now = DateTime.Now; - int seconds = (int)(now.TimeOfDay.TotalSeconds / 2); - int days = (int)(now - new DateTime(2000, 1, 1)).TotalDays; - if (count == 3) + if (jar.Name == name) { - str += days + "." + seconds; - } - else if (count == 4) - { - str += seconds; - } - else - { - version = null; - return false; + name = Path.GetFileNameWithoutExtension(jarName) + "-" + (++count) + Path.GetExtension(jarName); + goto retry; } } - try - { - version = new Version(str); - return version.Major <= 65535 && version.Minor <= 65535 && version.Build <= 65535 && version.Revision <= 65535; - } - catch (ArgumentException) { } - catch (FormatException) { } - catch (OverflowException) { } - version = null; - return false; - } - - static void SetStrongNameKeyPair(ref StrongNameKeyPair strongNameKeyPair, FileInfo keyFile, string keyContainer) - { - try - { - if (keyFile != null) - strongNameKeyPair = new StrongNameKeyPair(ReadAllBytes(keyFile)); - else - strongNameKeyPair = new StrongNameKeyPair(keyContainer); - - // FXBUG we explicitly try to access the public key force a check (the StrongNameKeyPair constructor doesn't validate the key) - if (strongNameKeyPair.PublicKey != null) - { - } - } - catch (Exception x) - { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidStrongNameKeyPair(keyFile != null ? "file" : "container", x.Message)); - } + var newJar = new Jar(name); + jars.Add(newJar); + return newJar; } - static void ResolveReferences(StaticCompiler compiler, IDiagnosticHandler diagnostics, List targets) + internal Jar GetClassesJar() { - var cache = new Dictionary(); - - foreach (var target in targets) - { - if (target.unresolvedReferences != null) - { - foreach (string reference in target.unresolvedReferences) - { - foreach (var peer in targets) - { - if (peer.assembly.Equals(reference, StringComparison.OrdinalIgnoreCase)) - { - ArrayAppend(ref target.peerReferences, peer.assembly); - goto next_reference; - } - } - - if (!resolver.ResolveReference(cache, ref target.references, reference)) - { - throw new FatalCompilerErrorException(DiagnosticEvent.ReferenceNotFound(reference)); - } - next_reference:; - } - } - } - - // verify that we didn't reference any secondary assemblies of a shared class loader group - foreach (var target in targets) + if (classesJar == -1) { - if (target.references != null) - { - foreach (var asm in target.references) - { - var forwarder = asm.GetType("__"); - if (forwarder != null && forwarder.Assembly != asm) - diagnostics.NonPrimaryAssemblyReference(asm.Location, forwarder.Assembly.GetName().Name); - } - } + classesJar = jars.Count; + CreateJar("classes.jar"); } - // add legacy references (from stub files) - foreach (var target in targets) - foreach (var assemblyName in target.legacyStubReferences.Keys) - ArrayAppend(ref target.references, resolver.LegacyLoad(new AssemblyName(assemblyName), null)); - - // now pre-load the secondary assemblies of any shared class loader groups - foreach (var target in targets) - if (target.references != null) - foreach (var asm in target.references) - RuntimeAssemblyClassLoader.PreloadExportedAssemblies(compiler, compiler.Symbols.GetOrCreateAssemblySymbol(asm)); + return jars[classesJar]; } - static void ArrayAppend(ref T[] array, T element) + internal bool IsClassesJar(Jar jar) { - if (array == null) - array = [element]; - else - array = ArrayUtil.Concat(array, element); + return classesJar != -1 && jars[classesJar] == jar; } - static void ArrayAppend(ref T[] array, T[] append) + internal Jar GetResourcesJar() { - if (array == null) - { - array = append; - } - else if (append != null) + if (resourcesJar == -1) { - T[] tmp = new T[array.Length + append.Length]; - Array.Copy(array, tmp, array.Length); - Array.Copy(append, 0, tmp, array.Length, append.Length); - array = tmp; + resourcesJar = jars.Count; + CreateJar("resources.jar"); } - } - static byte[] ReadFromZip(ZipArchiveEntry ze) - { - using MemoryStream ms = new MemoryStream(); - using Stream s = ze.Open(); - s.CopyTo(ms); - return ms.ToArray(); + return jars[resourcesJar]; } - static bool EmitStubWarning(RuntimeContext context, StaticCompiler compiler, ImportState options, IDiagnosticHandler diagnostics, byte[] buf) + internal bool IsResourcesJar(Jar jar) { - IKVM.Runtime.ClassFile cf; - - try - { - cf = new IKVM.Runtime.ClassFile(context, diagnostics, IKVM.ByteCode.Decoding.ClassFile.Read(buf), "", ClassFileParseOptions.None, null); - } - catch (ClassFormatError) - { - return false; - } - catch (ByteCodeException) - { - return false; - } - - if (cf.IKVMAssemblyAttribute == null) - { - return false; - } - - if (cf.IKVMAssemblyAttribute.StartsWith("[[")) - { - var r = new Regex(@"\[([^\[\]]+)\]"); - var mc = r.Matches(cf.IKVMAssemblyAttribute); - foreach (Match m in mc) - { - options.legacyStubReferences[m.Groups[1].Value] = null; - diagnostics.StubsAreDeprecated(m.Groups[1].Value); - } - } - else - { - options.legacyStubReferences[cf.IKVMAssemblyAttribute] = null; - diagnostics.StubsAreDeprecated(cf.IKVMAssemblyAttribute); - } - - return true; + return resourcesJar != -1 && jars[resourcesJar] == jar; } - static bool IsExcludedOrStubLegacy(RuntimeContext context, StaticCompiler compiler, ImportState options, IDiagnosticHandler diagnostics, ZipArchiveEntry ze, byte[] data) + internal bool IsExcludedClass(string className) { - if (ze.Name.EndsWith(".class", StringComparison.OrdinalIgnoreCase)) - { - try - { - var name = IKVM.Runtime.ClassFile.GetClassName(data, 0, data.Length, out var stub); - if (options.IsExcludedClass(name) || (stub && EmitStubWarning(context, compiler, options, diagnostics, data))) - { - // we use stubs to add references, but otherwise ignore them + if (classesToExclude != null) + for (int i = 0; i < classesToExclude.Length; i++) + if (Regex.IsMatch(className, classesToExclude[i])) return true; - } - } - catch (ClassFormatError) - { - - } - } return false; } - void ProcessManifest(StaticCompiler compiler, ImportState options, ZipArchiveEntry ze) - { - if (manifestMainClass == null) - { - // read main class from manifest - // TODO find out if we can use other information from manifest - using Stream stream = ze.Open(); - using StreamReader rdr = new StreamReader(stream); - string line; - while ((line = rdr.ReadLine()) != null) - { - if (line.StartsWith("Main-Class: ")) - { - line = line.Substring(12); - string continuation; - while ((continuation = rdr.ReadLine()) != null - && continuation.StartsWith(" ", StringComparison.Ordinal)) - { - line += continuation.Substring(1); - } - manifestMainClass = line.Replace('/', '.'); - break; - } - } - } - } - - bool ProcessZipFile(RuntimeContext context, StaticCompiler compiler, ImportState options, IDiagnosticHandler diagnostics, string file, Predicate filter) - { - try - { - using var zf = ZipFile.OpenRead(file); - - bool found = false; - Jar jar = null; - foreach (var ze in zf.Entries) - { - if (filter != null && !filter(ze)) - { - // skip - } - else - { - found = true; - var data = ReadFromZip(ze); - if (IsExcludedOrStubLegacy(context, compiler, options, diagnostics, ze, data)) - { - continue; - } - if (jar == null) - { - jar = options.GetJar(file); - } - jar.Add(ze.FullName, data); - if (string.Equals(ze.FullName, "META-INF/MANIFEST.MF", StringComparison.OrdinalIgnoreCase)) - { - ProcessManifest(compiler, options, ze); - } - } - } - - // include empty zip file - if (!found) - { - options.GetJar(file); - } - - return found; - } - catch (InvalidDataException x) - { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(file, x.Message)); - } - } - - void ProcessFile(RuntimeContext context, StaticCompiler compiler, ImportState options, IDiagnosticHandler diagnostics, DirectoryInfo baseDir, string file) - { - var fileInfo = GetFileInfo(file); - if (fileInfo.Extension.Equals(".jar", StringComparison.OrdinalIgnoreCase) || fileInfo.Extension.Equals(".zip", StringComparison.OrdinalIgnoreCase)) - { - ProcessZipFile(context, compiler, options, diagnostics, file, null); - } - else - { - if (fileInfo.Extension.Equals(".class", StringComparison.OrdinalIgnoreCase)) - { - byte[] data = ReadAllBytes(fileInfo); - try - { - var name = IKVM.Runtime.ClassFile.GetClassName(data, 0, data.Length, out var stub); - if (options.IsExcludedClass(name)) - return; - - // we use stubs to add references, but otherwise ignore them - if (stub && EmitStubWarning(context, compiler, options, diagnostics, data)) - return; - - options.GetClassesJar().Add(name.Replace('.', '/') + ".class", data, fileInfo); - return; - } - catch (ClassFormatError x) - { - diagnostics.ClassFormatError(file, x.Message); - } - } - - if (baseDir == null) - { - diagnostics.UnknownFileType(file); - } - else - { - // include as resource - // extract the resource name by chopping off the base directory - var name = file.Substring(baseDir.FullName.Length); - name = name.TrimStart(Path.DirectorySeparatorChar).Replace('\\', '/'); - options.GetResourcesJar().Add(name, ReadAllBytes(fileInfo), fileInfo); - } - } - } - - bool Recurse(RuntimeContext context, StaticCompiler compiler, ImportState options, IDiagnosticHandler diagnostics, DirectoryInfo baseDir, DirectoryInfo dir, string spec) - { - bool found = false; - - foreach (var file in dir.GetFiles(spec)) - { - found = true; - ProcessFile(context, compiler, options, diagnostics, baseDir, file.FullName); - } - - foreach (var sub in dir.GetDirectories()) - { - found |= Recurse(context, compiler, options, diagnostics, baseDir, sub, spec); - } - - return found; - } - - bool RecurseJar(RuntimeContext context, StaticCompiler compiler, ImportState options, IDiagnosticHandler diagnostics, string path) - { - var file = ""; - for (; ; ) - { - file = Path.Combine(Path.GetFileName(path), file); - path = Path.GetDirectoryName(path); - if (Directory.Exists(path)) - { - throw new DirectoryNotFoundException(); - } - else if (File.Exists(path)) - { - var pathFilter = Path.GetDirectoryName(file) + Path.DirectorySeparatorChar; - var fileFilter = "^" + Regex.Escape(Path.GetFileName(file)).Replace("\\*", ".*").Replace("\\?", ".") + "$"; - - return ProcessZipFile(context, compiler, options, diagnostics, path, delegate (ZipArchiveEntry ze) - { - // MONOBUG Path.GetDirectoryName() doesn't normalize / to \ on Windows - var name = ze.FullName.Replace('/', Path.DirectorySeparatorChar); - return (Path.GetDirectoryName(name) + Path.DirectorySeparatorChar).StartsWith(pathFilter) && Regex.IsMatch(Path.GetFileName(ze.FullName), fileFilter); - }); - } - } - } - - //This processes an exclusion file with a single regular expression per line - private static void ProcessExclusionFile(ref string[] classesToExclude, string filename) - { - try - { - var list = classesToExclude == null ? new List() : new List(classesToExclude); - using (var file = new StreamReader(filename)) - { - string line; - while ((line = file.ReadLine()) != null) - { - line = line.Trim(); - if (!line.StartsWith("//") && line.Length != 0) - { - list.Add(line); - } - } - } - - classesToExclude = list.ToArray(); - } - catch (Exception x) - { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(filename, x.Message)); - } - } - - static void ProcessAttributeAnnotationsClass(RuntimeContext context, IDiagnosticHandler diagnostics, ref object[] annotations, string filename) - { - try - { - using var file = File.OpenRead(filename); - var cf = new IKVM.Runtime.ClassFile(context, diagnostics, IKVM.ByteCode.Decoding.ClassFile.Read(file), null, ClassFileParseOptions.None, null); - ArrayAppend(ref annotations, cf.Annotations); - } - catch (Exception x) - { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(filename, x.Message)); - } - } - - internal static void HandleWarnArg(ICollection target, string arg) - { - foreach (var w in arg.Split(',')) - { - // Strip IKVM prefix - int prefixStart = w.StartsWith("IKVM", StringComparison.OrdinalIgnoreCase) ? 4 : 0; - int contextIndex = w.IndexOf(':', prefixStart); - string context = string.Empty; - string parse; - if (contextIndex != -1) - { - // context includes ':' separator - context = w.Substring(contextIndex); - parse = w.Substring(prefixStart, contextIndex - prefixStart); - } - else - { - parse = w.Substring(prefixStart); - } - - if (!int.TryParse(parse, out var intResult)) - { - // NamedResults aren't supported - continue; // silently continue - } - - target.Add($"{intResult}{context}"); - } - } - } -} +} \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportContextFactory.cs b/src/IKVM.Tools.Importer/ImportContextFactory.cs new file mode 100644 index 0000000000..ad514c740b --- /dev/null +++ b/src/IKVM.Tools.Importer/ImportContextFactory.cs @@ -0,0 +1,1096 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.IO.Compression; +using System.Linq; +using System.Text.RegularExpressions; +using System.Threading; + +using IKVM.ByteCode; +using IKVM.CoreLib.Diagnostics; +using IKVM.Reflection; +using IKVM.Runtime; +using IKVM.Tools.Core.Diagnostics; + +namespace IKVM.Tools.Importer +{ + + /// + /// Processes a hierarchy set of s into a hierarchal set of instances. + /// + class ImportContextFactory + { + + /// + /// for the importer. + /// + class CompilerOptionsDiagnosticHandler : FormattedDiagnosticHandler + { + + readonly ImportContext _options; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public CompilerOptionsDiagnosticHandler(ImportContext options, string spec, DiagnosticFormatterProvider formatters) : + base(spec, formatters) + { + _options = options ?? throw new ArgumentNullException(nameof(options)); + } + + /// + public override bool IsEnabled(Diagnostic diagnostic) + { + return diagnostic.Level is not DiagnosticLevel.Trace and not DiagnosticLevel.Info; + } + + /// + public override void Report(in DiagnosticEvent @event) + { + if (IsEnabled(@event.Diagnostic) == false) + return; + + var key = @event.Diagnostic.Id.ToString(); + for (int i = 0; ; i++) + { + if (_options.suppressWarnings.Contains(key)) + return; + + if (i == @event.Args.Length) + break; + + key += ":" + @event.Args[i]; + } + + _options.suppressWarnings.Add(key); + + base.Report(@event); + } + + } + + readonly RuntimeContext runtime; + readonly ImportAssemblyResolver resolver; + readonly StaticCompiler compiler; + readonly IDiagnosticHandler diagnostics; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public ImportContextFactory(RuntimeContext runtime, ImportAssemblyResolver resolver, StaticCompiler compiler, IDiagnosticHandler diagnostics) + { + this.runtime = runtime ?? throw new ArgumentNullException(nameof(runtime)); + this.resolver = resolver ?? throw new ArgumentNullException(nameof(resolver)); + this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); + this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); + } + + /// + /// Creates a hierarchy of instances that represent the compilation from a root options. + /// + /// + /// + public List Create(ImportOptions options) + { + if (options is null) + throw new ArgumentNullException(nameof(options)); + + var imports = new List(); + + // create root import context + var import = new ImportContext(); + import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.ConsoleApplication; + import.guessFileKind = true; + import.version = new Version(0, 0, 0, 0); + import.apartment = ApartmentState.STA; + import.props = new Dictionary(); + Create(options, import, imports); + ResolveReferences(imports); + ResolveStrongNameKeys(imports); + return imports; + } + + /// + /// Creates a hierarchy of instances that represent the compilation. + /// + /// + /// + /// + /// + void Create(ImportOptions options, ImportContext import, List targets) + { + if (options.Output != null) + import.path = options.Output; + + if (options.AssemblyName != null) + import.assembly = options.AssemblyName; + + switch (options.Target) + { + case ImportTarget.Exe: + import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.ConsoleApplication; + import.guessFileKind = false; + break; + case ImportTarget.WinExe: + import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.WindowApplication; + import.guessFileKind = false; + break; + case ImportTarget.Module: + import.targetIsModule = true; + import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; + import.guessFileKind = false; + break; + case ImportTarget.Library: + import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; + import.guessFileKind = false; + break; + default: + throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedTargetType(options.Target.ToString())); + } + + switch (options.Platform) + { + case ImportPlatform.X86: + import.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.Required32Bit; + import.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.I386; + break; + case ImportPlatform.X64: + import.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.PE32Plus; + import.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.AMD64; + break; + case ImportPlatform.ARM: + import.pekind = System.Reflection.PortableExecutableKinds.ILOnly; + import.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.ARM; + break; + case ImportPlatform.ARM64: + import.pekind = System.Reflection.PortableExecutableKinds.ILOnly; + import.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.ARM64; + break; + case ImportPlatform.AnyCpu32BitPreferred: + import.pekind = System.Reflection.PortableExecutableKinds.ILOnly | System.Reflection.PortableExecutableKinds.Preferred32Bit; + import.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.Unknown; + break; + case ImportPlatform.AnyCpu: + import.pekind = System.Reflection.PortableExecutableKinds.ILOnly; + import.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.Unknown; + break; + default: + throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedPlatform(options.Platform.ToString())); + } + + switch (options.Apartment) + { + case ImportApartment.STA: + import.apartment = ApartmentState.STA; + break; + case ImportApartment.MTA: + import.apartment = ApartmentState.MTA; + break; + case ImportApartment.None: + import.apartment = ApartmentState.Unknown; + break; + default: + throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedApartment(options.Apartment.ToString())); + } + + if (options.NoGlobbing) + import.noglobbing = true; + + if (options.Properties.Count > 0) + foreach (var kvp in options.Properties) + import.props[kvp.Key] = kvp.Value; + + if (options.EnableAssertions != null) + { + if (options.EnableAssertions.Length == 0) + import.props["ikvm.assert.default"] = "true"; + else + import.props["ikvm.assert.enable"] = string.Join(";", options.EnableAssertions); + } + + if (options.DisableAssertions != null) + { + if (options.DisableAssertions.Length == 0) + import.props["ikvm.assert.default"] = "false"; + else + import.props["ikvm.assert.disable"] = string.Join(";", options.DisableAssertions); + } + + if (options.RemoveAssertions) + import.codegenoptions |= CodeGenOptions.RemoveAsserts; + + if (options.Main != null) + import.mainClass = options.Main; + + foreach (var reference in options.References) + import.unresolvedReferences.Add(reference); + + foreach (var spec in options.Recurse) + { + var exists = false; + + // MONOBUG On Mono 1.0.2, Directory.Exists throws an exception if we pass an invalid directory name + try + { + exists = Directory.Exists((string)spec); + } + catch (IOException) + { + + } + + var found = false; + if (exists) + { + var dir = new DirectoryInfo(spec); + found = Recurse(import, dir, dir, "*"); + } + else + { + try + { + var dir = new DirectoryInfo(Path.GetDirectoryName(spec)); + if (dir.Exists) + { + found = Recurse(import, dir, dir, Path.GetFileName(spec)); + } + else + { + found = RecurseJar(import, spec); + } + } + catch (PathTooLongException) + { + throw new FatalCompilerErrorException(DiagnosticEvent.PathTooLong(spec)); + } + catch (DirectoryNotFoundException) + { + throw new FatalCompilerErrorException(DiagnosticEvent.PathNotFound(spec)); + } + catch (ArgumentException) + { + throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(spec)); + } + } + + if (!found) + throw new FatalCompilerErrorException(DiagnosticEvent.FileNotFound(spec)); + } + + foreach (var kvp in options.Resources) + { + var fileInfo = GetFileInfo(kvp.Value.FullName); + var fileName = kvp.Key.TrimStart('/').TrimEnd('/'); + import.GetResourcesJar().Add(fileName, ReadAllBytes(fileInfo), fileInfo); + } + + foreach (var kvp in options.ExternalResources) + { + if (!File.Exists(kvp.Value.FullName)) + throw new FatalCompilerErrorException(DiagnosticEvent.ExternalResourceNotFound(kvp.Value.FullName)); + if (Path.GetFileName(kvp.Value.FullName) != kvp.Value.FullName) + throw new FatalCompilerErrorException(DiagnosticEvent.ExternalResourceNameInvalid(kvp.Value.FullName)); + + // TODO resource name clashes should be tested + import.externalResources ??= new Dictionary(); + import.externalResources.Add(kvp.Key, kvp.Value.FullName); + } + + if (options.NoJNI) + import.codegenoptions |= CodeGenOptions.NoJNI; + + if (options.Exclude != null) + ProcessExclusionFile(ref import.classesToExclude, options.Exclude.FullName); + + if (options.Version != null) + import.version = options.Version; + + if (options.FileVersion != null) + import.fileversion = options.FileVersion.ToString(); + + if (options.Win32Icon != null) + import.iconfile = GetFileInfo(options.Win32Icon.FullName); + + if (options.Win32Manifest != null) + import.manifestFile = GetFileInfo(options.Win32Manifest.FullName); + + if (options.KeyFile != null) + import.keyfile = GetFileInfo(options.KeyFile.FullName); + + if (options.Key != null) + import.keycontainer = options.Key; + + if (options.DelaySign) + import.delaysign = true; + + switch (options.Debug) + { + case ImportDebug.Full: + import.codegenoptions |= CodeGenOptions.EmitSymbols; + import.debugMode = DebugMode.Full; + break; + case ImportDebug.Portable: + import.codegenoptions |= CodeGenOptions.EmitSymbols; + import.debugMode = DebugMode.Portable; + break; + case ImportDebug.Embedded: + import.codegenoptions |= CodeGenOptions.EmitSymbols; + import.debugMode = DebugMode.Embedded; + break; + } + + if (options.Optimize == false) + import.codegenoptions |= CodeGenOptions.DisableOptimizations; + + if (options.SourcePath != null) + import.sourcepath = options.SourcePath.FullName; + + if (options.Remap != null) + import.remapfile = GetFileInfo(options.Remap.FullName); + + if (options.NoStackTraceInfo) + import.codegenoptions |= CodeGenOptions.NoStackTraceInfo; + + if (options.RemoveUnusedPrivateFields) + import.codegenoptions |= CodeGenOptions.RemoveUnusedFields; + + if (options.CompressResources) + import.compressedResources = true; + + if (options.StrictFinalFieldSemantics) + import.codegenoptions |= CodeGenOptions.StrictFinalFieldSemantics; + + if (options.PrivatePackages != null) + foreach (var prefix in options.PrivatePackages) + import.privatePackages = [.. import.privatePackages, prefix]; + + if (options.PublicPackages != null) + foreach (var prefix in options.PublicPackages) + import.publicPackages = [.. import.privatePackages, prefix]; + + if (options.NoWarn != null) + foreach (var diagnostic in options.NoWarn) + import.suppressWarnings.Add($"IKVM{diagnostic.Id:D4}"); + + // TODO handle specific diagnostic IDs + if (options.WarnAsError != null) + { + if (options.WarnAsError.Length == 0) + import.warnaserror = true; + else + foreach (var i in options.WarnAsError) + import.errorWarnings.Add($"IKVM{i.Id:D4}"); + } + + if (options.ClassLoader != null) + import.classLoader = options.ClassLoader; + + if (options.SharedClassLoader) + import.sharedclassloader ??= new List(); + + if (options.BaseAddress != null) + { + var baseAddress = options.BaseAddress; + ulong baseAddressParsed; + if (baseAddress.StartsWith("0x", StringComparison.OrdinalIgnoreCase)) + baseAddressParsed = ulong.Parse(baseAddress.Substring(2), System.Globalization.NumberStyles.AllowHexSpecifier); + else + baseAddressParsed = ulong.Parse(baseAddress); // note that unlike CSC we don't support octal + + import.baseAddress = (baseAddressParsed & 0xFFFFFFFFFFFF0000UL); + } + + if (options.FileAlign != null) + { + if (!uint.TryParse(options.FileAlign, out var filealign) || filealign < 512 || filealign > 8192 || (filealign & (filealign - 1)) != 0) + throw new FatalCompilerErrorException(DiagnosticEvent.InvalidFileAlignment(options.FileAlign)); + + import.fileAlignment = filealign; + } + + if (options.NoPeerCrossReference) + import.crossReferenceAllPeers = false; + + if (options.NoAutoSerialization) + import.codegenoptions |= CodeGenOptions.NoAutomagicSerialization; + + if (options.HighEntropyVA) + import.highentropyva = true; + + if (options.Proxies != null) + { + foreach (var proxy in options.Proxies) + { + if (import.proxies.Contains(proxy)) + diagnostics.DuplicateProxy(proxy); + + import.proxies.Add(proxy); + } + } + + if (options.AllowNonVirtualCalls) + JVM.AllowNonVirtualCalls = true; + + if (options.Static) + { + // we abuse -static to also enable support for NoRefEmit scenarios + import.codegenoptions |= CodeGenOptions.DisableDynamicBinding | CodeGenOptions.NoRefEmitHelpers; + } + + if (options.NoJarStubs) // undocumented temporary option to mitigate risk + import.nojarstubs = true; + + if (options.AssemblyAttributes != null) + foreach (var i in options.AssemblyAttributes) + ProcessAttributeAnnotationsClass(import.assemblyAttributeAnnotations, i.FullName); + + if (options.WarningLevel4Option) // undocumented option to always warn if a class isn't found + import.warningLevelHigh = true; + + if (options.NoParameterReflection) // undocumented option to compile core class libraries with, to disable MethodParameter attribute + import.noParameterReflection = true; + + if (options.Bootstrap) + import.bootstrap = true; + + if (import.targetIsModule && import.sharedclassloader != null) + throw new FatalCompilerErrorException(DiagnosticEvent.SharedClassLoaderCannotBeUsedOnModuleTarget()); + + ReadFiles(import, options.Inputs.Select(i => i.FullName).ToList()); + + // process nested options + foreach (var nestedOptions in options.Nested) + { + var nestedImport = new ImportContext(); + nestedImport.manifestMainClass = import.manifestMainClass; + nestedImport.defaultAssemblyName = import.defaultAssemblyName; + Create(nestedOptions, nestedImport, targets); + } + + if (import.assembly == null) + { + var basename = import.path == null ? import.defaultAssemblyName : import.path.Name; + if (basename == null) + throw new FatalCompilerErrorException(DiagnosticEvent.NoOutputFileSpecified()); + + int idx = basename.LastIndexOf('.'); + if (idx > 0) + import.assembly = basename.Substring(0, idx); + else + import.assembly = basename; + } + + if (import.path != null && import.guessFileKind) + { + if (import.path.Extension.Equals(".dll", StringComparison.OrdinalIgnoreCase)) + import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; + + import.guessFileKind = false; + } + + if (import.mainClass == null && import.manifestMainClass != null && (import.guessFileKind || import.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll)) + { + diagnostics.MainMethodFromManifest(import.manifestMainClass); + import.mainClass = import.manifestMainClass; + } + + // schedule run if leaf-node + if (options.Nested == null || options.Nested.Length == 0) + targets.Add(import); + } + + /// + /// Resolves the intra-peer references in the list of imports. + /// + /// + /// + void ResolveReferences(List imports) + { + var cache = new Dictionary(); + + foreach (var import in imports) + { + if (import.unresolvedReferences.Count > 0) + { + var refs = new List(); + var cont = true; + + foreach (var reference in import.unresolvedReferences) + { + if (cont == false) + break; + + foreach (var peer in imports) + { + if (peer.assembly.Equals(reference, StringComparison.OrdinalIgnoreCase)) + { + import.peerReferences = [.. import.peerReferences, peer.assembly]; + cont = false; + break; + } + } + + if (resolver.ResolveReference(cache, refs, reference) == false) + throw new FatalCompilerErrorException(DiagnosticEvent.ReferenceNotFound(reference)); + } + + // transform references into symbols + foreach (var a in refs) + import.references.Add(runtime.Resolver.ImportAssembly(a)); + } + + } + + + // verify that we didn't reference any secondary assemblies of a shared class loader group + foreach (var import in imports) + { + if (import.references != null) + { + foreach (var asm in import.references) + { + var forwarder = asm.GetType("__"); + if (forwarder != null && forwarder.Assembly != asm) + diagnostics.NonPrimaryAssemblyReference(asm.Location, forwarder.Assembly.GetName().Name); + } + } + } + + // now pre-load the secondary assemblies of any shared class loader groups + foreach (var import in imports) + if (import.references != null) + foreach (var asm in import.references) + RuntimeAssemblyClassLoader.PreloadExportedAssemblies(compiler, asm); + } + + /// + /// Resolves any strong name keys. + /// + /// + /// + void ResolveStrongNameKeys(List targets) + { + foreach (var options in targets) + { + if (options.keyfile != null && options.keycontainer != null) + throw new FatalCompilerErrorException(DiagnosticEvent.CannotSpecifyBothKeyFileAndContainer()); + + if (options.keyfile == null && options.keycontainer == null && options.delaysign) + throw new FatalCompilerErrorException(DiagnosticEvent.DelaySignRequiresKey()); + + if (options.keyfile != null) + { + if (options.delaysign) + { + var buf = ReadAllBytes(options.keyfile); + try + { + // maybe it is a key pair, if so we need to extract just the public key + buf = new StrongNameKeyPair(buf).PublicKey; + } + catch + { + + } + + options.publicKey = buf; + } + else + { + SetStrongNameKeyPair(ref options.keyPair, options.keyfile, null); + } + } + else if (options.keycontainer != null) + { + StrongNameKeyPair keyPair = null; + SetStrongNameKeyPair(ref keyPair, null, options.keycontainer); + if (options.delaysign) + options.publicKey = keyPair.PublicKey; + else + options.keyPair = keyPair; + } + } + } + + static internal byte[] ReadAllBytes(FileInfo path) + { + try + { + return File.ReadAllBytes(path.FullName); + } + catch (Exception x) + { + throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(path.ToString(), x.Message)); + } + } + + static internal FileInfo GetFileInfo(string path) + { + try + { + var fileInfo = new FileInfo(path); + if (fileInfo.Directory == null) + { + // this happens with an incorrect unc path (e.g. "\\foo\bar") + throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + } + return fileInfo; + } + catch (ArgumentException) + { + throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + } + catch (NotSupportedException) + { + throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + } + catch (PathTooLongException) + { + throw new FatalCompilerErrorException(DiagnosticEvent.PathTooLong(path)); + } + catch (UnauthorizedAccessException) + { + // this exception does not appear to be possible + throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + } + } + + void ReadFiles(ImportContext import, List fileNames) + { + foreach (var fileName in fileNames) + { + if (import.defaultAssemblyName == null) + { + try + { + import.defaultAssemblyName = new FileInfo(Path.GetFileName(fileName)).Name; + } + catch (ArgumentException) + { + // if the filename contains a wildcard (or any other invalid character), we ignore + // it as a potential default assembly name + } + catch (NotSupportedException) + { + + } + catch (PathTooLongException) + { + + } + } + + string[] files = null; + try + { + var path = Path.GetDirectoryName(fileName); + files = Directory.GetFiles(path == "" ? "." : path, Path.GetFileName(fileName)); + } + catch + { + + } + + + if (files == null || files.Length == 0) + { + diagnostics.InputFileNotFound(fileName); + } + else + { + foreach (var f in files) + { + ProcessFile(import, null, f); + } + } + } + } + + static internal bool TryParseVersion(string str, out Version version) + { + if (str.EndsWith(".*")) + { + str = str.Substring(0, str.Length - 1); + int count = str.Split('.').Length; + // NOTE this is the published algorithm for generating automatic build and revision numbers + // (see AssemblyVersionAttribute constructor docs), but it turns out that the revision + // number is off an hour (on my system)... + var now = DateTime.Now; + int seconds = (int)(now.TimeOfDay.TotalSeconds / 2); + int days = (int)(now - new DateTime(2000, 1, 1)).TotalDays; + if (count == 3) + { + str += days + "." + seconds; + } + else if (count == 4) + { + str += seconds; + } + else + { + version = null; + return false; + } + } + try + { + version = new Version(str); + return version.Major <= 65535 && version.Minor <= 65535 && version.Build <= 65535 && version.Revision <= 65535; + } + catch (ArgumentException) + { + + } + catch (FormatException) + { + + } + catch (OverflowException) + { + + } + + version = null; + return false; + } + + void SetStrongNameKeyPair(ref StrongNameKeyPair strongNameKeyPair, FileInfo keyFile, string keyContainer) + { + try + { + if (keyFile != null) + strongNameKeyPair = new StrongNameKeyPair(ReadAllBytes(keyFile)); + else + strongNameKeyPair = new StrongNameKeyPair(keyContainer); + + // FXBUG we explicitly try to access the public key force a check (the StrongNameKeyPair constructor doesn't validate the key) + if (strongNameKeyPair.PublicKey != null) + { + + } + } + catch (Exception e) + { + throw new FatalCompilerErrorException(DiagnosticEvent.InvalidStrongNameKeyPair(keyFile != null ? "file" : "container", e.Message)); + } + } + + byte[] ReadFromZip(ZipArchiveEntry ze) + { + using MemoryStream ms = new MemoryStream(); + using Stream s = ze.Open(); + s.CopyTo(ms); + return ms.ToArray(); + } + + bool EmitStubWarning(ImportContext import, byte[] buf) + { + IKVM.Runtime.ClassFile cf; + + try + { + cf = new IKVM.Runtime.ClassFile(runtime, diagnostics, IKVM.ByteCode.Decoding.ClassFile.Read(buf), "", ClassFileParseOptions.None, null); + } + catch (ClassFormatError) + { + return false; + } + catch (ByteCodeException) + { + return false; + } + + if (cf.IKVMAssemblyAttribute == null) + { + return false; + } + + if (cf.IKVMAssemblyAttribute.StartsWith("[[")) + { + var r = new Regex(@"\[([^\[\]]+)\]"); + var mc = r.Matches(cf.IKVMAssemblyAttribute); + foreach (Match m in mc) + { + import.legacyStubReferences[m.Groups[1].Value] = null; + diagnostics.StubsAreDeprecated(m.Groups[1].Value); + } + } + else + { + import.legacyStubReferences[cf.IKVMAssemblyAttribute] = null; + diagnostics.StubsAreDeprecated(cf.IKVMAssemblyAttribute); + } + + return true; + } + + bool IsExcludedOrStubLegacy(ImportContext import, ZipArchiveEntry ze, byte[] data) + { + if (ze.Name.EndsWith(".class", StringComparison.OrdinalIgnoreCase)) + { + try + { + var name = IKVM.Runtime.ClassFile.GetClassName(data, 0, data.Length, out var stub); + if (import.IsExcludedClass(name) || (stub && EmitStubWarning(import, data))) + { + // we use stubs to add references, but otherwise ignore them + return true; + } + } + catch (ClassFormatError) + { + + } + } + + return false; + } + + void ProcessManifest(ImportContext import, ZipArchiveEntry ze) + { + if (import.manifestMainClass == null) + { + // read main class from manifest + // TODO find out if we can use other information from manifest + using Stream stream = ze.Open(); + using StreamReader rdr = new StreamReader(stream); + string line; + while ((line = rdr.ReadLine()) != null) + { + if (line.StartsWith("Main-Class: ")) + { + line = line.Substring(12); + string continuation; + while ((continuation = rdr.ReadLine()) != null + && continuation.StartsWith(" ", StringComparison.Ordinal)) + { + line += continuation.Substring(1); + } + + import.manifestMainClass = line.Replace('/', '.'); + break; + } + } + } + } + + bool ProcessZipFile(ImportContext import, string file, Predicate filter) + { + try + { + using var zf = ZipFile.OpenRead(file); + + bool found = false; + Jar jar = null; + foreach (var ze in zf.Entries) + { + if (filter != null && !filter(ze)) + { + // skip + } + else + { + found = true; + var data = ReadFromZip(ze); + if (IsExcludedOrStubLegacy(import, ze, data)) + { + continue; + } + if (jar == null) + { + jar = import.GetJar(file); + } + jar.Add(ze.FullName, data); + if (string.Equals(ze.FullName, "META-INF/MANIFEST.MF", StringComparison.OrdinalIgnoreCase)) + { + ProcessManifest(import, ze); + } + } + } + + // include empty zip file + if (!found) + { + import.GetJar(file); + } + + return found; + } + catch (InvalidDataException x) + { + throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(file, x.Message)); + } + } + + void ProcessFile(ImportContext import, DirectoryInfo baseDir, string file) + { + var fileInfo = GetFileInfo(file); + if (fileInfo.Extension.Equals(".jar", StringComparison.OrdinalIgnoreCase) || fileInfo.Extension.Equals(".zip", StringComparison.OrdinalIgnoreCase)) + { + ProcessZipFile(import, file, null); + } + else + { + if (fileInfo.Extension.Equals(".class", StringComparison.OrdinalIgnoreCase)) + { + byte[] data = ReadAllBytes(fileInfo); + try + { + var name = IKVM.Runtime.ClassFile.GetClassName(data, 0, data.Length, out var stub); + if (import.IsExcludedClass(name)) + return; + + // we use stubs to add references, but otherwise ignore them + if (stub && EmitStubWarning(import, data)) + return; + + import.GetClassesJar().Add(name.Replace('.', '/') + ".class", data, fileInfo); + return; + } + catch (ClassFormatError x) + { + diagnostics.ClassFormatError(file, x.Message); + } + } + + if (baseDir == null) + { + diagnostics.UnknownFileType(file); + } + else + { + // include as resource + // extract the resource name by chopping off the base directory + var name = file.Substring(baseDir.FullName.Length); + name = name.TrimStart(Path.DirectorySeparatorChar).Replace('\\', '/'); + import.GetResourcesJar().Add(name, ReadAllBytes(fileInfo), fileInfo); + } + } + } + + bool Recurse(ImportContext import, DirectoryInfo baseDir, DirectoryInfo dir, string spec) + { + bool found = false; + + foreach (var file in dir.GetFiles(spec)) + { + found = true; + ProcessFile(import, baseDir, file.FullName); + } + + foreach (var sub in dir.GetDirectories()) + { + found |= Recurse(import, baseDir, sub, spec); + } + + return found; + } + + bool RecurseJar(ImportContext import, string path) + { + var file = ""; + for (; ; ) + { + file = Path.Combine(Path.GetFileName(path), file); + path = Path.GetDirectoryName(path); + if (Directory.Exists(path)) + { + throw new DirectoryNotFoundException(); + } + else if (File.Exists(path)) + { + var pathFilter = Path.GetDirectoryName(file) + Path.DirectorySeparatorChar; + var fileFilter = "^" + Regex.Escape(Path.GetFileName(file)).Replace("\\*", ".*").Replace("\\?", ".") + "$"; + + return ProcessZipFile(import, path, delegate (ZipArchiveEntry ze) + { + // MONOBUG Path.GetDirectoryName() doesn't normalize / to \ on Windows + var name = ze.FullName.Replace('/', Path.DirectorySeparatorChar); + return (Path.GetDirectoryName(name) + Path.DirectorySeparatorChar).StartsWith(pathFilter) && Regex.IsMatch(Path.GetFileName(ze.FullName), fileFilter); + }); + } + } + } + + //This processes an exclusion file with a single regular expression per line + void ProcessExclusionFile(ref string[] classesToExclude, string filename) + { + try + { + var list = classesToExclude == null ? new List() : new List(classesToExclude); + using (var file = new StreamReader(filename)) + { + string line; + while ((line = file.ReadLine()) != null) + { + line = line.Trim(); + if (!line.StartsWith("//") && line.Length != 0) + { + list.Add(line); + } + } + } + + classesToExclude = list.ToArray(); + } + catch (Exception x) + { + throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(filename, x.Message)); + } + } + + void ProcessAttributeAnnotationsClass(List annotations, string filename) + { + try + { + using var file = File.OpenRead(filename); + var cf = new IKVM.Runtime.ClassFile(runtime, diagnostics, IKVM.ByteCode.Decoding.ClassFile.Read(file), null, ClassFileParseOptions.None, null); + annotations.AddRange(cf.Annotations); + } + catch (Exception x) + { + throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(filename, x.Message)); + } + } + + void HandleWarnArg(ICollection target, string arg) + { + foreach (var w in arg.Split(',')) + { + // Strip IKVM prefix + int prefixStart = w.StartsWith("IKVM", StringComparison.OrdinalIgnoreCase) ? 4 : 0; + int contextIndex = w.IndexOf(':', prefixStart); + string context = string.Empty; + string parse; + if (contextIndex != -1) + { + // context includes ':' separator + context = w.Substring(contextIndex); + parse = w.Substring(prefixStart, contextIndex - prefixStart); + } + else + { + parse = w.Substring(prefixStart); + } + + if (!int.TryParse(parse, out var intResult)) + { + // NamedResults aren't supported + continue; // silently continue + } + + target.Add($"{intResult}{context}"); + } + } + + } + +} diff --git a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs index 7f3eeecb84..927dbfc67b 100644 --- a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs +++ b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs @@ -22,7 +22,10 @@ Jeroen Frijters */ using System; +using System.IO; +using System.Threading; +using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols.IkvmReflection; @@ -38,104 +41,178 @@ namespace IKVM.Tools.Importer class ImportRuntimeSymbolResolver : IRuntimeSymbolResolver { - readonly StaticCompiler compiler; - readonly IkvmReflectionSymbolContext context; + readonly IDiagnosticHandler diagnostics; + readonly Universe universe; + readonly IkvmReflectionSymbolContext symbols; + readonly ImportOptions options; + IAssemblySymbol runtimeAssembly; + IAssemblySymbol baseAssembly; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols, ImportOptions options) + { + this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); + this.universe = universe ?? throw new ArgumentNullException(nameof(universe)); + this.symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); + this.options = options ?? throw new ArgumentNullException(nameof(options)); + } + + /// + public ISymbolContext Symbols => symbols; + + /// + public IAssemblySymbol ResolveCoreAssembly() + { + try + { + if (ImportAssembly(universe.CoreLib) is { } a) + return a; + } + catch (FileNotFoundException) + { + + } + + throw new FatalCompilerErrorException(DiagnosticEvent.CoreClassesMissing()); + } /// - public ISymbolContext Symbols => context; + public IAssemblySymbol ResolveRuntimeAssembly() + { + if (runtimeAssembly == null) + Interlocked.CompareExchange(ref runtimeAssembly, LoadRuntimeAssembly(), null); + + return runtimeAssembly; + } /// - /// Initializes a new instance. + /// Attempts to load the runtime assembly. /// - /// - public ImportRuntimeSymbolResolver(StaticCompiler compiler) + /// + IAssemblySymbol LoadRuntimeAssembly() { - this.compiler = compiler ?? throw new ArgumentNullException(nameof(compiler)); - this.context = new IkvmReflectionSymbolContext(compiler.Universe); + foreach (var assembly in universe.GetAssemblies()) + if (assembly.GetType("IKVM.Runtime.JVM") is Type) + return ImportAssembly(assembly); + + throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeNotFound()); } /// public IAssemblySymbol ResolveBaseAssembly() { - return compiler.baseAssembly; + if (baseAssembly == null) + Interlocked.CompareExchange(ref baseAssembly, LoadBaseAssembly(), null); + + return baseAssembly; } - /// - public IAssemblySymbol ResolveAssembly(string assemblyName) + /// + /// Attempts to load the base assembly. + /// + IAssemblySymbol LoadBaseAssembly() { - return compiler.Universe.Load(assemblyName) is { } a ? context.GetOrCreateAssemblySymbol(a) : null; + foreach (var assembly in universe.GetAssemblies()) + if (assembly.GetType("java.lang.Object") is Type) + return ImportAssembly(assembly); + + throw new Exception(); } /// public ITypeSymbol ResolveCoreType(string typeName) { - foreach (var assembly in compiler.Universe.GetAssemblies()) - if (assembly.GetType(typeName) is Type t) - return context.GetOrCreateTypeSymbol(t); - - return null; + return ResolveCoreAssembly().GetType(typeName); } /// public ITypeSymbol ResolveRuntimeType(string typeName) { - return compiler.GetRuntimeType(typeName); + return ResolveRuntimeAssembly().GetType(typeName); } /// - public IAssemblySymbol ResolveAssembly(Assembly assembly) + public ITypeSymbol ResolveBaseType(string typeName) { - return context.GetOrCreateAssemblySymbol(assembly); + return ResolveBaseAssembly().GetType(typeName); } /// - public IAssemblySymbolBuilder ResolveAssembly(AssemblyBuilder assembly) + public IAssemblySymbol ResolveAssembly(string assemblyName) { - return context.GetOrCreateAssemblySymbol(assembly); + return universe.Load(assemblyName) is { } a ? symbols.GetOrCreateAssemblySymbol(a) : null; } /// - public IModuleSymbol ResolveModule(Module module) + public ITypeSymbol ResolveType(string typeName) { - return context.GetOrCreateModuleSymbol(module); + foreach (var assembly in universe.GetAssemblies()) + if (assembly.GetType(typeName) is Type t) + return ImportType(t); + + return null; } /// - public IModuleSymbolBuilder ResolveModule(ModuleBuilder module) + public IAssemblySymbol ImportAssembly(Assembly assembly) { - return context.GetOrCreateModuleSymbol(module); + return symbols.GetOrCreateAssemblySymbol(assembly); } /// - public ITypeSymbol ResolveType(Type type) + public IAssemblySymbolBuilder ImportAssembly(AssemblyBuilder assembly) { - return context.GetOrCreateTypeSymbol(type); + return symbols.GetOrCreateAssemblySymbol(assembly); } /// - public IMemberSymbol ResolveMember(MemberInfo memberInfo) + public IModuleSymbol ImportModule(Module module) { - return context.GetOrCreateMemberSymbol(memberInfo); + return symbols.GetOrCreateModuleSymbol(module); } /// - public IMethodBaseSymbol ResolveMethodBase(MethodBase type) + public IModuleSymbolBuilder ImportModule(ModuleBuilder module) { - return context.GetOrCreateMethodBaseSymbol(type); + return symbols.GetOrCreateModuleSymbol(module); } /// - public IConstructorSymbol ResolveConstructor(ConstructorInfo ctor) + public ITypeSymbol ImportType(Type type) { - return context.GetOrCreateConstructorSymbol(ctor); + return symbols.GetOrCreateTypeSymbol(type); } /// - public IMethodSymbol ResolveMethod(MethodInfo method) + public IMemberSymbol ImportMember(MemberInfo memberInfo) { - return context.GetOrCreateMethodSymbol(method); + return symbols.GetOrCreateMemberSymbol(memberInfo); } + /// + public IMethodBaseSymbol ImportMethodBase(MethodBase type) + { + return symbols.GetOrCreateMethodBaseSymbol(type); + } + + /// + public IConstructorSymbol ImportConstructor(ConstructorInfo ctor) + { + return symbols.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IMethodSymbol ImportMethod(MethodInfo method) + { + return symbols.GetOrCreateMethodSymbol(method); + } } } \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportState.cs b/src/IKVM.Tools.Importer/ImportState.cs deleted file mode 100644 index 38ef6f3687..0000000000 --- a/src/IKVM.Tools.Importer/ImportState.cs +++ /dev/null @@ -1,198 +0,0 @@ -/* - Copyright (C) 2002-2014 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - -*/ -using System; -using System.Collections.Generic; -using System.IO; -using System.Text.RegularExpressions; -using System.Threading; - -using IKVM.Reflection; -using IKVM.Reflection.Emit; -using IKVM.Runtime; - -namespace IKVM.Tools.Importer -{ - - /// - /// Holds some state for an instance of . - /// - sealed class ImportState - { - - internal List jars = new List(); - private Dictionary jarMap = new Dictionary(); - internal int classesJar = -1; - internal int resourcesJar = -1; - internal bool nojarstubs; - internal FileInfo path; - internal FileInfo keyfile; - internal string keycontainer; - internal bool delaysign; - internal byte[] publicKey; - internal StrongNameKeyPair keyPair; - internal Version version; - internal string fileversion; - internal FileInfo iconfile; - internal FileInfo manifestFile; - internal bool targetIsModule; - internal string assembly; - internal string mainClass; - internal ApartmentState apartment; - internal IKVM.CoreLib.Symbols.Emit.PEFileKinds target; - internal bool guessFileKind; - internal string[] unresolvedReferences; // only used during command line parsing - internal Dictionary legacyStubReferences = new Dictionary(); // only used during command line parsing - internal Assembly[] references; - internal string[] peerReferences; - internal bool crossReferenceAllPeers = true; - internal string[] classesToExclude; // only used during command line parsing - internal FileInfo remapfile; - internal Dictionary props; - internal bool noglobbing; - internal CodeGenOptions codegenoptions; - internal DebugMode debugMode = DebugMode.Portable; - internal string debugFileName; - internal bool compressedResources; - internal string[] privatePackages; - internal string[] publicPackages; - internal string sourcepath; - internal Dictionary externalResources; - internal string classLoader; - internal System.Reflection.PortableExecutableKinds pekind = System.Reflection.PortableExecutableKinds.ILOnly; - internal IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.I386; - internal ulong baseAddress; - internal uint fileAlignment; - internal bool highentropyva; - internal List sharedclassloader; // should *not* be deep copied in Copy(), because we want the list of all compilers that share a class loader - internal HashSet suppressWarnings = new HashSet(StringComparer.OrdinalIgnoreCase); - internal HashSet errorWarnings = new HashSet(StringComparer.OrdinalIgnoreCase); - internal bool warnaserror; // treat all warnings as errors - internal List proxies = new List(); - internal object[] assemblyAttributeAnnotations; - internal bool warningLevelHigh; - internal bool noParameterReflection; - internal bool bootstrap; - internal string log; - - internal ImportState Copy() - { - ImportState copy = (ImportState)MemberwiseClone(); - copy.jars = Copy(jars); - copy.jarMap = new Dictionary(jarMap); - if (props != null) - { - copy.props = new Dictionary(props); - } - if (externalResources != null) - { - copy.externalResources = new Dictionary(externalResources); - } - copy.suppressWarnings = new(suppressWarnings, StringComparer.OrdinalIgnoreCase); - copy.errorWarnings = new(errorWarnings, StringComparer.OrdinalIgnoreCase); - return copy; - } - - private static List Copy(List jars) - { - List newJars = new List(); - foreach (Jar jar in jars) - { - newJars.Add(jar.Copy()); - } - return newJars; - } - - internal Jar GetJar(string file) - { - if (jarMap.TryGetValue(file, out var existingJar)) - return jars[existingJar]; - - jarMap.Add(file, jars.Count); - return CreateJar(Path.GetFileName(file)); - } - - Jar CreateJar(string jarName) - { - int count = 0; - var name = jarName; - retry: - foreach (var jar in jars) - { - if (jar.Name == name) - { - name = Path.GetFileNameWithoutExtension(jarName) + "-" + (++count) + Path.GetExtension(jarName); - goto retry; - } - } - - var newJar = new Jar(name); - jars.Add(newJar); - return newJar; - } - - internal Jar GetClassesJar() - { - if (classesJar == -1) - { - classesJar = jars.Count; - CreateJar("classes.jar"); - } - - return jars[classesJar]; - } - - internal bool IsClassesJar(Jar jar) - { - return classesJar != -1 && jars[classesJar] == jar; - } - - internal Jar GetResourcesJar() - { - if (resourcesJar == -1) - { - resourcesJar = jars.Count; - CreateJar("resources.jar"); - } - - return jars[resourcesJar]; - } - - internal bool IsResourcesJar(Jar jar) - { - return resourcesJar != -1 && jars[resourcesJar] == jar; - } - - internal bool IsExcludedClass(string className) - { - if (classesToExclude != null) - for (int i = 0; i < classesToExclude.Length; i++) - if (Regex.IsMatch(className, classesToExclude[i])) - return true; - - return false; - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportTool.cs b/src/IKVM.Tools.Importer/ImportTool.cs index f2d8406253..aa4a8e6d98 100644 --- a/src/IKVM.Tools.Importer/ImportTool.cs +++ b/src/IKVM.Tools.Importer/ImportTool.cs @@ -3,10 +3,17 @@ using System.CommandLine; using System.CommandLine.Builder; using System.CommandLine.Parsing; +using System.IO; +using System.Reflection.Metadata; +using System.Reflection.PortableExecutable; using System.Threading; using System.Threading.Tasks; using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols.IkvmReflection; +using IKVM.Reflection; +using IKVM.Reflection.Diagnostics; +using IKVM.Runtime; using IKVM.Tools.Core.CommandLine; using IKVM.Tools.Core.Diagnostics; @@ -51,40 +58,148 @@ internal static async Task ExecuteInContext(string[] args, CancellationToke /// /// /// - static Task ExecuteAsync(ImportOptions options, IDiagnosticHandler diagnostics, CancellationToken cancellationToken = default) + async Task ExecuteImplAsync(ImportOptions options, CancellationToken cancellationToken) { - return ExecuteImplAsync(options, _ => diagnostics, cancellationToken); + var services = new ServiceCollection(); + services.AddToolsDiagnostics(); + services.AddSingleton(options); + services.AddSingleton(p => GetDiagnostics(p, p.GetRequiredService().Log)); + services.AddSingleton(p => CreateResolver(p.GetRequiredService(), p.GetRequiredService())); + services.AddSingleton(p => p.GetRequiredService().Universe); + services.AddSingleton(); + services.AddSingleton(); + services.AddSingleton(p => new RuntimeContextOptions(p.GetRequiredService().Bootstrap)); + services.AddSingleton(); + services.AddSingleton(); + services.AddSingleton(); + using var provider = services.BuildServiceProvider(); + + // convert options to imports + var imports = provider.GetRequiredService().Create(options); + if (imports.Count == 0) + throw new FatalCompilerErrorException(DiagnosticEvent.NoTargetsFound()); + + // execute the compiler + return await Task.Run(() => Execute( + provider.GetRequiredService(), + provider.GetRequiredService(), + provider.GetRequiredService(), + imports)); } /// - /// Executes the importer. + /// Executes the imports. /// - /// - /// - /// + /// + /// + /// + /// /// - static Task ExecuteImplAsync(ImportOptions options, Func diagnostics, CancellationToken cancellationToken) + int Execute(RuntimeContext runtime, StaticCompiler compiler, IDiagnosticHandler diagnostic, List imports) { - var services = new ServiceCollection(); - services.AddToolsDiagnostics(); - services.AddSingleton(options); - services.AddSingleton(diagnostics); - using var provider = services.BuildServiceProvider(); - return ExecuteImplAsync(options, provider, cancellationToken); + return ImportClassLoader.Compile(runtime, compiler, diagnostic, imports); } /// - /// Executes the importer. + /// Creates the universe of types. /// - /// - /// /// - static Task ExecuteImplAsync(ImportOptions options, IServiceProvider services, CancellationToken cancellationToken) + ImportAssemblyResolver CreateResolver(IDiagnosticHandler diagnostics, ImportOptions options) { - if (services is null) - throw new ArgumentNullException(nameof(services)); + if (diagnostics is null) + throw new ArgumentNullException(nameof(diagnostics)); + if (options is null) + throw new ArgumentNullException(nameof(options)); + + var universeOptions = UniverseOptions.ResolveMissingMembers | UniverseOptions.EnableFunctionPointers; + if (options.Deterministic == false) + universeOptions |= UniverseOptions.DeterministicOutput; + + // discover the core lib from the references + var coreLibName = FindCoreLibName(options.References, options.Libraries); + if (coreLibName == null) + { + diagnostics.CoreClassesMissing(); + throw new Exception(); + } + + // create a new universe of types + var universe = new Universe(universeOptions, coreLibName); + + // warn when unable to resolve a member + universe.ResolvedMissingMember += (Module requestingModule, MemberInfo member) => + { + if (requestingModule != null && member is IKVM.Reflection.Type) + diagnostics.UnableToResolveType(requestingModule.Name, ((IKVM.Reflection.Type)member).FullName, member.Module.FullyQualifiedName); + }; + + // enable embedded symbol writer + if (options.Debug == ImportDebug.Portable) + universe.SetSymbolWriterFactory(module => new PortablePdbSymbolWriter(module)); + + // universe resolver calls back into import + var resolver = new ImportAssemblyResolver(universe, options, diagnostics); + universe.AssemblyResolve += resolver.AssemblyResolve; + + return resolver; + } + + /// + /// Finds the first potential core library in the reference set. + /// + /// + /// + /// + string FindCoreLibName(IList references, IList libpaths) + { + if (references != null) + foreach (var reference in references) + if (GetAssemblyNameIfCoreLib(reference) is string coreLibName) + return coreLibName; + + if (libpaths != null) + foreach (var libpath in libpaths) + foreach (var dll in libpath.GetFiles("*.dll")) + if (GetAssemblyNameIfCoreLib(dll.FullName) is string coreLibName) + return coreLibName; + + return null; + } + + /// + /// Returns true if the given assembly is a core library. + /// + /// + /// + string GetAssemblyNameIfCoreLib(string file) + { + if (File.Exists(file) == false) + return null; + + using var st = File.OpenRead(file); + using var pe = new PEReader(st); + var mr = pe.GetMetadataReader(); + + foreach (var handle in mr.TypeDefinitions) + if (IsSystemObject(mr, handle)) + return mr.GetString(mr.GetAssemblyDefinition().Name); + + return null; + } + + /// + /// Returns true if the given type definition handle refers to "System.Object". + /// + /// + /// + /// + bool IsSystemObject(MetadataReader reader, TypeDefinitionHandle th) + { + var td = reader.GetTypeDefinition(th); + var ns = reader.GetString(td.Namespace); + var nm = reader.GetString(td.Name); - return Task.Run(() => ImportContext.Execute(options)); + return ns == "System" && nm == "Object"; } /// @@ -93,12 +208,12 @@ static Task ExecuteImplAsync(ImportOptions options, IServiceProvider servic /// /// /// - static Task ExecuteAsync(ImportOptions options, CancellationToken cancellationToken = default) + Task ExecuteAsync(ImportOptions options, CancellationToken cancellationToken = default) { if (options is null) throw new ArgumentNullException(nameof(options)); - return ExecuteImplAsync(options, p => GetDiagnostics(p, options.Log), cancellationToken); + return ExecuteImplAsync(options, cancellationToken); } /// diff --git a/src/IKVM.Tools.Importer/MapXml/Call.cs b/src/IKVM.Tools.Importer/MapXml/Call.cs index b2049a1018..e6bbe85b86 100644 --- a/src/IKVM.Tools.Importer/MapXml/Call.cs +++ b/src/IKVM.Tools.Importer/MapXml/Call.cs @@ -101,7 +101,7 @@ internal sealed override void Generate(CodeGenContext context, CodeEmitter ilgen Debug.Assert(Class == null && Type != null); var argTypes = context.ClassLoader.ArgTypeListFromSig(Sig); - var ci = context.ClassLoader.Context.Resolver.ResolveCoreType(Type).GetConstructor(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance, argTypes); + var ci = context.ClassLoader.Context.Resolver.ResolveType(Type).GetConstructor(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance, argTypes); if (ci == null) throw new InvalidOperationException("Missing .ctor: " + Type + "..ctor" + Sig); @@ -115,9 +115,8 @@ internal sealed override void Generate(CodeGenContext context, CodeEmitter ilgen Debug.Assert(Sig != null); var method = context.ClassLoader.LoadClassByName(Class).GetMethodWrapper(Name, Sig, false); if (method == null) - { throw new InvalidOperationException("method not found: " + Class + "." + Name + Sig); - } + method.Link(); // TODO this code is part of what Compiler.CastInterfaceArgs (in compiler.cs) does, // it would be nice if we could avoid this duplication... @@ -126,7 +125,7 @@ internal sealed override void Generate(CodeGenContext context, CodeEmitter ilgen { if (argTypeWrappers[i].IsGhost) { - CodeEmitterLocal[] temps = new CodeEmitterLocal[argTypeWrappers.Length + (method.IsStatic ? 0 : 1)]; + var temps = new CodeEmitterLocal[argTypeWrappers.Length + (method.IsStatic ? 0 : 1)]; for (int j = temps.Length - 1; j >= 0; j--) { RuntimeJavaType tw; @@ -194,15 +193,13 @@ internal sealed override void Generate(CodeGenContext context, CodeEmitter ilgen argTypes = new ITypeSymbol[types.Length]; for (int i = 0; i < types.Length; i++) { - argTypes[i] = context.ClassLoader.Context.Resolver.ResolveCoreType(types[i]); + argTypes[i] = context.ClassLoader.Context.Resolver.ResolveType(types[i]); } } - var ti = context.ClassLoader.Context.Resolver.ResolveCoreType(Type); + var ti = context.ClassLoader.Context.Resolver.ResolveType(Type); if (ti == null) - { throw new InvalidOperationException("Missing type: " + Type); - } var mi = ti.GetMethod(Name, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static, argTypes); if (mi == null) diff --git a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs index f6b342afd5..0cad9fc1fb 100644 --- a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs +++ b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs @@ -75,7 +75,7 @@ sealed class ConstructorForwarder : RuntimeJavaMethod readonly RuntimeJavaTypeFactory context; readonly ITypeSymbolBuilder typeBuilder; readonly RuntimeJavaMethod ctor; - IMethodSymbolBuilder constructorBuilder; + IConstructorSymbolBuilder constructorBuilder; /// /// Initializes a new instance. @@ -129,7 +129,7 @@ internal void GetParameterNamesFromXml(string methodName, string methodSig, stri parameterNames[i] = parameters[i].Name; } - internal void AddXmlMapParameterAttributes(IMethodSymbolBuilder method, string className, string methodName, string methodSig, ref IParameterSymbolBuilder[] parameterBuilders) + internal void AddXmlMapParameterAttributes(IMethodBaseSymbolBuilder method, string className, string methodName, string methodSig, ref IParameterSymbolBuilder[] parameterBuilders) { var parameters = classLoader.GetXmlMapParameters(className, methodName, methodSig); if (parameters != null) diff --git a/src/IKVM.Tools.Importer/StaticCompiler.cs b/src/IKVM.Tools.Importer/StaticCompiler.cs index 795568db50..a0ccb68cc7 100644 --- a/src/IKVM.Tools.Importer/StaticCompiler.cs +++ b/src/IKVM.Tools.Importer/StaticCompiler.cs @@ -24,145 +24,46 @@ Jeroen Frijters using System; using System.Collections.Concurrent; -using System.Collections.Generic; using System.IO; -using System.Reflection.Metadata; -using System.Reflection.PortableExecutable; using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.IkvmReflection; using IKVM.Reflection; -using IKVM.Reflection.Diagnostics; using IKVM.Runtime; -using Type = IKVM.Reflection.Type; - namespace IKVM.Tools.Importer { class StaticCompiler { - readonly ConcurrentDictionary runtimeTypeCache = new(); - readonly IDiagnosticHandler diagnostics; readonly IkvmReflectionSymbolContext symbols; internal Universe universe; - internal IAssemblySymbol runtimeAssembly; - internal IAssemblySymbol baseAssembly; - internal ImportState rootTarget; - internal int errorCount; - - internal Universe Universe => universe; - - internal IkvmReflectionSymbolContext Symbols => symbols; /// /// Initializes a new instance. /// /// + /// /// - public StaticCompiler(IDiagnosticHandler diagnostics, IkvmReflectionSymbolContext symbols) + public StaticCompiler(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols) { this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); + this.universe = universe ?? throw new ArgumentNullException(nameof(universe)); this.symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); } /// - /// Initializes the universe. + /// Gets the symbol context. /// - /// - /// - /// - /// - internal void Init(bool nonDeterministicOutput, DebugMode debug, IList libpaths) - { - var options = UniverseOptions.ResolveMissingMembers | UniverseOptions.EnableFunctionPointers; - if (nonDeterministicOutput == false) - options |= UniverseOptions.DeterministicOutput; - - // discover the core lib from the references - var coreLibName = FindCoreLibName(rootTarget.unresolvedReferences, libpaths); - if (coreLibName == null) - { - diagnostics.CoreClassesMissing(); - throw new Exception(); - } - - universe = new Universe(options, coreLibName); - universe.ResolvedMissingMember += ResolvedMissingMember; - - // enable embedded symbol writer - if (debug == DebugMode.Portable) - universe.SetSymbolWriterFactory(module => new PortablePdbSymbolWriter(module)); - } - - /// - /// Finds the first potential core library in the reference set. - /// - /// - /// - /// - static string FindCoreLibName(IList references, IList libpaths) - { - if (references != null) - foreach (var reference in references) - if (GetAssemblyNameIfCoreLib(reference) is string coreLibName) - return coreLibName; - - if (libpaths != null) - foreach (var libpath in libpaths) - foreach (var dll in Directory.GetFiles(libpath, "*.dll")) - if (GetAssemblyNameIfCoreLib(dll) is string coreLibName) - return coreLibName; - - return null; - } - - /// - /// Returns true if the given assembly is a core library. - /// - /// - /// - static string GetAssemblyNameIfCoreLib(string path) - { - if (File.Exists(path) == false) - return null; - - using var st = File.OpenRead(path); - using var pe = new PEReader(st); - var mr = pe.GetMetadataReader(); - - foreach (var handle in mr.TypeDefinitions) - if (IsSystemObject(mr, handle)) - return mr.GetString(mr.GetAssemblyDefinition().Name); - - return null; - } + internal IkvmReflectionSymbolContext Symbols => symbols; /// - /// Returns true if the given type definition handle refers to "System.Object". + /// Gets the universe of types. /// - /// - /// - /// - static bool IsSystemObject(MetadataReader reader, TypeDefinitionHandle th) - { - var td = reader.GetTypeDefinition(th); - var ns = reader.GetString(td.Namespace); - var nm = reader.GetString(td.Name); - - return ns == "System" && nm == "Object"; - } - - void ResolvedMissingMember(Module requestingModule, MemberInfo member) - { - if (requestingModule != null && member is Type) - { - diagnostics.UnableToResolveType(requestingModule.Name, ((Type)member).FullName, member.Module.FullyQualifiedName); - } - } + internal Universe Universe => universe; internal Assembly Load(string assemblyString) { @@ -178,11 +79,6 @@ internal IAssemblySymbol LoadFile(string path) return symbols.GetOrCreateAssemblySymbol( universe.LoadFile(path)); } - internal ITypeSymbol GetRuntimeType(string name) - { - return runtimeTypeCache.GetOrAdd(name, runtimeAssembly.GetType); - } - internal ITypeSymbol GetTypeForMapXml(RuntimeClassLoader loader, string name) { return GetType(loader, name) ?? throw new FatalCompilerErrorException(DiagnosticEvent.MapFileTypeNotFound(name)); @@ -247,7 +143,7 @@ internal void IssueMissingTypeMessage(ITypeSymbol type) diagnostics.MissingType(type.FullName, type.Assembly.FullName); } - internal void SuppressWarning(ImportState options, Diagnostic diagnostic, string name) + internal void SuppressWarning(ImportContext options, Diagnostic diagnostic, string name) { options.suppressWarnings.Add($"{diagnostic.Id}:{name}"); } From 64ae586d601c7b0459b83c93a99d4bfef9e56552 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Thu, 26 Sep 2024 20:47:51 -0500 Subject: [PATCH 14/59] Put IsMissing back. Remove a number of ifdefs. Add a DiagnosticOptions to allow NoWarn/WarnAsError. These are quite how I want them, but they serve for now. Allow overriding levels using those options. Trap fatal exception. --- .../Diagnostics/DiagnosticEvent.cs | 5 - .../Diagnostics/DiagnosticEvent.g.cs | 1 - .../Diagnostics/DiagnosticLevel.cs | 1 + .../IkvmReflectionAssemblySymbol.cs | 3 + .../IkvmReflectionMemberSymbol.cs | 3 + .../IkvmReflectionModuleSymbol.cs | 3 + .../IkvmReflectionTypeSymbol.cs | 3 + .../IkvmToolTaskDiagnosticWriter.cs | 4 +- src/IKVM.Runtime/AttributeHelper.cs | 8 +- .../Attributes/EnclosingMethodAttribute.cs | 48 ++++---- .../Attributes/InnerClassAttribute.cs | 35 +++--- .../Attributes/RemappedClassAttribute.cs | 9 +- .../Attributes/RemappedTypeAttribute.cs | 6 +- .../Attributes/ThrowsAttribute.cs | 47 ++++---- src/IKVM.Runtime/BootstrapClassLoader.cs | 7 -- src/IKVM.Runtime/ByteCodeHelperMethods.cs | 2 - src/IKVM.Runtime/CodeEmitter.cs | 6 - src/IKVM.Runtime/DefineMethodHelper.cs | 17 +-- src/IKVM.Runtime/DynamicClassLoader.cs | 1 + src/IKVM.Runtime/GhostTag.cs | 5 +- src/IKVM.Runtime/InstructionState.cs | 26 +++- .../Java/Externs/java/io/ObjectStreamClass.cs | 2 +- src/IKVM.Runtime/LambdaMetafactory.cs | 2 +- src/IKVM.Runtime/RuntimeClassLoaderFactory.cs | 8 +- .../AsyncDiagnosticChannelWriter.cs | 19 ++- .../ConsoleDiagnosticFormatterOptions.cs | 2 +- .../Diagnostics/DiagnosticChannelFormatter.cs | 18 ++- .../DiagnosticChannelFormatterOptions.cs | 3 +- .../Diagnostics/DiagnosticFormatterOptions.cs | 37 ++++++ .../Diagnostics/DiagnosticOptions.cs | 33 +++++ .../DiagnosticServiceCollectionExtensions.cs | 1 + ...enericChannelDiagnosticFormatterFactory.cs | 11 +- .../Diagnostics/IDiagnosticFormatter.cs | 5 +- .../Diagnostics/JsonDiagnosticFormatter.cs | 7 +- .../JsonDiagnosticFormatterFactory.cs | 5 +- .../Diagnostics/TextDiagnosticFormatter.cs | 7 +- .../TextDiagnosticFormatterFactory.cs | 5 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 113 +++++++++--------- src/IKVM.Tools.Importer/ImportCommand.cs | 26 ++-- src/IKVM.Tools.Importer/ImportContext.cs | 20 ++-- .../ImportContextFactory.cs | 65 ---------- .../ImportDiagnosticHandler.cs | 50 ++++++++ .../ImportOptionsBinding.cs | 36 ++++-- src/IKVM.Tools.Importer/ImportTool.cs | 70 ++++++++--- src/IKVM.Tools.Importer/StaticCompiler.cs | 6 - src/ikvmc/Properties/launchSettings.json | 2 +- src/ikvmc/ikvmc.csproj | 2 +- 47 files changed, 460 insertions(+), 335 deletions(-) create mode 100644 src/IKVM.Tools.Core/Diagnostics/DiagnosticFormatterOptions.cs create mode 100644 src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs create mode 100644 src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs index c90a66a892..4b2ebd0f16 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.cs @@ -26,11 +26,6 @@ readonly partial struct DiagnosticEvent(Diagnostic Diagnostic, object?[] Args, E /// public readonly DiagnosticLocation Location = Location; - internal static DiagnosticEvent RuntimeMismatch(object location, string fullName1, string fullName2) - { - throw new NotImplementedException(); - } - /// /// Formats the diagnostic event message. /// diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs index 3dde983f23..0ad8a07f30 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs @@ -1,6 +1,5 @@ #nullable enable using System; -using System.Text; namespace IKVM.CoreLib.Diagnostics { diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticLevel.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticLevel.cs index 3226f9f800..476fe8d784 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticLevel.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticLevel.cs @@ -6,6 +6,7 @@ enum DiagnosticLevel { + Unknown, Trace, Info, Warning, diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 73163f1ba9..db6ef47b76 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -68,6 +68,9 @@ public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) /// public IEnumerable Modules => ResolveModuleSymbols(UnderlyingAssembly.Modules); + /// + public override bool IsMissing => UnderlyingAssembly.__IsMissing; + /// public ITypeSymbol[] GetExportedTypes() { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index c74eafbf30..7da4302ba3 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -174,6 +174,9 @@ public IkvmReflectionMemberSymbol(IkvmReflectionSymbolContext context, IIkvmRefl /// public virtual string Name => UnderlyingMember.Name; + /// + public override bool IsMissing => UnderlyingMember.__IsMissing; + /// public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index 1775a26925..e1e699c846 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -65,6 +65,9 @@ public IkvmReflectionModuleSymbol(IkvmReflectionSymbolContext context, IIkvmRefl /// public string ScopeName => UnderlyingModule.ScopeName; + /// + public override bool IsMissing => UnderlyingModule.__IsMissing; + /// public IFieldSymbol? GetField(string name) { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index b99a9ef220..405b59f233 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -283,6 +283,9 @@ public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericType /// public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); + /// + public override bool ContainsMissing => UnderlyingType.__ContainsMissingType; + /// public int GetArrayRank() { diff --git a/src/IKVM.MSBuild.Tasks/IkvmToolTaskDiagnosticWriter.cs b/src/IKVM.MSBuild.Tasks/IkvmToolTaskDiagnosticWriter.cs index 259b27dd00..1d73da7d9d 100644 --- a/src/IKVM.MSBuild.Tasks/IkvmToolTaskDiagnosticWriter.cs +++ b/src/IKVM.MSBuild.Tasks/IkvmToolTaskDiagnosticWriter.cs @@ -62,7 +62,7 @@ public async ValueTask ReceiveAsync(IkvmToolDiagnosticEvent @event, Cancellation } if (writer != null) - await WriteLogsync(writer, @event, cancellationToken); + await WriteLogAsync(writer, @event, cancellationToken); } catch (Exception e) { @@ -77,7 +77,7 @@ public async ValueTask ReceiveAsync(IkvmToolDiagnosticEvent @event, Cancellation /// /// /// - async Task WriteLogsync(TextWriter writer, IkvmToolDiagnosticEvent @event, CancellationToken cancellationToken) + async Task WriteLogAsync(TextWriter writer, IkvmToolDiagnosticEvent @event, CancellationToken cancellationToken) { await TextDiagnosticFormat.WriteAsync(@event.Id, Convert(@event.Level), @event.Message, @event.Args, null, Convert(@event.Location), writer, cancellationToken); await writer.WriteLineAsync(); diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index f510655810..a54bacb1fa 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -374,8 +374,8 @@ ICustomAttributeBuilder GetEditorBrowsableNever() { if (editorBrowsableNever == null) { - var typeofEditorBrowsableAttribute = context.Resolver.ResolveCoreType(typeof(EditorBrowsableAttribute).FullName); - var typeofEditorBrowsableState = context.Resolver.ResolveCoreType(typeof(EditorBrowsableState).FullName); + var typeofEditorBrowsableAttribute = context.Resolver.ResolveType(typeof(EditorBrowsableAttribute).FullName); + var typeofEditorBrowsableState = context.Resolver.ResolveType(typeof(EditorBrowsableState).FullName); var ctor = typeofEditorBrowsableAttribute.GetConstructor([typeofEditorBrowsableState]); editorBrowsableNever = context.Resolver.Symbols.CreateCustomAttribute(ctor, [EditorBrowsableState.Never]); } @@ -700,8 +700,6 @@ internal void SetDebuggingModes(IAssemblySymbolBuilder assemblyBuilder, Debuggab assemblyBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(debuggableAttribute, [modes])); } -#if IMPORTER - internal void SetModifiers(IMethodBaseSymbolBuilder mb, Modifiers modifiers, bool isInternal) { ICustomAttributeBuilder customAttributeBuilder; @@ -865,8 +863,6 @@ internal void SetParamArrayAttribute(IParameterSymbolBuilder pb) pb.SetCustomAttribute(paramArrayAttribute); } -#endif // IMPORTER - internal NameSigAttribute GetNameSig(IMemberSymbol member) { foreach (var cad in member.GetCustomAttributes(TypeOfNameSigAttribute)) diff --git a/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs b/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs index 39e1efa398..a93dfb48ce 100644 --- a/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs +++ b/src/IKVM.Runtime/Attributes/EnclosingMethodAttribute.cs @@ -26,33 +26,35 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; using IKVM.Runtime; -#if IMPORTER || EXPORTER -using Type = IKVM.Reflection.Type; -#endif - namespace IKVM.Attributes { [AttributeUsage(AttributeTargets.Class | AttributeTargets.Interface)] - public sealed class EnclosingMethodAttribute : Attribute - { - - private string className; - private string methodName; - private string methodSig; - - public EnclosingMethodAttribute(string className, string methodName, string methodSig) - { - this.className = UnicodeUtil.UnescapeInvalidSurrogates(className); - this.methodName = UnicodeUtil.UnescapeInvalidSurrogates(methodName); - this.methodSig = UnicodeUtil.UnescapeInvalidSurrogates(methodSig); - } - - internal EnclosingMethodAttribute SetClassName(RuntimeContext context, ITypeSymbol type) - { - className ??= context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).Name; - return this; - } + public sealed class EnclosingMethodAttribute : Attribute + { + + string className; + readonly string methodName; + readonly string methodSig; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public EnclosingMethodAttribute(string className, string methodName, string methodSig) + { + this.className = UnicodeUtil.UnescapeInvalidSurrogates(className); + this.methodName = UnicodeUtil.UnescapeInvalidSurrogates(methodName); + this.methodSig = UnicodeUtil.UnescapeInvalidSurrogates(methodSig); + } + + internal EnclosingMethodAttribute SetClassName(RuntimeContext context, ITypeSymbol type) + { + className ??= context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).Name; + return this; + } public string ClassName => className; diff --git a/src/IKVM.Runtime/Attributes/InnerClassAttribute.cs b/src/IKVM.Runtime/Attributes/InnerClassAttribute.cs index 08c36ff3f9..88dda7985c 100644 --- a/src/IKVM.Runtime/Attributes/InnerClassAttribute.cs +++ b/src/IKVM.Runtime/Attributes/InnerClassAttribute.cs @@ -25,40 +25,33 @@ Jeroen Frijters using IKVM.Runtime; -#if IMPORTER || EXPORTER -using Type = IKVM.Reflection.Type; -#endif - namespace IKVM.Attributes { + // NOTE this attribute is also used by annotation attribute classes, // to give them a different name in the Java world ($Proxy[Annotation]). [AttributeUsage(AttributeTargets.Class | AttributeTargets.Interface)] public sealed class InnerClassAttribute : Attribute { - private string innerClassName; - private Modifiers modifiers; + readonly string innerClassName; + readonly Modifiers modifiers; + + /// + /// Initializes a new instance. + /// + /// + /// public InnerClassAttribute(string innerClassName, Modifiers modifiers) { this.innerClassName = UnicodeUtil.UnescapeInvalidSurrogates(innerClassName); this.modifiers = modifiers; } - public string InnerClassName - { - get - { - return innerClassName; - } - } + public string InnerClassName => innerClassName; + + public Modifiers Modifiers => modifiers; + + } - public Modifiers Modifiers - { - get - { - return modifiers; - } - } - } } diff --git a/src/IKVM.Runtime/Attributes/RemappedClassAttribute.cs b/src/IKVM.Runtime/Attributes/RemappedClassAttribute.cs index 522bb201a5..541c6dac4d 100644 --- a/src/IKVM.Runtime/Attributes/RemappedClassAttribute.cs +++ b/src/IKVM.Runtime/Attributes/RemappedClassAttribute.cs @@ -34,8 +34,8 @@ namespace IKVM.Attributes public sealed class RemappedClassAttribute : Attribute { - private string name; - private Type remappedType; + readonly string name; + readonly Type remappedType; #if EXPORTER @@ -46,6 +46,11 @@ public RemappedClassAttribute(string name, System.Type remappedType) #endif + /// + /// Initializes a new instance. + /// + /// + /// public RemappedClassAttribute(string name, Type remappedType) { this.name = name; diff --git a/src/IKVM.Runtime/Attributes/RemappedTypeAttribute.cs b/src/IKVM.Runtime/Attributes/RemappedTypeAttribute.cs index da10979780..54358c0a17 100644 --- a/src/IKVM.Runtime/Attributes/RemappedTypeAttribute.cs +++ b/src/IKVM.Runtime/Attributes/RemappedTypeAttribute.cs @@ -34,7 +34,7 @@ namespace IKVM.Attributes public sealed class RemappedTypeAttribute : Attribute { - private Type type; + readonly Type type; #if EXPORTER @@ -45,6 +45,10 @@ public RemappedTypeAttribute(System.Type type) #endif + /// + /// Initializes a new instance. + /// + /// public RemappedTypeAttribute(Type type) { this.type = type; diff --git a/src/IKVM.Runtime/Attributes/ThrowsAttribute.cs b/src/IKVM.Runtime/Attributes/ThrowsAttribute.cs index 94a481223b..39b387edfa 100644 --- a/src/IKVM.Runtime/Attributes/ThrowsAttribute.cs +++ b/src/IKVM.Runtime/Attributes/ThrowsAttribute.cs @@ -33,27 +33,32 @@ namespace IKVM.Attributes { [AttributeUsage(AttributeTargets.Constructor | AttributeTargets.Method)] - public sealed class ThrowsAttribute : Attribute - { - - internal string[] classes; - internal Type[] types; - - // this constructor is used by ikvmc, the other constructors are for use in other .NET languages - public ThrowsAttribute(string[] classes) - { - this.classes = UnicodeUtil.UnescapeInvalidSurrogates(classes); - } - - public ThrowsAttribute(Type type) - : this(new Type[] { type }) - { - } - - public ThrowsAttribute(params Type[] types) - { - this.types = types; - } + public sealed class ThrowsAttribute : Attribute + { + + internal string[] classes; + internal Type[] types; + + // this constructor is used by ikvmc, the other constructors are for use in other .NET languages + public ThrowsAttribute(string[] classes) + { + this.classes = UnicodeUtil.UnescapeInvalidSurrogates(classes); + } + + /// + /// Initializes a new instance. + /// + /// + public ThrowsAttribute(Type type) : + this(new Type[] { type }) + { + + } + + public ThrowsAttribute(params Type[] types) + { + this.types = types; + } // dotted Java class names (e.g. java.lang.Throwable) [Obsolete] diff --git a/src/IKVM.Runtime/BootstrapClassLoader.cs b/src/IKVM.Runtime/BootstrapClassLoader.cs index 1e9d42aeb4..758fab3740 100644 --- a/src/IKVM.Runtime/BootstrapClassLoader.cs +++ b/src/IKVM.Runtime/BootstrapClassLoader.cs @@ -26,13 +26,6 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; - -#if IMPORTER || EXPORTER -using IKVM.Reflection; - -using Type = IKVM.Reflection.Type; -#endif - namespace IKVM.Runtime { diff --git a/src/IKVM.Runtime/ByteCodeHelperMethods.cs b/src/IKVM.Runtime/ByteCodeHelperMethods.cs index e0691d5f28..fffd0b72bc 100644 --- a/src/IKVM.Runtime/ByteCodeHelperMethods.cs +++ b/src/IKVM.Runtime/ByteCodeHelperMethods.cs @@ -21,8 +21,6 @@ Jeroen Frijters jeroen@frijters.net */ -using System.Reflection; - using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index 1df5466c44..4f0c6d73e9 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -2405,10 +2405,8 @@ internal void ThrowException(ITypeSymbol excType) internal void SetLineNumber(ushort line) { -#if NETFRAMEWORK || IMPORTER if (symbols != null) EmitPseudoOpCode(CodeType.SequencePoint, (int)line); -#endif EmitPseudoOpCode(CodeType.LineNumber, (int)line); } @@ -2418,16 +2416,12 @@ internal byte[] GetLineNumberTable() return linenums == null ? null : linenums.ToArray(); } -#if IMPORTER - internal void EmitLineNumberTable(IMethodBaseSymbolBuilder mb) { if (linenums != null) context.AttributeHelper.SetLineNumberTable(mb, linenums); } -#endif - internal void EmitThrow(string dottedClassName) { var exception = context.ClassLoaderFactory.GetBootstrapClassLoader().LoadClassByName(dottedClassName); diff --git a/src/IKVM.Runtime/DefineMethodHelper.cs b/src/IKVM.Runtime/DefineMethodHelper.cs index 78a4731442..2e0558b14c 100644 --- a/src/IKVM.Runtime/DefineMethodHelper.cs +++ b/src/IKVM.Runtime/DefineMethodHelper.cs @@ -21,21 +21,8 @@ Jeroen Frijters jeroen@frijters.net */ -using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols; - -#if IMPORTER -using IKVM.Reflection; -using IKVM.Reflection.Emit; -using IKVM.Tools.Importer; - -using Type = IKVM.Reflection.Type; -using DynamicOrAotTypeWrapper = IKVM.Tools.Importer.RuntimeImportByteCodeJavaType; -using ProtectionDomain = System.Object; -#else -using System.Reflection; -using System.Reflection.Emit; -#endif +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.Runtime { @@ -43,7 +30,7 @@ namespace IKVM.Runtime sealed class DefineMethodHelper { - private readonly RuntimeJavaMethod mw; + readonly RuntimeJavaMethod mw; internal DefineMethodHelper(RuntimeJavaMethod mw) { diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index dff4b46568..3feb88869c 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -32,6 +32,7 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; using static System.Diagnostics.DebuggableAttribute; + using System.Collections.Immutable; diff --git a/src/IKVM.Runtime/GhostTag.cs b/src/IKVM.Runtime/GhostTag.cs index 7998b29c5f..8bf1e289a1 100644 --- a/src/IKVM.Runtime/GhostTag.cs +++ b/src/IKVM.Runtime/GhostTag.cs @@ -71,12 +71,13 @@ internal static bool IsGhostArrayInstance(object obj, RuntimeTypeHandle typeHand #if FIRST_PASS || IMPORTER throw new NotImplementedException(); #else - RuntimeJavaType tw1 = GhostTag.GetTag(obj); + var tw1 = GhostTag.GetTag(obj); if (tw1 != null) { - RuntimeJavaType tw2 = tw1.Context.ClassLoaderFactory.GetJavaTypeFromType(Type.GetTypeFromHandle(typeHandle)).MakeArrayType(rank); + var tw2 = tw1.Context.ClassLoaderFactory.GetJavaTypeFromType(Type.GetTypeFromHandle(typeHandle)).MakeArrayType(rank); return tw1.IsAssignableTo(tw2); } + return false; #endif } diff --git a/src/IKVM.Runtime/InstructionState.cs b/src/IKVM.Runtime/InstructionState.cs index 33c1b3afe5..27312c3aff 100644 --- a/src/IKVM.Runtime/InstructionState.cs +++ b/src/IKVM.Runtime/InstructionState.cs @@ -34,12 +34,12 @@ namespace IKVM.Runtime sealed class InstructionState { - private struct LocalStoreSites + struct LocalStoreSites { - private int[] data; - private int count; - private bool shared; + int[] data; + int count; + bool shared; internal LocalStoreSites Copy() { @@ -121,8 +121,19 @@ private enum ShareFlags : byte Locals = 2, All = Stack | Locals } + private ShareFlags flags; + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + /// private InstructionState(RuntimeContext context, RuntimeJavaType[] stack, int stackSize, int stackEnd, RuntimeJavaType[] locals, bool unitializedThis) { this.context = context ?? throw new ArgumentNullException(nameof(context)); @@ -134,6 +145,13 @@ private InstructionState(RuntimeContext context, RuntimeJavaType[] stack, int st this.unitializedThis = unitializedThis; } + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// internal InstructionState(RuntimeContext context, int maxLocals, int maxStack) { this.context = context ?? throw new ArgumentNullException(nameof(context)); diff --git a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs index 34a9554256..22ba987616 100644 --- a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs +++ b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs @@ -120,7 +120,7 @@ public static int ReadInt(byte[] buf, int offset) public static float ReadFloat(byte[] buf, int offset) { #if FIRST_PASS || IMPORTER - return 0; + return 0; #else return global::java.lang.Float.intBitsToFloat(ReadInt(buf, offset)); #endif diff --git a/src/IKVM.Runtime/LambdaMetafactory.cs b/src/IKVM.Runtime/LambdaMetafactory.cs index 92079c97a7..6b88472003 100644 --- a/src/IKVM.Runtime/LambdaMetafactory.cs +++ b/src/IKVM.Runtime/LambdaMetafactory.cs @@ -41,7 +41,7 @@ namespace IKVM.Runtime sealed class LambdaMetafactory { - private IMethodSymbolBuilder getInstance; + IMethodSymbolBuilder getInstance; internal static bool Emit(RuntimeByteCodeJavaType.FinishContext context, ClassFile classFile, int constantPoolIndex, ClassFile.ConstantPoolItemInvokeDynamic cpi, CodeEmitter ilgen) { diff --git a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs index 1625345a5c..27f07f5dbf 100644 --- a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs @@ -174,14 +174,10 @@ internal RuntimeClassLoader GetClassLoaderWrapper(java.lang.ClassLoader javaClas /// internal RuntimeJavaType GetJavaTypeFromType(ITypeSymbol type) { -#if IMPORTER - if (type.ContainsMissing) - return new RuntimeUnloadableJavaType(context, type); -#endif - #if !IMPORTER RuntimeJavaType.AssertFinished(type); #endif + Debug.Assert(!type.IsPointer); Debug.Assert(!type.IsByRef); @@ -192,14 +188,12 @@ internal RuntimeJavaType GetJavaTypeFromType(ITypeSymbol type) if (wrapper != null) return wrapper; -#if EXPORTER if (type.IsMissing || type.ContainsMissing) { wrapper = new RuntimeUnloadableJavaType(context, type); globalTypeToTypeWrapper.Add(type, wrapper); return wrapper; } -#endif if (remappedTypes.TryGetValue(type, out var remapped)) { diff --git a/src/IKVM.Tools.Core/Diagnostics/AsyncDiagnosticChannelWriter.cs b/src/IKVM.Tools.Core/Diagnostics/AsyncDiagnosticChannelWriter.cs index 2173ccb245..0b9b2eb5d0 100644 --- a/src/IKVM.Tools.Core/Diagnostics/AsyncDiagnosticChannelWriter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/AsyncDiagnosticChannelWriter.cs @@ -1,5 +1,6 @@ using System; using System.Buffers; +using System.IO.Pipelines; using System.Threading; using System.Threading.Channels; using System.Threading.Tasks; @@ -20,7 +21,7 @@ class AsyncDiagnosticChannelWriter : IDiagnosticChannelWriter, IDisposable AllowSynchronousContinuations = true }; - readonly IBufferWriter _writer; + readonly PipeWriter _writer; readonly Channel<(IMemoryOwner Owner, int Length)> _channel = Channel.CreateUnbounded<(IMemoryOwner Owner, int Length)>(unboundedChannelOptions); Task? _task; @@ -31,7 +32,7 @@ class AsyncDiagnosticChannelWriter : IDiagnosticChannelWriter, IDisposable /// /// /// - public AsyncDiagnosticChannelWriter(IBufferWriter writer) + public AsyncDiagnosticChannelWriter(PipeWriter writer) { _writer = writer ?? throw new ArgumentNullException(nameof(writer)); } @@ -71,7 +72,7 @@ async Task DequeueLoop(CancellationToken cancellationToken) { while (await _channel.Reader.WaitToReadAsync(cancellationToken)) while (_channel.Reader.TryRead(out var item)) - WriteData(item.Owner, item.Length); + await WriteData(item.Owner, item.Length, cancellationToken); } catch (OperationCanceledException) { @@ -85,12 +86,13 @@ async Task DequeueLoop(CancellationToken cancellationToken) /// /// /// - void WriteData(IMemoryOwner owner, int length) + async ValueTask WriteData(IMemoryOwner owner, int length, CancellationToken cancellationToken) { // allocate memory and copy data var buffer = _writer.GetMemory(length); owner.Memory.Slice(0, length).CopyTo(buffer); _writer.Advance(length); + await _writer.FlushAsync(cancellationToken); // we are finished with the owner owner.Dispose(); @@ -114,7 +116,14 @@ public void Dispose() item.Owner.Dispose(); // complete the channel - _channel.Writer.Complete(); + try + { + _channel.Writer.Complete(); + } + catch (ChannelClosedException) + { + // ignore + } } } diff --git a/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatterOptions.cs b/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatterOptions.cs index 4b4e58580f..d6f159510a 100644 --- a/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatterOptions.cs +++ b/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatterOptions.cs @@ -1,7 +1,7 @@ namespace IKVM.Tools.Core.Diagnostics { - class ConsoleDiagnosticFormatterOptions + class ConsoleDiagnosticFormatterOptions : DiagnosticFormatterOptions { diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs index 310119e228..f407ef8c05 100644 --- a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs @@ -21,11 +21,22 @@ public DiagnosticChannelFormatter(TOptions options) _options = options ?? throw new ArgumentNullException(nameof(options)); } + /// + /// Gets the options. + /// + public TOptions Options => _options; + /// public void Write(in DiagnosticEvent @event) { + var level = @event.Diagnostic.Level; + if (level is DiagnosticLevel.Warning && Options.WarnAsError) + level = DiagnosticLevel.Error; + if (level is DiagnosticLevel.Warning && Options.WarnAsErrorDiagnostics.Contains(@event.Diagnostic)) + level = DiagnosticLevel.Error; + // find the writer for the event's level - var channel = @event.Diagnostic.Level switch + var channel = level switch { DiagnosticLevel.Trace => _options.TraceChannel, DiagnosticLevel.Info => _options.InfoChannel, @@ -39,15 +50,16 @@ public void Write(in DiagnosticEvent @event) if (channel == null) return; - WriteImpl(@event, channel); + WriteImpl(@event, level, channel); } /// /// Implement this method to write the diagnostic event to the channel. /// /// + /// /// - protected abstract void WriteImpl(in DiagnosticEvent @event, IDiagnosticChannel channel); + protected abstract void WriteImpl(in DiagnosticEvent @event, DiagnosticLevel level, IDiagnosticChannel channel); /// /// Disposes of the instance. diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatterOptions.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatterOptions.cs index 5bedd556af..8438ec438f 100644 --- a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatterOptions.cs +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatterOptions.cs @@ -1,11 +1,12 @@ using System; +using System.Collections.Generic; using IKVM.CoreLib.Diagnostics; namespace IKVM.Tools.Core.Diagnostics { - abstract class DiagnosticChannelFormatterOptions + abstract class DiagnosticChannelFormatterOptions : DiagnosticFormatterOptions { /// diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticFormatterOptions.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticFormatterOptions.cs new file mode 100644 index 0000000000..03230ef6b8 --- /dev/null +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticFormatterOptions.cs @@ -0,0 +1,37 @@ +using System.Collections.Generic; +using System.Collections.Immutable; + +using IKVM.CoreLib.Diagnostics; + +namespace IKVM.Tools.Core.Diagnostics +{ + + /// + /// Base class for common diagnostic options. + /// + abstract class DiagnosticFormatterOptions + { + + /// + /// Gets or sets whether all warnings should be suppressed. + /// + public bool NoWarn { get; set; } + + /// + /// Gets or sets whether the specified diagnostics should be suppressed. + /// + public ImmutableArray NoWarnDiagnostics { get; set; } = []; + + /// + /// All warnings should be elevated to errors. + /// + public bool WarnAsError { get; set; } + + /// + /// Set of warning diagnostics that should be elevated to errors. + /// + public ImmutableArray WarnAsErrorDiagnostics { get; set; } = []; + + } + +} \ No newline at end of file diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs new file mode 100644 index 0000000000..9870c9356a --- /dev/null +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs @@ -0,0 +1,33 @@ +using System.Collections.Immutable; + +using IKVM.CoreLib.Diagnostics; + +namespace IKVM.Tools.Core.Diagnostics +{ + + class DiagnosticOptions + { + + /// + /// Gets or sets whether all warnings should be suppressed. + /// + public bool NoWarn { get; set; } + + /// + /// Gets or sets whether the specified diagnostics should be suppressed. + /// + public ImmutableArray NoWarnDiagnostics { get; set; } + + /// + /// Gets or sets whether all warnings should be promoted to errors. + /// + public bool WarnAsError { get; set; } + + /// + /// Gets or sets whether the specified diagnostics should be promoted to errors. + /// + public ImmutableArray WarnAsErrorDiagnostics { get; set; } + + } + +} \ No newline at end of file diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs index d8afd9c95d..fef86d45bc 100644 --- a/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs @@ -13,6 +13,7 @@ public static class DiagnosticServiceCollectionExtensions /// public static IServiceCollection AddToolsDiagnostics(this IServiceCollection services) { + services.AddSingleton(); services.AddSingleton(); services.AddSingleton(); services.AddSingleton(); diff --git a/src/IKVM.Tools.Core/Diagnostics/GenericChannelDiagnosticFormatterFactory.cs b/src/IKVM.Tools.Core/Diagnostics/GenericChannelDiagnosticFormatterFactory.cs index cbcdee87ce..01594b5ae9 100644 --- a/src/IKVM.Tools.Core/Diagnostics/GenericChannelDiagnosticFormatterFactory.cs +++ b/src/IKVM.Tools.Core/Diagnostics/GenericChannelDiagnosticFormatterFactory.cs @@ -18,6 +18,7 @@ abstract class GenericChannelDiagnosticFormatterFactory : static readonly char[] SEPARATOR = ['=']; readonly DiagnosticChannelProvider _channels; + readonly DiagnosticOptions _options; readonly string _format; readonly string _formatPrefix; @@ -25,10 +26,13 @@ abstract class GenericChannelDiagnosticFormatterFactory : /// Initializes a new instance. /// /// + /// + /// /// - public GenericChannelDiagnosticFormatterFactory(DiagnosticChannelProvider channels, string format) + public GenericChannelDiagnosticFormatterFactory(DiagnosticChannelProvider channels, DiagnosticOptions options, string format) { _channels = channels ?? throw new ArgumentNullException(nameof(channels)); + _options = options ?? throw new ArgumentNullException(nameof(options)); _format = format ?? throw new ArgumentNullException(nameof(format)); _formatPrefix = $"{_format},"; } @@ -57,6 +61,11 @@ public GenericChannelDiagnosticFormatterFactory(DiagnosticChannelProvider channe opts.ErrorChannel ??= GetOrCreateChannel(chls, FileDiagnosticChannelFactory.STDERR); opts.FatalChannel ??= GetOrCreateChannel(chls, FileDiagnosticChannelFactory.STDERR); + opts.NoWarn = _options.NoWarn; + opts.NoWarnDiagnostics = _options.NoWarnDiagnostics; + opts.WarnAsError = _options.WarnAsError; + opts.WarnAsErrorDiagnostics = _options.WarnAsErrorDiagnostics; + // process options and create formatter return CreateFormatter(opts); } diff --git a/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs b/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs index 900c6daae3..02dfebe0a4 100644 --- a/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs @@ -1,7 +1,4 @@ -using System.Threading; -using System.Threading.Tasks; - -using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Diagnostics; namespace IKVM.Tools.Core.Diagnostics { diff --git a/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatter.cs b/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatter.cs index 0d24a7ee4a..27514b1091 100644 --- a/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatter.cs @@ -25,15 +25,14 @@ public JsonDiagnosticFormatter(JsonDiagnosticFormatterOptions options) : } /// - protected override void WriteImpl(in DiagnosticEvent @event, IDiagnosticChannel channel) + protected override void WriteImpl(in DiagnosticEvent @event, DiagnosticLevel level, IDiagnosticChannel channel) { var encoding = channel.Encoding ?? Encoding.UTF8; - using var buffer = MemoryPool.Shared.Rent(8192); + var buffer = MemoryPool.Shared.Rent(8192); var writer = new MemoryBufferWriter(buffer.Memory); - JsonDiagnosticFormat.Write(@event.Diagnostic.Id, @event.Diagnostic.Level, @event.Diagnostic.Message, @event.Args, @event.Exception, @event.Location, ref writer, encoding); + JsonDiagnosticFormat.Write(@event.Diagnostic.Id, level, @event.Diagnostic.Message, @event.Args, @event.Exception, @event.Location, ref writer, encoding); WriteLine(writer, encoding); channel.Writer.Write(buffer, writer.WrittenCount); - return; } /// diff --git a/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatterFactory.cs b/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatterFactory.cs index f10a530525..384f18d179 100644 --- a/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatterFactory.cs +++ b/src/IKVM.Tools.Core/Diagnostics/JsonDiagnosticFormatterFactory.cs @@ -15,9 +15,10 @@ class JsonDiagnosticFormatterFactory : /// Initializes a new instance. /// /// + /// /// - public JsonDiagnosticFormatterFactory(DiagnosticChannelProvider channels) : - base(channels, "json") + public JsonDiagnosticFormatterFactory(DiagnosticChannelProvider channels, DiagnosticOptions options) : + base(channels, options, "json") { } diff --git a/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatter.cs b/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatter.cs index d1730936fb..6ad1db2afb 100644 --- a/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatter.cs @@ -25,15 +25,14 @@ public TextDiagnosticFormatter(TextDiagnosticFormatterOptions options) : } /// - protected override void WriteImpl(in DiagnosticEvent @event, IDiagnosticChannel channel) + protected override void WriteImpl(in DiagnosticEvent @event, DiagnosticLevel level, IDiagnosticChannel channel) { var encoding = channel.Encoding ?? Encoding.UTF8; - using var buffer = MemoryPool.Shared.Rent(8192); + var buffer = MemoryPool.Shared.Rent(8192); var writer = new MemoryBufferWriter(buffer.Memory); - TextDiagnosticFormat.Write(@event.Diagnostic.Id, @event.Diagnostic.Level, @event.Diagnostic.Message, @event.Args, @event.Exception, @event.Location, ref writer, encoding); + TextDiagnosticFormat.Write(@event.Diagnostic.Id, level, @event.Diagnostic.Message, @event.Args, @event.Exception, @event.Location, ref writer, encoding); WriteLine(writer, encoding); channel.Writer.Write(buffer, writer.WrittenCount); - return; } /// diff --git a/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatterFactory.cs b/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatterFactory.cs index 918930bc67..2aac5bcaaf 100644 --- a/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatterFactory.cs +++ b/src/IKVM.Tools.Core/Diagnostics/TextDiagnosticFormatterFactory.cs @@ -15,9 +15,10 @@ class TextDiagnosticFormatterFactory : /// Initializes a new instance. /// /// + /// /// - public TextDiagnosticFormatterFactory(DiagnosticChannelProvider channels) : - base(channels, "text") + public TextDiagnosticFormatterFactory(DiagnosticChannelProvider channels, DiagnosticOptions options) : + base(channels, options, "text") { } diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index 08d4327fb4..b889c289c6 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -306,26 +306,22 @@ RuntimeJavaType GetTypeWrapperCompilerHook(string name) } catch (UnsupportedClassVersionException e) { - Context.StaticCompiler.SuppressWarning(state, Diagnostic.ClassNotFound, name); Diagnostics.ClassFormatError(name, e.Message); return null; } catch (ByteCodeException e) { - Context.StaticCompiler.SuppressWarning(state, Diagnostic.ClassNotFound, name); Diagnostics.ClassFormatError(name, e.Message); return null; } catch (ClassFormatError e) { - Context.StaticCompiler.SuppressWarning(state, Diagnostic.ClassNotFound, name); Diagnostics.ClassFormatError(name, e.Message); return null; } if (f.Name != name) { - Context.StaticCompiler.SuppressWarning(state, Diagnostic.ClassNotFound, name); Diagnostics.WrongClassName(name, f.Name); return null; } @@ -434,7 +430,6 @@ RuntimeJavaType GetTypeWrapperCompilerHook(string name) Diagnostics.GenericUnableToCompileError(name, x.GetType().Name, x.Message); } - Context.StaticCompiler.SuppressWarning(state, Diagnostic.ClassNotFound, name); return null; } else @@ -2526,78 +2521,82 @@ private static bool IsSigned(IAssemblySymbol asm) /// internal static int Compile(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, List imports) { - var loaders = new List(); - - // create class loaders for each import - foreach (var import in imports) + try { - int rc = CreateCompiler(context, compiler, diagnostics, import, out var loader); - if (rc != 0) - return rc; + var loaders = new List(); - loaders.Add(loader); - import.sharedclassloader?.Add(loader); - } + // create class loaders for each import + foreach (var import in imports) + { + int rc = CreateCompiler(context, compiler, diagnostics, import, out var loader); + if (rc != 0) + return rc; - // add a reference between all of the loaders. - foreach (var loader1 in loaders) - foreach (var loader2 in loaders) - if (loader1 != loader2 && (loader1.state.crossReferenceAllPeers || (loader1.state.peerReferences != null && Array.IndexOf(loader1.state.peerReferences, loader2.state.assembly) != -1))) - loader1.AddReference(loader2); + loaders.Add(loader); + import.sharedclassloader?.Add(loader); + } - // first compilation pass - foreach (var loader in loaders) - loader.CompilePass0(); + // add a reference between all of the loaders. + foreach (var loader1 in loaders) + foreach (var loader2 in loaders) + if (loader1 != loader2 && (loader1.state.crossReferenceAllPeers || (loader1.state.peerReferences != null && Array.IndexOf(loader1.state.peerReferences, loader2.state.assembly) != -1))) + loader1.AddReference(loader2); - var mainAssemblyTypes = new Dictionary(); + // first compilation pass + foreach (var loader in loaders) + loader.CompilePass0(); - foreach (var loader in loaders) - { - if (loader.state.sharedclassloader != null) + var mainAssemblyTypes = new Dictionary(); + + foreach (var loader in loaders) { - if (mainAssemblyTypes.TryGetValue(loader.state.sharedclassloader[0], out var mainAssemblyType) == false) + if (loader.state.sharedclassloader != null) { - var tb = loader.state.sharedclassloader[0].GetTypeWrapperFactory().ModuleBuilder.DefineType("__", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Abstract | System.Reflection.TypeAttributes.SpecialName); - loader.Context.AttributeHelper.HideFromJava(tb); - tb.Complete(); + if (mainAssemblyTypes.TryGetValue(loader.state.sharedclassloader[0], out var mainAssemblyType) == false) + { + var tb = loader.state.sharedclassloader[0].GetTypeWrapperFactory().ModuleBuilder.DefineType("__", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Abstract | System.Reflection.TypeAttributes.SpecialName); + loader.Context.AttributeHelper.HideFromJava(tb); + tb.Complete(); + + mainAssemblyType = tb; + mainAssemblyTypes.Add(loader.state.sharedclassloader[0], mainAssemblyType); + } - mainAssemblyType = tb; - mainAssemblyTypes.Add(loader.state.sharedclassloader[0], mainAssemblyType); + if (loader.state.sharedclassloader[0] != loader) + ((IAssemblySymbolBuilder)loader.GetTypeWrapperFactory().ModuleBuilder.Assembly).AddTypeForwarder(mainAssemblyType); } - if (loader.state.sharedclassloader[0] != loader) - ((IAssemblySymbolBuilder)loader.GetTypeWrapperFactory().ModuleBuilder.Assembly).AddTypeForwarder(mainAssemblyType); + loader.CompilePass1(); } - loader.CompilePass1(); - } - - foreach (var loader in loaders) - loader.CompilePass2(); - - if (context.Options.Bootstrap) foreach (var loader in loaders) - loader.EmitRemappedTypes2ndPass(); + loader.CompilePass2(); - foreach (var loader in loaders) - { - int rc = loader.CompilePass3(); - if (rc != 0) - return rc; - } + if (context.Options.Bootstrap) + foreach (var loader in loaders) + loader.EmitRemappedTypes2ndPass(); - diagnostics.GenericCompilerInfo("CompilerClassLoader.Save..."); + foreach (var loader in loaders) + { + int rc = loader.CompilePass3(); + if (rc != 0) + return rc; + } - foreach (var loader in loaders) - loader.PrepareSave(); + diagnostics.GenericCompilerInfo("CompilerClassLoader.Save..."); - //if (compiler.errorCount > 0) - // return 1; + foreach (var loader in loaders) + loader.PrepareSave(); - foreach (var loader in loaders) - loader.Save(); + foreach (var loader in loaders) + loader.Save(); + } + catch (FileFormatLimitationExceededException e) + { + throw new FatalCompilerErrorException(DiagnosticEvent.FileFormatLimitationExceeded(e.Message)); + } - return 1; + return 0; } static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiagnosticHandler diagnostics, ImportContext import, out ImportClassLoader loader) diff --git a/src/IKVM.Tools.Importer/ImportCommand.cs b/src/IKVM.Tools.Importer/ImportCommand.cs index 10e5803eb4..b2e088a8d7 100644 --- a/src/IKVM.Tools.Importer/ImportCommand.cs +++ b/src/IKVM.Tools.Importer/ImportCommand.cs @@ -200,15 +200,13 @@ public ImportCommand(bool root = true) aliases: ["-publicpackage"], description: "Mark all classes with a package name starting with as public to the assembly.")); - Add(NoWarnOption = new Option( + Add(NoWarnOption = new Option( aliases: ["-nowarn"], - description: "Disable specific warning messages.", - parseArgument: ParseDiagnosticArray)); + description: "Disable specific warning messages.")); - Add(WarnAsErrorOption = new Option( + Add(WarnAsErrorOption = new Option( aliases: ["-warnaserror"], - description: "Report all warnings as errors.", - parseArgument: ParseDiagnosticArray)); + description: "Report all warnings as errors.")); if (root) Add(RuntimeOption = new Option( @@ -301,23 +299,29 @@ public ImportCommand(bool root = true) /// /// /// - Diagnostic[] ParseDiagnosticArray(ArgumentResult result) + Diagnostic[]? ParseDiagnosticArray(ArgumentResult result) { - var l = new List(); + List? l = null; foreach (var i in result.Tokens) { foreach (var j in i.Value.Split(LIST_SEPARATOR, StringSplitOptions.RemoveEmptyEntries)) { if (int.TryParse(j, out var id) && Diagnostic.GetById(id) is { } diagnostic) + { + l ??= new(); l.Add(diagnostic); + } if (j.StartsWith("IKVM", StringComparison.OrdinalIgnoreCase) && int.TryParse(j["IKVM".Length..], out var id2) && Diagnostic.GetById(id2) is { } diagnostic2) + { + l ??= new(); l.Add(diagnostic2); + } } } - return l.ToArray(); + return l?.ToArray(); } /// @@ -427,9 +431,9 @@ void ValidateResource(OptionResult symbolResult) public Option PublicPackageOption { get; set; } - public Option NoWarnOption { get; set; } + public Option NoWarnOption { get; set; } - public Option WarnAsErrorOption { get; set; } + public Option WarnAsErrorOption { get; set; } public Option? RuntimeOption { get; set; } diff --git a/src/IKVM.Tools.Importer/ImportContext.cs b/src/IKVM.Tools.Importer/ImportContext.cs index ddad70d932..55eefe5009 100644 --- a/src/IKVM.Tools.Importer/ImportContext.cs +++ b/src/IKVM.Tools.Importer/ImportContext.cs @@ -29,7 +29,6 @@ Jeroen Frijters using IKVM.CoreLib.Symbols; using IKVM.Reflection; -using IKVM.Reflection.Emit; using IKVM.Runtime; namespace IKVM.Tools.Importer @@ -88,31 +87,28 @@ sealed class ImportContext internal uint fileAlignment; internal bool highentropyva; internal List sharedclassloader; // should *not* be deep copied in Copy(), because we want the list of all compilers that share a class loader - internal HashSet suppressWarnings = new HashSet(StringComparer.OrdinalIgnoreCase); - internal HashSet errorWarnings = new HashSet(StringComparer.OrdinalIgnoreCase); - internal bool warnaserror; // treat all warnings as errors internal List proxies = new(); internal List assemblyAttributeAnnotations = new(); internal bool warningLevelHigh; internal bool noParameterReflection; internal bool bootstrap; - internal string log; + /// + /// Creates a copy of the current . + /// + /// internal ImportContext Copy() { - ImportContext copy = (ImportContext)MemberwiseClone(); + var copy = (ImportContext)MemberwiseClone(); copy.jars = Copy(jars); copy.jarMap = new Dictionary(jarMap); + if (props != null) - { copy.props = new Dictionary(props); - } + if (externalResources != null) - { copy.externalResources = new Dictionary(externalResources); - } - copy.suppressWarnings = new(suppressWarnings, StringComparer.OrdinalIgnoreCase); - copy.errorWarnings = new(errorWarnings, StringComparer.OrdinalIgnoreCase); + return copy; } diff --git a/src/IKVM.Tools.Importer/ImportContextFactory.cs b/src/IKVM.Tools.Importer/ImportContextFactory.cs index ad514c740b..b151d670a9 100644 --- a/src/IKVM.Tools.Importer/ImportContextFactory.cs +++ b/src/IKVM.Tools.Importer/ImportContextFactory.cs @@ -21,57 +21,6 @@ namespace IKVM.Tools.Importer class ImportContextFactory { - /// - /// for the importer. - /// - class CompilerOptionsDiagnosticHandler : FormattedDiagnosticHandler - { - - readonly ImportContext _options; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public CompilerOptionsDiagnosticHandler(ImportContext options, string spec, DiagnosticFormatterProvider formatters) : - base(spec, formatters) - { - _options = options ?? throw new ArgumentNullException(nameof(options)); - } - - /// - public override bool IsEnabled(Diagnostic diagnostic) - { - return diagnostic.Level is not DiagnosticLevel.Trace and not DiagnosticLevel.Info; - } - - /// - public override void Report(in DiagnosticEvent @event) - { - if (IsEnabled(@event.Diagnostic) == false) - return; - - var key = @event.Diagnostic.Id.ToString(); - for (int i = 0; ; i++) - { - if (_options.suppressWarnings.Contains(key)) - return; - - if (i == @event.Args.Length) - break; - - key += ":" + @event.Args[i]; - } - - _options.suppressWarnings.Add(key); - - base.Report(@event); - } - - } - readonly RuntimeContext runtime; readonly ImportAssemblyResolver resolver; readonly StaticCompiler compiler; @@ -376,20 +325,6 @@ void Create(ImportOptions options, ImportContext import, List tar foreach (var prefix in options.PublicPackages) import.publicPackages = [.. import.privatePackages, prefix]; - if (options.NoWarn != null) - foreach (var diagnostic in options.NoWarn) - import.suppressWarnings.Add($"IKVM{diagnostic.Id:D4}"); - - // TODO handle specific diagnostic IDs - if (options.WarnAsError != null) - { - if (options.WarnAsError.Length == 0) - import.warnaserror = true; - else - foreach (var i in options.WarnAsError) - import.errorWarnings.Add($"IKVM{i.Id:D4}"); - } - if (options.ClassLoader != null) import.classLoader = options.ClassLoader; diff --git a/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs b/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs new file mode 100644 index 0000000000..09a816b42b --- /dev/null +++ b/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs @@ -0,0 +1,50 @@ +using System; +using System.Linq; + +using IKVM.CoreLib.Diagnostics; +using IKVM.Tools.Core.Diagnostics; + +namespace IKVM.Tools.Importer +{ + + /// + /// for the importer. + /// + class ImportDiagnosticHandler : FormattedDiagnosticHandler + { + + readonly ImportOptions _options; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ImportDiagnosticHandler(ImportOptions options, string spec, DiagnosticFormatterProvider formatters) : + base(spec, formatters) + { + _options = options ?? throw new ArgumentNullException(nameof(options)); + } + + /// + public override bool IsEnabled(Diagnostic diagnostic) + { + if (diagnostic.Level is DiagnosticLevel.Trace or DiagnosticLevel.Info) + return false; + + if (diagnostic.Level == DiagnosticLevel.Warning && _options.NoWarn.Any(i => i.Id == diagnostic.Id)) + return false; + + return true; + } + + /// + public override void Report(in DiagnosticEvent @event) + { + base.Report(@event); + } + + } + +} diff --git a/src/IKVM.Tools.Importer/ImportOptionsBinding.cs b/src/IKVM.Tools.Importer/ImportOptionsBinding.cs index 97b84affb1..be3c464f08 100644 --- a/src/IKVM.Tools.Importer/ImportOptionsBinding.cs +++ b/src/IKVM.Tools.Importer/ImportOptionsBinding.cs @@ -153,10 +153,10 @@ protected override ImportOptions GetBoundValue(BindingContext context) if (context.ParseResult.GetValueForOption(command.PublicPackageOption) is string[] _publicpackages) options.PublicPackages = AppendArray(options.PublicPackages, _publicpackages); - if (context.ParseResult.GetValueForOption(command.NoWarnOption) is Diagnostic[] _nowarn) + if (ParseDiagnosticIdListForOption(context, command.NoWarnOption, LIST_SEPARATOR, null) is Diagnostic[] _nowarn) options.NoWarn = options.NoWarn != null ? AppendArray(options.NoWarn, _nowarn) : _nowarn; - if (context.ParseResult.GetValueForOption(command.WarnAsErrorOption) is Diagnostic[] _warnaserror) + if (ParseDiagnosticIdListForOption(context, command.WarnAsErrorOption, LIST_SEPARATOR, null) is Diagnostic[] _warnaserror) options.WarnAsError = options.WarnAsError != null ? AppendArray(options.WarnAsError, _warnaserror) : _warnaserror; if (command.RuntimeOption != null) @@ -239,10 +239,7 @@ protected override ImportOptions GetBoundValue(BindingContext context) /// T[] AppendArray(T[] a, T[] b) { - var tmp = new T[a.Length + b.Length]; - a.CopyTo(tmp, 0); - b.CopyTo(tmp, a.Length); - return tmp; + return [.. a, .. b]; } /// @@ -299,12 +296,27 @@ T GetParsedValueForOption(BindingContext context, Option option, T d /// /// /// - int[]? ParseDiagnosticIdListForOption(BindingContext context, Option option, char[] separator, int[]? defaultValue) + Diagnostic[]? ParseDiagnosticIdListForOption(BindingContext context, Option option, char[] separator, Diagnostic[]? defaultValue) { if (context.ParseResult.GetValueForOption(option) is string v) - return (int[]?)v.Split(separator, StringSplitOptions.RemoveEmptyEntries).Select(SafeParseDiagnosticId).Where(i => i != null).OfType().ToArray(); - else - return defaultValue; + { + List? l = null; + + foreach (var i in v.Split(separator, StringSplitOptions.RemoveEmptyEntries)) + { + var d = SafeParseDiagnosticId(i); + if (d != null) + { + l ??= []; + l.Add(d); + } + } + + if (l != null) + return l.ToArray(); + } + + return defaultValue; } /// @@ -312,10 +324,10 @@ T GetParsedValueForOption(BindingContext context, Option option, T d /// /// /// - int? SafeParseDiagnosticId(string value) + Diagnostic? SafeParseDiagnosticId(string value) { if (int.TryParse(value, out var i)) - return i; + return Diagnostic.GetById(i); if (value.StartsWith("IKVM", StringComparison.OrdinalIgnoreCase)) return SafeParseDiagnosticId(value["IKVM".Length..]); diff --git a/src/IKVM.Tools.Importer/ImportTool.cs b/src/IKVM.Tools.Importer/ImportTool.cs index aa4a8e6d98..5690e4466c 100644 --- a/src/IKVM.Tools.Importer/ImportTool.cs +++ b/src/IKVM.Tools.Importer/ImportTool.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.CommandLine; using System.CommandLine.Builder; using System.CommandLine.Parsing; @@ -25,7 +26,7 @@ namespace IKVM.Tools.Importer /// /// Main entry point for the application. /// - public class ImportTool + public partial class ImportTool { /// @@ -55,7 +56,6 @@ internal static async Task ExecuteInContext(string[] args, CancellationToke /// Executes the importer. /// /// - /// /// /// async Task ExecuteImplAsync(ImportOptions options, CancellationToken cancellationToken) @@ -63,7 +63,9 @@ async Task ExecuteImplAsync(ImportOptions options, CancellationToken cancel var services = new ServiceCollection(); services.AddToolsDiagnostics(); services.AddSingleton(options); - services.AddSingleton(p => GetDiagnostics(p, p.GetRequiredService().Log)); + services.AddSingleton(p => GetDiagnosticOptions(p, p.GetRequiredService())); + services.AddSingleton(p => GetDiagnostics(p, p.GetRequiredService().Log)); + services.AddSingleton(p => p.GetRequiredService()); services.AddSingleton(p => CreateResolver(p.GetRequiredService(), p.GetRequiredService())); services.AddSingleton(p => p.GetRequiredService().Universe); services.AddSingleton(); @@ -74,17 +76,31 @@ async Task ExecuteImplAsync(ImportOptions options, CancellationToken cancel services.AddSingleton(); using var provider = services.BuildServiceProvider(); - // convert options to imports - var imports = provider.GetRequiredService().Create(options); - if (imports.Count == 0) - throw new FatalCompilerErrorException(DiagnosticEvent.NoTargetsFound()); - - // execute the compiler - return await Task.Run(() => Execute( - provider.GetRequiredService(), - provider.GetRequiredService(), - provider.GetRequiredService(), - imports)); + try + { + // convert options to imports + var imports = provider.GetRequiredService().Create(options); + if (imports.Count == 0) + throw new FatalCompilerErrorException(DiagnosticEvent.NoTargetsFound()); + + // execute the compiler + return await Task.Run(() => Execute( + provider.GetRequiredService(), + provider.GetRequiredService(), + provider.GetRequiredService(), + imports)); + } + catch (FatalCompilerErrorException e) + { + provider.GetRequiredService().Report(e.Event); + return e.Event.Diagnostic.Id; + + } + catch (Exception e) + { + provider.GetRequiredService().GenericCompilerError(e.Message); + return Diagnostic.GenericCompilerError.Id; + } } /// @@ -222,14 +238,36 @@ Task ExecuteAsync(ImportOptions options, CancellationToken cancellationToken = d /// /// /// - static FormattedDiagnosticHandler GetDiagnostics(IServiceProvider services, string spec) + static ImportDiagnosticHandler GetDiagnostics(IServiceProvider services, string spec) { if (services is null) throw new ArgumentNullException(nameof(services)); if (string.IsNullOrWhiteSpace(spec)) throw new ArgumentException($"'{nameof(spec)}' cannot be null or whitespace.", nameof(spec)); - return ActivatorUtilities.CreateInstance(services, spec); + return ActivatorUtilities.CreateInstance(services, spec); + } + + /// + /// Generates a diagnostic instance from the diagnostics options. + /// + /// + /// + /// + static DiagnosticOptions GetDiagnosticOptions(IServiceProvider services, ImportOptions options) + { + if (services is null) + throw new ArgumentNullException(nameof(services)); + if (options is null) + throw new ArgumentNullException(nameof(options)); + + return new DiagnosticOptions() + { + NoWarn = options.NoWarn != null && options.NoWarn.Length == 0, + NoWarnDiagnostics = options.NoWarn?.ToImmutableArray() ?? [], + WarnAsError = options.WarnAsError != null && options.WarnAsError.Length == 0, + WarnAsErrorDiagnostics = options.WarnAsError?.ToImmutableArray() ?? [], + }; } /// diff --git a/src/IKVM.Tools.Importer/StaticCompiler.cs b/src/IKVM.Tools.Importer/StaticCompiler.cs index a0ccb68cc7..52f8d526ca 100644 --- a/src/IKVM.Tools.Importer/StaticCompiler.cs +++ b/src/IKVM.Tools.Importer/StaticCompiler.cs @@ -23,7 +23,6 @@ Jeroen Frijters */ using System; -using System.Collections.Concurrent; using System.IO; using IKVM.CoreLib.Diagnostics; @@ -143,11 +142,6 @@ internal void IssueMissingTypeMessage(ITypeSymbol type) diagnostics.MissingType(type.FullName, type.Assembly.FullName); } - internal void SuppressWarning(ImportContext options, Diagnostic diagnostic, string name) - { - options.suppressWarnings.Add($"{diagnostic.Id}:{name}"); - } - } } \ No newline at end of file diff --git a/src/ikvmc/Properties/launchSettings.json b/src/ikvmc/Properties/launchSettings.json index 31d9cf8012..a472b2cdaf 100644 --- a/src/ikvmc/Properties/launchSettings.json +++ b/src/ikvmc/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmc": { "commandName": "Project", - "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net8.0\\IKVM.Java.ikvmc.rsp" + "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net472\\IKVM.Java.ikvmc.rsp" } } } diff --git a/src/ikvmc/ikvmc.csproj b/src/ikvmc/ikvmc.csproj index 3b5519e290..2be36ac434 100644 --- a/src/ikvmc/ikvmc.csproj +++ b/src/ikvmc/ikvmc.csproj @@ -1,7 +1,7 @@  Exe - net8.0;net472;net6.0; + net472;net8.0;;net6.0; $(_SupportedToolRuntimes) true true From ef32c6287e5fcbffadaca117ee198e687ca8943f Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 27 Sep 2024 16:13:59 -0500 Subject: [PATCH 15/59] Weee. --- src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs | 280 ++++++++-------- src/IKVM.CoreLib/Diagnostics/Diagnostic.g.tt | 2 +- src/IKVM.CoreLib/Diagnostics/Diagnostic.t4 | 4 +- .../Diagnostics/DiagnosticEvent.g.cs | 281 ++++++++-------- .../Diagnostics/DiagnosticEvent.g.tt | 2 +- .../Diagnostics/DiagnosticEventException.cs} | 8 +- .../Diagnostics/DiagnosticEventHandler.g.cs | 280 ++++++++-------- .../Diagnostics/DiagnosticEventHandler.g.tt | 2 +- .../Diagnostics/IDiagnosticHandler.g.cs | 280 ++++++++-------- .../Diagnostics/IDiagnosticHandler.g.tt | 2 +- .../Diagnostics/NullDiagnosticHandler.g.cs | 280 ++++++++-------- .../Diagnostics/NullDiagnosticHandler.g.tt | 2 +- .../Tracing/DiagnosticEventSource.g.cs | 280 ++++++++-------- .../Tracing/DiagnosticEventSource.g.tt | 2 +- src/IKVM.CoreLib/Symbols/ISymbolResolver.cs | 6 - .../Emit/IkvmReflectionILGenerator.cs | 2 - src/IKVM.Runtime/AttributeHelper.cs | 26 +- src/IKVM.Runtime/BigEndianBinaryReader.cs | 2 +- src/IKVM.Runtime/BootstrapClassLoader.cs | 2 +- src/IKVM.Runtime/ByteCodeHelper.cs | 4 +- src/IKVM.Runtime/ByteCodeHelperMethods.cs | 2 +- src/IKVM.Runtime/CodeEmitter.cs | 6 +- src/IKVM.Runtime/DynamicCallerIDProvider.cs | 7 +- src/IKVM.Runtime/ExceptionHelper.cs | 4 +- src/IKVM.Runtime/GhostTag.cs | 4 +- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 64 +++- src/IKVM.Runtime/JNI/JNIEnv.cs | 14 +- src/IKVM.Runtime/JVM.Internal.cs | 20 +- src/IKVM.Runtime/JVM.Properties.cs | 2 +- src/IKVM.Runtime/JVM.Resolver.cs | 184 +++++++++-- .../Java/Externs/ikvm/runtime/Util.cs | 8 +- .../Java/Externs/java/io/ObjectStreamClass.cs | 86 ++--- .../Java/Externs/java/lang/Class.cs | 2 +- .../Java/Externs/java/lang/Package.cs | 2 +- .../Java/Externs/java/lang/reflect/Proxy.cs | 32 +- .../Externs/sun/reflect/ReflectionFactory.cs | 312 +++++++++--------- src/IKVM.Runtime/MethodAnalyzer.cs | 24 +- .../MethodHandleUtil.jniexport.cs | 84 ++--- .../RuntimeAssemblyClassLoader.cs | 2 +- .../RuntimeByteCodeJavaType.FinishContext.cs | 8 +- src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 6 +- src/IKVM.Runtime/RuntimeClassLoaderFactory.cs | 12 +- src/IKVM.Runtime/RuntimeContextOptions.cs | 9 +- src/IKVM.Runtime/RuntimeJavaType.cs | 2 +- ...anagedByteCodeJavaType.RemappedJavaType.cs | 2 +- .../RuntimeManagedByteCodeJavaType.cs | 12 +- ...gedJavaType.AttributeAnnotationJavaType.cs | 2 +- ...agedJavaType.DelegateInnerClassJavaType.cs | 2 +- ...RuntimeManagedJavaType.EnumEnumJavaType.cs | 2 +- src/IKVM.Runtime/RuntimeManagedJavaType.cs | 2 +- src/IKVM.Runtime/StubGen/StubGenerator.cs | 22 +- .../Invoke/NativeInvokerBytecodeGenerator.cs | 22 +- src/IKVM.Runtime/atomic.cs | 2 +- src/IKVM.Runtime/compiler.cs | 41 ++- src/IKVM.Runtime/intrinsics.cs | 2 +- .../Diagnostics/ConsoleDiagnosticFormatter.cs | 31 +- .../Diagnostics/DiagnosticChannelFormatter.cs | 30 +- .../DiagnosticServiceCollectionExtensions.cs | 1 + .../Diagnostics/IDiagnosticFormatter.cs | 7 + src/IKVM.Tools.Core/IKVM.Tools.Core.csproj | 6 +- src/IKVM.Tools.Exporter/ExportImpl.cs | 9 +- .../ExportRuntimeSymbolResolver.cs | 287 ++++++++++++++++ src/IKVM.Tools.Exporter/ExportTool.cs | 2 +- .../ManagedTypeResolver.cs | 163 --------- .../ImportAssemblyResolver.cs | 4 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 64 ++-- src/IKVM.Tools.Importer/ImportCommand.cs | 30 -- .../ImportContextFactory.cs | 58 ++-- .../ImportDiagnosticHandler.cs | 4 +- .../ImportRuntimeSymbolResolver.cs | 217 +++++++----- src/IKVM.Tools.Importer/ImportTool.cs | 58 ++-- .../RuntimeImportByteCodeJavaType.cs | 2 +- src/IKVM.Tools.Importer/StaticCompiler.cs | 8 +- src/ikvmc/Properties/launchSettings.json | 2 +- src/ikvmc/ikvmc.csproj | 2 +- src/ikvmstub/Properties/launchSettings.json | 4 +- 76 files changed, 2067 insertions(+), 1676 deletions(-) rename src/{IKVM.Tools.Importer/FatalCompilerErrorException.cs => IKVM.CoreLib/Diagnostics/DiagnosticEventException.cs} (88%) create mode 100644 src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs delete mode 100644 src/IKVM.Tools.Exporter/ManagedTypeResolver.cs diff --git a/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs b/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs index 36c9374bf6..c5edb304d0 100644 --- a/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.cs @@ -302,7 +302,7 @@ partial record class Diagnostic /// The 'MainMethodFound' diagnostic. /// /// -/// Found main method in class "{arg0}". +/// Info: Found main method in class "{arg0}". /// public static readonly Diagnostic MainMethodFound = new Diagnostic(1, nameof(MainMethodFound), "Found main method in class \"{0}\".", DiagnosticLevel.Info); @@ -310,7 +310,7 @@ partial record class Diagnostic /// The 'OutputFileIs' diagnostic. /// /// -/// Output file is "{arg0}". +/// Info: Output file is "{arg0}". /// public static readonly Diagnostic OutputFileIs = new Diagnostic(2, nameof(OutputFileIs), "Output file is \"{0}\".", DiagnosticLevel.Info); @@ -318,7 +318,7 @@ partial record class Diagnostic /// The 'AutoAddRef' diagnostic. /// /// -/// Automatically adding reference to "{arg0}". +/// Info: Automatically adding reference to "{arg0}". /// public static readonly Diagnostic AutoAddRef = new Diagnostic(3, nameof(AutoAddRef), "Automatically adding reference to \"{0}\".", DiagnosticLevel.Info); @@ -326,7 +326,7 @@ partial record class Diagnostic /// The 'MainMethodFromManifest' diagnostic. /// /// -/// Using main class "{arg0}" based on jar manifest. +/// Info: Using main class "{arg0}" based on jar manifest. /// public static readonly Diagnostic MainMethodFromManifest = new Diagnostic(4, nameof(MainMethodFromManifest), "Using main class \"{0}\" based on jar manifest.", DiagnosticLevel.Info); @@ -334,7 +334,7 @@ partial record class Diagnostic /// The 'GenericCompilerInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static readonly Diagnostic GenericCompilerInfo = new Diagnostic(5, nameof(GenericCompilerInfo), "{0}", DiagnosticLevel.Info); @@ -342,7 +342,7 @@ partial record class Diagnostic /// The 'GenericClassLoadingInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static readonly Diagnostic GenericClassLoadingInfo = new Diagnostic(6, nameof(GenericClassLoadingInfo), "{0}", DiagnosticLevel.Info); @@ -350,7 +350,7 @@ partial record class Diagnostic /// The 'GenericVerifierInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static readonly Diagnostic GenericVerifierInfo = new Diagnostic(7, nameof(GenericVerifierInfo), "{0}", DiagnosticLevel.Info); @@ -358,7 +358,7 @@ partial record class Diagnostic /// The 'GenericRuntimeInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static readonly Diagnostic GenericRuntimeInfo = new Diagnostic(8, nameof(GenericRuntimeInfo), "{0}", DiagnosticLevel.Info); @@ -366,7 +366,7 @@ partial record class Diagnostic /// The 'GenericJniInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static readonly Diagnostic GenericJniInfo = new Diagnostic(9, nameof(GenericJniInfo), "{0}", DiagnosticLevel.Info); @@ -374,7 +374,7 @@ partial record class Diagnostic /// The 'ClassNotFound' diagnostic. /// /// -/// Class "{arg0}" not found. +/// Warning: Class "{arg0}" not found. /// public static readonly Diagnostic ClassNotFound = new Diagnostic(100, nameof(ClassNotFound), "Class \"{0}\" not found.", DiagnosticLevel.Warning); @@ -382,7 +382,7 @@ partial record class Diagnostic /// The 'ClassFormatError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (class format error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (class format error "{arg1}") /// public static readonly Diagnostic ClassFormatError = new Diagnostic(101, nameof(ClassFormatError), "Unable to compile class \"{0}\". (class format error \"{1}\")", DiagnosticLevel.Warning); @@ -390,7 +390,7 @@ partial record class Diagnostic /// The 'DuplicateClassName' diagnostic. /// /// -/// Duplicate class name: "{arg0}". +/// Warning: Duplicate class name: "{arg0}". /// public static readonly Diagnostic DuplicateClassName = new Diagnostic(102, nameof(DuplicateClassName), "Duplicate class name: \"{0}\".", DiagnosticLevel.Warning); @@ -398,7 +398,7 @@ partial record class Diagnostic /// The 'IllegalAccessError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (illegal access error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (illegal access error "{arg1}") /// public static readonly Diagnostic IllegalAccessError = new Diagnostic(103, nameof(IllegalAccessError), "Unable to compile class \"{0}\". (illegal access error \"{1}\")", DiagnosticLevel.Warning); @@ -406,7 +406,7 @@ partial record class Diagnostic /// The 'VerificationError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (verification error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (verification error "{arg1}") /// public static readonly Diagnostic VerificationError = new Diagnostic(104, nameof(VerificationError), "Unable to compile class \"{0}\". (verification error \"{1}\")", DiagnosticLevel.Warning); @@ -414,7 +414,7 @@ partial record class Diagnostic /// The 'NoClassDefFoundError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (missing class "{arg1}") +/// Warning: Unable to compile class "{arg0}". (missing class "{arg1}") /// public static readonly Diagnostic NoClassDefFoundError = new Diagnostic(105, nameof(NoClassDefFoundError), "Unable to compile class \"{0}\". (missing class \"{1}\")", DiagnosticLevel.Warning); @@ -422,7 +422,7 @@ partial record class Diagnostic /// The 'GenericUnableToCompileError' diagnostic. /// /// -/// Unable to compile class "{arg0}". ("{arg1}": "{arg2}") +/// Warning: Unable to compile class "{arg0}". ("{arg1}": "{arg2}") /// public static readonly Diagnostic GenericUnableToCompileError = new Diagnostic(106, nameof(GenericUnableToCompileError), "Unable to compile class \"{0}\". (\"{1}\": \"{2}\")", DiagnosticLevel.Warning); @@ -430,7 +430,7 @@ partial record class Diagnostic /// The 'DuplicateResourceName' diagnostic. /// /// -/// Skipping resource (name clash): "{arg0}" +/// Warning: Skipping resource (name clash): "{arg0}" /// public static readonly Diagnostic DuplicateResourceName = new Diagnostic(107, nameof(DuplicateResourceName), "Skipping resource (name clash): \"{0}\"", DiagnosticLevel.Warning); @@ -438,7 +438,7 @@ partial record class Diagnostic /// The 'SkippingReferencedClass' diagnostic. /// /// -/// Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") +/// Warning: Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") /// public static readonly Diagnostic SkippingReferencedClass = new Diagnostic(109, nameof(SkippingReferencedClass), "Skipping class: \"{0}\". (class is already available in referenced assembly \"{1}\")", DiagnosticLevel.Warning); @@ -446,7 +446,7 @@ partial record class Diagnostic /// The 'NoJniRuntime' diagnostic. /// /// -/// Unable to load runtime JNI assembly. +/// Warning: Unable to load runtime JNI assembly. /// public static readonly Diagnostic NoJniRuntime = new Diagnostic(110, nameof(NoJniRuntime), "Unable to load runtime JNI assembly.", DiagnosticLevel.Warning); @@ -454,7 +454,7 @@ partial record class Diagnostic /// The 'EmittedNoClassDefFoundError' diagnostic. /// /// -/// Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). +/// Warning: Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). /// public static readonly Diagnostic EmittedNoClassDefFoundError = new Diagnostic(111, nameof(EmittedNoClassDefFoundError), "Emitted java.lang.NoClassDefFoundError in \"{0}\". (\"{1}\").", DiagnosticLevel.Warning); @@ -462,7 +462,7 @@ partial record class Diagnostic /// The 'EmittedIllegalAccessError' diagnostic. /// /// -/// Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedIllegalAccessError = new Diagnostic(112, nameof(EmittedIllegalAccessError), "Emitted java.lang.IllegalAccessError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -470,7 +470,7 @@ partial record class Diagnostic /// The 'EmittedInstantiationError' diagnostic. /// /// -/// Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedInstantiationError = new Diagnostic(113, nameof(EmittedInstantiationError), "Emitted java.lang.InstantiationError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -478,7 +478,7 @@ partial record class Diagnostic /// The 'EmittedIncompatibleClassChangeError' diagnostic. /// /// -/// Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedIncompatibleClassChangeError = new Diagnostic(114, nameof(EmittedIncompatibleClassChangeError), "Emitted java.lang.IncompatibleClassChangeError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -486,7 +486,7 @@ partial record class Diagnostic /// The 'EmittedNoSuchFieldError' diagnostic. /// /// -/// Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedNoSuchFieldError = new Diagnostic(115, nameof(EmittedNoSuchFieldError), "Emitted java.lang.NoSuchFieldError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -494,7 +494,7 @@ partial record class Diagnostic /// The 'EmittedAbstractMethodError' diagnostic. /// /// -/// Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedAbstractMethodError = new Diagnostic(116, nameof(EmittedAbstractMethodError), "Emitted java.lang.AbstractMethodError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -502,7 +502,7 @@ partial record class Diagnostic /// The 'EmittedNoSuchMethodError' diagnostic. /// /// -/// Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedNoSuchMethodError = new Diagnostic(117, nameof(EmittedNoSuchMethodError), "Emitted java.lang.NoSuchMethodError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -510,7 +510,7 @@ partial record class Diagnostic /// The 'EmittedLinkageError' diagnostic. /// /// -/// Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedLinkageError = new Diagnostic(118, nameof(EmittedLinkageError), "Emitted java.lang.LinkageError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -518,7 +518,7 @@ partial record class Diagnostic /// The 'EmittedVerificationError' diagnostic. /// /// -/// Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedVerificationError = new Diagnostic(119, nameof(EmittedVerificationError), "Emitted java.lang.VerificationError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -526,7 +526,7 @@ partial record class Diagnostic /// The 'EmittedClassFormatError' diagnostic. /// /// -/// Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") /// public static readonly Diagnostic EmittedClassFormatError = new Diagnostic(120, nameof(EmittedClassFormatError), "Emitted java.lang.ClassFormatError in \"{0}\". (\"{1}\")", DiagnosticLevel.Warning); @@ -534,7 +534,7 @@ partial record class Diagnostic /// The 'InvalidCustomAttribute' diagnostic. /// /// -/// Error emitting "{arg0}" custom attribute. ("{arg1}") +/// Warning: Error emitting "{arg0}" custom attribute. ("{arg1}") /// public static readonly Diagnostic InvalidCustomAttribute = new Diagnostic(121, nameof(InvalidCustomAttribute), "Error emitting \"{0}\" custom attribute. (\"{1}\")", DiagnosticLevel.Warning); @@ -542,7 +542,7 @@ partial record class Diagnostic /// The 'IgnoredCustomAttribute' diagnostic. /// /// -/// Custom attribute "{arg0}" was ignored. ("{arg1}") +/// Warning: Custom attribute "{arg0}" was ignored. ("{arg1}") /// public static readonly Diagnostic IgnoredCustomAttribute = new Diagnostic(122, nameof(IgnoredCustomAttribute), "Custom attribute \"{0}\" was ignored. (\"{1}\")", DiagnosticLevel.Warning); @@ -550,7 +550,7 @@ partial record class Diagnostic /// The 'AssumeAssemblyVersionMatch' diagnostic. /// /// -/// Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy +/// Warning: Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy /// public static readonly Diagnostic AssumeAssemblyVersionMatch = new Diagnostic(123, nameof(AssumeAssemblyVersionMatch), "Assuming assembly reference \"{0}\" matches \"{1}\", you may need to supply runtime p" + "olicy", DiagnosticLevel.Warning); @@ -559,7 +559,7 @@ partial record class Diagnostic /// The 'InvalidDirectoryInLibOptionPath' diagnostic. /// /// -/// Directory "{arg0}" specified in -lib option is not valid. +/// Warning: Directory "{arg0}" specified in -lib option is not valid. /// public static readonly Diagnostic InvalidDirectoryInLibOptionPath = new Diagnostic(124, nameof(InvalidDirectoryInLibOptionPath), "Directory \"{0}\" specified in -lib option is not valid.", DiagnosticLevel.Warning); @@ -567,7 +567,7 @@ partial record class Diagnostic /// The 'InvalidDirectoryInLibEnvironmentPath' diagnostic. /// /// -/// Directory "{arg0}" specified in LIB environment is not valid. +/// Warning: Directory "{arg0}" specified in LIB environment is not valid. /// public static readonly Diagnostic InvalidDirectoryInLibEnvironmentPath = new Diagnostic(125, nameof(InvalidDirectoryInLibEnvironmentPath), "Directory \"{0}\" specified in LIB environment is not valid.", DiagnosticLevel.Warning); @@ -575,7 +575,7 @@ partial record class Diagnostic /// The 'LegacySearchRule' diagnostic. /// /// -/// Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. +/// Warning: Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. /// public static readonly Diagnostic LegacySearchRule = new Diagnostic(126, nameof(LegacySearchRule), "Found assembly \"{0}\" using legacy search rule, please append \'.dll\' to the refere" + "nce.", DiagnosticLevel.Warning); @@ -584,7 +584,7 @@ partial record class Diagnostic /// The 'AssemblyLocationIgnored' diagnostic. /// /// -/// Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". +/// Warning: Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". /// public static readonly Diagnostic AssemblyLocationIgnored = new Diagnostic(127, nameof(AssemblyLocationIgnored), "Assembly \"{0}\" is ignored as previously loaded assembly \"{1}\" has the same identi" + "ty \"{2}\".", DiagnosticLevel.Warning); @@ -593,7 +593,7 @@ partial record class Diagnostic /// The 'InterfaceMethodCantBeInternal' diagnostic. /// /// -/// Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") +/// Warning: Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") /// public static readonly Diagnostic InterfaceMethodCantBeInternal = new Diagnostic(128, nameof(InterfaceMethodCantBeInternal), "Ignoring @ikvm.lang.Internal annotation on interface method. (\"{0}.{1}{2}\")", DiagnosticLevel.Warning); @@ -601,7 +601,7 @@ partial record class Diagnostic /// The 'DuplicateAssemblyReference' diagnostic. /// /// -/// Duplicate assembly reference "{arg0}" +/// Warning: Duplicate assembly reference "{arg0}" /// public static readonly Diagnostic DuplicateAssemblyReference = new Diagnostic(132, nameof(DuplicateAssemblyReference), "Duplicate assembly reference \"{0}\"", DiagnosticLevel.Warning); @@ -609,7 +609,7 @@ partial record class Diagnostic /// The 'UnableToResolveType' diagnostic. /// /// -/// Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. +/// Warning: Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. /// public static readonly Diagnostic UnableToResolveType = new Diagnostic(133, nameof(UnableToResolveType), "Reference in \"{0}\" to type \"{1}\" claims it is defined in \"{2}\", but it could not " + "be found.", DiagnosticLevel.Warning); @@ -618,7 +618,7 @@ partial record class Diagnostic /// The 'StubsAreDeprecated' diagnostic. /// /// -/// Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. +/// Warning: Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. /// public static readonly Diagnostic StubsAreDeprecated = new Diagnostic(134, nameof(StubsAreDeprecated), "Compiling stubs is deprecated. Please add a reference to assembly \"{0}\" instead.", DiagnosticLevel.Warning); @@ -626,7 +626,7 @@ partial record class Diagnostic /// The 'WrongClassName' diagnostic. /// /// -/// Unable to compile "{arg0}" (wrong name: "{arg1}") +/// Warning: Unable to compile "{arg0}" (wrong name: "{arg1}") /// public static readonly Diagnostic WrongClassName = new Diagnostic(135, nameof(WrongClassName), "Unable to compile \"{0}\" (wrong name: \"{1}\")", DiagnosticLevel.Warning); @@ -634,7 +634,7 @@ partial record class Diagnostic /// The 'ReflectionCallerClassRequiresCallerID' diagnostic. /// /// -/// Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") +/// Warning: Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") /// public static readonly Diagnostic ReflectionCallerClassRequiresCallerID = new Diagnostic(136, nameof(ReflectionCallerClassRequiresCallerID), "Reflection.getCallerClass() called from non-CallerID method. (\"{0}.{1}{2}\")", DiagnosticLevel.Warning); @@ -642,7 +642,7 @@ partial record class Diagnostic /// The 'LegacyAssemblyAttributesFound' diagnostic. /// /// -/// Legacy assembly attributes container found. Please use the -assemblyattributes: option. +/// Warning: Legacy assembly attributes container found. Please use the -assemblyattributes: option. /// public static readonly Diagnostic LegacyAssemblyAttributesFound = new Diagnostic(137, nameof(LegacyAssemblyAttributesFound), "Legacy assembly attributes container found. Please use the -assemblyattributes: option.", DiagnosticLevel.Warning); @@ -651,7 +651,7 @@ partial record class Diagnostic /// The 'UnableToCreateLambdaFactory' diagnostic. /// /// -/// Unable to create static lambda factory. +/// Warning: Unable to create static lambda factory. /// public static readonly Diagnostic UnableToCreateLambdaFactory = new Diagnostic(138, nameof(UnableToCreateLambdaFactory), "Unable to create static lambda factory.", DiagnosticLevel.Warning); @@ -659,7 +659,7 @@ partial record class Diagnostic /// The 'UnknownWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static readonly Diagnostic UnknownWarning = new Diagnostic(999, nameof(UnknownWarning), "{0}", DiagnosticLevel.Warning); @@ -667,7 +667,7 @@ partial record class Diagnostic /// The 'DuplicateIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public static readonly Diagnostic DuplicateIkvmLangProperty = new Diagnostic(139, nameof(DuplicateIkvmLangProperty), "Ignoring duplicate ikvm.lang.Property annotation on {0}.{1}.", DiagnosticLevel.Warning); @@ -675,7 +675,7 @@ partial record class Diagnostic /// The 'MalformedIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public static readonly Diagnostic MalformedIkvmLangProperty = new Diagnostic(140, nameof(MalformedIkvmLangProperty), "Ignoring duplicate ikvm.lang.Property annotation on {0}.{1}.", DiagnosticLevel.Warning); @@ -683,7 +683,7 @@ partial record class Diagnostic /// The 'GenericCompilerWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static readonly Diagnostic GenericCompilerWarning = new Diagnostic(141, nameof(GenericCompilerWarning), "{0}", DiagnosticLevel.Warning); @@ -691,7 +691,7 @@ partial record class Diagnostic /// The 'GenericClassLoadingWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static readonly Diagnostic GenericClassLoadingWarning = new Diagnostic(142, nameof(GenericClassLoadingWarning), "{0}", DiagnosticLevel.Warning); @@ -699,7 +699,7 @@ partial record class Diagnostic /// The 'GenericVerifierWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static readonly Diagnostic GenericVerifierWarning = new Diagnostic(143, nameof(GenericVerifierWarning), "{0}", DiagnosticLevel.Warning); @@ -707,7 +707,7 @@ partial record class Diagnostic /// The 'GenericRuntimeWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static readonly Diagnostic GenericRuntimeWarning = new Diagnostic(144, nameof(GenericRuntimeWarning), "{0}", DiagnosticLevel.Warning); @@ -715,7 +715,7 @@ partial record class Diagnostic /// The 'GenericJniWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static readonly Diagnostic GenericJniWarning = new Diagnostic(145, nameof(GenericJniWarning), "{0}", DiagnosticLevel.Warning); @@ -723,7 +723,7 @@ partial record class Diagnostic /// The 'UnableToCreateProxy' diagnostic. /// /// -/// Unable to create proxy "{arg0}". ("{arg1}") +/// Error: Unable to create proxy "{arg0}". ("{arg1}") /// public static readonly Diagnostic UnableToCreateProxy = new Diagnostic(4001, nameof(UnableToCreateProxy), "Unable to create proxy \"{0}\". (\"{1}\")", DiagnosticLevel.Error); @@ -731,7 +731,7 @@ partial record class Diagnostic /// The 'DuplicateProxy' diagnostic. /// /// -/// Duplicate proxy "{arg0}". +/// Error: Duplicate proxy "{arg0}". /// public static readonly Diagnostic DuplicateProxy = new Diagnostic(4002, nameof(DuplicateProxy), "Duplicate proxy \"{0}\".", DiagnosticLevel.Error); @@ -739,7 +739,7 @@ partial record class Diagnostic /// The 'MapXmlUnableToResolveOpCode' diagnostic. /// /// -/// Unable to resolve opcode in remap file: {arg0}. +/// Error: Unable to resolve opcode in remap file: {arg0}. /// public static readonly Diagnostic MapXmlUnableToResolveOpCode = new Diagnostic(4003, nameof(MapXmlUnableToResolveOpCode), "Unable to resolve opcode in remap file: {0}.", DiagnosticLevel.Error); @@ -747,7 +747,7 @@ partial record class Diagnostic /// The 'MapXmlError' diagnostic. /// /// -/// Error in remap file: {arg0}. +/// Error: Error in remap file: {arg0}. /// public static readonly Diagnostic MapXmlError = new Diagnostic(4004, nameof(MapXmlError), "Error in remap file: {0}.", DiagnosticLevel.Error); @@ -755,7 +755,7 @@ partial record class Diagnostic /// The 'InputFileNotFound' diagnostic. /// /// -/// Source file '{arg0}' not found. +/// Error: Source file '{arg0}' not found. /// public static readonly Diagnostic InputFileNotFound = new Diagnostic(4005, nameof(InputFileNotFound), "Source file \'{0}\' not found.", DiagnosticLevel.Error); @@ -763,7 +763,7 @@ partial record class Diagnostic /// The 'UnknownFileType' diagnostic. /// /// -/// Unknown file type: {arg0}. +/// Error: Unknown file type: {arg0}. /// public static readonly Diagnostic UnknownFileType = new Diagnostic(4006, nameof(UnknownFileType), "Unknown file type: {0}.", DiagnosticLevel.Error); @@ -771,7 +771,7 @@ partial record class Diagnostic /// The 'UnknownElementInMapFile' diagnostic. /// /// -/// Unknown element {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown element {arg0} in remap file, line {arg1}, column {arg2}. /// public static readonly Diagnostic UnknownElementInMapFile = new Diagnostic(4007, nameof(UnknownElementInMapFile), "Unknown element {0} in remap file, line {1}, column {2}.", DiagnosticLevel.Error); @@ -779,7 +779,7 @@ partial record class Diagnostic /// The 'UnknownAttributeInMapFile' diagnostic. /// /// -/// Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. /// public static readonly Diagnostic UnknownAttributeInMapFile = new Diagnostic(4008, nameof(UnknownAttributeInMapFile), "Unknown attribute {0} in remap file, line {1}, column {2}.", DiagnosticLevel.Error); @@ -787,7 +787,7 @@ partial record class Diagnostic /// The 'InvalidMemberNameInMapFile' diagnostic. /// /// -/// Invalid {arg0} name '{arg1}' in remap file in class {arg2}. +/// Error: Invalid {arg0} name '{arg1}' in remap file in class {arg2}. /// public static readonly Diagnostic InvalidMemberNameInMapFile = new Diagnostic(4009, nameof(InvalidMemberNameInMapFile), "Invalid {0} name \'{1}\' in remap file in class {2}.", DiagnosticLevel.Error); @@ -795,7 +795,7 @@ partial record class Diagnostic /// The 'InvalidMemberSignatureInMapFile' diagnostic. /// /// -/// Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. +/// Error: Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. /// public static readonly Diagnostic InvalidMemberSignatureInMapFile = new Diagnostic(4010, nameof(InvalidMemberSignatureInMapFile), "Invalid {0} signature \'{3}\' in remap file for {0} {1}.{2}.", DiagnosticLevel.Error); @@ -803,7 +803,7 @@ partial record class Diagnostic /// The 'InvalidPropertyNameInMapFile' diagnostic. /// /// -/// Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. /// public static readonly Diagnostic InvalidPropertyNameInMapFile = new Diagnostic(4011, nameof(InvalidPropertyNameInMapFile), "Invalid property {0} name \'{3}\' in remap file for property {1}.{2}.", DiagnosticLevel.Error); @@ -811,7 +811,7 @@ partial record class Diagnostic /// The 'InvalidPropertySignatureInMapFile' diagnostic. /// /// -/// Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. /// public static readonly Diagnostic InvalidPropertySignatureInMapFile = new Diagnostic(4012, nameof(InvalidPropertySignatureInMapFile), "Invalid property {0} signature \'{3}\' in remap file for property {1}.{2}.", DiagnosticLevel.Error); @@ -819,7 +819,7 @@ partial record class Diagnostic /// The 'NonPrimaryAssemblyReference' diagnostic. /// /// -/// Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. +/// Error: Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. /// public static readonly Diagnostic NonPrimaryAssemblyReference = new Diagnostic(4013, nameof(NonPrimaryAssemblyReference), "Referenced assembly \"{0}\" is not the primary assembly of a shared class loader gr" + "oup, please reference primary assembly \"{1}\" instead.", DiagnosticLevel.Error); @@ -828,7 +828,7 @@ partial record class Diagnostic /// The 'MissingType' diagnostic. /// /// -/// Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. +/// Error: Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. /// public static readonly Diagnostic MissingType = new Diagnostic(4014, nameof(MissingType), "Reference to type \"{0}\" claims it is defined in \"{1}\", but it could not be found." + "", DiagnosticLevel.Error); @@ -837,7 +837,7 @@ partial record class Diagnostic /// The 'MissingReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. +/// Error: The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. /// public static readonly Diagnostic MissingReference = new Diagnostic(4015, nameof(MissingReference), "The type \'{0}\' is defined in an assembly that is notResponseFileDepthExceeded ref" + "erenced. You must add a reference to assembly \'{1}\'.", DiagnosticLevel.Error); @@ -846,7 +846,7 @@ partial record class Diagnostic /// The 'CallerSensitiveOnUnsupportedMethod' diagnostic. /// /// -/// CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") +/// Error: CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") /// public static readonly Diagnostic CallerSensitiveOnUnsupportedMethod = new Diagnostic(4016, nameof(CallerSensitiveOnUnsupportedMethod), "CallerSensitive annotation on unsupported method. (\"{0}.{1}{2}\")", DiagnosticLevel.Error); @@ -854,7 +854,7 @@ partial record class Diagnostic /// The 'RemappedTypeMissingDefaultInterfaceMethod' diagnostic. /// /// -/// {arg0} does not implement default interface method {arg1}. +/// Error: {arg0} does not implement default interface method {arg1}. /// public static readonly Diagnostic RemappedTypeMissingDefaultInterfaceMethod = new Diagnostic(4017, nameof(RemappedTypeMissingDefaultInterfaceMethod), "{0} does not implement default interface method {1}.", DiagnosticLevel.Error); @@ -862,7 +862,7 @@ partial record class Diagnostic /// The 'GenericCompilerError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static readonly Diagnostic GenericCompilerError = new Diagnostic(4018, nameof(GenericCompilerError), "{0}", DiagnosticLevel.Error); @@ -870,7 +870,7 @@ partial record class Diagnostic /// The 'GenericClassLoadingError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static readonly Diagnostic GenericClassLoadingError = new Diagnostic(4019, nameof(GenericClassLoadingError), "{0}", DiagnosticLevel.Error); @@ -878,7 +878,7 @@ partial record class Diagnostic /// The 'GenericVerifierError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static readonly Diagnostic GenericVerifierError = new Diagnostic(4020, nameof(GenericVerifierError), "{0}", DiagnosticLevel.Error); @@ -886,7 +886,7 @@ partial record class Diagnostic /// The 'GenericRuntimeError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static readonly Diagnostic GenericRuntimeError = new Diagnostic(4021, nameof(GenericRuntimeError), "{0}", DiagnosticLevel.Error); @@ -894,7 +894,7 @@ partial record class Diagnostic /// The 'GenericJniError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static readonly Diagnostic GenericJniError = new Diagnostic(4022, nameof(GenericJniError), "{0}", DiagnosticLevel.Error); @@ -902,7 +902,7 @@ partial record class Diagnostic /// The 'ExportingImportsNotSupported' diagnostic. /// /// -/// Exporting previously imported assemblies is not supported. +/// Error: Exporting previously imported assemblies is not supported. /// public static readonly Diagnostic ExportingImportsNotSupported = new Diagnostic(4023, nameof(ExportingImportsNotSupported), "Exporting previously imported assemblies is not supported.", DiagnosticLevel.Error); @@ -910,7 +910,7 @@ partial record class Diagnostic /// The 'ResponseFileDepthExceeded' diagnostic. /// /// -/// Response file nesting depth exceeded. +/// Fatal: Response file nesting depth exceeded. /// public static readonly Diagnostic ResponseFileDepthExceeded = new Diagnostic(5000, nameof(ResponseFileDepthExceeded), "Response file nesting depth exceeded.", DiagnosticLevel.Fatal); @@ -918,7 +918,7 @@ partial record class Diagnostic /// The 'ErrorReadingFile' diagnostic. /// /// -/// Unable to read file: {arg0}. ({arg1}) +/// Fatal: Unable to read file: {arg0}. ({arg1}) /// public static readonly Diagnostic ErrorReadingFile = new Diagnostic(5001, nameof(ErrorReadingFile), "Unable to read file: {0}. ({1})", DiagnosticLevel.Fatal); @@ -926,7 +926,7 @@ partial record class Diagnostic /// The 'NoTargetsFound' diagnostic. /// /// -/// No targets found +/// Fatal: No targets found /// public static readonly Diagnostic NoTargetsFound = new Diagnostic(5002, nameof(NoTargetsFound), "No targets found", DiagnosticLevel.Fatal); @@ -934,7 +934,7 @@ partial record class Diagnostic /// The 'FileFormatLimitationExceeded' diagnostic. /// /// -/// File format limitation exceeded: {arg0}. +/// Fatal: File format limitation exceeded: {arg0}. /// public static readonly Diagnostic FileFormatLimitationExceeded = new Diagnostic(5003, nameof(FileFormatLimitationExceeded), "File format limitation exceeded: {0}.", DiagnosticLevel.Fatal); @@ -942,7 +942,7 @@ partial record class Diagnostic /// The 'CannotSpecifyBothKeyFileAndContainer' diagnostic. /// /// -/// You cannot specify both a key file and container. +/// Fatal: You cannot specify both a key file and container. /// public static readonly Diagnostic CannotSpecifyBothKeyFileAndContainer = new Diagnostic(5004, nameof(CannotSpecifyBothKeyFileAndContainer), "You cannot specify both a key file and container.", DiagnosticLevel.Fatal); @@ -950,7 +950,7 @@ partial record class Diagnostic /// The 'DelaySignRequiresKey' diagnostic. /// /// -/// You cannot delay sign without a key file or container. +/// Fatal: You cannot delay sign without a key file or container. /// public static readonly Diagnostic DelaySignRequiresKey = new Diagnostic(5005, nameof(DelaySignRequiresKey), "You cannot delay sign without a key file or container.", DiagnosticLevel.Fatal); @@ -958,7 +958,7 @@ partial record class Diagnostic /// The 'InvalidStrongNameKeyPair' diagnostic. /// /// -/// Invalid key {arg0} specified. ("{arg1}") +/// Fatal: Invalid key {arg0} specified. ("{arg1}") /// public static readonly Diagnostic InvalidStrongNameKeyPair = new Diagnostic(5006, nameof(InvalidStrongNameKeyPair), "Invalid key {0} specified. (\"{1}\")", DiagnosticLevel.Fatal); @@ -966,7 +966,7 @@ partial record class Diagnostic /// The 'ReferenceNotFound' diagnostic. /// /// -/// Reference not found: {arg0} +/// Fatal: Reference not found: {arg0} /// public static readonly Diagnostic ReferenceNotFound = new Diagnostic(5007, nameof(ReferenceNotFound), "Reference not found: {0}", DiagnosticLevel.Fatal); @@ -974,7 +974,7 @@ partial record class Diagnostic /// The 'OptionsMustPreceedChildLevels' diagnostic. /// /// -/// You can only specify options before any child levels. +/// Fatal: You can only specify options before any child levels. /// public static readonly Diagnostic OptionsMustPreceedChildLevels = new Diagnostic(5008, nameof(OptionsMustPreceedChildLevels), "You can only specify options before any child levels.", DiagnosticLevel.Fatal); @@ -982,7 +982,7 @@ partial record class Diagnostic /// The 'UnrecognizedTargetType' diagnostic. /// /// -/// Invalid value '{arg0}' for -target option. +/// Fatal: Invalid value '{arg0}' for -target option. /// public static readonly Diagnostic UnrecognizedTargetType = new Diagnostic(5009, nameof(UnrecognizedTargetType), "Invalid value \'{0}\' for -target option.", DiagnosticLevel.Fatal); @@ -990,7 +990,7 @@ partial record class Diagnostic /// The 'UnrecognizedPlatform' diagnostic. /// /// -/// Invalid value '{arg0}' for -platform option. +/// Fatal: Invalid value '{arg0}' for -platform option. /// public static readonly Diagnostic UnrecognizedPlatform = new Diagnostic(5010, nameof(UnrecognizedPlatform), "Invalid value \'{0}\' for -platform option.", DiagnosticLevel.Fatal); @@ -998,7 +998,7 @@ partial record class Diagnostic /// The 'UnrecognizedApartment' diagnostic. /// /// -/// Invalid value '{arg0}' for -apartment option. +/// Fatal: Invalid value '{arg0}' for -apartment option. /// public static readonly Diagnostic UnrecognizedApartment = new Diagnostic(5011, nameof(UnrecognizedApartment), "Invalid value \'{0}\' for -apartment option.", DiagnosticLevel.Fatal); @@ -1006,7 +1006,7 @@ partial record class Diagnostic /// The 'MissingFileSpecification' diagnostic. /// /// -/// Missing file specification for '{arg0}' option. +/// Fatal: Missing file specification for '{arg0}' option. /// public static readonly Diagnostic MissingFileSpecification = new Diagnostic(5012, nameof(MissingFileSpecification), "Missing file specification for \'{0}\' option.", DiagnosticLevel.Fatal); @@ -1014,7 +1014,7 @@ partial record class Diagnostic /// The 'PathTooLong' diagnostic. /// /// -/// Path too long: {arg0}. +/// Fatal: Path too long: {arg0}. /// public static readonly Diagnostic PathTooLong = new Diagnostic(5013, nameof(PathTooLong), "Path too long: {0}.", DiagnosticLevel.Fatal); @@ -1022,7 +1022,7 @@ partial record class Diagnostic /// The 'PathNotFound' diagnostic. /// /// -/// Path not found: {arg0}. +/// Fatal: Path not found: {arg0}. /// public static readonly Diagnostic PathNotFound = new Diagnostic(5014, nameof(PathNotFound), "Path not found: {0}.", DiagnosticLevel.Fatal); @@ -1030,7 +1030,7 @@ partial record class Diagnostic /// The 'InvalidPath' diagnostic. /// /// -/// Invalid path: {arg0}. +/// Fatal: Invalid path: {arg0}. /// public static readonly Diagnostic InvalidPath = new Diagnostic(5015, nameof(InvalidPath), "Invalid path: {0}.", DiagnosticLevel.Fatal); @@ -1038,7 +1038,7 @@ partial record class Diagnostic /// The 'InvalidOptionSyntax' diagnostic. /// /// -/// Invalid option: {arg0}. +/// Fatal: Invalid option: {arg0}. /// public static readonly Diagnostic InvalidOptionSyntax = new Diagnostic(5016, nameof(InvalidOptionSyntax), "Invalid option: {0}.", DiagnosticLevel.Fatal); @@ -1046,7 +1046,7 @@ partial record class Diagnostic /// The 'ExternalResourceNotFound' diagnostic. /// /// -/// External resource file does not exist: {arg0}. +/// Fatal: External resource file does not exist: {arg0}. /// public static readonly Diagnostic ExternalResourceNotFound = new Diagnostic(5017, nameof(ExternalResourceNotFound), "External resource file does not exist: {0}.", DiagnosticLevel.Fatal); @@ -1054,7 +1054,7 @@ partial record class Diagnostic /// The 'ExternalResourceNameInvalid' diagnostic. /// /// -/// External resource file may not include path specification: {arg0}. +/// Fatal: External resource file may not include path specification: {arg0}. /// public static readonly Diagnostic ExternalResourceNameInvalid = new Diagnostic(5018, nameof(ExternalResourceNameInvalid), "External resource file may not include path specification: {0}.", DiagnosticLevel.Fatal); @@ -1062,7 +1062,7 @@ partial record class Diagnostic /// The 'InvalidVersionFormat' diagnostic. /// /// -/// Invalid version specified: {arg0}. +/// Fatal: Invalid version specified: {arg0}. /// public static readonly Diagnostic InvalidVersionFormat = new Diagnostic(5019, nameof(InvalidVersionFormat), "Invalid version specified: {0}.", DiagnosticLevel.Fatal); @@ -1070,7 +1070,7 @@ partial record class Diagnostic /// The 'InvalidFileAlignment' diagnostic. /// /// -/// Invalid value '{arg0}' for -filealign option. +/// Fatal: Invalid value '{arg0}' for -filealign option. /// public static readonly Diagnostic InvalidFileAlignment = new Diagnostic(5020, nameof(InvalidFileAlignment), "Invalid value \'{0}\' for -filealign option.", DiagnosticLevel.Fatal); @@ -1078,7 +1078,7 @@ partial record class Diagnostic /// The 'ErrorWritingFile' diagnostic. /// /// -/// Unable to write file: {arg0}. ({arg1}) +/// Fatal: Unable to write file: {arg0}. ({arg1}) /// public static readonly Diagnostic ErrorWritingFile = new Diagnostic(5021, nameof(ErrorWritingFile), "Unable to write file: {0}. ({1})", DiagnosticLevel.Fatal); @@ -1086,7 +1086,7 @@ partial record class Diagnostic /// The 'UnrecognizedOption' diagnostic. /// /// -/// Unrecognized option: {arg0}. +/// Fatal: Unrecognized option: {arg0}. /// public static readonly Diagnostic UnrecognizedOption = new Diagnostic(5022, nameof(UnrecognizedOption), "Unrecognized option: {0}.", DiagnosticLevel.Fatal); @@ -1094,7 +1094,7 @@ partial record class Diagnostic /// The 'NoOutputFileSpecified' diagnostic. /// /// -/// No output file specified. +/// Fatal: No output file specified. /// public static readonly Diagnostic NoOutputFileSpecified = new Diagnostic(5023, nameof(NoOutputFileSpecified), "No output file specified.", DiagnosticLevel.Fatal); @@ -1102,7 +1102,7 @@ partial record class Diagnostic /// The 'SharedClassLoaderCannotBeUsedOnModuleTarget' diagnostic. /// /// -/// Incompatible options: -target:module and -sharedclassloader cannot be combined. +/// Fatal: Incompatible options: -target:module and -sharedclassloader cannot be combined. /// public static readonly Diagnostic SharedClassLoaderCannotBeUsedOnModuleTarget = new Diagnostic(5024, nameof(SharedClassLoaderCannotBeUsedOnModuleTarget), "Incompatible options: -target:module and -sharedclassloader cannot be combined.", DiagnosticLevel.Fatal); @@ -1110,7 +1110,7 @@ partial record class Diagnostic /// The 'RuntimeNotFound' diagnostic. /// /// -/// Unable to load runtime assembly. +/// Fatal: Unable to load runtime assembly. /// public static readonly Diagnostic RuntimeNotFound = new Diagnostic(5025, nameof(RuntimeNotFound), "Unable to load runtime assembly.", DiagnosticLevel.Fatal); @@ -1118,7 +1118,7 @@ partial record class Diagnostic /// The 'MainClassRequiresExe' diagnostic. /// /// -/// Main class cannot be specified for library or module. +/// Fatal: Main class cannot be specified for library or module. /// public static readonly Diagnostic MainClassRequiresExe = new Diagnostic(5026, nameof(MainClassRequiresExe), "Main class cannot be specified for library or module.", DiagnosticLevel.Fatal); @@ -1126,7 +1126,7 @@ partial record class Diagnostic /// The 'ExeRequiresMainClass' diagnostic. /// /// -/// No main method found. +/// Fatal: No main method found. /// public static readonly Diagnostic ExeRequiresMainClass = new Diagnostic(5027, nameof(ExeRequiresMainClass), "No main method found.", DiagnosticLevel.Fatal); @@ -1134,7 +1134,7 @@ partial record class Diagnostic /// The 'PropertiesRequireExe' diagnostic. /// /// -/// Properties cannot be specified for library or module. +/// Fatal: Properties cannot be specified for library or module. /// public static readonly Diagnostic PropertiesRequireExe = new Diagnostic(5028, nameof(PropertiesRequireExe), "Properties cannot be specified for library or module.", DiagnosticLevel.Fatal); @@ -1142,7 +1142,7 @@ partial record class Diagnostic /// The 'ModuleCannotHaveClassLoader' diagnostic. /// /// -/// Cannot specify assembly class loader for modules. +/// Fatal: Cannot specify assembly class loader for modules. /// public static readonly Diagnostic ModuleCannotHaveClassLoader = new Diagnostic(5029, nameof(ModuleCannotHaveClassLoader), "Cannot specify assembly class loader for modules.", DiagnosticLevel.Fatal); @@ -1150,7 +1150,7 @@ partial record class Diagnostic /// The 'ErrorParsingMapFile' diagnostic. /// /// -/// Unable to parse remap file: {arg0}. ({arg1}) +/// Fatal: Unable to parse remap file: {arg0}. ({arg1}) /// public static readonly Diagnostic ErrorParsingMapFile = new Diagnostic(5030, nameof(ErrorParsingMapFile), "Unable to parse remap file: {0}. ({1})", DiagnosticLevel.Fatal); @@ -1158,7 +1158,7 @@ partial record class Diagnostic /// The 'BootstrapClassesMissing' diagnostic. /// /// -/// Bootstrap classes missing and core assembly not found. +/// Fatal: Bootstrap classes missing and core assembly not found. /// public static readonly Diagnostic BootstrapClassesMissing = new Diagnostic(5031, nameof(BootstrapClassesMissing), "Bootstrap classes missing and core assembly not found.", DiagnosticLevel.Fatal); @@ -1166,7 +1166,7 @@ partial record class Diagnostic /// The 'StrongNameRequiresStrongNamedRefs' diagnostic. /// /// -/// All referenced assemblies must be strong named, to be able to sign the output assembly. +/// Fatal: All referenced assemblies must be strong named, to be able to sign the output assembly. /// public static readonly Diagnostic StrongNameRequiresStrongNamedRefs = new Diagnostic(5032, nameof(StrongNameRequiresStrongNamedRefs), "All referenced assemblies must be strong named, to be able to sign the output ass" + "embly.", DiagnosticLevel.Fatal); @@ -1175,7 +1175,7 @@ partial record class Diagnostic /// The 'MainClassNotFound' diagnostic. /// /// -/// Main class not found. +/// Fatal: Main class not found. /// public static readonly Diagnostic MainClassNotFound = new Diagnostic(5033, nameof(MainClassNotFound), "Main class not found.", DiagnosticLevel.Fatal); @@ -1183,7 +1183,7 @@ partial record class Diagnostic /// The 'MainMethodNotFound' diagnostic. /// /// -/// Main method not found. +/// Fatal: Main method not found. /// public static readonly Diagnostic MainMethodNotFound = new Diagnostic(5034, nameof(MainMethodNotFound), "Main method not found.", DiagnosticLevel.Fatal); @@ -1191,7 +1191,7 @@ partial record class Diagnostic /// The 'UnsupportedMainMethod' diagnostic. /// /// -/// Redirected main method not supported. +/// Fatal: Redirected main method not supported. /// public static readonly Diagnostic UnsupportedMainMethod = new Diagnostic(5035, nameof(UnsupportedMainMethod), "Redirected main method not supported.", DiagnosticLevel.Fatal); @@ -1199,7 +1199,7 @@ partial record class Diagnostic /// The 'ExternalMainNotAccessible' diagnostic. /// /// -/// External main method must be public and in a public class. +/// Fatal: External main method must be public and in a public class. /// public static readonly Diagnostic ExternalMainNotAccessible = new Diagnostic(5036, nameof(ExternalMainNotAccessible), "External main method must be public and in a public class.", DiagnosticLevel.Fatal); @@ -1207,7 +1207,7 @@ partial record class Diagnostic /// The 'ClassLoaderNotFound' diagnostic. /// /// -/// Custom assembly class loader class not found. +/// Fatal: Custom assembly class loader class not found. /// public static readonly Diagnostic ClassLoaderNotFound = new Diagnostic(5037, nameof(ClassLoaderNotFound), "Custom assembly class loader class not found.", DiagnosticLevel.Fatal); @@ -1215,7 +1215,7 @@ partial record class Diagnostic /// The 'ClassLoaderNotAccessible' diagnostic. /// /// -/// Custom assembly class loader class is not accessible. +/// Fatal: Custom assembly class loader class is not accessible. /// public static readonly Diagnostic ClassLoaderNotAccessible = new Diagnostic(5038, nameof(ClassLoaderNotAccessible), "Custom assembly class loader class is not accessible.", DiagnosticLevel.Fatal); @@ -1223,7 +1223,7 @@ partial record class Diagnostic /// The 'ClassLoaderIsAbstract' diagnostic. /// /// -/// Custom assembly class loader class is abstract. +/// Fatal: Custom assembly class loader class is abstract. /// public static readonly Diagnostic ClassLoaderIsAbstract = new Diagnostic(5039, nameof(ClassLoaderIsAbstract), "Custom assembly class loader class is abstract.", DiagnosticLevel.Fatal); @@ -1231,7 +1231,7 @@ partial record class Diagnostic /// The 'ClassLoaderNotClassLoader' diagnostic. /// /// -/// Custom assembly class loader class does not extend java.lang.ClassLoader. +/// Fatal: Custom assembly class loader class does not extend java.lang.ClassLoader. /// public static readonly Diagnostic ClassLoaderNotClassLoader = new Diagnostic(5040, nameof(ClassLoaderNotClassLoader), "Custom assembly class loader class does not extend java.lang.ClassLoader.", DiagnosticLevel.Fatal); @@ -1239,7 +1239,7 @@ partial record class Diagnostic /// The 'ClassLoaderConstructorMissing' diagnostic. /// /// -/// Custom assembly class loader constructor is missing. +/// Fatal: Custom assembly class loader constructor is missing. /// public static readonly Diagnostic ClassLoaderConstructorMissing = new Diagnostic(5041, nameof(ClassLoaderConstructorMissing), "Custom assembly class loader constructor is missing.", DiagnosticLevel.Fatal); @@ -1247,7 +1247,7 @@ partial record class Diagnostic /// The 'MapFileTypeNotFound' diagnostic. /// /// -/// Type '{arg0}' referenced in remap file was not found. +/// Fatal: Type '{arg0}' referenced in remap file was not found. /// public static readonly Diagnostic MapFileTypeNotFound = new Diagnostic(5042, nameof(MapFileTypeNotFound), "Type \'{0}\' referenced in remap file was not found.", DiagnosticLevel.Fatal); @@ -1255,7 +1255,7 @@ partial record class Diagnostic /// The 'MapFileClassNotFound' diagnostic. /// /// -/// Class '{arg0}' referenced in remap file was not found. +/// Fatal: Class '{arg0}' referenced in remap file was not found. /// public static readonly Diagnostic MapFileClassNotFound = new Diagnostic(5043, nameof(MapFileClassNotFound), "Class \'{0}\' referenced in remap file was not found.", DiagnosticLevel.Fatal); @@ -1263,7 +1263,7 @@ partial record class Diagnostic /// The 'MaximumErrorCountReached' diagnostic. /// /// -/// Maximum error count reached. +/// Fatal: Maximum error count reached. /// public static readonly Diagnostic MaximumErrorCountReached = new Diagnostic(5044, nameof(MaximumErrorCountReached), "Maximum error count reached.", DiagnosticLevel.Fatal); @@ -1271,7 +1271,7 @@ partial record class Diagnostic /// The 'LinkageError' diagnostic. /// /// -/// Link error: {arg0} +/// Fatal: Link error: {arg0} /// public static readonly Diagnostic LinkageError = new Diagnostic(5045, nameof(LinkageError), "Link error: {0}", DiagnosticLevel.Fatal); @@ -1279,7 +1279,7 @@ partial record class Diagnostic /// The 'RuntimeMismatch' diagnostic. /// /// -/// Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} +/// Fatal: Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} /// public static readonly Diagnostic RuntimeMismatch = new Diagnostic(5046, nameof(RuntimeMismatch), "Referenced assembly {0} was compiled with an incompatible IKVM.Runtime version. C" + "urrent runtime: {1}. Referenced assembly runtime: {2}", DiagnosticLevel.Fatal); @@ -1288,7 +1288,7 @@ partial record class Diagnostic /// The 'RuntimeMismatchStrongName' diagnostic. /// /// -/// +/// Fatal: /// public static readonly Diagnostic RuntimeMismatchStrongName = new Diagnostic(5047, nameof(RuntimeMismatchStrongName), "", DiagnosticLevel.Fatal); @@ -1296,7 +1296,7 @@ partial record class Diagnostic /// The 'CoreClassesMissing' diagnostic. /// /// -/// Failed to find core classes in core library. +/// Fatal: Failed to find core classes in core library. /// public static readonly Diagnostic CoreClassesMissing = new Diagnostic(5048, nameof(CoreClassesMissing), "Failed to find core classes in core library.", DiagnosticLevel.Fatal); @@ -1304,7 +1304,7 @@ partial record class Diagnostic /// The 'CriticalClassNotFound' diagnostic. /// /// -/// Unable to load critical class '{arg0}'. +/// Fatal: Unable to load critical class '{arg0}'. /// public static readonly Diagnostic CriticalClassNotFound = new Diagnostic(5049, nameof(CriticalClassNotFound), "Unable to load critical class \'{0}\'.", DiagnosticLevel.Fatal); @@ -1312,7 +1312,7 @@ partial record class Diagnostic /// The 'AssemblyContainsDuplicateClassNames' diagnostic. /// /// -/// Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) +/// Fatal: Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) /// public static readonly Diagnostic AssemblyContainsDuplicateClassNames = new Diagnostic(5050, nameof(AssemblyContainsDuplicateClassNames), "Type \'{0}\' and \'{1}\' both map to the same name \'{2}\'. ({3})", DiagnosticLevel.Fatal); @@ -1320,7 +1320,7 @@ partial record class Diagnostic /// The 'CallerIDRequiresHasCallerIDAnnotation' diagnostic. /// /// -/// CallerID.getCallerID() requires a HasCallerID annotation. +/// Fatal: CallerID.getCallerID() requires a HasCallerID annotation. /// public static readonly Diagnostic CallerIDRequiresHasCallerIDAnnotation = new Diagnostic(5051, nameof(CallerIDRequiresHasCallerIDAnnotation), "CallerID.getCallerID() requires a HasCallerID annotation.", DiagnosticLevel.Fatal); @@ -1328,7 +1328,7 @@ partial record class Diagnostic /// The 'UnableToResolveInterface' diagnostic. /// /// -/// Unable to resolve interface '{arg0}' on type '{arg1}'. +/// Fatal: Unable to resolve interface '{arg0}' on type '{arg1}'. /// public static readonly Diagnostic UnableToResolveInterface = new Diagnostic(5052, nameof(UnableToResolveInterface), "Unable to resolve interface \'{0}\' on type \'{1}\'.", DiagnosticLevel.Fatal); @@ -1336,7 +1336,7 @@ partial record class Diagnostic /// The 'MissingBaseType' diagnostic. /// /// -/// The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. +/// Fatal: The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. /// public static readonly Diagnostic MissingBaseType = new Diagnostic(5053, nameof(MissingBaseType), "The base class or interface \'{0}\' in assembly \'{1}\' referenced by type \'{2}\' in \'" + "{3}\' could not be resolved.", DiagnosticLevel.Fatal); @@ -1345,7 +1345,7 @@ partial record class Diagnostic /// The 'MissingBaseTypeReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. +/// Fatal: The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. /// public static readonly Diagnostic MissingBaseTypeReference = new Diagnostic(5054, nameof(MissingBaseTypeReference), "The type \'{0}\' is defined in an assembly that is not referenced. You must add a r" + "eference to assembly \'{1}\'.", DiagnosticLevel.Fatal); @@ -1354,7 +1354,7 @@ partial record class Diagnostic /// The 'FileNotFound' diagnostic. /// /// -/// File not found: {arg0}. +/// Fatal: File not found: {arg0}. /// public static readonly Diagnostic FileNotFound = new Diagnostic(5055, nameof(FileNotFound), "File not found: {0}.", DiagnosticLevel.Fatal); @@ -1362,7 +1362,7 @@ partial record class Diagnostic /// The 'RuntimeMethodMissing' diagnostic. /// /// -/// Runtime method '{arg0}' not found. +/// Fatal: Runtime method '{arg0}' not found. /// public static readonly Diagnostic RuntimeMethodMissing = new Diagnostic(5056, nameof(RuntimeMethodMissing), "Runtime method \'{0}\' not found.", DiagnosticLevel.Fatal); @@ -1370,7 +1370,7 @@ partial record class Diagnostic /// The 'MapFileFieldNotFound' diagnostic. /// /// -/// Field '{arg0}' referenced in remap file was not found in class '{arg1}'. +/// Fatal: Field '{arg0}' referenced in remap file was not found in class '{arg1}'. /// public static readonly Diagnostic MapFileFieldNotFound = new Diagnostic(5057, nameof(MapFileFieldNotFound), "Field \'{0}\' referenced in remap file was not found in class \'{1}\'.", DiagnosticLevel.Fatal); @@ -1378,7 +1378,7 @@ partial record class Diagnostic /// The 'GhostInterfaceMethodMissing' diagnostic. /// /// -/// Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) +/// Fatal: Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) /// public static readonly Diagnostic GhostInterfaceMethodMissing = new Diagnostic(5058, nameof(GhostInterfaceMethodMissing), "Remapped class \'{0}\' does not implement ghost interface method. ({1}.{2}{3})", DiagnosticLevel.Fatal); @@ -1386,7 +1386,7 @@ partial record class Diagnostic /// The 'ModuleInitializerMethodRequirements' diagnostic. /// /// -/// Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. +/// Fatal: Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. /// public static readonly Diagnostic ModuleInitializerMethodRequirements = new Diagnostic(5059, nameof(ModuleInitializerMethodRequirements), "Method \'{0}.{1}{2}\' does not meet the requirements of a module initializer.", DiagnosticLevel.Fatal); @@ -1394,7 +1394,7 @@ partial record class Diagnostic /// The 'InvalidZip' diagnostic. /// /// -/// Invalid zip: {name}. +/// Fatal: Invalid zip: {name}. /// public static readonly Diagnostic InvalidZip = new Diagnostic(5060, nameof(InvalidZip), "Invalid zip: {0}.", DiagnosticLevel.Fatal); @@ -1402,7 +1402,7 @@ partial record class Diagnostic /// The 'CoreAssemblyVersionMismatch' diagnostic. /// /// -/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. +/// Fatal: Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. /// public static readonly Diagnostic CoreAssemblyVersionMismatch = new Diagnostic(5061, nameof(CoreAssemblyVersionMismatch), "Unable to load assembly \'{-1}\' as it depends on a higher version of {-1} than the" + " one currently loaded.", DiagnosticLevel.Fatal); @@ -1411,7 +1411,7 @@ partial record class Diagnostic /// The 'GenericRuntimeTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public static readonly Diagnostic GenericRuntimeTrace = new Diagnostic(6000, nameof(GenericRuntimeTrace), "{0}", DiagnosticLevel.Trace); @@ -1419,7 +1419,7 @@ partial record class Diagnostic /// The 'GenericJniTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public static readonly Diagnostic GenericJniTrace = new Diagnostic(6001, nameof(GenericJniTrace), "{0}", DiagnosticLevel.Trace); @@ -1427,7 +1427,7 @@ partial record class Diagnostic /// The 'GenericCompilerTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public static readonly Diagnostic GenericCompilerTrace = new Diagnostic(6002, nameof(GenericCompilerTrace), "{0}", DiagnosticLevel.Trace); diff --git a/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.tt b/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.tt index 975d42ffb9..6d64b08652 100644 --- a/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.tt +++ b/src/IKVM.CoreLib/Diagnostics/Diagnostic.g.tt @@ -63,7 +63,7 @@ foreach (var kvp in DiagnosticFile.Read(Host.ResolvePath(Path.Combine("Diagnosti /// <#= desc #> /// /// -<#= Util.ToCommentString(kvp.Value.Message ?? "") #> +<#= Util.ToCommentString(kvp.Value) #> /// public static readonly Diagnostic <#= kvp.Key #> = new Diagnostic(<#= kvp.Value.Id #>, nameof(<#= kvp.Key #>), <#= Util.ToStringLiteral(string.Join("", message)) #>, DiagnosticLevel.<#= kvp.Value.Level #>); diff --git a/src/IKVM.CoreLib/Diagnostics/Diagnostic.t4 b/src/IKVM.CoreLib/Diagnostics/Diagnostic.t4 index e7fe518497..eaf85ec045 100644 --- a/src/IKVM.CoreLib/Diagnostics/Diagnostic.t4 +++ b/src/IKVM.CoreLib/Diagnostics/Diagnostic.t4 @@ -56,13 +56,13 @@ public static class Util } } - public static string ToCommentString(string input) + public static string ToCommentString(Diagnostic diagnostic) { using (var writer = new StringWriter()) { using (var provider = CodeDomProvider.CreateProvider("CSharp")) { - provider.GenerateCodeFromStatement(new CodeCommentStatement(input, true), writer, null); + provider.GenerateCodeFromStatement(new CodeCommentStatement(diagnostic.Level + ": " + diagnostic.Message, true), writer, null); return writer.ToString().Trim(); } } diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs index 0ad8a07f30..6d96eb2c80 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.cs @@ -1,5 +1,6 @@ #nullable enable using System; +using System.Text; namespace IKVM.CoreLib.Diagnostics { @@ -11,7 +12,7 @@ readonly partial struct DiagnosticEvent /// The 'MainMethodFound' diagnostic. /// /// -/// Found main method in class "{arg0}". +/// Info: Found main method in class "{arg0}". /// public static DiagnosticEvent MainMethodFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MainMethodFound.Event([arg0], exception, location); @@ -19,7 +20,7 @@ readonly partial struct DiagnosticEvent /// The 'OutputFileIs' diagnostic. /// /// -/// Output file is "{arg0}". +/// Info: Output file is "{arg0}". /// public static DiagnosticEvent OutputFileIs(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.OutputFileIs.Event([arg0], exception, location); @@ -27,7 +28,7 @@ readonly partial struct DiagnosticEvent /// The 'AutoAddRef' diagnostic. /// /// -/// Automatically adding reference to "{arg0}". +/// Info: Automatically adding reference to "{arg0}". /// public static DiagnosticEvent AutoAddRef(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.AutoAddRef.Event([arg0], exception, location); @@ -35,7 +36,7 @@ readonly partial struct DiagnosticEvent /// The 'MainMethodFromManifest' diagnostic. /// /// -/// Using main class "{arg0}" based on jar manifest. +/// Info: Using main class "{arg0}" based on jar manifest. /// public static DiagnosticEvent MainMethodFromManifest(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MainMethodFromManifest.Event([arg0], exception, location); @@ -43,7 +44,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericCompilerInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static DiagnosticEvent GenericCompilerInfo(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericCompilerInfo.Event([arg0], exception, location); @@ -51,7 +52,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericClassLoadingInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static DiagnosticEvent GenericClassLoadingInfo(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericClassLoadingInfo.Event([arg0], exception, location); @@ -59,7 +60,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericVerifierInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static DiagnosticEvent GenericVerifierInfo(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericVerifierInfo.Event([arg0], exception, location); @@ -67,7 +68,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericRuntimeInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static DiagnosticEvent GenericRuntimeInfo(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericRuntimeInfo.Event([arg0], exception, location); @@ -75,7 +76,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericJniInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public static DiagnosticEvent GenericJniInfo(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericJniInfo.Event([arg0], exception, location); @@ -83,7 +84,7 @@ readonly partial struct DiagnosticEvent /// The 'ClassNotFound' diagnostic. /// /// -/// Class "{arg0}" not found. +/// Warning: Class "{arg0}" not found. /// public static DiagnosticEvent ClassNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ClassNotFound.Event([arg0], exception, location); @@ -91,7 +92,7 @@ readonly partial struct DiagnosticEvent /// The 'ClassFormatError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (class format error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (class format error "{arg1}") /// public static DiagnosticEvent ClassFormatError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ClassFormatError.Event([arg0, arg1], exception, location); @@ -99,7 +100,7 @@ readonly partial struct DiagnosticEvent /// The 'DuplicateClassName' diagnostic. /// /// -/// Duplicate class name: "{arg0}". +/// Warning: Duplicate class name: "{arg0}". /// public static DiagnosticEvent DuplicateClassName(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.DuplicateClassName.Event([arg0], exception, location); @@ -107,7 +108,7 @@ readonly partial struct DiagnosticEvent /// The 'IllegalAccessError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (illegal access error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (illegal access error "{arg1}") /// public static DiagnosticEvent IllegalAccessError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.IllegalAccessError.Event([arg0, arg1], exception, location); @@ -115,7 +116,7 @@ readonly partial struct DiagnosticEvent /// The 'VerificationError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (verification error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (verification error "{arg1}") /// public static DiagnosticEvent VerificationError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.VerificationError.Event([arg0, arg1], exception, location); @@ -123,7 +124,7 @@ readonly partial struct DiagnosticEvent /// The 'NoClassDefFoundError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (missing class "{arg1}") +/// Warning: Unable to compile class "{arg0}". (missing class "{arg1}") /// public static DiagnosticEvent NoClassDefFoundError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.NoClassDefFoundError.Event([arg0, arg1], exception, location); @@ -131,7 +132,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericUnableToCompileError' diagnostic. /// /// -/// Unable to compile class "{arg0}". ("{arg1}": "{arg2}") +/// Warning: Unable to compile class "{arg0}". ("{arg1}": "{arg2}") /// public static DiagnosticEvent GenericUnableToCompileError(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericUnableToCompileError.Event([arg0, arg1, arg2], exception, location); @@ -139,7 +140,7 @@ readonly partial struct DiagnosticEvent /// The 'DuplicateResourceName' diagnostic. /// /// -/// Skipping resource (name clash): "{arg0}" +/// Warning: Skipping resource (name clash): "{arg0}" /// public static DiagnosticEvent DuplicateResourceName(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.DuplicateResourceName.Event([arg0], exception, location); @@ -147,7 +148,7 @@ readonly partial struct DiagnosticEvent /// The 'SkippingReferencedClass' diagnostic. /// /// -/// Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") +/// Warning: Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") /// public static DiagnosticEvent SkippingReferencedClass(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.SkippingReferencedClass.Event([arg0, arg1], exception, location); @@ -155,7 +156,7 @@ readonly partial struct DiagnosticEvent /// The 'NoJniRuntime' diagnostic. /// /// -/// Unable to load runtime JNI assembly. +/// Warning: Unable to load runtime JNI assembly. /// public static DiagnosticEvent NoJniRuntime(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.NoJniRuntime.Event([], exception, location); @@ -163,7 +164,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedNoClassDefFoundError' diagnostic. /// /// -/// Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). +/// Warning: Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). /// public static DiagnosticEvent EmittedNoClassDefFoundError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedNoClassDefFoundError.Event([arg0, arg1], exception, location); @@ -171,7 +172,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedIllegalAccessError' diagnostic. /// /// -/// Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedIllegalAccessError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedIllegalAccessError.Event([arg0, arg1], exception, location); @@ -179,7 +180,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedInstantiationError' diagnostic. /// /// -/// Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedInstantiationError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedInstantiationError.Event([arg0, arg1], exception, location); @@ -187,7 +188,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedIncompatibleClassChangeError' diagnostic. /// /// -/// Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedIncompatibleClassChangeError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedIncompatibleClassChangeError.Event([arg0, arg1], exception, location); @@ -195,7 +196,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedNoSuchFieldError' diagnostic. /// /// -/// Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedNoSuchFieldError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedNoSuchFieldError.Event([arg0, arg1], exception, location); @@ -203,7 +204,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedAbstractMethodError' diagnostic. /// /// -/// Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedAbstractMethodError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedAbstractMethodError.Event([arg0, arg1], exception, location); @@ -211,7 +212,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedNoSuchMethodError' diagnostic. /// /// -/// Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedNoSuchMethodError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedNoSuchMethodError.Event([arg0, arg1], exception, location); @@ -219,7 +220,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedLinkageError' diagnostic. /// /// -/// Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedLinkageError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedLinkageError.Event([arg0, arg1], exception, location); @@ -227,7 +228,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedVerificationError' diagnostic. /// /// -/// Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedVerificationError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedVerificationError.Event([arg0, arg1], exception, location); @@ -235,7 +236,7 @@ readonly partial struct DiagnosticEvent /// The 'EmittedClassFormatError' diagnostic. /// /// -/// Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") /// public static DiagnosticEvent EmittedClassFormatError(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.EmittedClassFormatError.Event([arg0, arg1], exception, location); @@ -243,7 +244,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidCustomAttribute' diagnostic. /// /// -/// Error emitting "{arg0}" custom attribute. ("{arg1}") +/// Warning: Error emitting "{arg0}" custom attribute. ("{arg1}") /// public static DiagnosticEvent InvalidCustomAttribute(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidCustomAttribute.Event([arg0, arg1], exception, location); @@ -251,7 +252,7 @@ readonly partial struct DiagnosticEvent /// The 'IgnoredCustomAttribute' diagnostic. /// /// -/// Custom attribute "{arg0}" was ignored. ("{arg1}") +/// Warning: Custom attribute "{arg0}" was ignored. ("{arg1}") /// public static DiagnosticEvent IgnoredCustomAttribute(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.IgnoredCustomAttribute.Event([arg0, arg1], exception, location); @@ -259,7 +260,7 @@ readonly partial struct DiagnosticEvent /// The 'AssumeAssemblyVersionMatch' diagnostic. /// /// -/// Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy +/// Warning: Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy /// public static DiagnosticEvent AssumeAssemblyVersionMatch(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.AssumeAssemblyVersionMatch.Event([arg0, arg1], exception, location); @@ -267,7 +268,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidDirectoryInLibOptionPath' diagnostic. /// /// -/// Directory "{arg0}" specified in -lib option is not valid. +/// Warning: Directory "{arg0}" specified in -lib option is not valid. /// public static DiagnosticEvent InvalidDirectoryInLibOptionPath(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidDirectoryInLibOptionPath.Event([arg0], exception, location); @@ -275,7 +276,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidDirectoryInLibEnvironmentPath' diagnostic. /// /// -/// Directory "{arg0}" specified in LIB environment is not valid. +/// Warning: Directory "{arg0}" specified in LIB environment is not valid. /// public static DiagnosticEvent InvalidDirectoryInLibEnvironmentPath(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidDirectoryInLibEnvironmentPath.Event([arg0], exception, location); @@ -283,7 +284,7 @@ readonly partial struct DiagnosticEvent /// The 'LegacySearchRule' diagnostic. /// /// -/// Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. +/// Warning: Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. /// public static DiagnosticEvent LegacySearchRule(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.LegacySearchRule.Event([arg0], exception, location); @@ -291,7 +292,7 @@ readonly partial struct DiagnosticEvent /// The 'AssemblyLocationIgnored' diagnostic. /// /// -/// Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". +/// Warning: Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". /// public static DiagnosticEvent AssemblyLocationIgnored(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.AssemblyLocationIgnored.Event([arg0, arg1, arg2], exception, location); @@ -299,7 +300,7 @@ readonly partial struct DiagnosticEvent /// The 'InterfaceMethodCantBeInternal' diagnostic. /// /// -/// Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") +/// Warning: Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") /// public static DiagnosticEvent InterfaceMethodCantBeInternal(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InterfaceMethodCantBeInternal.Event([arg0, arg1, arg2], exception, location); @@ -307,7 +308,7 @@ readonly partial struct DiagnosticEvent /// The 'DuplicateAssemblyReference' diagnostic. /// /// -/// Duplicate assembly reference "{arg0}" +/// Warning: Duplicate assembly reference "{arg0}" /// public static DiagnosticEvent DuplicateAssemblyReference(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.DuplicateAssemblyReference.Event([arg0], exception, location); @@ -315,7 +316,7 @@ readonly partial struct DiagnosticEvent /// The 'UnableToResolveType' diagnostic. /// /// -/// Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. +/// Warning: Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. /// public static DiagnosticEvent UnableToResolveType(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnableToResolveType.Event([arg0, arg1, arg2], exception, location); @@ -323,7 +324,7 @@ readonly partial struct DiagnosticEvent /// The 'StubsAreDeprecated' diagnostic. /// /// -/// Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. +/// Warning: Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. /// public static DiagnosticEvent StubsAreDeprecated(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.StubsAreDeprecated.Event([arg0], exception, location); @@ -331,7 +332,7 @@ readonly partial struct DiagnosticEvent /// The 'WrongClassName' diagnostic. /// /// -/// Unable to compile "{arg0}" (wrong name: "{arg1}") +/// Warning: Unable to compile "{arg0}" (wrong name: "{arg1}") /// public static DiagnosticEvent WrongClassName(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.WrongClassName.Event([arg0, arg1], exception, location); @@ -339,7 +340,7 @@ readonly partial struct DiagnosticEvent /// The 'ReflectionCallerClassRequiresCallerID' diagnostic. /// /// -/// Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") +/// Warning: Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") /// public static DiagnosticEvent ReflectionCallerClassRequiresCallerID(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ReflectionCallerClassRequiresCallerID.Event([arg0, arg1, arg2], exception, location); @@ -347,7 +348,7 @@ readonly partial struct DiagnosticEvent /// The 'LegacyAssemblyAttributesFound' diagnostic. /// /// -/// Legacy assembly attributes container found. Please use the -assemblyattributes: option. +/// Warning: Legacy assembly attributes container found. Please use the -assemblyattributes: option. /// public static DiagnosticEvent LegacyAssemblyAttributesFound(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.LegacyAssemblyAttributesFound.Event([], exception, location); @@ -355,7 +356,7 @@ readonly partial struct DiagnosticEvent /// The 'UnableToCreateLambdaFactory' diagnostic. /// /// -/// Unable to create static lambda factory. +/// Warning: Unable to create static lambda factory. /// public static DiagnosticEvent UnableToCreateLambdaFactory(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnableToCreateLambdaFactory.Event([], exception, location); @@ -363,7 +364,7 @@ readonly partial struct DiagnosticEvent /// The 'UnknownWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static DiagnosticEvent UnknownWarning(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnknownWarning.Event([arg0], exception, location); @@ -371,7 +372,7 @@ readonly partial struct DiagnosticEvent /// The 'DuplicateIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public static DiagnosticEvent DuplicateIkvmLangProperty(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.DuplicateIkvmLangProperty.Event([arg0, arg1], exception, location); @@ -379,7 +380,7 @@ readonly partial struct DiagnosticEvent /// The 'MalformedIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public static DiagnosticEvent MalformedIkvmLangProperty(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MalformedIkvmLangProperty.Event([arg0, arg1], exception, location); @@ -387,7 +388,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericCompilerWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static DiagnosticEvent GenericCompilerWarning(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericCompilerWarning.Event([arg0], exception, location); @@ -395,7 +396,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericClassLoadingWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static DiagnosticEvent GenericClassLoadingWarning(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericClassLoadingWarning.Event([arg0], exception, location); @@ -403,7 +404,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericVerifierWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static DiagnosticEvent GenericVerifierWarning(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericVerifierWarning.Event([arg0], exception, location); @@ -411,7 +412,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericRuntimeWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static DiagnosticEvent GenericRuntimeWarning(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericRuntimeWarning.Event([arg0], exception, location); @@ -419,7 +420,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericJniWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public static DiagnosticEvent GenericJniWarning(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericJniWarning.Event([arg0], exception, location); @@ -427,7 +428,7 @@ readonly partial struct DiagnosticEvent /// The 'UnableToCreateProxy' diagnostic. /// /// -/// Unable to create proxy "{arg0}". ("{arg1}") +/// Error: Unable to create proxy "{arg0}". ("{arg1}") /// public static DiagnosticEvent UnableToCreateProxy(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnableToCreateProxy.Event([arg0, arg1], exception, location); @@ -435,7 +436,7 @@ readonly partial struct DiagnosticEvent /// The 'DuplicateProxy' diagnostic. /// /// -/// Duplicate proxy "{arg0}". +/// Error: Duplicate proxy "{arg0}". /// public static DiagnosticEvent DuplicateProxy(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.DuplicateProxy.Event([arg0], exception, location); @@ -443,7 +444,7 @@ readonly partial struct DiagnosticEvent /// The 'MapXmlUnableToResolveOpCode' diagnostic. /// /// -/// Unable to resolve opcode in remap file: {arg0}. +/// Error: Unable to resolve opcode in remap file: {arg0}. /// public static DiagnosticEvent MapXmlUnableToResolveOpCode(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MapXmlUnableToResolveOpCode.Event([arg0], exception, location); @@ -451,7 +452,7 @@ readonly partial struct DiagnosticEvent /// The 'MapXmlError' diagnostic. /// /// -/// Error in remap file: {arg0}. +/// Error: Error in remap file: {arg0}. /// public static DiagnosticEvent MapXmlError(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MapXmlError.Event([arg0], exception, location); @@ -459,7 +460,7 @@ readonly partial struct DiagnosticEvent /// The 'InputFileNotFound' diagnostic. /// /// -/// Source file '{arg0}' not found. +/// Error: Source file '{arg0}' not found. /// public static DiagnosticEvent InputFileNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InputFileNotFound.Event([arg0], exception, location); @@ -467,7 +468,7 @@ readonly partial struct DiagnosticEvent /// The 'UnknownFileType' diagnostic. /// /// -/// Unknown file type: {arg0}. +/// Error: Unknown file type: {arg0}. /// public static DiagnosticEvent UnknownFileType(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnknownFileType.Event([arg0], exception, location); @@ -475,7 +476,7 @@ readonly partial struct DiagnosticEvent /// The 'UnknownElementInMapFile' diagnostic. /// /// -/// Unknown element {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown element {arg0} in remap file, line {arg1}, column {arg2}. /// public static DiagnosticEvent UnknownElementInMapFile(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnknownElementInMapFile.Event([arg0, arg1, arg2], exception, location); @@ -483,7 +484,7 @@ readonly partial struct DiagnosticEvent /// The 'UnknownAttributeInMapFile' diagnostic. /// /// -/// Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. /// public static DiagnosticEvent UnknownAttributeInMapFile(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnknownAttributeInMapFile.Event([arg0, arg1, arg2], exception, location); @@ -491,7 +492,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidMemberNameInMapFile' diagnostic. /// /// -/// Invalid {arg0} name '{arg1}' in remap file in class {arg2}. +/// Error: Invalid {arg0} name '{arg1}' in remap file in class {arg2}. /// public static DiagnosticEvent InvalidMemberNameInMapFile(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidMemberNameInMapFile.Event([arg0, arg1, arg2], exception, location); @@ -499,7 +500,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidMemberSignatureInMapFile' diagnostic. /// /// -/// Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. +/// Error: Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. /// public static DiagnosticEvent InvalidMemberSignatureInMapFile(string arg0, string arg1, string arg2, string arg3, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidMemberSignatureInMapFile.Event([arg0, arg1, arg2, arg3], exception, location); @@ -507,7 +508,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidPropertyNameInMapFile' diagnostic. /// /// -/// Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. /// public static DiagnosticEvent InvalidPropertyNameInMapFile(string arg0, string arg1, string arg2, string arg3, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidPropertyNameInMapFile.Event([arg0, arg1, arg2, arg3], exception, location); @@ -515,7 +516,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidPropertySignatureInMapFile' diagnostic. /// /// -/// Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. /// public static DiagnosticEvent InvalidPropertySignatureInMapFile(string arg0, string arg1, string arg2, string arg3, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidPropertySignatureInMapFile.Event([arg0, arg1, arg2, arg3], exception, location); @@ -523,7 +524,7 @@ readonly partial struct DiagnosticEvent /// The 'NonPrimaryAssemblyReference' diagnostic. /// /// -/// Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. +/// Error: Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. /// public static DiagnosticEvent NonPrimaryAssemblyReference(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.NonPrimaryAssemblyReference.Event([arg0, arg1], exception, location); @@ -531,7 +532,7 @@ readonly partial struct DiagnosticEvent /// The 'MissingType' diagnostic. /// /// -/// Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. +/// Error: Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. /// public static DiagnosticEvent MissingType(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MissingType.Event([arg0, arg1], exception, location); @@ -539,7 +540,7 @@ readonly partial struct DiagnosticEvent /// The 'MissingReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. +/// Error: The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. /// public static DiagnosticEvent MissingReference(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MissingReference.Event([arg0, arg1], exception, location); @@ -547,7 +548,7 @@ readonly partial struct DiagnosticEvent /// The 'CallerSensitiveOnUnsupportedMethod' diagnostic. /// /// -/// CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") +/// Error: CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") /// public static DiagnosticEvent CallerSensitiveOnUnsupportedMethod(string arg0, string arg1, string arg2, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.CallerSensitiveOnUnsupportedMethod.Event([arg0, arg1, arg2], exception, location); @@ -555,7 +556,7 @@ readonly partial struct DiagnosticEvent /// The 'RemappedTypeMissingDefaultInterfaceMethod' diagnostic. /// /// -/// {arg0} does not implement default interface method {arg1}. +/// Error: {arg0} does not implement default interface method {arg1}. /// public static DiagnosticEvent RemappedTypeMissingDefaultInterfaceMethod(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.RemappedTypeMissingDefaultInterfaceMethod.Event([arg0, arg1], exception, location); @@ -563,7 +564,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericCompilerError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static DiagnosticEvent GenericCompilerError(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericCompilerError.Event([arg0], exception, location); @@ -571,7 +572,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericClassLoadingError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static DiagnosticEvent GenericClassLoadingError(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericClassLoadingError.Event([arg0], exception, location); @@ -579,7 +580,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericVerifierError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static DiagnosticEvent GenericVerifierError(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericVerifierError.Event([arg0], exception, location); @@ -587,7 +588,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericRuntimeError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static DiagnosticEvent GenericRuntimeError(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericRuntimeError.Event([arg0], exception, location); @@ -595,7 +596,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericJniError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public static DiagnosticEvent GenericJniError(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericJniError.Event([arg0], exception, location); @@ -603,7 +604,7 @@ readonly partial struct DiagnosticEvent /// The 'ExportingImportsNotSupported' diagnostic. /// /// -/// Exporting previously imported assemblies is not supported. +/// Error: Exporting previously imported assemblies is not supported. /// public static DiagnosticEvent ExportingImportsNotSupported(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ExportingImportsNotSupported.Event([], exception, location); @@ -611,7 +612,7 @@ readonly partial struct DiagnosticEvent /// The 'ResponseFileDepthExceeded' diagnostic. /// /// -/// Response file nesting depth exceeded. +/// Fatal: Response file nesting depth exceeded. /// public static DiagnosticEvent ResponseFileDepthExceeded(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ResponseFileDepthExceeded.Event([], exception, location); @@ -619,7 +620,7 @@ readonly partial struct DiagnosticEvent /// The 'ErrorReadingFile' diagnostic. /// /// -/// Unable to read file: {arg0}. ({arg1}) +/// Fatal: Unable to read file: {arg0}. ({arg1}) /// public static DiagnosticEvent ErrorReadingFile(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ErrorReadingFile.Event([arg0, arg1], exception, location); @@ -627,7 +628,7 @@ readonly partial struct DiagnosticEvent /// The 'NoTargetsFound' diagnostic. /// /// -/// No targets found +/// Fatal: No targets found /// public static DiagnosticEvent NoTargetsFound(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.NoTargetsFound.Event([], exception, location); @@ -635,7 +636,7 @@ readonly partial struct DiagnosticEvent /// The 'FileFormatLimitationExceeded' diagnostic. /// /// -/// File format limitation exceeded: {arg0}. +/// Fatal: File format limitation exceeded: {arg0}. /// public static DiagnosticEvent FileFormatLimitationExceeded(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.FileFormatLimitationExceeded.Event([arg0], exception, location); @@ -643,7 +644,7 @@ readonly partial struct DiagnosticEvent /// The 'CannotSpecifyBothKeyFileAndContainer' diagnostic. /// /// -/// You cannot specify both a key file and container. +/// Fatal: You cannot specify both a key file and container. /// public static DiagnosticEvent CannotSpecifyBothKeyFileAndContainer(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.CannotSpecifyBothKeyFileAndContainer.Event([], exception, location); @@ -651,7 +652,7 @@ readonly partial struct DiagnosticEvent /// The 'DelaySignRequiresKey' diagnostic. /// /// -/// You cannot delay sign without a key file or container. +/// Fatal: You cannot delay sign without a key file or container. /// public static DiagnosticEvent DelaySignRequiresKey(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.DelaySignRequiresKey.Event([], exception, location); @@ -659,7 +660,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidStrongNameKeyPair' diagnostic. /// /// -/// Invalid key {arg0} specified. ("{arg1}") +/// Fatal: Invalid key {arg0} specified. ("{arg1}") /// public static DiagnosticEvent InvalidStrongNameKeyPair(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidStrongNameKeyPair.Event([arg0, arg1], exception, location); @@ -667,7 +668,7 @@ readonly partial struct DiagnosticEvent /// The 'ReferenceNotFound' diagnostic. /// /// -/// Reference not found: {arg0} +/// Fatal: Reference not found: {arg0} /// public static DiagnosticEvent ReferenceNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ReferenceNotFound.Event([arg0], exception, location); @@ -675,7 +676,7 @@ readonly partial struct DiagnosticEvent /// The 'OptionsMustPreceedChildLevels' diagnostic. /// /// -/// You can only specify options before any child levels. +/// Fatal: You can only specify options before any child levels. /// public static DiagnosticEvent OptionsMustPreceedChildLevels(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.OptionsMustPreceedChildLevels.Event([], exception, location); @@ -683,7 +684,7 @@ readonly partial struct DiagnosticEvent /// The 'UnrecognizedTargetType' diagnostic. /// /// -/// Invalid value '{arg0}' for -target option. +/// Fatal: Invalid value '{arg0}' for -target option. /// public static DiagnosticEvent UnrecognizedTargetType(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnrecognizedTargetType.Event([arg0], exception, location); @@ -691,7 +692,7 @@ readonly partial struct DiagnosticEvent /// The 'UnrecognizedPlatform' diagnostic. /// /// -/// Invalid value '{arg0}' for -platform option. +/// Fatal: Invalid value '{arg0}' for -platform option. /// public static DiagnosticEvent UnrecognizedPlatform(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnrecognizedPlatform.Event([arg0], exception, location); @@ -699,7 +700,7 @@ readonly partial struct DiagnosticEvent /// The 'UnrecognizedApartment' diagnostic. /// /// -/// Invalid value '{arg0}' for -apartment option. +/// Fatal: Invalid value '{arg0}' for -apartment option. /// public static DiagnosticEvent UnrecognizedApartment(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnrecognizedApartment.Event([arg0], exception, location); @@ -707,7 +708,7 @@ readonly partial struct DiagnosticEvent /// The 'MissingFileSpecification' diagnostic. /// /// -/// Missing file specification for '{arg0}' option. +/// Fatal: Missing file specification for '{arg0}' option. /// public static DiagnosticEvent MissingFileSpecification(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MissingFileSpecification.Event([arg0], exception, location); @@ -715,7 +716,7 @@ readonly partial struct DiagnosticEvent /// The 'PathTooLong' diagnostic. /// /// -/// Path too long: {arg0}. +/// Fatal: Path too long: {arg0}. /// public static DiagnosticEvent PathTooLong(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.PathTooLong.Event([arg0], exception, location); @@ -723,7 +724,7 @@ readonly partial struct DiagnosticEvent /// The 'PathNotFound' diagnostic. /// /// -/// Path not found: {arg0}. +/// Fatal: Path not found: {arg0}. /// public static DiagnosticEvent PathNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.PathNotFound.Event([arg0], exception, location); @@ -731,7 +732,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidPath' diagnostic. /// /// -/// Invalid path: {arg0}. +/// Fatal: Invalid path: {arg0}. /// public static DiagnosticEvent InvalidPath(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidPath.Event([arg0], exception, location); @@ -739,7 +740,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidOptionSyntax' diagnostic. /// /// -/// Invalid option: {arg0}. +/// Fatal: Invalid option: {arg0}. /// public static DiagnosticEvent InvalidOptionSyntax(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidOptionSyntax.Event([arg0], exception, location); @@ -747,7 +748,7 @@ readonly partial struct DiagnosticEvent /// The 'ExternalResourceNotFound' diagnostic. /// /// -/// External resource file does not exist: {arg0}. +/// Fatal: External resource file does not exist: {arg0}. /// public static DiagnosticEvent ExternalResourceNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ExternalResourceNotFound.Event([arg0], exception, location); @@ -755,7 +756,7 @@ readonly partial struct DiagnosticEvent /// The 'ExternalResourceNameInvalid' diagnostic. /// /// -/// External resource file may not include path specification: {arg0}. +/// Fatal: External resource file may not include path specification: {arg0}. /// public static DiagnosticEvent ExternalResourceNameInvalid(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ExternalResourceNameInvalid.Event([arg0], exception, location); @@ -763,7 +764,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidVersionFormat' diagnostic. /// /// -/// Invalid version specified: {arg0}. +/// Fatal: Invalid version specified: {arg0}. /// public static DiagnosticEvent InvalidVersionFormat(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidVersionFormat.Event([arg0], exception, location); @@ -771,7 +772,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidFileAlignment' diagnostic. /// /// -/// Invalid value '{arg0}' for -filealign option. +/// Fatal: Invalid value '{arg0}' for -filealign option. /// public static DiagnosticEvent InvalidFileAlignment(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidFileAlignment.Event([arg0], exception, location); @@ -779,7 +780,7 @@ readonly partial struct DiagnosticEvent /// The 'ErrorWritingFile' diagnostic. /// /// -/// Unable to write file: {arg0}. ({arg1}) +/// Fatal: Unable to write file: {arg0}. ({arg1}) /// public static DiagnosticEvent ErrorWritingFile(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ErrorWritingFile.Event([arg0, arg1], exception, location); @@ -787,7 +788,7 @@ readonly partial struct DiagnosticEvent /// The 'UnrecognizedOption' diagnostic. /// /// -/// Unrecognized option: {arg0}. +/// Fatal: Unrecognized option: {arg0}. /// public static DiagnosticEvent UnrecognizedOption(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnrecognizedOption.Event([arg0], exception, location); @@ -795,7 +796,7 @@ readonly partial struct DiagnosticEvent /// The 'NoOutputFileSpecified' diagnostic. /// /// -/// No output file specified. +/// Fatal: No output file specified. /// public static DiagnosticEvent NoOutputFileSpecified(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.NoOutputFileSpecified.Event([], exception, location); @@ -803,7 +804,7 @@ readonly partial struct DiagnosticEvent /// The 'SharedClassLoaderCannotBeUsedOnModuleTarget' diagnostic. /// /// -/// Incompatible options: -target:module and -sharedclassloader cannot be combined. +/// Fatal: Incompatible options: -target:module and -sharedclassloader cannot be combined. /// public static DiagnosticEvent SharedClassLoaderCannotBeUsedOnModuleTarget(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.SharedClassLoaderCannotBeUsedOnModuleTarget.Event([], exception, location); @@ -811,7 +812,7 @@ readonly partial struct DiagnosticEvent /// The 'RuntimeNotFound' diagnostic. /// /// -/// Unable to load runtime assembly. +/// Fatal: Unable to load runtime assembly. /// public static DiagnosticEvent RuntimeNotFound(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.RuntimeNotFound.Event([], exception, location); @@ -819,7 +820,7 @@ readonly partial struct DiagnosticEvent /// The 'MainClassRequiresExe' diagnostic. /// /// -/// Main class cannot be specified for library or module. +/// Fatal: Main class cannot be specified for library or module. /// public static DiagnosticEvent MainClassRequiresExe(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MainClassRequiresExe.Event([], exception, location); @@ -827,7 +828,7 @@ readonly partial struct DiagnosticEvent /// The 'ExeRequiresMainClass' diagnostic. /// /// -/// No main method found. +/// Fatal: No main method found. /// public static DiagnosticEvent ExeRequiresMainClass(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ExeRequiresMainClass.Event([], exception, location); @@ -835,7 +836,7 @@ readonly partial struct DiagnosticEvent /// The 'PropertiesRequireExe' diagnostic. /// /// -/// Properties cannot be specified for library or module. +/// Fatal: Properties cannot be specified for library or module. /// public static DiagnosticEvent PropertiesRequireExe(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.PropertiesRequireExe.Event([], exception, location); @@ -843,7 +844,7 @@ readonly partial struct DiagnosticEvent /// The 'ModuleCannotHaveClassLoader' diagnostic. /// /// -/// Cannot specify assembly class loader for modules. +/// Fatal: Cannot specify assembly class loader for modules. /// public static DiagnosticEvent ModuleCannotHaveClassLoader(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ModuleCannotHaveClassLoader.Event([], exception, location); @@ -851,7 +852,7 @@ readonly partial struct DiagnosticEvent /// The 'ErrorParsingMapFile' diagnostic. /// /// -/// Unable to parse remap file: {arg0}. ({arg1}) +/// Fatal: Unable to parse remap file: {arg0}. ({arg1}) /// public static DiagnosticEvent ErrorParsingMapFile(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ErrorParsingMapFile.Event([arg0, arg1], exception, location); @@ -859,7 +860,7 @@ readonly partial struct DiagnosticEvent /// The 'BootstrapClassesMissing' diagnostic. /// /// -/// Bootstrap classes missing and core assembly not found. +/// Fatal: Bootstrap classes missing and core assembly not found. /// public static DiagnosticEvent BootstrapClassesMissing(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.BootstrapClassesMissing.Event([], exception, location); @@ -867,7 +868,7 @@ readonly partial struct DiagnosticEvent /// The 'StrongNameRequiresStrongNamedRefs' diagnostic. /// /// -/// All referenced assemblies must be strong named, to be able to sign the output assembly. +/// Fatal: All referenced assemblies must be strong named, to be able to sign the output assembly. /// public static DiagnosticEvent StrongNameRequiresStrongNamedRefs(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.StrongNameRequiresStrongNamedRefs.Event([], exception, location); @@ -875,7 +876,7 @@ readonly partial struct DiagnosticEvent /// The 'MainClassNotFound' diagnostic. /// /// -/// Main class not found. +/// Fatal: Main class not found. /// public static DiagnosticEvent MainClassNotFound(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MainClassNotFound.Event([], exception, location); @@ -883,7 +884,7 @@ readonly partial struct DiagnosticEvent /// The 'MainMethodNotFound' diagnostic. /// /// -/// Main method not found. +/// Fatal: Main method not found. /// public static DiagnosticEvent MainMethodNotFound(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MainMethodNotFound.Event([], exception, location); @@ -891,7 +892,7 @@ readonly partial struct DiagnosticEvent /// The 'UnsupportedMainMethod' diagnostic. /// /// -/// Redirected main method not supported. +/// Fatal: Redirected main method not supported. /// public static DiagnosticEvent UnsupportedMainMethod(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnsupportedMainMethod.Event([], exception, location); @@ -899,7 +900,7 @@ readonly partial struct DiagnosticEvent /// The 'ExternalMainNotAccessible' diagnostic. /// /// -/// External main method must be public and in a public class. +/// Fatal: External main method must be public and in a public class. /// public static DiagnosticEvent ExternalMainNotAccessible(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ExternalMainNotAccessible.Event([], exception, location); @@ -907,7 +908,7 @@ readonly partial struct DiagnosticEvent /// The 'ClassLoaderNotFound' diagnostic. /// /// -/// Custom assembly class loader class not found. +/// Fatal: Custom assembly class loader class not found. /// public static DiagnosticEvent ClassLoaderNotFound(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ClassLoaderNotFound.Event([], exception, location); @@ -915,7 +916,7 @@ readonly partial struct DiagnosticEvent /// The 'ClassLoaderNotAccessible' diagnostic. /// /// -/// Custom assembly class loader class is not accessible. +/// Fatal: Custom assembly class loader class is not accessible. /// public static DiagnosticEvent ClassLoaderNotAccessible(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ClassLoaderNotAccessible.Event([], exception, location); @@ -923,7 +924,7 @@ readonly partial struct DiagnosticEvent /// The 'ClassLoaderIsAbstract' diagnostic. /// /// -/// Custom assembly class loader class is abstract. +/// Fatal: Custom assembly class loader class is abstract. /// public static DiagnosticEvent ClassLoaderIsAbstract(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ClassLoaderIsAbstract.Event([], exception, location); @@ -931,7 +932,7 @@ readonly partial struct DiagnosticEvent /// The 'ClassLoaderNotClassLoader' diagnostic. /// /// -/// Custom assembly class loader class does not extend java.lang.ClassLoader. +/// Fatal: Custom assembly class loader class does not extend java.lang.ClassLoader. /// public static DiagnosticEvent ClassLoaderNotClassLoader(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ClassLoaderNotClassLoader.Event([], exception, location); @@ -939,7 +940,7 @@ readonly partial struct DiagnosticEvent /// The 'ClassLoaderConstructorMissing' diagnostic. /// /// -/// Custom assembly class loader constructor is missing. +/// Fatal: Custom assembly class loader constructor is missing. /// public static DiagnosticEvent ClassLoaderConstructorMissing(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ClassLoaderConstructorMissing.Event([], exception, location); @@ -947,7 +948,7 @@ readonly partial struct DiagnosticEvent /// The 'MapFileTypeNotFound' diagnostic. /// /// -/// Type '{arg0}' referenced in remap file was not found. +/// Fatal: Type '{arg0}' referenced in remap file was not found. /// public static DiagnosticEvent MapFileTypeNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MapFileTypeNotFound.Event([arg0], exception, location); @@ -955,7 +956,7 @@ readonly partial struct DiagnosticEvent /// The 'MapFileClassNotFound' diagnostic. /// /// -/// Class '{arg0}' referenced in remap file was not found. +/// Fatal: Class '{arg0}' referenced in remap file was not found. /// public static DiagnosticEvent MapFileClassNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MapFileClassNotFound.Event([arg0], exception, location); @@ -963,7 +964,7 @@ readonly partial struct DiagnosticEvent /// The 'MaximumErrorCountReached' diagnostic. /// /// -/// Maximum error count reached. +/// Fatal: Maximum error count reached. /// public static DiagnosticEvent MaximumErrorCountReached(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MaximumErrorCountReached.Event([], exception, location); @@ -971,7 +972,7 @@ readonly partial struct DiagnosticEvent /// The 'LinkageError' diagnostic. /// /// -/// Link error: {arg0} +/// Fatal: Link error: {arg0} /// public static DiagnosticEvent LinkageError(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.LinkageError.Event([arg0], exception, location); @@ -979,7 +980,7 @@ readonly partial struct DiagnosticEvent /// The 'RuntimeMismatch' diagnostic. /// /// -/// Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} +/// Fatal: Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} /// public static DiagnosticEvent RuntimeMismatch(string referencedAssemblyPath, string runtimeAssemblyName, string referencedAssemblyName, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.RuntimeMismatch.Event([referencedAssemblyPath, runtimeAssemblyName, referencedAssemblyName], exception, location); @@ -987,7 +988,7 @@ readonly partial struct DiagnosticEvent /// The 'RuntimeMismatchStrongName' diagnostic. /// /// -/// +/// Fatal: /// public static DiagnosticEvent RuntimeMismatchStrongName(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.RuntimeMismatchStrongName.Event([], exception, location); @@ -995,7 +996,7 @@ readonly partial struct DiagnosticEvent /// The 'CoreClassesMissing' diagnostic. /// /// -/// Failed to find core classes in core library. +/// Fatal: Failed to find core classes in core library. /// public static DiagnosticEvent CoreClassesMissing(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.CoreClassesMissing.Event([], exception, location); @@ -1003,7 +1004,7 @@ readonly partial struct DiagnosticEvent /// The 'CriticalClassNotFound' diagnostic. /// /// -/// Unable to load critical class '{arg0}'. +/// Fatal: Unable to load critical class '{arg0}'. /// public static DiagnosticEvent CriticalClassNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.CriticalClassNotFound.Event([arg0], exception, location); @@ -1011,7 +1012,7 @@ readonly partial struct DiagnosticEvent /// The 'AssemblyContainsDuplicateClassNames' diagnostic. /// /// -/// Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) +/// Fatal: Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) /// public static DiagnosticEvent AssemblyContainsDuplicateClassNames(string arg0, string arg1, string arg2, string arg3, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.AssemblyContainsDuplicateClassNames.Event([arg0, arg1, arg2, arg3], exception, location); @@ -1019,7 +1020,7 @@ readonly partial struct DiagnosticEvent /// The 'CallerIDRequiresHasCallerIDAnnotation' diagnostic. /// /// -/// CallerID.getCallerID() requires a HasCallerID annotation. +/// Fatal: CallerID.getCallerID() requires a HasCallerID annotation. /// public static DiagnosticEvent CallerIDRequiresHasCallerIDAnnotation(Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.CallerIDRequiresHasCallerIDAnnotation.Event([], exception, location); @@ -1027,7 +1028,7 @@ readonly partial struct DiagnosticEvent /// The 'UnableToResolveInterface' diagnostic. /// /// -/// Unable to resolve interface '{arg0}' on type '{arg1}'. +/// Fatal: Unable to resolve interface '{arg0}' on type '{arg1}'. /// public static DiagnosticEvent UnableToResolveInterface(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.UnableToResolveInterface.Event([arg0, arg1], exception, location); @@ -1035,7 +1036,7 @@ readonly partial struct DiagnosticEvent /// The 'MissingBaseType' diagnostic. /// /// -/// The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. +/// Fatal: The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. /// public static DiagnosticEvent MissingBaseType(string arg0, string arg1, string arg2, string arg3, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MissingBaseType.Event([arg0, arg1, arg2, arg3], exception, location); @@ -1043,7 +1044,7 @@ readonly partial struct DiagnosticEvent /// The 'MissingBaseTypeReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. +/// Fatal: The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. /// public static DiagnosticEvent MissingBaseTypeReference(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MissingBaseTypeReference.Event([arg0, arg1], exception, location); @@ -1051,7 +1052,7 @@ readonly partial struct DiagnosticEvent /// The 'FileNotFound' diagnostic. /// /// -/// File not found: {arg0}. +/// Fatal: File not found: {arg0}. /// public static DiagnosticEvent FileNotFound(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.FileNotFound.Event([arg0], exception, location); @@ -1059,7 +1060,7 @@ readonly partial struct DiagnosticEvent /// The 'RuntimeMethodMissing' diagnostic. /// /// -/// Runtime method '{arg0}' not found. +/// Fatal: Runtime method '{arg0}' not found. /// public static DiagnosticEvent RuntimeMethodMissing(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.RuntimeMethodMissing.Event([arg0], exception, location); @@ -1067,7 +1068,7 @@ readonly partial struct DiagnosticEvent /// The 'MapFileFieldNotFound' diagnostic. /// /// -/// Field '{arg0}' referenced in remap file was not found in class '{arg1}'. +/// Fatal: Field '{arg0}' referenced in remap file was not found in class '{arg1}'. /// public static DiagnosticEvent MapFileFieldNotFound(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.MapFileFieldNotFound.Event([arg0, arg1], exception, location); @@ -1075,7 +1076,7 @@ readonly partial struct DiagnosticEvent /// The 'GhostInterfaceMethodMissing' diagnostic. /// /// -/// Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) +/// Fatal: Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) /// public static DiagnosticEvent GhostInterfaceMethodMissing(string arg0, string arg1, string arg2, string arg3, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GhostInterfaceMethodMissing.Event([arg0, arg1, arg2, arg3], exception, location); @@ -1083,7 +1084,7 @@ readonly partial struct DiagnosticEvent /// The 'ModuleInitializerMethodRequirements' diagnostic. /// /// -/// Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. +/// Fatal: Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. /// public static DiagnosticEvent ModuleInitializerMethodRequirements(string arg1, string arg2, string arg3, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.ModuleInitializerMethodRequirements.Event([arg1, arg2, arg3], exception, location); @@ -1091,7 +1092,7 @@ readonly partial struct DiagnosticEvent /// The 'InvalidZip' diagnostic. /// /// -/// Invalid zip: {name}. +/// Fatal: Invalid zip: {name}. /// public static DiagnosticEvent InvalidZip(string name, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.InvalidZip.Event([name], exception, location); @@ -1099,7 +1100,7 @@ readonly partial struct DiagnosticEvent /// The 'CoreAssemblyVersionMismatch' diagnostic. /// /// -/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. +/// Fatal: Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. /// public static DiagnosticEvent CoreAssemblyVersionMismatch(string arg0, string arg1, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.CoreAssemblyVersionMismatch.Event([arg0, arg1], exception, location); @@ -1107,7 +1108,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericRuntimeTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public static DiagnosticEvent GenericRuntimeTrace(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericRuntimeTrace.Event([arg0], exception, location); @@ -1115,7 +1116,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericJniTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public static DiagnosticEvent GenericJniTrace(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericJniTrace.Event([arg0], exception, location); @@ -1123,7 +1124,7 @@ readonly partial struct DiagnosticEvent /// The 'GenericCompilerTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public static DiagnosticEvent GenericCompilerTrace(string arg0, Exception? exception = null, DiagnosticLocation location = default) => Diagnostic.GenericCompilerTrace.Event([arg0], exception, location); diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.tt b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.tt index a7cdf4ab6d..9b3b95ecb8 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.tt +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEvent.g.tt @@ -50,7 +50,7 @@ foreach (var kvp in DiagnosticFile.Read(Host.ResolvePath(Path.Combine("Diagnosti /// <#= desc #> /// /// -<#= Util.ToCommentString(kvp.Value.Message ?? "") #> +<#= Util.ToCommentString(kvp.Value) #> /// public static DiagnosticEvent <#= kvp.Key #>(<#= string.Join(", ", argDecl) #>) => Diagnostic.<#= kvp.Key #>.Event([<#= string.Join(", ", argList) #>], exception, location); diff --git a/src/IKVM.Tools.Importer/FatalCompilerErrorException.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventException.cs similarity index 88% rename from src/IKVM.Tools.Importer/FatalCompilerErrorException.cs rename to src/IKVM.CoreLib/Diagnostics/DiagnosticEventException.cs index 8296518f42..bf64df0b37 100644 --- a/src/IKVM.Tools.Importer/FatalCompilerErrorException.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventException.cs @@ -1,11 +1,9 @@ using System; -using IKVM.CoreLib.Diagnostics; - -namespace IKVM.Tools.Importer +namespace IKVM.CoreLib.Diagnostics { - sealed class FatalCompilerErrorException : Exception + sealed class DiagnosticEventException : Exception { /// @@ -33,7 +31,7 @@ static string FormatDiagnosticLevel(DiagnosticLevel level) /// Initializes a new instance. /// /// - internal FatalCompilerErrorException(in DiagnosticEvent evt) : + internal DiagnosticEventException(in DiagnosticEvent evt) : #if NET8_0_OR_GREATER base($"{FormatDiagnosticLevel(evt.Diagnostic.Level)} IKVM{evt.Diagnostic.Id:D4}: {string.Format(null, evt.Diagnostic.Message, evt.Args)}") #else diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs index 53fc27600f..782a3309c4 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.cs @@ -10,7 +10,7 @@ internal abstract partial class DiagnosticEventHandler /// The 'MainMethodFound' diagnostic. /// /// -/// Found main method in class "{arg0}". +/// Info: Found main method in class "{arg0}". /// public void MainMethodFound(string arg0) { @@ -22,7 +22,7 @@ public void MainMethodFound(string arg0) /// The 'OutputFileIs' diagnostic. /// /// -/// Output file is "{arg0}". +/// Info: Output file is "{arg0}". /// public void OutputFileIs(string arg0) { @@ -34,7 +34,7 @@ public void OutputFileIs(string arg0) /// The 'AutoAddRef' diagnostic. /// /// -/// Automatically adding reference to "{arg0}". +/// Info: Automatically adding reference to "{arg0}". /// public void AutoAddRef(string arg0) { @@ -46,7 +46,7 @@ public void AutoAddRef(string arg0) /// The 'MainMethodFromManifest' diagnostic. /// /// -/// Using main class "{arg0}" based on jar manifest. +/// Info: Using main class "{arg0}" based on jar manifest. /// public void MainMethodFromManifest(string arg0) { @@ -58,7 +58,7 @@ public void MainMethodFromManifest(string arg0) /// The 'GenericCompilerInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericCompilerInfo(string arg0) { @@ -70,7 +70,7 @@ public void GenericCompilerInfo(string arg0) /// The 'GenericClassLoadingInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericClassLoadingInfo(string arg0) { @@ -82,7 +82,7 @@ public void GenericClassLoadingInfo(string arg0) /// The 'GenericVerifierInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericVerifierInfo(string arg0) { @@ -94,7 +94,7 @@ public void GenericVerifierInfo(string arg0) /// The 'GenericRuntimeInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericRuntimeInfo(string arg0) { @@ -106,7 +106,7 @@ public void GenericRuntimeInfo(string arg0) /// The 'GenericJniInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericJniInfo(string arg0) { @@ -118,7 +118,7 @@ public void GenericJniInfo(string arg0) /// The 'ClassNotFound' diagnostic. /// /// -/// Class "{arg0}" not found. +/// Warning: Class "{arg0}" not found. /// public void ClassNotFound(string arg0) { @@ -130,7 +130,7 @@ public void ClassNotFound(string arg0) /// The 'ClassFormatError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (class format error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (class format error "{arg1}") /// public void ClassFormatError(string arg0, string arg1) { @@ -142,7 +142,7 @@ public void ClassFormatError(string arg0, string arg1) /// The 'DuplicateClassName' diagnostic. /// /// -/// Duplicate class name: "{arg0}". +/// Warning: Duplicate class name: "{arg0}". /// public void DuplicateClassName(string arg0) { @@ -154,7 +154,7 @@ public void DuplicateClassName(string arg0) /// The 'IllegalAccessError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (illegal access error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (illegal access error "{arg1}") /// public void IllegalAccessError(string arg0, string arg1) { @@ -166,7 +166,7 @@ public void IllegalAccessError(string arg0, string arg1) /// The 'VerificationError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (verification error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (verification error "{arg1}") /// public void VerificationError(string arg0, string arg1) { @@ -178,7 +178,7 @@ public void VerificationError(string arg0, string arg1) /// The 'NoClassDefFoundError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (missing class "{arg1}") +/// Warning: Unable to compile class "{arg0}". (missing class "{arg1}") /// public void NoClassDefFoundError(string arg0, string arg1) { @@ -190,7 +190,7 @@ public void NoClassDefFoundError(string arg0, string arg1) /// The 'GenericUnableToCompileError' diagnostic. /// /// -/// Unable to compile class "{arg0}". ("{arg1}": "{arg2}") +/// Warning: Unable to compile class "{arg0}". ("{arg1}": "{arg2}") /// public void GenericUnableToCompileError(string arg0, string arg1, string arg2) { @@ -202,7 +202,7 @@ public void GenericUnableToCompileError(string arg0, string arg1, string arg2) /// The 'DuplicateResourceName' diagnostic. /// /// -/// Skipping resource (name clash): "{arg0}" +/// Warning: Skipping resource (name clash): "{arg0}" /// public void DuplicateResourceName(string arg0) { @@ -214,7 +214,7 @@ public void DuplicateResourceName(string arg0) /// The 'SkippingReferencedClass' diagnostic. /// /// -/// Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") +/// Warning: Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") /// public void SkippingReferencedClass(string arg0, string arg1) { @@ -226,7 +226,7 @@ public void SkippingReferencedClass(string arg0, string arg1) /// The 'NoJniRuntime' diagnostic. /// /// -/// Unable to load runtime JNI assembly. +/// Warning: Unable to load runtime JNI assembly. /// public void NoJniRuntime() { @@ -238,7 +238,7 @@ public void NoJniRuntime() /// The 'EmittedNoClassDefFoundError' diagnostic. /// /// -/// Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). +/// Warning: Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). /// public void EmittedNoClassDefFoundError(string arg0, string arg1) { @@ -250,7 +250,7 @@ public void EmittedNoClassDefFoundError(string arg0, string arg1) /// The 'EmittedIllegalAccessError' diagnostic. /// /// -/// Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") /// public void EmittedIllegalAccessError(string arg0, string arg1) { @@ -262,7 +262,7 @@ public void EmittedIllegalAccessError(string arg0, string arg1) /// The 'EmittedInstantiationError' diagnostic. /// /// -/// Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") /// public void EmittedInstantiationError(string arg0, string arg1) { @@ -274,7 +274,7 @@ public void EmittedInstantiationError(string arg0, string arg1) /// The 'EmittedIncompatibleClassChangeError' diagnostic. /// /// -/// Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") /// public void EmittedIncompatibleClassChangeError(string arg0, string arg1) { @@ -286,7 +286,7 @@ public void EmittedIncompatibleClassChangeError(string arg0, string arg1) /// The 'EmittedNoSuchFieldError' diagnostic. /// /// -/// Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") /// public void EmittedNoSuchFieldError(string arg0, string arg1) { @@ -298,7 +298,7 @@ public void EmittedNoSuchFieldError(string arg0, string arg1) /// The 'EmittedAbstractMethodError' diagnostic. /// /// -/// Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") /// public void EmittedAbstractMethodError(string arg0, string arg1) { @@ -310,7 +310,7 @@ public void EmittedAbstractMethodError(string arg0, string arg1) /// The 'EmittedNoSuchMethodError' diagnostic. /// /// -/// Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") /// public void EmittedNoSuchMethodError(string arg0, string arg1) { @@ -322,7 +322,7 @@ public void EmittedNoSuchMethodError(string arg0, string arg1) /// The 'EmittedLinkageError' diagnostic. /// /// -/// Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") /// public void EmittedLinkageError(string arg0, string arg1) { @@ -334,7 +334,7 @@ public void EmittedLinkageError(string arg0, string arg1) /// The 'EmittedVerificationError' diagnostic. /// /// -/// Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") /// public void EmittedVerificationError(string arg0, string arg1) { @@ -346,7 +346,7 @@ public void EmittedVerificationError(string arg0, string arg1) /// The 'EmittedClassFormatError' diagnostic. /// /// -/// Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") /// public void EmittedClassFormatError(string arg0, string arg1) { @@ -358,7 +358,7 @@ public void EmittedClassFormatError(string arg0, string arg1) /// The 'InvalidCustomAttribute' diagnostic. /// /// -/// Error emitting "{arg0}" custom attribute. ("{arg1}") +/// Warning: Error emitting "{arg0}" custom attribute. ("{arg1}") /// public void InvalidCustomAttribute(string arg0, string arg1) { @@ -370,7 +370,7 @@ public void InvalidCustomAttribute(string arg0, string arg1) /// The 'IgnoredCustomAttribute' diagnostic. /// /// -/// Custom attribute "{arg0}" was ignored. ("{arg1}") +/// Warning: Custom attribute "{arg0}" was ignored. ("{arg1}") /// public void IgnoredCustomAttribute(string arg0, string arg1) { @@ -382,7 +382,7 @@ public void IgnoredCustomAttribute(string arg0, string arg1) /// The 'AssumeAssemblyVersionMatch' diagnostic. /// /// -/// Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy +/// Warning: Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy /// public void AssumeAssemblyVersionMatch(string arg0, string arg1) { @@ -394,7 +394,7 @@ public void AssumeAssemblyVersionMatch(string arg0, string arg1) /// The 'InvalidDirectoryInLibOptionPath' diagnostic. /// /// -/// Directory "{arg0}" specified in -lib option is not valid. +/// Warning: Directory "{arg0}" specified in -lib option is not valid. /// public void InvalidDirectoryInLibOptionPath(string arg0) { @@ -406,7 +406,7 @@ public void InvalidDirectoryInLibOptionPath(string arg0) /// The 'InvalidDirectoryInLibEnvironmentPath' diagnostic. /// /// -/// Directory "{arg0}" specified in LIB environment is not valid. +/// Warning: Directory "{arg0}" specified in LIB environment is not valid. /// public void InvalidDirectoryInLibEnvironmentPath(string arg0) { @@ -418,7 +418,7 @@ public void InvalidDirectoryInLibEnvironmentPath(string arg0) /// The 'LegacySearchRule' diagnostic. /// /// -/// Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. +/// Warning: Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. /// public void LegacySearchRule(string arg0) { @@ -430,7 +430,7 @@ public void LegacySearchRule(string arg0) /// The 'AssemblyLocationIgnored' diagnostic. /// /// -/// Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". +/// Warning: Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". /// public void AssemblyLocationIgnored(string arg0, string arg1, string arg2) { @@ -442,7 +442,7 @@ public void AssemblyLocationIgnored(string arg0, string arg1, string arg2) /// The 'InterfaceMethodCantBeInternal' diagnostic. /// /// -/// Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") +/// Warning: Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") /// public void InterfaceMethodCantBeInternal(string arg0, string arg1, string arg2) { @@ -454,7 +454,7 @@ public void InterfaceMethodCantBeInternal(string arg0, string arg1, string arg2) /// The 'DuplicateAssemblyReference' diagnostic. /// /// -/// Duplicate assembly reference "{arg0}" +/// Warning: Duplicate assembly reference "{arg0}" /// public void DuplicateAssemblyReference(string arg0) { @@ -466,7 +466,7 @@ public void DuplicateAssemblyReference(string arg0) /// The 'UnableToResolveType' diagnostic. /// /// -/// Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. +/// Warning: Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. /// public void UnableToResolveType(string arg0, string arg1, string arg2) { @@ -478,7 +478,7 @@ public void UnableToResolveType(string arg0, string arg1, string arg2) /// The 'StubsAreDeprecated' diagnostic. /// /// -/// Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. +/// Warning: Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. /// public void StubsAreDeprecated(string arg0) { @@ -490,7 +490,7 @@ public void StubsAreDeprecated(string arg0) /// The 'WrongClassName' diagnostic. /// /// -/// Unable to compile "{arg0}" (wrong name: "{arg1}") +/// Warning: Unable to compile "{arg0}" (wrong name: "{arg1}") /// public void WrongClassName(string arg0, string arg1) { @@ -502,7 +502,7 @@ public void WrongClassName(string arg0, string arg1) /// The 'ReflectionCallerClassRequiresCallerID' diagnostic. /// /// -/// Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") +/// Warning: Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") /// public void ReflectionCallerClassRequiresCallerID(string arg0, string arg1, string arg2) { @@ -514,7 +514,7 @@ public void ReflectionCallerClassRequiresCallerID(string arg0, string arg1, stri /// The 'LegacyAssemblyAttributesFound' diagnostic. /// /// -/// Legacy assembly attributes container found. Please use the -assemblyattributes: option. +/// Warning: Legacy assembly attributes container found. Please use the -assemblyattributes: option. /// public void LegacyAssemblyAttributesFound() { @@ -526,7 +526,7 @@ public void LegacyAssemblyAttributesFound() /// The 'UnableToCreateLambdaFactory' diagnostic. /// /// -/// Unable to create static lambda factory. +/// Warning: Unable to create static lambda factory. /// public void UnableToCreateLambdaFactory() { @@ -538,7 +538,7 @@ public void UnableToCreateLambdaFactory() /// The 'UnknownWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void UnknownWarning(string arg0) { @@ -550,7 +550,7 @@ public void UnknownWarning(string arg0) /// The 'DuplicateIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public void DuplicateIkvmLangProperty(string arg0, string arg1) { @@ -562,7 +562,7 @@ public void DuplicateIkvmLangProperty(string arg0, string arg1) /// The 'MalformedIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public void MalformedIkvmLangProperty(string arg0, string arg1) { @@ -574,7 +574,7 @@ public void MalformedIkvmLangProperty(string arg0, string arg1) /// The 'GenericCompilerWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericCompilerWarning(string arg0) { @@ -586,7 +586,7 @@ public void GenericCompilerWarning(string arg0) /// The 'GenericClassLoadingWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericClassLoadingWarning(string arg0) { @@ -598,7 +598,7 @@ public void GenericClassLoadingWarning(string arg0) /// The 'GenericVerifierWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericVerifierWarning(string arg0) { @@ -610,7 +610,7 @@ public void GenericVerifierWarning(string arg0) /// The 'GenericRuntimeWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericRuntimeWarning(string arg0) { @@ -622,7 +622,7 @@ public void GenericRuntimeWarning(string arg0) /// The 'GenericJniWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericJniWarning(string arg0) { @@ -634,7 +634,7 @@ public void GenericJniWarning(string arg0) /// The 'UnableToCreateProxy' diagnostic. /// /// -/// Unable to create proxy "{arg0}". ("{arg1}") +/// Error: Unable to create proxy "{arg0}". ("{arg1}") /// public void UnableToCreateProxy(string arg0, string arg1) { @@ -646,7 +646,7 @@ public void UnableToCreateProxy(string arg0, string arg1) /// The 'DuplicateProxy' diagnostic. /// /// -/// Duplicate proxy "{arg0}". +/// Error: Duplicate proxy "{arg0}". /// public void DuplicateProxy(string arg0) { @@ -658,7 +658,7 @@ public void DuplicateProxy(string arg0) /// The 'MapXmlUnableToResolveOpCode' diagnostic. /// /// -/// Unable to resolve opcode in remap file: {arg0}. +/// Error: Unable to resolve opcode in remap file: {arg0}. /// public void MapXmlUnableToResolveOpCode(string arg0) { @@ -670,7 +670,7 @@ public void MapXmlUnableToResolveOpCode(string arg0) /// The 'MapXmlError' diagnostic. /// /// -/// Error in remap file: {arg0}. +/// Error: Error in remap file: {arg0}. /// public void MapXmlError(string arg0) { @@ -682,7 +682,7 @@ public void MapXmlError(string arg0) /// The 'InputFileNotFound' diagnostic. /// /// -/// Source file '{arg0}' not found. +/// Error: Source file '{arg0}' not found. /// public void InputFileNotFound(string arg0) { @@ -694,7 +694,7 @@ public void InputFileNotFound(string arg0) /// The 'UnknownFileType' diagnostic. /// /// -/// Unknown file type: {arg0}. +/// Error: Unknown file type: {arg0}. /// public void UnknownFileType(string arg0) { @@ -706,7 +706,7 @@ public void UnknownFileType(string arg0) /// The 'UnknownElementInMapFile' diagnostic. /// /// -/// Unknown element {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown element {arg0} in remap file, line {arg1}, column {arg2}. /// public void UnknownElementInMapFile(string arg0, string arg1, string arg2) { @@ -718,7 +718,7 @@ public void UnknownElementInMapFile(string arg0, string arg1, string arg2) /// The 'UnknownAttributeInMapFile' diagnostic. /// /// -/// Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. /// public void UnknownAttributeInMapFile(string arg0, string arg1, string arg2) { @@ -730,7 +730,7 @@ public void UnknownAttributeInMapFile(string arg0, string arg1, string arg2) /// The 'InvalidMemberNameInMapFile' diagnostic. /// /// -/// Invalid {arg0} name '{arg1}' in remap file in class {arg2}. +/// Error: Invalid {arg0} name '{arg1}' in remap file in class {arg2}. /// public void InvalidMemberNameInMapFile(string arg0, string arg1, string arg2) { @@ -742,7 +742,7 @@ public void InvalidMemberNameInMapFile(string arg0, string arg1, string arg2) /// The 'InvalidMemberSignatureInMapFile' diagnostic. /// /// -/// Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. +/// Error: Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. /// public void InvalidMemberSignatureInMapFile(string arg0, string arg1, string arg2, string arg3) { @@ -754,7 +754,7 @@ public void InvalidMemberSignatureInMapFile(string arg0, string arg1, string arg /// The 'InvalidPropertyNameInMapFile' diagnostic. /// /// -/// Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. /// public void InvalidPropertyNameInMapFile(string arg0, string arg1, string arg2, string arg3) { @@ -766,7 +766,7 @@ public void InvalidPropertyNameInMapFile(string arg0, string arg1, string arg2, /// The 'InvalidPropertySignatureInMapFile' diagnostic. /// /// -/// Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. /// public void InvalidPropertySignatureInMapFile(string arg0, string arg1, string arg2, string arg3) { @@ -778,7 +778,7 @@ public void InvalidPropertySignatureInMapFile(string arg0, string arg1, string a /// The 'NonPrimaryAssemblyReference' diagnostic. /// /// -/// Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. +/// Error: Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. /// public void NonPrimaryAssemblyReference(string arg0, string arg1) { @@ -790,7 +790,7 @@ public void NonPrimaryAssemblyReference(string arg0, string arg1) /// The 'MissingType' diagnostic. /// /// -/// Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. +/// Error: Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. /// public void MissingType(string arg0, string arg1) { @@ -802,7 +802,7 @@ public void MissingType(string arg0, string arg1) /// The 'MissingReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. +/// Error: The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. /// public void MissingReference(string arg0, string arg1) { @@ -814,7 +814,7 @@ public void MissingReference(string arg0, string arg1) /// The 'CallerSensitiveOnUnsupportedMethod' diagnostic. /// /// -/// CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") +/// Error: CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") /// public void CallerSensitiveOnUnsupportedMethod(string arg0, string arg1, string arg2) { @@ -826,7 +826,7 @@ public void CallerSensitiveOnUnsupportedMethod(string arg0, string arg1, string /// The 'RemappedTypeMissingDefaultInterfaceMethod' diagnostic. /// /// -/// {arg0} does not implement default interface method {arg1}. +/// Error: {arg0} does not implement default interface method {arg1}. /// public void RemappedTypeMissingDefaultInterfaceMethod(string arg0, string arg1) { @@ -838,7 +838,7 @@ public void RemappedTypeMissingDefaultInterfaceMethod(string arg0, string arg1) /// The 'GenericCompilerError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericCompilerError(string arg0) { @@ -850,7 +850,7 @@ public void GenericCompilerError(string arg0) /// The 'GenericClassLoadingError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericClassLoadingError(string arg0) { @@ -862,7 +862,7 @@ public void GenericClassLoadingError(string arg0) /// The 'GenericVerifierError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericVerifierError(string arg0) { @@ -874,7 +874,7 @@ public void GenericVerifierError(string arg0) /// The 'GenericRuntimeError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericRuntimeError(string arg0) { @@ -886,7 +886,7 @@ public void GenericRuntimeError(string arg0) /// The 'GenericJniError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericJniError(string arg0) { @@ -898,7 +898,7 @@ public void GenericJniError(string arg0) /// The 'ExportingImportsNotSupported' diagnostic. /// /// -/// Exporting previously imported assemblies is not supported. +/// Error: Exporting previously imported assemblies is not supported. /// public void ExportingImportsNotSupported() { @@ -910,7 +910,7 @@ public void ExportingImportsNotSupported() /// The 'ResponseFileDepthExceeded' diagnostic. /// /// -/// Response file nesting depth exceeded. +/// Fatal: Response file nesting depth exceeded. /// public void ResponseFileDepthExceeded() { @@ -922,7 +922,7 @@ public void ResponseFileDepthExceeded() /// The 'ErrorReadingFile' diagnostic. /// /// -/// Unable to read file: {arg0}. ({arg1}) +/// Fatal: Unable to read file: {arg0}. ({arg1}) /// public void ErrorReadingFile(string arg0, string arg1) { @@ -934,7 +934,7 @@ public void ErrorReadingFile(string arg0, string arg1) /// The 'NoTargetsFound' diagnostic. /// /// -/// No targets found +/// Fatal: No targets found /// public void NoTargetsFound() { @@ -946,7 +946,7 @@ public void NoTargetsFound() /// The 'FileFormatLimitationExceeded' diagnostic. /// /// -/// File format limitation exceeded: {arg0}. +/// Fatal: File format limitation exceeded: {arg0}. /// public void FileFormatLimitationExceeded(string arg0) { @@ -958,7 +958,7 @@ public void FileFormatLimitationExceeded(string arg0) /// The 'CannotSpecifyBothKeyFileAndContainer' diagnostic. /// /// -/// You cannot specify both a key file and container. +/// Fatal: You cannot specify both a key file and container. /// public void CannotSpecifyBothKeyFileAndContainer() { @@ -970,7 +970,7 @@ public void CannotSpecifyBothKeyFileAndContainer() /// The 'DelaySignRequiresKey' diagnostic. /// /// -/// You cannot delay sign without a key file or container. +/// Fatal: You cannot delay sign without a key file or container. /// public void DelaySignRequiresKey() { @@ -982,7 +982,7 @@ public void DelaySignRequiresKey() /// The 'InvalidStrongNameKeyPair' diagnostic. /// /// -/// Invalid key {arg0} specified. ("{arg1}") +/// Fatal: Invalid key {arg0} specified. ("{arg1}") /// public void InvalidStrongNameKeyPair(string arg0, string arg1) { @@ -994,7 +994,7 @@ public void InvalidStrongNameKeyPair(string arg0, string arg1) /// The 'ReferenceNotFound' diagnostic. /// /// -/// Reference not found: {arg0} +/// Fatal: Reference not found: {arg0} /// public void ReferenceNotFound(string arg0) { @@ -1006,7 +1006,7 @@ public void ReferenceNotFound(string arg0) /// The 'OptionsMustPreceedChildLevels' diagnostic. /// /// -/// You can only specify options before any child levels. +/// Fatal: You can only specify options before any child levels. /// public void OptionsMustPreceedChildLevels() { @@ -1018,7 +1018,7 @@ public void OptionsMustPreceedChildLevels() /// The 'UnrecognizedTargetType' diagnostic. /// /// -/// Invalid value '{arg0}' for -target option. +/// Fatal: Invalid value '{arg0}' for -target option. /// public void UnrecognizedTargetType(string arg0) { @@ -1030,7 +1030,7 @@ public void UnrecognizedTargetType(string arg0) /// The 'UnrecognizedPlatform' diagnostic. /// /// -/// Invalid value '{arg0}' for -platform option. +/// Fatal: Invalid value '{arg0}' for -platform option. /// public void UnrecognizedPlatform(string arg0) { @@ -1042,7 +1042,7 @@ public void UnrecognizedPlatform(string arg0) /// The 'UnrecognizedApartment' diagnostic. /// /// -/// Invalid value '{arg0}' for -apartment option. +/// Fatal: Invalid value '{arg0}' for -apartment option. /// public void UnrecognizedApartment(string arg0) { @@ -1054,7 +1054,7 @@ public void UnrecognizedApartment(string arg0) /// The 'MissingFileSpecification' diagnostic. /// /// -/// Missing file specification for '{arg0}' option. +/// Fatal: Missing file specification for '{arg0}' option. /// public void MissingFileSpecification(string arg0) { @@ -1066,7 +1066,7 @@ public void MissingFileSpecification(string arg0) /// The 'PathTooLong' diagnostic. /// /// -/// Path too long: {arg0}. +/// Fatal: Path too long: {arg0}. /// public void PathTooLong(string arg0) { @@ -1078,7 +1078,7 @@ public void PathTooLong(string arg0) /// The 'PathNotFound' diagnostic. /// /// -/// Path not found: {arg0}. +/// Fatal: Path not found: {arg0}. /// public void PathNotFound(string arg0) { @@ -1090,7 +1090,7 @@ public void PathNotFound(string arg0) /// The 'InvalidPath' diagnostic. /// /// -/// Invalid path: {arg0}. +/// Fatal: Invalid path: {arg0}. /// public void InvalidPath(string arg0) { @@ -1102,7 +1102,7 @@ public void InvalidPath(string arg0) /// The 'InvalidOptionSyntax' diagnostic. /// /// -/// Invalid option: {arg0}. +/// Fatal: Invalid option: {arg0}. /// public void InvalidOptionSyntax(string arg0) { @@ -1114,7 +1114,7 @@ public void InvalidOptionSyntax(string arg0) /// The 'ExternalResourceNotFound' diagnostic. /// /// -/// External resource file does not exist: {arg0}. +/// Fatal: External resource file does not exist: {arg0}. /// public void ExternalResourceNotFound(string arg0) { @@ -1126,7 +1126,7 @@ public void ExternalResourceNotFound(string arg0) /// The 'ExternalResourceNameInvalid' diagnostic. /// /// -/// External resource file may not include path specification: {arg0}. +/// Fatal: External resource file may not include path specification: {arg0}. /// public void ExternalResourceNameInvalid(string arg0) { @@ -1138,7 +1138,7 @@ public void ExternalResourceNameInvalid(string arg0) /// The 'InvalidVersionFormat' diagnostic. /// /// -/// Invalid version specified: {arg0}. +/// Fatal: Invalid version specified: {arg0}. /// public void InvalidVersionFormat(string arg0) { @@ -1150,7 +1150,7 @@ public void InvalidVersionFormat(string arg0) /// The 'InvalidFileAlignment' diagnostic. /// /// -/// Invalid value '{arg0}' for -filealign option. +/// Fatal: Invalid value '{arg0}' for -filealign option. /// public void InvalidFileAlignment(string arg0) { @@ -1162,7 +1162,7 @@ public void InvalidFileAlignment(string arg0) /// The 'ErrorWritingFile' diagnostic. /// /// -/// Unable to write file: {arg0}. ({arg1}) +/// Fatal: Unable to write file: {arg0}. ({arg1}) /// public void ErrorWritingFile(string arg0, string arg1) { @@ -1174,7 +1174,7 @@ public void ErrorWritingFile(string arg0, string arg1) /// The 'UnrecognizedOption' diagnostic. /// /// -/// Unrecognized option: {arg0}. +/// Fatal: Unrecognized option: {arg0}. /// public void UnrecognizedOption(string arg0) { @@ -1186,7 +1186,7 @@ public void UnrecognizedOption(string arg0) /// The 'NoOutputFileSpecified' diagnostic. /// /// -/// No output file specified. +/// Fatal: No output file specified. /// public void NoOutputFileSpecified() { @@ -1198,7 +1198,7 @@ public void NoOutputFileSpecified() /// The 'SharedClassLoaderCannotBeUsedOnModuleTarget' diagnostic. /// /// -/// Incompatible options: -target:module and -sharedclassloader cannot be combined. +/// Fatal: Incompatible options: -target:module and -sharedclassloader cannot be combined. /// public void SharedClassLoaderCannotBeUsedOnModuleTarget() { @@ -1210,7 +1210,7 @@ public void SharedClassLoaderCannotBeUsedOnModuleTarget() /// The 'RuntimeNotFound' diagnostic. /// /// -/// Unable to load runtime assembly. +/// Fatal: Unable to load runtime assembly. /// public void RuntimeNotFound() { @@ -1222,7 +1222,7 @@ public void RuntimeNotFound() /// The 'MainClassRequiresExe' diagnostic. /// /// -/// Main class cannot be specified for library or module. +/// Fatal: Main class cannot be specified for library or module. /// public void MainClassRequiresExe() { @@ -1234,7 +1234,7 @@ public void MainClassRequiresExe() /// The 'ExeRequiresMainClass' diagnostic. /// /// -/// No main method found. +/// Fatal: No main method found. /// public void ExeRequiresMainClass() { @@ -1246,7 +1246,7 @@ public void ExeRequiresMainClass() /// The 'PropertiesRequireExe' diagnostic. /// /// -/// Properties cannot be specified for library or module. +/// Fatal: Properties cannot be specified for library or module. /// public void PropertiesRequireExe() { @@ -1258,7 +1258,7 @@ public void PropertiesRequireExe() /// The 'ModuleCannotHaveClassLoader' diagnostic. /// /// -/// Cannot specify assembly class loader for modules. +/// Fatal: Cannot specify assembly class loader for modules. /// public void ModuleCannotHaveClassLoader() { @@ -1270,7 +1270,7 @@ public void ModuleCannotHaveClassLoader() /// The 'ErrorParsingMapFile' diagnostic. /// /// -/// Unable to parse remap file: {arg0}. ({arg1}) +/// Fatal: Unable to parse remap file: {arg0}. ({arg1}) /// public void ErrorParsingMapFile(string arg0, string arg1) { @@ -1282,7 +1282,7 @@ public void ErrorParsingMapFile(string arg0, string arg1) /// The 'BootstrapClassesMissing' diagnostic. /// /// -/// Bootstrap classes missing and core assembly not found. +/// Fatal: Bootstrap classes missing and core assembly not found. /// public void BootstrapClassesMissing() { @@ -1294,7 +1294,7 @@ public void BootstrapClassesMissing() /// The 'StrongNameRequiresStrongNamedRefs' diagnostic. /// /// -/// All referenced assemblies must be strong named, to be able to sign the output assembly. +/// Fatal: All referenced assemblies must be strong named, to be able to sign the output assembly. /// public void StrongNameRequiresStrongNamedRefs() { @@ -1306,7 +1306,7 @@ public void StrongNameRequiresStrongNamedRefs() /// The 'MainClassNotFound' diagnostic. /// /// -/// Main class not found. +/// Fatal: Main class not found. /// public void MainClassNotFound() { @@ -1318,7 +1318,7 @@ public void MainClassNotFound() /// The 'MainMethodNotFound' diagnostic. /// /// -/// Main method not found. +/// Fatal: Main method not found. /// public void MainMethodNotFound() { @@ -1330,7 +1330,7 @@ public void MainMethodNotFound() /// The 'UnsupportedMainMethod' diagnostic. /// /// -/// Redirected main method not supported. +/// Fatal: Redirected main method not supported. /// public void UnsupportedMainMethod() { @@ -1342,7 +1342,7 @@ public void UnsupportedMainMethod() /// The 'ExternalMainNotAccessible' diagnostic. /// /// -/// External main method must be public and in a public class. +/// Fatal: External main method must be public and in a public class. /// public void ExternalMainNotAccessible() { @@ -1354,7 +1354,7 @@ public void ExternalMainNotAccessible() /// The 'ClassLoaderNotFound' diagnostic. /// /// -/// Custom assembly class loader class not found. +/// Fatal: Custom assembly class loader class not found. /// public void ClassLoaderNotFound() { @@ -1366,7 +1366,7 @@ public void ClassLoaderNotFound() /// The 'ClassLoaderNotAccessible' diagnostic. /// /// -/// Custom assembly class loader class is not accessible. +/// Fatal: Custom assembly class loader class is not accessible. /// public void ClassLoaderNotAccessible() { @@ -1378,7 +1378,7 @@ public void ClassLoaderNotAccessible() /// The 'ClassLoaderIsAbstract' diagnostic. /// /// -/// Custom assembly class loader class is abstract. +/// Fatal: Custom assembly class loader class is abstract. /// public void ClassLoaderIsAbstract() { @@ -1390,7 +1390,7 @@ public void ClassLoaderIsAbstract() /// The 'ClassLoaderNotClassLoader' diagnostic. /// /// -/// Custom assembly class loader class does not extend java.lang.ClassLoader. +/// Fatal: Custom assembly class loader class does not extend java.lang.ClassLoader. /// public void ClassLoaderNotClassLoader() { @@ -1402,7 +1402,7 @@ public void ClassLoaderNotClassLoader() /// The 'ClassLoaderConstructorMissing' diagnostic. /// /// -/// Custom assembly class loader constructor is missing. +/// Fatal: Custom assembly class loader constructor is missing. /// public void ClassLoaderConstructorMissing() { @@ -1414,7 +1414,7 @@ public void ClassLoaderConstructorMissing() /// The 'MapFileTypeNotFound' diagnostic. /// /// -/// Type '{arg0}' referenced in remap file was not found. +/// Fatal: Type '{arg0}' referenced in remap file was not found. /// public void MapFileTypeNotFound(string arg0) { @@ -1426,7 +1426,7 @@ public void MapFileTypeNotFound(string arg0) /// The 'MapFileClassNotFound' diagnostic. /// /// -/// Class '{arg0}' referenced in remap file was not found. +/// Fatal: Class '{arg0}' referenced in remap file was not found. /// public void MapFileClassNotFound(string arg0) { @@ -1438,7 +1438,7 @@ public void MapFileClassNotFound(string arg0) /// The 'MaximumErrorCountReached' diagnostic. /// /// -/// Maximum error count reached. +/// Fatal: Maximum error count reached. /// public void MaximumErrorCountReached() { @@ -1450,7 +1450,7 @@ public void MaximumErrorCountReached() /// The 'LinkageError' diagnostic. /// /// -/// Link error: {arg0} +/// Fatal: Link error: {arg0} /// public void LinkageError(string arg0) { @@ -1462,7 +1462,7 @@ public void LinkageError(string arg0) /// The 'RuntimeMismatch' diagnostic. /// /// -/// Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} +/// Fatal: Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} /// public void RuntimeMismatch(string referencedAssemblyPath, string runtimeAssemblyName, string referencedAssemblyName) { @@ -1474,7 +1474,7 @@ public void RuntimeMismatch(string referencedAssemblyPath, string runtimeAssembl /// The 'RuntimeMismatchStrongName' diagnostic. /// /// -/// +/// Fatal: /// public void RuntimeMismatchStrongName() { @@ -1486,7 +1486,7 @@ public void RuntimeMismatchStrongName() /// The 'CoreClassesMissing' diagnostic. /// /// -/// Failed to find core classes in core library. +/// Fatal: Failed to find core classes in core library. /// public void CoreClassesMissing() { @@ -1498,7 +1498,7 @@ public void CoreClassesMissing() /// The 'CriticalClassNotFound' diagnostic. /// /// -/// Unable to load critical class '{arg0}'. +/// Fatal: Unable to load critical class '{arg0}'. /// public void CriticalClassNotFound(string arg0) { @@ -1510,7 +1510,7 @@ public void CriticalClassNotFound(string arg0) /// The 'AssemblyContainsDuplicateClassNames' diagnostic. /// /// -/// Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) +/// Fatal: Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) /// public void AssemblyContainsDuplicateClassNames(string arg0, string arg1, string arg2, string arg3) { @@ -1522,7 +1522,7 @@ public void AssemblyContainsDuplicateClassNames(string arg0, string arg1, string /// The 'CallerIDRequiresHasCallerIDAnnotation' diagnostic. /// /// -/// CallerID.getCallerID() requires a HasCallerID annotation. +/// Fatal: CallerID.getCallerID() requires a HasCallerID annotation. /// public void CallerIDRequiresHasCallerIDAnnotation() { @@ -1534,7 +1534,7 @@ public void CallerIDRequiresHasCallerIDAnnotation() /// The 'UnableToResolveInterface' diagnostic. /// /// -/// Unable to resolve interface '{arg0}' on type '{arg1}'. +/// Fatal: Unable to resolve interface '{arg0}' on type '{arg1}'. /// public void UnableToResolveInterface(string arg0, string arg1) { @@ -1546,7 +1546,7 @@ public void UnableToResolveInterface(string arg0, string arg1) /// The 'MissingBaseType' diagnostic. /// /// -/// The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. +/// Fatal: The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. /// public void MissingBaseType(string arg0, string arg1, string arg2, string arg3) { @@ -1558,7 +1558,7 @@ public void MissingBaseType(string arg0, string arg1, string arg2, string arg3) /// The 'MissingBaseTypeReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. +/// Fatal: The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. /// public void MissingBaseTypeReference(string arg0, string arg1) { @@ -1570,7 +1570,7 @@ public void MissingBaseTypeReference(string arg0, string arg1) /// The 'FileNotFound' diagnostic. /// /// -/// File not found: {arg0}. +/// Fatal: File not found: {arg0}. /// public void FileNotFound(string arg0) { @@ -1582,7 +1582,7 @@ public void FileNotFound(string arg0) /// The 'RuntimeMethodMissing' diagnostic. /// /// -/// Runtime method '{arg0}' not found. +/// Fatal: Runtime method '{arg0}' not found. /// public void RuntimeMethodMissing(string arg0) { @@ -1594,7 +1594,7 @@ public void RuntimeMethodMissing(string arg0) /// The 'MapFileFieldNotFound' diagnostic. /// /// -/// Field '{arg0}' referenced in remap file was not found in class '{arg1}'. +/// Fatal: Field '{arg0}' referenced in remap file was not found in class '{arg1}'. /// public void MapFileFieldNotFound(string arg0, string arg1) { @@ -1606,7 +1606,7 @@ public void MapFileFieldNotFound(string arg0, string arg1) /// The 'GhostInterfaceMethodMissing' diagnostic. /// /// -/// Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) +/// Fatal: Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) /// public void GhostInterfaceMethodMissing(string arg0, string arg1, string arg2, string arg3) { @@ -1618,7 +1618,7 @@ public void GhostInterfaceMethodMissing(string arg0, string arg1, string arg2, s /// The 'ModuleInitializerMethodRequirements' diagnostic. /// /// -/// Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. +/// Fatal: Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. /// public void ModuleInitializerMethodRequirements(string arg1, string arg2, string arg3) { @@ -1630,7 +1630,7 @@ public void ModuleInitializerMethodRequirements(string arg1, string arg2, string /// The 'InvalidZip' diagnostic. /// /// -/// Invalid zip: {name}. +/// Fatal: Invalid zip: {name}. /// public void InvalidZip(string name) { @@ -1642,7 +1642,7 @@ public void InvalidZip(string name) /// The 'CoreAssemblyVersionMismatch' diagnostic. /// /// -/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. +/// Fatal: Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. /// public void CoreAssemblyVersionMismatch(string arg0, string arg1) { @@ -1654,7 +1654,7 @@ public void CoreAssemblyVersionMismatch(string arg0, string arg1) /// The 'GenericRuntimeTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public void GenericRuntimeTrace(string arg0) { @@ -1666,7 +1666,7 @@ public void GenericRuntimeTrace(string arg0) /// The 'GenericJniTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public void GenericJniTrace(string arg0) { @@ -1678,7 +1678,7 @@ public void GenericJniTrace(string arg0) /// The 'GenericCompilerTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public void GenericCompilerTrace(string arg0) { diff --git a/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.tt b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.tt index 415e1deedb..328b47bcc8 100644 --- a/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.tt +++ b/src/IKVM.CoreLib/Diagnostics/DiagnosticEventHandler.g.tt @@ -45,7 +45,7 @@ foreach (var kvp in DiagnosticFile.Read(Host.ResolvePath(Path.Combine("Diagnosti /// <#= desc #> /// /// -<#= Util.ToCommentString(kvp.Value.Message ?? "") #> +<#= Util.ToCommentString(kvp.Value) #> /// public void <#= kvp.Key #>(<#= string.Join(", ", argDecl) #>) { diff --git a/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs b/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs index 1bac0acbc8..cbd53a7275 100644 --- a/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.cs @@ -10,7 +10,7 @@ partial interface IDiagnosticHandler /// The 'MainMethodFound' diagnostic. /// /// -/// Found main method in class "{arg0}". +/// Info: Found main method in class "{arg0}". /// void MainMethodFound(string arg0); @@ -18,7 +18,7 @@ partial interface IDiagnosticHandler /// The 'OutputFileIs' diagnostic. /// /// -/// Output file is "{arg0}". +/// Info: Output file is "{arg0}". /// void OutputFileIs(string arg0); @@ -26,7 +26,7 @@ partial interface IDiagnosticHandler /// The 'AutoAddRef' diagnostic. /// /// -/// Automatically adding reference to "{arg0}". +/// Info: Automatically adding reference to "{arg0}". /// void AutoAddRef(string arg0); @@ -34,7 +34,7 @@ partial interface IDiagnosticHandler /// The 'MainMethodFromManifest' diagnostic. /// /// -/// Using main class "{arg0}" based on jar manifest. +/// Info: Using main class "{arg0}" based on jar manifest. /// void MainMethodFromManifest(string arg0); @@ -42,7 +42,7 @@ partial interface IDiagnosticHandler /// The 'GenericCompilerInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// void GenericCompilerInfo(string arg0); @@ -50,7 +50,7 @@ partial interface IDiagnosticHandler /// The 'GenericClassLoadingInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// void GenericClassLoadingInfo(string arg0); @@ -58,7 +58,7 @@ partial interface IDiagnosticHandler /// The 'GenericVerifierInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// void GenericVerifierInfo(string arg0); @@ -66,7 +66,7 @@ partial interface IDiagnosticHandler /// The 'GenericRuntimeInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// void GenericRuntimeInfo(string arg0); @@ -74,7 +74,7 @@ partial interface IDiagnosticHandler /// The 'GenericJniInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// void GenericJniInfo(string arg0); @@ -82,7 +82,7 @@ partial interface IDiagnosticHandler /// The 'ClassNotFound' diagnostic. /// /// -/// Class "{arg0}" not found. +/// Warning: Class "{arg0}" not found. /// void ClassNotFound(string arg0); @@ -90,7 +90,7 @@ partial interface IDiagnosticHandler /// The 'ClassFormatError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (class format error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (class format error "{arg1}") /// void ClassFormatError(string arg0, string arg1); @@ -98,7 +98,7 @@ partial interface IDiagnosticHandler /// The 'DuplicateClassName' diagnostic. /// /// -/// Duplicate class name: "{arg0}". +/// Warning: Duplicate class name: "{arg0}". /// void DuplicateClassName(string arg0); @@ -106,7 +106,7 @@ partial interface IDiagnosticHandler /// The 'IllegalAccessError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (illegal access error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (illegal access error "{arg1}") /// void IllegalAccessError(string arg0, string arg1); @@ -114,7 +114,7 @@ partial interface IDiagnosticHandler /// The 'VerificationError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (verification error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (verification error "{arg1}") /// void VerificationError(string arg0, string arg1); @@ -122,7 +122,7 @@ partial interface IDiagnosticHandler /// The 'NoClassDefFoundError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (missing class "{arg1}") +/// Warning: Unable to compile class "{arg0}". (missing class "{arg1}") /// void NoClassDefFoundError(string arg0, string arg1); @@ -130,7 +130,7 @@ partial interface IDiagnosticHandler /// The 'GenericUnableToCompileError' diagnostic. /// /// -/// Unable to compile class "{arg0}". ("{arg1}": "{arg2}") +/// Warning: Unable to compile class "{arg0}". ("{arg1}": "{arg2}") /// void GenericUnableToCompileError(string arg0, string arg1, string arg2); @@ -138,7 +138,7 @@ partial interface IDiagnosticHandler /// The 'DuplicateResourceName' diagnostic. /// /// -/// Skipping resource (name clash): "{arg0}" +/// Warning: Skipping resource (name clash): "{arg0}" /// void DuplicateResourceName(string arg0); @@ -146,7 +146,7 @@ partial interface IDiagnosticHandler /// The 'SkippingReferencedClass' diagnostic. /// /// -/// Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") +/// Warning: Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") /// void SkippingReferencedClass(string arg0, string arg1); @@ -154,7 +154,7 @@ partial interface IDiagnosticHandler /// The 'NoJniRuntime' diagnostic. /// /// -/// Unable to load runtime JNI assembly. +/// Warning: Unable to load runtime JNI assembly. /// void NoJniRuntime(); @@ -162,7 +162,7 @@ partial interface IDiagnosticHandler /// The 'EmittedNoClassDefFoundError' diagnostic. /// /// -/// Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). +/// Warning: Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). /// void EmittedNoClassDefFoundError(string arg0, string arg1); @@ -170,7 +170,7 @@ partial interface IDiagnosticHandler /// The 'EmittedIllegalAccessError' diagnostic. /// /// -/// Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") /// void EmittedIllegalAccessError(string arg0, string arg1); @@ -178,7 +178,7 @@ partial interface IDiagnosticHandler /// The 'EmittedInstantiationError' diagnostic. /// /// -/// Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") /// void EmittedInstantiationError(string arg0, string arg1); @@ -186,7 +186,7 @@ partial interface IDiagnosticHandler /// The 'EmittedIncompatibleClassChangeError' diagnostic. /// /// -/// Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") /// void EmittedIncompatibleClassChangeError(string arg0, string arg1); @@ -194,7 +194,7 @@ partial interface IDiagnosticHandler /// The 'EmittedNoSuchFieldError' diagnostic. /// /// -/// Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") /// void EmittedNoSuchFieldError(string arg0, string arg1); @@ -202,7 +202,7 @@ partial interface IDiagnosticHandler /// The 'EmittedAbstractMethodError' diagnostic. /// /// -/// Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") /// void EmittedAbstractMethodError(string arg0, string arg1); @@ -210,7 +210,7 @@ partial interface IDiagnosticHandler /// The 'EmittedNoSuchMethodError' diagnostic. /// /// -/// Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") /// void EmittedNoSuchMethodError(string arg0, string arg1); @@ -218,7 +218,7 @@ partial interface IDiagnosticHandler /// The 'EmittedLinkageError' diagnostic. /// /// -/// Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") /// void EmittedLinkageError(string arg0, string arg1); @@ -226,7 +226,7 @@ partial interface IDiagnosticHandler /// The 'EmittedVerificationError' diagnostic. /// /// -/// Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") /// void EmittedVerificationError(string arg0, string arg1); @@ -234,7 +234,7 @@ partial interface IDiagnosticHandler /// The 'EmittedClassFormatError' diagnostic. /// /// -/// Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") /// void EmittedClassFormatError(string arg0, string arg1); @@ -242,7 +242,7 @@ partial interface IDiagnosticHandler /// The 'InvalidCustomAttribute' diagnostic. /// /// -/// Error emitting "{arg0}" custom attribute. ("{arg1}") +/// Warning: Error emitting "{arg0}" custom attribute. ("{arg1}") /// void InvalidCustomAttribute(string arg0, string arg1); @@ -250,7 +250,7 @@ partial interface IDiagnosticHandler /// The 'IgnoredCustomAttribute' diagnostic. /// /// -/// Custom attribute "{arg0}" was ignored. ("{arg1}") +/// Warning: Custom attribute "{arg0}" was ignored. ("{arg1}") /// void IgnoredCustomAttribute(string arg0, string arg1); @@ -258,7 +258,7 @@ partial interface IDiagnosticHandler /// The 'AssumeAssemblyVersionMatch' diagnostic. /// /// -/// Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy +/// Warning: Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy /// void AssumeAssemblyVersionMatch(string arg0, string arg1); @@ -266,7 +266,7 @@ partial interface IDiagnosticHandler /// The 'InvalidDirectoryInLibOptionPath' diagnostic. /// /// -/// Directory "{arg0}" specified in -lib option is not valid. +/// Warning: Directory "{arg0}" specified in -lib option is not valid. /// void InvalidDirectoryInLibOptionPath(string arg0); @@ -274,7 +274,7 @@ partial interface IDiagnosticHandler /// The 'InvalidDirectoryInLibEnvironmentPath' diagnostic. /// /// -/// Directory "{arg0}" specified in LIB environment is not valid. +/// Warning: Directory "{arg0}" specified in LIB environment is not valid. /// void InvalidDirectoryInLibEnvironmentPath(string arg0); @@ -282,7 +282,7 @@ partial interface IDiagnosticHandler /// The 'LegacySearchRule' diagnostic. /// /// -/// Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. +/// Warning: Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. /// void LegacySearchRule(string arg0); @@ -290,7 +290,7 @@ partial interface IDiagnosticHandler /// The 'AssemblyLocationIgnored' diagnostic. /// /// -/// Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". +/// Warning: Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". /// void AssemblyLocationIgnored(string arg0, string arg1, string arg2); @@ -298,7 +298,7 @@ partial interface IDiagnosticHandler /// The 'InterfaceMethodCantBeInternal' diagnostic. /// /// -/// Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") +/// Warning: Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") /// void InterfaceMethodCantBeInternal(string arg0, string arg1, string arg2); @@ -306,7 +306,7 @@ partial interface IDiagnosticHandler /// The 'DuplicateAssemblyReference' diagnostic. /// /// -/// Duplicate assembly reference "{arg0}" +/// Warning: Duplicate assembly reference "{arg0}" /// void DuplicateAssemblyReference(string arg0); @@ -314,7 +314,7 @@ partial interface IDiagnosticHandler /// The 'UnableToResolveType' diagnostic. /// /// -/// Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. +/// Warning: Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. /// void UnableToResolveType(string arg0, string arg1, string arg2); @@ -322,7 +322,7 @@ partial interface IDiagnosticHandler /// The 'StubsAreDeprecated' diagnostic. /// /// -/// Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. +/// Warning: Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. /// void StubsAreDeprecated(string arg0); @@ -330,7 +330,7 @@ partial interface IDiagnosticHandler /// The 'WrongClassName' diagnostic. /// /// -/// Unable to compile "{arg0}" (wrong name: "{arg1}") +/// Warning: Unable to compile "{arg0}" (wrong name: "{arg1}") /// void WrongClassName(string arg0, string arg1); @@ -338,7 +338,7 @@ partial interface IDiagnosticHandler /// The 'ReflectionCallerClassRequiresCallerID' diagnostic. /// /// -/// Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") +/// Warning: Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") /// void ReflectionCallerClassRequiresCallerID(string arg0, string arg1, string arg2); @@ -346,7 +346,7 @@ partial interface IDiagnosticHandler /// The 'LegacyAssemblyAttributesFound' diagnostic. /// /// -/// Legacy assembly attributes container found. Please use the -assemblyattributes: option. +/// Warning: Legacy assembly attributes container found. Please use the -assemblyattributes: option. /// void LegacyAssemblyAttributesFound(); @@ -354,7 +354,7 @@ partial interface IDiagnosticHandler /// The 'UnableToCreateLambdaFactory' diagnostic. /// /// -/// Unable to create static lambda factory. +/// Warning: Unable to create static lambda factory. /// void UnableToCreateLambdaFactory(); @@ -362,7 +362,7 @@ partial interface IDiagnosticHandler /// The 'UnknownWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// void UnknownWarning(string arg0); @@ -370,7 +370,7 @@ partial interface IDiagnosticHandler /// The 'DuplicateIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// void DuplicateIkvmLangProperty(string arg0, string arg1); @@ -378,7 +378,7 @@ partial interface IDiagnosticHandler /// The 'MalformedIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// void MalformedIkvmLangProperty(string arg0, string arg1); @@ -386,7 +386,7 @@ partial interface IDiagnosticHandler /// The 'GenericCompilerWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// void GenericCompilerWarning(string arg0); @@ -394,7 +394,7 @@ partial interface IDiagnosticHandler /// The 'GenericClassLoadingWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// void GenericClassLoadingWarning(string arg0); @@ -402,7 +402,7 @@ partial interface IDiagnosticHandler /// The 'GenericVerifierWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// void GenericVerifierWarning(string arg0); @@ -410,7 +410,7 @@ partial interface IDiagnosticHandler /// The 'GenericRuntimeWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// void GenericRuntimeWarning(string arg0); @@ -418,7 +418,7 @@ partial interface IDiagnosticHandler /// The 'GenericJniWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// void GenericJniWarning(string arg0); @@ -426,7 +426,7 @@ partial interface IDiagnosticHandler /// The 'UnableToCreateProxy' diagnostic. /// /// -/// Unable to create proxy "{arg0}". ("{arg1}") +/// Error: Unable to create proxy "{arg0}". ("{arg1}") /// void UnableToCreateProxy(string arg0, string arg1); @@ -434,7 +434,7 @@ partial interface IDiagnosticHandler /// The 'DuplicateProxy' diagnostic. /// /// -/// Duplicate proxy "{arg0}". +/// Error: Duplicate proxy "{arg0}". /// void DuplicateProxy(string arg0); @@ -442,7 +442,7 @@ partial interface IDiagnosticHandler /// The 'MapXmlUnableToResolveOpCode' diagnostic. /// /// -/// Unable to resolve opcode in remap file: {arg0}. +/// Error: Unable to resolve opcode in remap file: {arg0}. /// void MapXmlUnableToResolveOpCode(string arg0); @@ -450,7 +450,7 @@ partial interface IDiagnosticHandler /// The 'MapXmlError' diagnostic. /// /// -/// Error in remap file: {arg0}. +/// Error: Error in remap file: {arg0}. /// void MapXmlError(string arg0); @@ -458,7 +458,7 @@ partial interface IDiagnosticHandler /// The 'InputFileNotFound' diagnostic. /// /// -/// Source file '{arg0}' not found. +/// Error: Source file '{arg0}' not found. /// void InputFileNotFound(string arg0); @@ -466,7 +466,7 @@ partial interface IDiagnosticHandler /// The 'UnknownFileType' diagnostic. /// /// -/// Unknown file type: {arg0}. +/// Error: Unknown file type: {arg0}. /// void UnknownFileType(string arg0); @@ -474,7 +474,7 @@ partial interface IDiagnosticHandler /// The 'UnknownElementInMapFile' diagnostic. /// /// -/// Unknown element {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown element {arg0} in remap file, line {arg1}, column {arg2}. /// void UnknownElementInMapFile(string arg0, string arg1, string arg2); @@ -482,7 +482,7 @@ partial interface IDiagnosticHandler /// The 'UnknownAttributeInMapFile' diagnostic. /// /// -/// Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. /// void UnknownAttributeInMapFile(string arg0, string arg1, string arg2); @@ -490,7 +490,7 @@ partial interface IDiagnosticHandler /// The 'InvalidMemberNameInMapFile' diagnostic. /// /// -/// Invalid {arg0} name '{arg1}' in remap file in class {arg2}. +/// Error: Invalid {arg0} name '{arg1}' in remap file in class {arg2}. /// void InvalidMemberNameInMapFile(string arg0, string arg1, string arg2); @@ -498,7 +498,7 @@ partial interface IDiagnosticHandler /// The 'InvalidMemberSignatureInMapFile' diagnostic. /// /// -/// Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. +/// Error: Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. /// void InvalidMemberSignatureInMapFile(string arg0, string arg1, string arg2, string arg3); @@ -506,7 +506,7 @@ partial interface IDiagnosticHandler /// The 'InvalidPropertyNameInMapFile' diagnostic. /// /// -/// Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. /// void InvalidPropertyNameInMapFile(string arg0, string arg1, string arg2, string arg3); @@ -514,7 +514,7 @@ partial interface IDiagnosticHandler /// The 'InvalidPropertySignatureInMapFile' diagnostic. /// /// -/// Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. /// void InvalidPropertySignatureInMapFile(string arg0, string arg1, string arg2, string arg3); @@ -522,7 +522,7 @@ partial interface IDiagnosticHandler /// The 'NonPrimaryAssemblyReference' diagnostic. /// /// -/// Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. +/// Error: Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. /// void NonPrimaryAssemblyReference(string arg0, string arg1); @@ -530,7 +530,7 @@ partial interface IDiagnosticHandler /// The 'MissingType' diagnostic. /// /// -/// Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. +/// Error: Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. /// void MissingType(string arg0, string arg1); @@ -538,7 +538,7 @@ partial interface IDiagnosticHandler /// The 'MissingReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. +/// Error: The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. /// void MissingReference(string arg0, string arg1); @@ -546,7 +546,7 @@ partial interface IDiagnosticHandler /// The 'CallerSensitiveOnUnsupportedMethod' diagnostic. /// /// -/// CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") +/// Error: CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") /// void CallerSensitiveOnUnsupportedMethod(string arg0, string arg1, string arg2); @@ -554,7 +554,7 @@ partial interface IDiagnosticHandler /// The 'RemappedTypeMissingDefaultInterfaceMethod' diagnostic. /// /// -/// {arg0} does not implement default interface method {arg1}. +/// Error: {arg0} does not implement default interface method {arg1}. /// void RemappedTypeMissingDefaultInterfaceMethod(string arg0, string arg1); @@ -562,7 +562,7 @@ partial interface IDiagnosticHandler /// The 'GenericCompilerError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// void GenericCompilerError(string arg0); @@ -570,7 +570,7 @@ partial interface IDiagnosticHandler /// The 'GenericClassLoadingError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// void GenericClassLoadingError(string arg0); @@ -578,7 +578,7 @@ partial interface IDiagnosticHandler /// The 'GenericVerifierError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// void GenericVerifierError(string arg0); @@ -586,7 +586,7 @@ partial interface IDiagnosticHandler /// The 'GenericRuntimeError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// void GenericRuntimeError(string arg0); @@ -594,7 +594,7 @@ partial interface IDiagnosticHandler /// The 'GenericJniError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// void GenericJniError(string arg0); @@ -602,7 +602,7 @@ partial interface IDiagnosticHandler /// The 'ExportingImportsNotSupported' diagnostic. /// /// -/// Exporting previously imported assemblies is not supported. +/// Error: Exporting previously imported assemblies is not supported. /// void ExportingImportsNotSupported(); @@ -610,7 +610,7 @@ partial interface IDiagnosticHandler /// The 'ResponseFileDepthExceeded' diagnostic. /// /// -/// Response file nesting depth exceeded. +/// Fatal: Response file nesting depth exceeded. /// void ResponseFileDepthExceeded(); @@ -618,7 +618,7 @@ partial interface IDiagnosticHandler /// The 'ErrorReadingFile' diagnostic. /// /// -/// Unable to read file: {arg0}. ({arg1}) +/// Fatal: Unable to read file: {arg0}. ({arg1}) /// void ErrorReadingFile(string arg0, string arg1); @@ -626,7 +626,7 @@ partial interface IDiagnosticHandler /// The 'NoTargetsFound' diagnostic. /// /// -/// No targets found +/// Fatal: No targets found /// void NoTargetsFound(); @@ -634,7 +634,7 @@ partial interface IDiagnosticHandler /// The 'FileFormatLimitationExceeded' diagnostic. /// /// -/// File format limitation exceeded: {arg0}. +/// Fatal: File format limitation exceeded: {arg0}. /// void FileFormatLimitationExceeded(string arg0); @@ -642,7 +642,7 @@ partial interface IDiagnosticHandler /// The 'CannotSpecifyBothKeyFileAndContainer' diagnostic. /// /// -/// You cannot specify both a key file and container. +/// Fatal: You cannot specify both a key file and container. /// void CannotSpecifyBothKeyFileAndContainer(); @@ -650,7 +650,7 @@ partial interface IDiagnosticHandler /// The 'DelaySignRequiresKey' diagnostic. /// /// -/// You cannot delay sign without a key file or container. +/// Fatal: You cannot delay sign without a key file or container. /// void DelaySignRequiresKey(); @@ -658,7 +658,7 @@ partial interface IDiagnosticHandler /// The 'InvalidStrongNameKeyPair' diagnostic. /// /// -/// Invalid key {arg0} specified. ("{arg1}") +/// Fatal: Invalid key {arg0} specified. ("{arg1}") /// void InvalidStrongNameKeyPair(string arg0, string arg1); @@ -666,7 +666,7 @@ partial interface IDiagnosticHandler /// The 'ReferenceNotFound' diagnostic. /// /// -/// Reference not found: {arg0} +/// Fatal: Reference not found: {arg0} /// void ReferenceNotFound(string arg0); @@ -674,7 +674,7 @@ partial interface IDiagnosticHandler /// The 'OptionsMustPreceedChildLevels' diagnostic. /// /// -/// You can only specify options before any child levels. +/// Fatal: You can only specify options before any child levels. /// void OptionsMustPreceedChildLevels(); @@ -682,7 +682,7 @@ partial interface IDiagnosticHandler /// The 'UnrecognizedTargetType' diagnostic. /// /// -/// Invalid value '{arg0}' for -target option. +/// Fatal: Invalid value '{arg0}' for -target option. /// void UnrecognizedTargetType(string arg0); @@ -690,7 +690,7 @@ partial interface IDiagnosticHandler /// The 'UnrecognizedPlatform' diagnostic. /// /// -/// Invalid value '{arg0}' for -platform option. +/// Fatal: Invalid value '{arg0}' for -platform option. /// void UnrecognizedPlatform(string arg0); @@ -698,7 +698,7 @@ partial interface IDiagnosticHandler /// The 'UnrecognizedApartment' diagnostic. /// /// -/// Invalid value '{arg0}' for -apartment option. +/// Fatal: Invalid value '{arg0}' for -apartment option. /// void UnrecognizedApartment(string arg0); @@ -706,7 +706,7 @@ partial interface IDiagnosticHandler /// The 'MissingFileSpecification' diagnostic. /// /// -/// Missing file specification for '{arg0}' option. +/// Fatal: Missing file specification for '{arg0}' option. /// void MissingFileSpecification(string arg0); @@ -714,7 +714,7 @@ partial interface IDiagnosticHandler /// The 'PathTooLong' diagnostic. /// /// -/// Path too long: {arg0}. +/// Fatal: Path too long: {arg0}. /// void PathTooLong(string arg0); @@ -722,7 +722,7 @@ partial interface IDiagnosticHandler /// The 'PathNotFound' diagnostic. /// /// -/// Path not found: {arg0}. +/// Fatal: Path not found: {arg0}. /// void PathNotFound(string arg0); @@ -730,7 +730,7 @@ partial interface IDiagnosticHandler /// The 'InvalidPath' diagnostic. /// /// -/// Invalid path: {arg0}. +/// Fatal: Invalid path: {arg0}. /// void InvalidPath(string arg0); @@ -738,7 +738,7 @@ partial interface IDiagnosticHandler /// The 'InvalidOptionSyntax' diagnostic. /// /// -/// Invalid option: {arg0}. +/// Fatal: Invalid option: {arg0}. /// void InvalidOptionSyntax(string arg0); @@ -746,7 +746,7 @@ partial interface IDiagnosticHandler /// The 'ExternalResourceNotFound' diagnostic. /// /// -/// External resource file does not exist: {arg0}. +/// Fatal: External resource file does not exist: {arg0}. /// void ExternalResourceNotFound(string arg0); @@ -754,7 +754,7 @@ partial interface IDiagnosticHandler /// The 'ExternalResourceNameInvalid' diagnostic. /// /// -/// External resource file may not include path specification: {arg0}. +/// Fatal: External resource file may not include path specification: {arg0}. /// void ExternalResourceNameInvalid(string arg0); @@ -762,7 +762,7 @@ partial interface IDiagnosticHandler /// The 'InvalidVersionFormat' diagnostic. /// /// -/// Invalid version specified: {arg0}. +/// Fatal: Invalid version specified: {arg0}. /// void InvalidVersionFormat(string arg0); @@ -770,7 +770,7 @@ partial interface IDiagnosticHandler /// The 'InvalidFileAlignment' diagnostic. /// /// -/// Invalid value '{arg0}' for -filealign option. +/// Fatal: Invalid value '{arg0}' for -filealign option. /// void InvalidFileAlignment(string arg0); @@ -778,7 +778,7 @@ partial interface IDiagnosticHandler /// The 'ErrorWritingFile' diagnostic. /// /// -/// Unable to write file: {arg0}. ({arg1}) +/// Fatal: Unable to write file: {arg0}. ({arg1}) /// void ErrorWritingFile(string arg0, string arg1); @@ -786,7 +786,7 @@ partial interface IDiagnosticHandler /// The 'UnrecognizedOption' diagnostic. /// /// -/// Unrecognized option: {arg0}. +/// Fatal: Unrecognized option: {arg0}. /// void UnrecognizedOption(string arg0); @@ -794,7 +794,7 @@ partial interface IDiagnosticHandler /// The 'NoOutputFileSpecified' diagnostic. /// /// -/// No output file specified. +/// Fatal: No output file specified. /// void NoOutputFileSpecified(); @@ -802,7 +802,7 @@ partial interface IDiagnosticHandler /// The 'SharedClassLoaderCannotBeUsedOnModuleTarget' diagnostic. /// /// -/// Incompatible options: -target:module and -sharedclassloader cannot be combined. +/// Fatal: Incompatible options: -target:module and -sharedclassloader cannot be combined. /// void SharedClassLoaderCannotBeUsedOnModuleTarget(); @@ -810,7 +810,7 @@ partial interface IDiagnosticHandler /// The 'RuntimeNotFound' diagnostic. /// /// -/// Unable to load runtime assembly. +/// Fatal: Unable to load runtime assembly. /// void RuntimeNotFound(); @@ -818,7 +818,7 @@ partial interface IDiagnosticHandler /// The 'MainClassRequiresExe' diagnostic. /// /// -/// Main class cannot be specified for library or module. +/// Fatal: Main class cannot be specified for library or module. /// void MainClassRequiresExe(); @@ -826,7 +826,7 @@ partial interface IDiagnosticHandler /// The 'ExeRequiresMainClass' diagnostic. /// /// -/// No main method found. +/// Fatal: No main method found. /// void ExeRequiresMainClass(); @@ -834,7 +834,7 @@ partial interface IDiagnosticHandler /// The 'PropertiesRequireExe' diagnostic. /// /// -/// Properties cannot be specified for library or module. +/// Fatal: Properties cannot be specified for library or module. /// void PropertiesRequireExe(); @@ -842,7 +842,7 @@ partial interface IDiagnosticHandler /// The 'ModuleCannotHaveClassLoader' diagnostic. /// /// -/// Cannot specify assembly class loader for modules. +/// Fatal: Cannot specify assembly class loader for modules. /// void ModuleCannotHaveClassLoader(); @@ -850,7 +850,7 @@ partial interface IDiagnosticHandler /// The 'ErrorParsingMapFile' diagnostic. /// /// -/// Unable to parse remap file: {arg0}. ({arg1}) +/// Fatal: Unable to parse remap file: {arg0}. ({arg1}) /// void ErrorParsingMapFile(string arg0, string arg1); @@ -858,7 +858,7 @@ partial interface IDiagnosticHandler /// The 'BootstrapClassesMissing' diagnostic. /// /// -/// Bootstrap classes missing and core assembly not found. +/// Fatal: Bootstrap classes missing and core assembly not found. /// void BootstrapClassesMissing(); @@ -866,7 +866,7 @@ partial interface IDiagnosticHandler /// The 'StrongNameRequiresStrongNamedRefs' diagnostic. /// /// -/// All referenced assemblies must be strong named, to be able to sign the output assembly. +/// Fatal: All referenced assemblies must be strong named, to be able to sign the output assembly. /// void StrongNameRequiresStrongNamedRefs(); @@ -874,7 +874,7 @@ partial interface IDiagnosticHandler /// The 'MainClassNotFound' diagnostic. /// /// -/// Main class not found. +/// Fatal: Main class not found. /// void MainClassNotFound(); @@ -882,7 +882,7 @@ partial interface IDiagnosticHandler /// The 'MainMethodNotFound' diagnostic. /// /// -/// Main method not found. +/// Fatal: Main method not found. /// void MainMethodNotFound(); @@ -890,7 +890,7 @@ partial interface IDiagnosticHandler /// The 'UnsupportedMainMethod' diagnostic. /// /// -/// Redirected main method not supported. +/// Fatal: Redirected main method not supported. /// void UnsupportedMainMethod(); @@ -898,7 +898,7 @@ partial interface IDiagnosticHandler /// The 'ExternalMainNotAccessible' diagnostic. /// /// -/// External main method must be public and in a public class. +/// Fatal: External main method must be public and in a public class. /// void ExternalMainNotAccessible(); @@ -906,7 +906,7 @@ partial interface IDiagnosticHandler /// The 'ClassLoaderNotFound' diagnostic. /// /// -/// Custom assembly class loader class not found. +/// Fatal: Custom assembly class loader class not found. /// void ClassLoaderNotFound(); @@ -914,7 +914,7 @@ partial interface IDiagnosticHandler /// The 'ClassLoaderNotAccessible' diagnostic. /// /// -/// Custom assembly class loader class is not accessible. +/// Fatal: Custom assembly class loader class is not accessible. /// void ClassLoaderNotAccessible(); @@ -922,7 +922,7 @@ partial interface IDiagnosticHandler /// The 'ClassLoaderIsAbstract' diagnostic. /// /// -/// Custom assembly class loader class is abstract. +/// Fatal: Custom assembly class loader class is abstract. /// void ClassLoaderIsAbstract(); @@ -930,7 +930,7 @@ partial interface IDiagnosticHandler /// The 'ClassLoaderNotClassLoader' diagnostic. /// /// -/// Custom assembly class loader class does not extend java.lang.ClassLoader. +/// Fatal: Custom assembly class loader class does not extend java.lang.ClassLoader. /// void ClassLoaderNotClassLoader(); @@ -938,7 +938,7 @@ partial interface IDiagnosticHandler /// The 'ClassLoaderConstructorMissing' diagnostic. /// /// -/// Custom assembly class loader constructor is missing. +/// Fatal: Custom assembly class loader constructor is missing. /// void ClassLoaderConstructorMissing(); @@ -946,7 +946,7 @@ partial interface IDiagnosticHandler /// The 'MapFileTypeNotFound' diagnostic. /// /// -/// Type '{arg0}' referenced in remap file was not found. +/// Fatal: Type '{arg0}' referenced in remap file was not found. /// void MapFileTypeNotFound(string arg0); @@ -954,7 +954,7 @@ partial interface IDiagnosticHandler /// The 'MapFileClassNotFound' diagnostic. /// /// -/// Class '{arg0}' referenced in remap file was not found. +/// Fatal: Class '{arg0}' referenced in remap file was not found. /// void MapFileClassNotFound(string arg0); @@ -962,7 +962,7 @@ partial interface IDiagnosticHandler /// The 'MaximumErrorCountReached' diagnostic. /// /// -/// Maximum error count reached. +/// Fatal: Maximum error count reached. /// void MaximumErrorCountReached(); @@ -970,7 +970,7 @@ partial interface IDiagnosticHandler /// The 'LinkageError' diagnostic. /// /// -/// Link error: {arg0} +/// Fatal: Link error: {arg0} /// void LinkageError(string arg0); @@ -978,7 +978,7 @@ partial interface IDiagnosticHandler /// The 'RuntimeMismatch' diagnostic. /// /// -/// Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} +/// Fatal: Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} /// void RuntimeMismatch(string referencedAssemblyPath, string runtimeAssemblyName, string referencedAssemblyName); @@ -986,7 +986,7 @@ partial interface IDiagnosticHandler /// The 'RuntimeMismatchStrongName' diagnostic. /// /// -/// +/// Fatal: /// void RuntimeMismatchStrongName(); @@ -994,7 +994,7 @@ partial interface IDiagnosticHandler /// The 'CoreClassesMissing' diagnostic. /// /// -/// Failed to find core classes in core library. +/// Fatal: Failed to find core classes in core library. /// void CoreClassesMissing(); @@ -1002,7 +1002,7 @@ partial interface IDiagnosticHandler /// The 'CriticalClassNotFound' diagnostic. /// /// -/// Unable to load critical class '{arg0}'. +/// Fatal: Unable to load critical class '{arg0}'. /// void CriticalClassNotFound(string arg0); @@ -1010,7 +1010,7 @@ partial interface IDiagnosticHandler /// The 'AssemblyContainsDuplicateClassNames' diagnostic. /// /// -/// Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) +/// Fatal: Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) /// void AssemblyContainsDuplicateClassNames(string arg0, string arg1, string arg2, string arg3); @@ -1018,7 +1018,7 @@ partial interface IDiagnosticHandler /// The 'CallerIDRequiresHasCallerIDAnnotation' diagnostic. /// /// -/// CallerID.getCallerID() requires a HasCallerID annotation. +/// Fatal: CallerID.getCallerID() requires a HasCallerID annotation. /// void CallerIDRequiresHasCallerIDAnnotation(); @@ -1026,7 +1026,7 @@ partial interface IDiagnosticHandler /// The 'UnableToResolveInterface' diagnostic. /// /// -/// Unable to resolve interface '{arg0}' on type '{arg1}'. +/// Fatal: Unable to resolve interface '{arg0}' on type '{arg1}'. /// void UnableToResolveInterface(string arg0, string arg1); @@ -1034,7 +1034,7 @@ partial interface IDiagnosticHandler /// The 'MissingBaseType' diagnostic. /// /// -/// The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. +/// Fatal: The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. /// void MissingBaseType(string arg0, string arg1, string arg2, string arg3); @@ -1042,7 +1042,7 @@ partial interface IDiagnosticHandler /// The 'MissingBaseTypeReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. +/// Fatal: The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. /// void MissingBaseTypeReference(string arg0, string arg1); @@ -1050,7 +1050,7 @@ partial interface IDiagnosticHandler /// The 'FileNotFound' diagnostic. /// /// -/// File not found: {arg0}. +/// Fatal: File not found: {arg0}. /// void FileNotFound(string arg0); @@ -1058,7 +1058,7 @@ partial interface IDiagnosticHandler /// The 'RuntimeMethodMissing' diagnostic. /// /// -/// Runtime method '{arg0}' not found. +/// Fatal: Runtime method '{arg0}' not found. /// void RuntimeMethodMissing(string arg0); @@ -1066,7 +1066,7 @@ partial interface IDiagnosticHandler /// The 'MapFileFieldNotFound' diagnostic. /// /// -/// Field '{arg0}' referenced in remap file was not found in class '{arg1}'. +/// Fatal: Field '{arg0}' referenced in remap file was not found in class '{arg1}'. /// void MapFileFieldNotFound(string arg0, string arg1); @@ -1074,7 +1074,7 @@ partial interface IDiagnosticHandler /// The 'GhostInterfaceMethodMissing' diagnostic. /// /// -/// Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) +/// Fatal: Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) /// void GhostInterfaceMethodMissing(string arg0, string arg1, string arg2, string arg3); @@ -1082,7 +1082,7 @@ partial interface IDiagnosticHandler /// The 'ModuleInitializerMethodRequirements' diagnostic. /// /// -/// Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. +/// Fatal: Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. /// void ModuleInitializerMethodRequirements(string arg1, string arg2, string arg3); @@ -1090,7 +1090,7 @@ partial interface IDiagnosticHandler /// The 'InvalidZip' diagnostic. /// /// -/// Invalid zip: {name}. +/// Fatal: Invalid zip: {name}. /// void InvalidZip(string name); @@ -1098,7 +1098,7 @@ partial interface IDiagnosticHandler /// The 'CoreAssemblyVersionMismatch' diagnostic. /// /// -/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. +/// Fatal: Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. /// void CoreAssemblyVersionMismatch(string arg0, string arg1); @@ -1106,7 +1106,7 @@ partial interface IDiagnosticHandler /// The 'GenericRuntimeTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// void GenericRuntimeTrace(string arg0); @@ -1114,7 +1114,7 @@ partial interface IDiagnosticHandler /// The 'GenericJniTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// void GenericJniTrace(string arg0); @@ -1122,7 +1122,7 @@ partial interface IDiagnosticHandler /// The 'GenericCompilerTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// void GenericCompilerTrace(string arg0); diff --git a/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.tt b/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.tt index 947391123f..4708f92331 100644 --- a/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.tt +++ b/src/IKVM.CoreLib/Diagnostics/IDiagnosticHandler.g.tt @@ -41,7 +41,7 @@ foreach (var kvp in DiagnosticFile.Read(Host.ResolvePath(Path.Combine("Diagnosti /// <#= desc #> /// /// -<#= Util.ToCommentString(kvp.Value.Message ?? "") #> +<#= Util.ToCommentString(kvp.Value) #> /// void <#= kvp.Key #>(<#= string.Join(", ", argList) #>); diff --git a/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs b/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs index 1283a95575..77f88e4dbf 100644 --- a/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.cs @@ -10,7 +10,7 @@ partial class NullDiagnosticHandler /// The 'MainMethodFound' diagnostic. /// /// -/// Found main method in class "{arg0}". +/// Info: Found main method in class "{arg0}". /// public void MainMethodFound(string arg0) { @@ -21,7 +21,7 @@ public void MainMethodFound(string arg0) /// The 'OutputFileIs' diagnostic. /// /// -/// Output file is "{arg0}". +/// Info: Output file is "{arg0}". /// public void OutputFileIs(string arg0) { @@ -32,7 +32,7 @@ public void OutputFileIs(string arg0) /// The 'AutoAddRef' diagnostic. /// /// -/// Automatically adding reference to "{arg0}". +/// Info: Automatically adding reference to "{arg0}". /// public void AutoAddRef(string arg0) { @@ -43,7 +43,7 @@ public void AutoAddRef(string arg0) /// The 'MainMethodFromManifest' diagnostic. /// /// -/// Using main class "{arg0}" based on jar manifest. +/// Info: Using main class "{arg0}" based on jar manifest. /// public void MainMethodFromManifest(string arg0) { @@ -54,7 +54,7 @@ public void MainMethodFromManifest(string arg0) /// The 'GenericCompilerInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericCompilerInfo(string arg0) { @@ -65,7 +65,7 @@ public void GenericCompilerInfo(string arg0) /// The 'GenericClassLoadingInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericClassLoadingInfo(string arg0) { @@ -76,7 +76,7 @@ public void GenericClassLoadingInfo(string arg0) /// The 'GenericVerifierInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericVerifierInfo(string arg0) { @@ -87,7 +87,7 @@ public void GenericVerifierInfo(string arg0) /// The 'GenericRuntimeInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericRuntimeInfo(string arg0) { @@ -98,7 +98,7 @@ public void GenericRuntimeInfo(string arg0) /// The 'GenericJniInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// public void GenericJniInfo(string arg0) { @@ -109,7 +109,7 @@ public void GenericJniInfo(string arg0) /// The 'ClassNotFound' diagnostic. /// /// -/// Class "{arg0}" not found. +/// Warning: Class "{arg0}" not found. /// public void ClassNotFound(string arg0) { @@ -120,7 +120,7 @@ public void ClassNotFound(string arg0) /// The 'ClassFormatError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (class format error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (class format error "{arg1}") /// public void ClassFormatError(string arg0, string arg1) { @@ -131,7 +131,7 @@ public void ClassFormatError(string arg0, string arg1) /// The 'DuplicateClassName' diagnostic. /// /// -/// Duplicate class name: "{arg0}". +/// Warning: Duplicate class name: "{arg0}". /// public void DuplicateClassName(string arg0) { @@ -142,7 +142,7 @@ public void DuplicateClassName(string arg0) /// The 'IllegalAccessError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (illegal access error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (illegal access error "{arg1}") /// public void IllegalAccessError(string arg0, string arg1) { @@ -153,7 +153,7 @@ public void IllegalAccessError(string arg0, string arg1) /// The 'VerificationError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (verification error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (verification error "{arg1}") /// public void VerificationError(string arg0, string arg1) { @@ -164,7 +164,7 @@ public void VerificationError(string arg0, string arg1) /// The 'NoClassDefFoundError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (missing class "{arg1}") +/// Warning: Unable to compile class "{arg0}". (missing class "{arg1}") /// public void NoClassDefFoundError(string arg0, string arg1) { @@ -175,7 +175,7 @@ public void NoClassDefFoundError(string arg0, string arg1) /// The 'GenericUnableToCompileError' diagnostic. /// /// -/// Unable to compile class "{arg0}". ("{arg1}": "{arg2}") +/// Warning: Unable to compile class "{arg0}". ("{arg1}": "{arg2}") /// public void GenericUnableToCompileError(string arg0, string arg1, string arg2) { @@ -186,7 +186,7 @@ public void GenericUnableToCompileError(string arg0, string arg1, string arg2) /// The 'DuplicateResourceName' diagnostic. /// /// -/// Skipping resource (name clash): "{arg0}" +/// Warning: Skipping resource (name clash): "{arg0}" /// public void DuplicateResourceName(string arg0) { @@ -197,7 +197,7 @@ public void DuplicateResourceName(string arg0) /// The 'SkippingReferencedClass' diagnostic. /// /// -/// Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") +/// Warning: Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") /// public void SkippingReferencedClass(string arg0, string arg1) { @@ -208,7 +208,7 @@ public void SkippingReferencedClass(string arg0, string arg1) /// The 'NoJniRuntime' diagnostic. /// /// -/// Unable to load runtime JNI assembly. +/// Warning: Unable to load runtime JNI assembly. /// public void NoJniRuntime() { @@ -219,7 +219,7 @@ public void NoJniRuntime() /// The 'EmittedNoClassDefFoundError' diagnostic. /// /// -/// Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). +/// Warning: Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). /// public void EmittedNoClassDefFoundError(string arg0, string arg1) { @@ -230,7 +230,7 @@ public void EmittedNoClassDefFoundError(string arg0, string arg1) /// The 'EmittedIllegalAccessError' diagnostic. /// /// -/// Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") /// public void EmittedIllegalAccessError(string arg0, string arg1) { @@ -241,7 +241,7 @@ public void EmittedIllegalAccessError(string arg0, string arg1) /// The 'EmittedInstantiationError' diagnostic. /// /// -/// Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") /// public void EmittedInstantiationError(string arg0, string arg1) { @@ -252,7 +252,7 @@ public void EmittedInstantiationError(string arg0, string arg1) /// The 'EmittedIncompatibleClassChangeError' diagnostic. /// /// -/// Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") /// public void EmittedIncompatibleClassChangeError(string arg0, string arg1) { @@ -263,7 +263,7 @@ public void EmittedIncompatibleClassChangeError(string arg0, string arg1) /// The 'EmittedNoSuchFieldError' diagnostic. /// /// -/// Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") /// public void EmittedNoSuchFieldError(string arg0, string arg1) { @@ -274,7 +274,7 @@ public void EmittedNoSuchFieldError(string arg0, string arg1) /// The 'EmittedAbstractMethodError' diagnostic. /// /// -/// Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") /// public void EmittedAbstractMethodError(string arg0, string arg1) { @@ -285,7 +285,7 @@ public void EmittedAbstractMethodError(string arg0, string arg1) /// The 'EmittedNoSuchMethodError' diagnostic. /// /// -/// Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") /// public void EmittedNoSuchMethodError(string arg0, string arg1) { @@ -296,7 +296,7 @@ public void EmittedNoSuchMethodError(string arg0, string arg1) /// The 'EmittedLinkageError' diagnostic. /// /// -/// Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") /// public void EmittedLinkageError(string arg0, string arg1) { @@ -307,7 +307,7 @@ public void EmittedLinkageError(string arg0, string arg1) /// The 'EmittedVerificationError' diagnostic. /// /// -/// Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") /// public void EmittedVerificationError(string arg0, string arg1) { @@ -318,7 +318,7 @@ public void EmittedVerificationError(string arg0, string arg1) /// The 'EmittedClassFormatError' diagnostic. /// /// -/// Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") /// public void EmittedClassFormatError(string arg0, string arg1) { @@ -329,7 +329,7 @@ public void EmittedClassFormatError(string arg0, string arg1) /// The 'InvalidCustomAttribute' diagnostic. /// /// -/// Error emitting "{arg0}" custom attribute. ("{arg1}") +/// Warning: Error emitting "{arg0}" custom attribute. ("{arg1}") /// public void InvalidCustomAttribute(string arg0, string arg1) { @@ -340,7 +340,7 @@ public void InvalidCustomAttribute(string arg0, string arg1) /// The 'IgnoredCustomAttribute' diagnostic. /// /// -/// Custom attribute "{arg0}" was ignored. ("{arg1}") +/// Warning: Custom attribute "{arg0}" was ignored. ("{arg1}") /// public void IgnoredCustomAttribute(string arg0, string arg1) { @@ -351,7 +351,7 @@ public void IgnoredCustomAttribute(string arg0, string arg1) /// The 'AssumeAssemblyVersionMatch' diagnostic. /// /// -/// Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy +/// Warning: Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy /// public void AssumeAssemblyVersionMatch(string arg0, string arg1) { @@ -362,7 +362,7 @@ public void AssumeAssemblyVersionMatch(string arg0, string arg1) /// The 'InvalidDirectoryInLibOptionPath' diagnostic. /// /// -/// Directory "{arg0}" specified in -lib option is not valid. +/// Warning: Directory "{arg0}" specified in -lib option is not valid. /// public void InvalidDirectoryInLibOptionPath(string arg0) { @@ -373,7 +373,7 @@ public void InvalidDirectoryInLibOptionPath(string arg0) /// The 'InvalidDirectoryInLibEnvironmentPath' diagnostic. /// /// -/// Directory "{arg0}" specified in LIB environment is not valid. +/// Warning: Directory "{arg0}" specified in LIB environment is not valid. /// public void InvalidDirectoryInLibEnvironmentPath(string arg0) { @@ -384,7 +384,7 @@ public void InvalidDirectoryInLibEnvironmentPath(string arg0) /// The 'LegacySearchRule' diagnostic. /// /// -/// Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. +/// Warning: Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. /// public void LegacySearchRule(string arg0) { @@ -395,7 +395,7 @@ public void LegacySearchRule(string arg0) /// The 'AssemblyLocationIgnored' diagnostic. /// /// -/// Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". +/// Warning: Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". /// public void AssemblyLocationIgnored(string arg0, string arg1, string arg2) { @@ -406,7 +406,7 @@ public void AssemblyLocationIgnored(string arg0, string arg1, string arg2) /// The 'InterfaceMethodCantBeInternal' diagnostic. /// /// -/// Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") +/// Warning: Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") /// public void InterfaceMethodCantBeInternal(string arg0, string arg1, string arg2) { @@ -417,7 +417,7 @@ public void InterfaceMethodCantBeInternal(string arg0, string arg1, string arg2) /// The 'DuplicateAssemblyReference' diagnostic. /// /// -/// Duplicate assembly reference "{arg0}" +/// Warning: Duplicate assembly reference "{arg0}" /// public void DuplicateAssemblyReference(string arg0) { @@ -428,7 +428,7 @@ public void DuplicateAssemblyReference(string arg0) /// The 'UnableToResolveType' diagnostic. /// /// -/// Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. +/// Warning: Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. /// public void UnableToResolveType(string arg0, string arg1, string arg2) { @@ -439,7 +439,7 @@ public void UnableToResolveType(string arg0, string arg1, string arg2) /// The 'StubsAreDeprecated' diagnostic. /// /// -/// Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. +/// Warning: Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. /// public void StubsAreDeprecated(string arg0) { @@ -450,7 +450,7 @@ public void StubsAreDeprecated(string arg0) /// The 'WrongClassName' diagnostic. /// /// -/// Unable to compile "{arg0}" (wrong name: "{arg1}") +/// Warning: Unable to compile "{arg0}" (wrong name: "{arg1}") /// public void WrongClassName(string arg0, string arg1) { @@ -461,7 +461,7 @@ public void WrongClassName(string arg0, string arg1) /// The 'ReflectionCallerClassRequiresCallerID' diagnostic. /// /// -/// Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") +/// Warning: Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") /// public void ReflectionCallerClassRequiresCallerID(string arg0, string arg1, string arg2) { @@ -472,7 +472,7 @@ public void ReflectionCallerClassRequiresCallerID(string arg0, string arg1, stri /// The 'LegacyAssemblyAttributesFound' diagnostic. /// /// -/// Legacy assembly attributes container found. Please use the -assemblyattributes: option. +/// Warning: Legacy assembly attributes container found. Please use the -assemblyattributes: option. /// public void LegacyAssemblyAttributesFound() { @@ -483,7 +483,7 @@ public void LegacyAssemblyAttributesFound() /// The 'UnableToCreateLambdaFactory' diagnostic. /// /// -/// Unable to create static lambda factory. +/// Warning: Unable to create static lambda factory. /// public void UnableToCreateLambdaFactory() { @@ -494,7 +494,7 @@ public void UnableToCreateLambdaFactory() /// The 'UnknownWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void UnknownWarning(string arg0) { @@ -505,7 +505,7 @@ public void UnknownWarning(string arg0) /// The 'DuplicateIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public void DuplicateIkvmLangProperty(string arg0, string arg1) { @@ -516,7 +516,7 @@ public void DuplicateIkvmLangProperty(string arg0, string arg1) /// The 'MalformedIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// public void MalformedIkvmLangProperty(string arg0, string arg1) { @@ -527,7 +527,7 @@ public void MalformedIkvmLangProperty(string arg0, string arg1) /// The 'GenericCompilerWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericCompilerWarning(string arg0) { @@ -538,7 +538,7 @@ public void GenericCompilerWarning(string arg0) /// The 'GenericClassLoadingWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericClassLoadingWarning(string arg0) { @@ -549,7 +549,7 @@ public void GenericClassLoadingWarning(string arg0) /// The 'GenericVerifierWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericVerifierWarning(string arg0) { @@ -560,7 +560,7 @@ public void GenericVerifierWarning(string arg0) /// The 'GenericRuntimeWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericRuntimeWarning(string arg0) { @@ -571,7 +571,7 @@ public void GenericRuntimeWarning(string arg0) /// The 'GenericJniWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// public void GenericJniWarning(string arg0) { @@ -582,7 +582,7 @@ public void GenericJniWarning(string arg0) /// The 'UnableToCreateProxy' diagnostic. /// /// -/// Unable to create proxy "{arg0}". ("{arg1}") +/// Error: Unable to create proxy "{arg0}". ("{arg1}") /// public void UnableToCreateProxy(string arg0, string arg1) { @@ -593,7 +593,7 @@ public void UnableToCreateProxy(string arg0, string arg1) /// The 'DuplicateProxy' diagnostic. /// /// -/// Duplicate proxy "{arg0}". +/// Error: Duplicate proxy "{arg0}". /// public void DuplicateProxy(string arg0) { @@ -604,7 +604,7 @@ public void DuplicateProxy(string arg0) /// The 'MapXmlUnableToResolveOpCode' diagnostic. /// /// -/// Unable to resolve opcode in remap file: {arg0}. +/// Error: Unable to resolve opcode in remap file: {arg0}. /// public void MapXmlUnableToResolveOpCode(string arg0) { @@ -615,7 +615,7 @@ public void MapXmlUnableToResolveOpCode(string arg0) /// The 'MapXmlError' diagnostic. /// /// -/// Error in remap file: {arg0}. +/// Error: Error in remap file: {arg0}. /// public void MapXmlError(string arg0) { @@ -626,7 +626,7 @@ public void MapXmlError(string arg0) /// The 'InputFileNotFound' diagnostic. /// /// -/// Source file '{arg0}' not found. +/// Error: Source file '{arg0}' not found. /// public void InputFileNotFound(string arg0) { @@ -637,7 +637,7 @@ public void InputFileNotFound(string arg0) /// The 'UnknownFileType' diagnostic. /// /// -/// Unknown file type: {arg0}. +/// Error: Unknown file type: {arg0}. /// public void UnknownFileType(string arg0) { @@ -648,7 +648,7 @@ public void UnknownFileType(string arg0) /// The 'UnknownElementInMapFile' diagnostic. /// /// -/// Unknown element {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown element {arg0} in remap file, line {arg1}, column {arg2}. /// public void UnknownElementInMapFile(string arg0, string arg1, string arg2) { @@ -659,7 +659,7 @@ public void UnknownElementInMapFile(string arg0, string arg1, string arg2) /// The 'UnknownAttributeInMapFile' diagnostic. /// /// -/// Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. /// public void UnknownAttributeInMapFile(string arg0, string arg1, string arg2) { @@ -670,7 +670,7 @@ public void UnknownAttributeInMapFile(string arg0, string arg1, string arg2) /// The 'InvalidMemberNameInMapFile' diagnostic. /// /// -/// Invalid {arg0} name '{arg1}' in remap file in class {arg2}. +/// Error: Invalid {arg0} name '{arg1}' in remap file in class {arg2}. /// public void InvalidMemberNameInMapFile(string arg0, string arg1, string arg2) { @@ -681,7 +681,7 @@ public void InvalidMemberNameInMapFile(string arg0, string arg1, string arg2) /// The 'InvalidMemberSignatureInMapFile' diagnostic. /// /// -/// Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. +/// Error: Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. /// public void InvalidMemberSignatureInMapFile(string arg0, string arg1, string arg2, string arg3) { @@ -692,7 +692,7 @@ public void InvalidMemberSignatureInMapFile(string arg0, string arg1, string arg /// The 'InvalidPropertyNameInMapFile' diagnostic. /// /// -/// Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. /// public void InvalidPropertyNameInMapFile(string arg0, string arg1, string arg2, string arg3) { @@ -703,7 +703,7 @@ public void InvalidPropertyNameInMapFile(string arg0, string arg1, string arg2, /// The 'InvalidPropertySignatureInMapFile' diagnostic. /// /// -/// Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. /// public void InvalidPropertySignatureInMapFile(string arg0, string arg1, string arg2, string arg3) { @@ -714,7 +714,7 @@ public void InvalidPropertySignatureInMapFile(string arg0, string arg1, string a /// The 'NonPrimaryAssemblyReference' diagnostic. /// /// -/// Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. +/// Error: Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. /// public void NonPrimaryAssemblyReference(string arg0, string arg1) { @@ -725,7 +725,7 @@ public void NonPrimaryAssemblyReference(string arg0, string arg1) /// The 'MissingType' diagnostic. /// /// -/// Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. +/// Error: Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. /// public void MissingType(string arg0, string arg1) { @@ -736,7 +736,7 @@ public void MissingType(string arg0, string arg1) /// The 'MissingReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. +/// Error: The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. /// public void MissingReference(string arg0, string arg1) { @@ -747,7 +747,7 @@ public void MissingReference(string arg0, string arg1) /// The 'CallerSensitiveOnUnsupportedMethod' diagnostic. /// /// -/// CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") +/// Error: CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") /// public void CallerSensitiveOnUnsupportedMethod(string arg0, string arg1, string arg2) { @@ -758,7 +758,7 @@ public void CallerSensitiveOnUnsupportedMethod(string arg0, string arg1, string /// The 'RemappedTypeMissingDefaultInterfaceMethod' diagnostic. /// /// -/// {arg0} does not implement default interface method {arg1}. +/// Error: {arg0} does not implement default interface method {arg1}. /// public void RemappedTypeMissingDefaultInterfaceMethod(string arg0, string arg1) { @@ -769,7 +769,7 @@ public void RemappedTypeMissingDefaultInterfaceMethod(string arg0, string arg1) /// The 'GenericCompilerError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericCompilerError(string arg0) { @@ -780,7 +780,7 @@ public void GenericCompilerError(string arg0) /// The 'GenericClassLoadingError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericClassLoadingError(string arg0) { @@ -791,7 +791,7 @@ public void GenericClassLoadingError(string arg0) /// The 'GenericVerifierError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericVerifierError(string arg0) { @@ -802,7 +802,7 @@ public void GenericVerifierError(string arg0) /// The 'GenericRuntimeError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericRuntimeError(string arg0) { @@ -813,7 +813,7 @@ public void GenericRuntimeError(string arg0) /// The 'GenericJniError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// public void GenericJniError(string arg0) { @@ -824,7 +824,7 @@ public void GenericJniError(string arg0) /// The 'ExportingImportsNotSupported' diagnostic. /// /// -/// Exporting previously imported assemblies is not supported. +/// Error: Exporting previously imported assemblies is not supported. /// public void ExportingImportsNotSupported() { @@ -835,7 +835,7 @@ public void ExportingImportsNotSupported() /// The 'ResponseFileDepthExceeded' diagnostic. /// /// -/// Response file nesting depth exceeded. +/// Fatal: Response file nesting depth exceeded. /// public void ResponseFileDepthExceeded() { @@ -846,7 +846,7 @@ public void ResponseFileDepthExceeded() /// The 'ErrorReadingFile' diagnostic. /// /// -/// Unable to read file: {arg0}. ({arg1}) +/// Fatal: Unable to read file: {arg0}. ({arg1}) /// public void ErrorReadingFile(string arg0, string arg1) { @@ -857,7 +857,7 @@ public void ErrorReadingFile(string arg0, string arg1) /// The 'NoTargetsFound' diagnostic. /// /// -/// No targets found +/// Fatal: No targets found /// public void NoTargetsFound() { @@ -868,7 +868,7 @@ public void NoTargetsFound() /// The 'FileFormatLimitationExceeded' diagnostic. /// /// -/// File format limitation exceeded: {arg0}. +/// Fatal: File format limitation exceeded: {arg0}. /// public void FileFormatLimitationExceeded(string arg0) { @@ -879,7 +879,7 @@ public void FileFormatLimitationExceeded(string arg0) /// The 'CannotSpecifyBothKeyFileAndContainer' diagnostic. /// /// -/// You cannot specify both a key file and container. +/// Fatal: You cannot specify both a key file and container. /// public void CannotSpecifyBothKeyFileAndContainer() { @@ -890,7 +890,7 @@ public void CannotSpecifyBothKeyFileAndContainer() /// The 'DelaySignRequiresKey' diagnostic. /// /// -/// You cannot delay sign without a key file or container. +/// Fatal: You cannot delay sign without a key file or container. /// public void DelaySignRequiresKey() { @@ -901,7 +901,7 @@ public void DelaySignRequiresKey() /// The 'InvalidStrongNameKeyPair' diagnostic. /// /// -/// Invalid key {arg0} specified. ("{arg1}") +/// Fatal: Invalid key {arg0} specified. ("{arg1}") /// public void InvalidStrongNameKeyPair(string arg0, string arg1) { @@ -912,7 +912,7 @@ public void InvalidStrongNameKeyPair(string arg0, string arg1) /// The 'ReferenceNotFound' diagnostic. /// /// -/// Reference not found: {arg0} +/// Fatal: Reference not found: {arg0} /// public void ReferenceNotFound(string arg0) { @@ -923,7 +923,7 @@ public void ReferenceNotFound(string arg0) /// The 'OptionsMustPreceedChildLevels' diagnostic. /// /// -/// You can only specify options before any child levels. +/// Fatal: You can only specify options before any child levels. /// public void OptionsMustPreceedChildLevels() { @@ -934,7 +934,7 @@ public void OptionsMustPreceedChildLevels() /// The 'UnrecognizedTargetType' diagnostic. /// /// -/// Invalid value '{arg0}' for -target option. +/// Fatal: Invalid value '{arg0}' for -target option. /// public void UnrecognizedTargetType(string arg0) { @@ -945,7 +945,7 @@ public void UnrecognizedTargetType(string arg0) /// The 'UnrecognizedPlatform' diagnostic. /// /// -/// Invalid value '{arg0}' for -platform option. +/// Fatal: Invalid value '{arg0}' for -platform option. /// public void UnrecognizedPlatform(string arg0) { @@ -956,7 +956,7 @@ public void UnrecognizedPlatform(string arg0) /// The 'UnrecognizedApartment' diagnostic. /// /// -/// Invalid value '{arg0}' for -apartment option. +/// Fatal: Invalid value '{arg0}' for -apartment option. /// public void UnrecognizedApartment(string arg0) { @@ -967,7 +967,7 @@ public void UnrecognizedApartment(string arg0) /// The 'MissingFileSpecification' diagnostic. /// /// -/// Missing file specification for '{arg0}' option. +/// Fatal: Missing file specification for '{arg0}' option. /// public void MissingFileSpecification(string arg0) { @@ -978,7 +978,7 @@ public void MissingFileSpecification(string arg0) /// The 'PathTooLong' diagnostic. /// /// -/// Path too long: {arg0}. +/// Fatal: Path too long: {arg0}. /// public void PathTooLong(string arg0) { @@ -989,7 +989,7 @@ public void PathTooLong(string arg0) /// The 'PathNotFound' diagnostic. /// /// -/// Path not found: {arg0}. +/// Fatal: Path not found: {arg0}. /// public void PathNotFound(string arg0) { @@ -1000,7 +1000,7 @@ public void PathNotFound(string arg0) /// The 'InvalidPath' diagnostic. /// /// -/// Invalid path: {arg0}. +/// Fatal: Invalid path: {arg0}. /// public void InvalidPath(string arg0) { @@ -1011,7 +1011,7 @@ public void InvalidPath(string arg0) /// The 'InvalidOptionSyntax' diagnostic. /// /// -/// Invalid option: {arg0}. +/// Fatal: Invalid option: {arg0}. /// public void InvalidOptionSyntax(string arg0) { @@ -1022,7 +1022,7 @@ public void InvalidOptionSyntax(string arg0) /// The 'ExternalResourceNotFound' diagnostic. /// /// -/// External resource file does not exist: {arg0}. +/// Fatal: External resource file does not exist: {arg0}. /// public void ExternalResourceNotFound(string arg0) { @@ -1033,7 +1033,7 @@ public void ExternalResourceNotFound(string arg0) /// The 'ExternalResourceNameInvalid' diagnostic. /// /// -/// External resource file may not include path specification: {arg0}. +/// Fatal: External resource file may not include path specification: {arg0}. /// public void ExternalResourceNameInvalid(string arg0) { @@ -1044,7 +1044,7 @@ public void ExternalResourceNameInvalid(string arg0) /// The 'InvalidVersionFormat' diagnostic. /// /// -/// Invalid version specified: {arg0}. +/// Fatal: Invalid version specified: {arg0}. /// public void InvalidVersionFormat(string arg0) { @@ -1055,7 +1055,7 @@ public void InvalidVersionFormat(string arg0) /// The 'InvalidFileAlignment' diagnostic. /// /// -/// Invalid value '{arg0}' for -filealign option. +/// Fatal: Invalid value '{arg0}' for -filealign option. /// public void InvalidFileAlignment(string arg0) { @@ -1066,7 +1066,7 @@ public void InvalidFileAlignment(string arg0) /// The 'ErrorWritingFile' diagnostic. /// /// -/// Unable to write file: {arg0}. ({arg1}) +/// Fatal: Unable to write file: {arg0}. ({arg1}) /// public void ErrorWritingFile(string arg0, string arg1) { @@ -1077,7 +1077,7 @@ public void ErrorWritingFile(string arg0, string arg1) /// The 'UnrecognizedOption' diagnostic. /// /// -/// Unrecognized option: {arg0}. +/// Fatal: Unrecognized option: {arg0}. /// public void UnrecognizedOption(string arg0) { @@ -1088,7 +1088,7 @@ public void UnrecognizedOption(string arg0) /// The 'NoOutputFileSpecified' diagnostic. /// /// -/// No output file specified. +/// Fatal: No output file specified. /// public void NoOutputFileSpecified() { @@ -1099,7 +1099,7 @@ public void NoOutputFileSpecified() /// The 'SharedClassLoaderCannotBeUsedOnModuleTarget' diagnostic. /// /// -/// Incompatible options: -target:module and -sharedclassloader cannot be combined. +/// Fatal: Incompatible options: -target:module and -sharedclassloader cannot be combined. /// public void SharedClassLoaderCannotBeUsedOnModuleTarget() { @@ -1110,7 +1110,7 @@ public void SharedClassLoaderCannotBeUsedOnModuleTarget() /// The 'RuntimeNotFound' diagnostic. /// /// -/// Unable to load runtime assembly. +/// Fatal: Unable to load runtime assembly. /// public void RuntimeNotFound() { @@ -1121,7 +1121,7 @@ public void RuntimeNotFound() /// The 'MainClassRequiresExe' diagnostic. /// /// -/// Main class cannot be specified for library or module. +/// Fatal: Main class cannot be specified for library or module. /// public void MainClassRequiresExe() { @@ -1132,7 +1132,7 @@ public void MainClassRequiresExe() /// The 'ExeRequiresMainClass' diagnostic. /// /// -/// No main method found. +/// Fatal: No main method found. /// public void ExeRequiresMainClass() { @@ -1143,7 +1143,7 @@ public void ExeRequiresMainClass() /// The 'PropertiesRequireExe' diagnostic. /// /// -/// Properties cannot be specified for library or module. +/// Fatal: Properties cannot be specified for library or module. /// public void PropertiesRequireExe() { @@ -1154,7 +1154,7 @@ public void PropertiesRequireExe() /// The 'ModuleCannotHaveClassLoader' diagnostic. /// /// -/// Cannot specify assembly class loader for modules. +/// Fatal: Cannot specify assembly class loader for modules. /// public void ModuleCannotHaveClassLoader() { @@ -1165,7 +1165,7 @@ public void ModuleCannotHaveClassLoader() /// The 'ErrorParsingMapFile' diagnostic. /// /// -/// Unable to parse remap file: {arg0}. ({arg1}) +/// Fatal: Unable to parse remap file: {arg0}. ({arg1}) /// public void ErrorParsingMapFile(string arg0, string arg1) { @@ -1176,7 +1176,7 @@ public void ErrorParsingMapFile(string arg0, string arg1) /// The 'BootstrapClassesMissing' diagnostic. /// /// -/// Bootstrap classes missing and core assembly not found. +/// Fatal: Bootstrap classes missing and core assembly not found. /// public void BootstrapClassesMissing() { @@ -1187,7 +1187,7 @@ public void BootstrapClassesMissing() /// The 'StrongNameRequiresStrongNamedRefs' diagnostic. /// /// -/// All referenced assemblies must be strong named, to be able to sign the output assembly. +/// Fatal: All referenced assemblies must be strong named, to be able to sign the output assembly. /// public void StrongNameRequiresStrongNamedRefs() { @@ -1198,7 +1198,7 @@ public void StrongNameRequiresStrongNamedRefs() /// The 'MainClassNotFound' diagnostic. /// /// -/// Main class not found. +/// Fatal: Main class not found. /// public void MainClassNotFound() { @@ -1209,7 +1209,7 @@ public void MainClassNotFound() /// The 'MainMethodNotFound' diagnostic. /// /// -/// Main method not found. +/// Fatal: Main method not found. /// public void MainMethodNotFound() { @@ -1220,7 +1220,7 @@ public void MainMethodNotFound() /// The 'UnsupportedMainMethod' diagnostic. /// /// -/// Redirected main method not supported. +/// Fatal: Redirected main method not supported. /// public void UnsupportedMainMethod() { @@ -1231,7 +1231,7 @@ public void UnsupportedMainMethod() /// The 'ExternalMainNotAccessible' diagnostic. /// /// -/// External main method must be public and in a public class. +/// Fatal: External main method must be public and in a public class. /// public void ExternalMainNotAccessible() { @@ -1242,7 +1242,7 @@ public void ExternalMainNotAccessible() /// The 'ClassLoaderNotFound' diagnostic. /// /// -/// Custom assembly class loader class not found. +/// Fatal: Custom assembly class loader class not found. /// public void ClassLoaderNotFound() { @@ -1253,7 +1253,7 @@ public void ClassLoaderNotFound() /// The 'ClassLoaderNotAccessible' diagnostic. /// /// -/// Custom assembly class loader class is not accessible. +/// Fatal: Custom assembly class loader class is not accessible. /// public void ClassLoaderNotAccessible() { @@ -1264,7 +1264,7 @@ public void ClassLoaderNotAccessible() /// The 'ClassLoaderIsAbstract' diagnostic. /// /// -/// Custom assembly class loader class is abstract. +/// Fatal: Custom assembly class loader class is abstract. /// public void ClassLoaderIsAbstract() { @@ -1275,7 +1275,7 @@ public void ClassLoaderIsAbstract() /// The 'ClassLoaderNotClassLoader' diagnostic. /// /// -/// Custom assembly class loader class does not extend java.lang.ClassLoader. +/// Fatal: Custom assembly class loader class does not extend java.lang.ClassLoader. /// public void ClassLoaderNotClassLoader() { @@ -1286,7 +1286,7 @@ public void ClassLoaderNotClassLoader() /// The 'ClassLoaderConstructorMissing' diagnostic. /// /// -/// Custom assembly class loader constructor is missing. +/// Fatal: Custom assembly class loader constructor is missing. /// public void ClassLoaderConstructorMissing() { @@ -1297,7 +1297,7 @@ public void ClassLoaderConstructorMissing() /// The 'MapFileTypeNotFound' diagnostic. /// /// -/// Type '{arg0}' referenced in remap file was not found. +/// Fatal: Type '{arg0}' referenced in remap file was not found. /// public void MapFileTypeNotFound(string arg0) { @@ -1308,7 +1308,7 @@ public void MapFileTypeNotFound(string arg0) /// The 'MapFileClassNotFound' diagnostic. /// /// -/// Class '{arg0}' referenced in remap file was not found. +/// Fatal: Class '{arg0}' referenced in remap file was not found. /// public void MapFileClassNotFound(string arg0) { @@ -1319,7 +1319,7 @@ public void MapFileClassNotFound(string arg0) /// The 'MaximumErrorCountReached' diagnostic. /// /// -/// Maximum error count reached. +/// Fatal: Maximum error count reached. /// public void MaximumErrorCountReached() { @@ -1330,7 +1330,7 @@ public void MaximumErrorCountReached() /// The 'LinkageError' diagnostic. /// /// -/// Link error: {arg0} +/// Fatal: Link error: {arg0} /// public void LinkageError(string arg0) { @@ -1341,7 +1341,7 @@ public void LinkageError(string arg0) /// The 'RuntimeMismatch' diagnostic. /// /// -/// Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} +/// Fatal: Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} /// public void RuntimeMismatch(string referencedAssemblyPath, string runtimeAssemblyName, string referencedAssemblyName) { @@ -1352,7 +1352,7 @@ public void RuntimeMismatch(string referencedAssemblyPath, string runtimeAssembl /// The 'RuntimeMismatchStrongName' diagnostic. /// /// -/// +/// Fatal: /// public void RuntimeMismatchStrongName() { @@ -1363,7 +1363,7 @@ public void RuntimeMismatchStrongName() /// The 'CoreClassesMissing' diagnostic. /// /// -/// Failed to find core classes in core library. +/// Fatal: Failed to find core classes in core library. /// public void CoreClassesMissing() { @@ -1374,7 +1374,7 @@ public void CoreClassesMissing() /// The 'CriticalClassNotFound' diagnostic. /// /// -/// Unable to load critical class '{arg0}'. +/// Fatal: Unable to load critical class '{arg0}'. /// public void CriticalClassNotFound(string arg0) { @@ -1385,7 +1385,7 @@ public void CriticalClassNotFound(string arg0) /// The 'AssemblyContainsDuplicateClassNames' diagnostic. /// /// -/// Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) +/// Fatal: Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) /// public void AssemblyContainsDuplicateClassNames(string arg0, string arg1, string arg2, string arg3) { @@ -1396,7 +1396,7 @@ public void AssemblyContainsDuplicateClassNames(string arg0, string arg1, string /// The 'CallerIDRequiresHasCallerIDAnnotation' diagnostic. /// /// -/// CallerID.getCallerID() requires a HasCallerID annotation. +/// Fatal: CallerID.getCallerID() requires a HasCallerID annotation. /// public void CallerIDRequiresHasCallerIDAnnotation() { @@ -1407,7 +1407,7 @@ public void CallerIDRequiresHasCallerIDAnnotation() /// The 'UnableToResolveInterface' diagnostic. /// /// -/// Unable to resolve interface '{arg0}' on type '{arg1}'. +/// Fatal: Unable to resolve interface '{arg0}' on type '{arg1}'. /// public void UnableToResolveInterface(string arg0, string arg1) { @@ -1418,7 +1418,7 @@ public void UnableToResolveInterface(string arg0, string arg1) /// The 'MissingBaseType' diagnostic. /// /// -/// The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. +/// Fatal: The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. /// public void MissingBaseType(string arg0, string arg1, string arg2, string arg3) { @@ -1429,7 +1429,7 @@ public void MissingBaseType(string arg0, string arg1, string arg2, string arg3) /// The 'MissingBaseTypeReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. +/// Fatal: The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. /// public void MissingBaseTypeReference(string arg0, string arg1) { @@ -1440,7 +1440,7 @@ public void MissingBaseTypeReference(string arg0, string arg1) /// The 'FileNotFound' diagnostic. /// /// -/// File not found: {arg0}. +/// Fatal: File not found: {arg0}. /// public void FileNotFound(string arg0) { @@ -1451,7 +1451,7 @@ public void FileNotFound(string arg0) /// The 'RuntimeMethodMissing' diagnostic. /// /// -/// Runtime method '{arg0}' not found. +/// Fatal: Runtime method '{arg0}' not found. /// public void RuntimeMethodMissing(string arg0) { @@ -1462,7 +1462,7 @@ public void RuntimeMethodMissing(string arg0) /// The 'MapFileFieldNotFound' diagnostic. /// /// -/// Field '{arg0}' referenced in remap file was not found in class '{arg1}'. +/// Fatal: Field '{arg0}' referenced in remap file was not found in class '{arg1}'. /// public void MapFileFieldNotFound(string arg0, string arg1) { @@ -1473,7 +1473,7 @@ public void MapFileFieldNotFound(string arg0, string arg1) /// The 'GhostInterfaceMethodMissing' diagnostic. /// /// -/// Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) +/// Fatal: Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) /// public void GhostInterfaceMethodMissing(string arg0, string arg1, string arg2, string arg3) { @@ -1484,7 +1484,7 @@ public void GhostInterfaceMethodMissing(string arg0, string arg1, string arg2, s /// The 'ModuleInitializerMethodRequirements' diagnostic. /// /// -/// Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. +/// Fatal: Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. /// public void ModuleInitializerMethodRequirements(string arg1, string arg2, string arg3) { @@ -1495,7 +1495,7 @@ public void ModuleInitializerMethodRequirements(string arg1, string arg2, string /// The 'InvalidZip' diagnostic. /// /// -/// Invalid zip: {name}. +/// Fatal: Invalid zip: {name}. /// public void InvalidZip(string name) { @@ -1506,7 +1506,7 @@ public void InvalidZip(string name) /// The 'CoreAssemblyVersionMismatch' diagnostic. /// /// -/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. +/// Fatal: Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. /// public void CoreAssemblyVersionMismatch(string arg0, string arg1) { @@ -1517,7 +1517,7 @@ public void CoreAssemblyVersionMismatch(string arg0, string arg1) /// The 'GenericRuntimeTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public void GenericRuntimeTrace(string arg0) { @@ -1528,7 +1528,7 @@ public void GenericRuntimeTrace(string arg0) /// The 'GenericJniTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public void GenericJniTrace(string arg0) { @@ -1539,7 +1539,7 @@ public void GenericJniTrace(string arg0) /// The 'GenericCompilerTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// public void GenericCompilerTrace(string arg0) { diff --git a/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.tt b/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.tt index 10badb18b9..9d652e8078 100644 --- a/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.tt +++ b/src/IKVM.CoreLib/Diagnostics/NullDiagnosticHandler.g.tt @@ -45,7 +45,7 @@ foreach (var kvp in DiagnosticFile.Read(Host.ResolvePath(Path.Combine("Diagnosti /// <#= desc #> /// /// -<#= Util.ToCommentString(kvp.Value.Message ?? "") #> +<#= Util.ToCommentString(kvp.Value) #> /// public void <#= kvp.Key #>(<#= string.Join(", ", argDecl) #>) { diff --git a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs index 8d447587b1..123b06795b 100644 --- a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs +++ b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.cs @@ -12,7 +12,7 @@ partial class DiagnosticEventSource /// The 'MainMethodFound' diagnostic. /// /// -/// Found main method in class "{arg0}". +/// Info: Found main method in class "{arg0}". /// [Event(1, Message = "Found main method in class \"{0}\".", Level = EventLevel.Informational)] public void MainMethodFound(string arg0) => WriteEvent(1, arg0); @@ -21,7 +21,7 @@ partial class DiagnosticEventSource /// The 'OutputFileIs' diagnostic. /// /// -/// Output file is "{arg0}". +/// Info: Output file is "{arg0}". /// [Event(2, Message = "Output file is \"{0}\".", Level = EventLevel.Informational)] public void OutputFileIs(string arg0) => WriteEvent(2, arg0); @@ -30,7 +30,7 @@ partial class DiagnosticEventSource /// The 'AutoAddRef' diagnostic. /// /// -/// Automatically adding reference to "{arg0}". +/// Info: Automatically adding reference to "{arg0}". /// [Event(3, Message = "Automatically adding reference to \"{0}\".", Level = EventLevel.Informational)] public void AutoAddRef(string arg0) => WriteEvent(3, arg0); @@ -39,7 +39,7 @@ partial class DiagnosticEventSource /// The 'MainMethodFromManifest' diagnostic. /// /// -/// Using main class "{arg0}" based on jar manifest. +/// Info: Using main class "{arg0}" based on jar manifest. /// [Event(4, Message = "Using main class \"{0}\" based on jar manifest.", Level = EventLevel.Informational)] public void MainMethodFromManifest(string arg0) => WriteEvent(4, arg0); @@ -48,7 +48,7 @@ partial class DiagnosticEventSource /// The 'GenericCompilerInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// [Event(5, Message = "{0}", Level = EventLevel.Informational)] public void GenericCompilerInfo(string arg0) => WriteEvent(5, arg0); @@ -57,7 +57,7 @@ partial class DiagnosticEventSource /// The 'GenericClassLoadingInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// [Event(6, Message = "{0}", Level = EventLevel.Informational)] public void GenericClassLoadingInfo(string arg0) => WriteEvent(6, arg0); @@ -66,7 +66,7 @@ partial class DiagnosticEventSource /// The 'GenericVerifierInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// [Event(7, Message = "{0}", Level = EventLevel.Informational)] public void GenericVerifierInfo(string arg0) => WriteEvent(7, arg0); @@ -75,7 +75,7 @@ partial class DiagnosticEventSource /// The 'GenericRuntimeInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// [Event(8, Message = "{0}", Level = EventLevel.Informational)] public void GenericRuntimeInfo(string arg0) => WriteEvent(8, arg0); @@ -84,7 +84,7 @@ partial class DiagnosticEventSource /// The 'GenericJniInfo' diagnostic. /// /// -/// {arg0} +/// Info: {arg0} /// [Event(9, Message = "{0}", Level = EventLevel.Informational)] public void GenericJniInfo(string arg0) => WriteEvent(9, arg0); @@ -93,7 +93,7 @@ partial class DiagnosticEventSource /// The 'ClassNotFound' diagnostic. /// /// -/// Class "{arg0}" not found. +/// Warning: Class "{arg0}" not found. /// [Event(100, Message = "Class \"{0}\" not found.", Level = EventLevel.Warning)] public void ClassNotFound(string arg0) => WriteEvent(100, arg0); @@ -102,7 +102,7 @@ partial class DiagnosticEventSource /// The 'ClassFormatError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (class format error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (class format error "{arg1}") /// [Event(101, Message = "Unable to compile class \"{0}\". (class format error \"{1}\")", Level = EventLevel.Warning)] public void ClassFormatError(string arg0, string arg1) => WriteEvent(101, arg0, arg1); @@ -111,7 +111,7 @@ partial class DiagnosticEventSource /// The 'DuplicateClassName' diagnostic. /// /// -/// Duplicate class name: "{arg0}". +/// Warning: Duplicate class name: "{arg0}". /// [Event(102, Message = "Duplicate class name: \"{0}\".", Level = EventLevel.Warning)] public void DuplicateClassName(string arg0) => WriteEvent(102, arg0); @@ -120,7 +120,7 @@ partial class DiagnosticEventSource /// The 'IllegalAccessError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (illegal access error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (illegal access error "{arg1}") /// [Event(103, Message = "Unable to compile class \"{0}\". (illegal access error \"{1}\")", Level = EventLevel.Warning)] public void IllegalAccessError(string arg0, string arg1) => WriteEvent(103, arg0, arg1); @@ -129,7 +129,7 @@ partial class DiagnosticEventSource /// The 'VerificationError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (verification error "{arg1}") +/// Warning: Unable to compile class "{arg0}". (verification error "{arg1}") /// [Event(104, Message = "Unable to compile class \"{0}\". (verification error \"{1}\")", Level = EventLevel.Warning)] public void VerificationError(string arg0, string arg1) => WriteEvent(104, arg0, arg1); @@ -138,7 +138,7 @@ partial class DiagnosticEventSource /// The 'NoClassDefFoundError' diagnostic. /// /// -/// Unable to compile class "{arg0}". (missing class "{arg1}") +/// Warning: Unable to compile class "{arg0}". (missing class "{arg1}") /// [Event(105, Message = "Unable to compile class \"{0}\". (missing class \"{1}\")", Level = EventLevel.Warning)] public void NoClassDefFoundError(string arg0, string arg1) => WriteEvent(105, arg0, arg1); @@ -147,7 +147,7 @@ partial class DiagnosticEventSource /// The 'GenericUnableToCompileError' diagnostic. /// /// -/// Unable to compile class "{arg0}". ("{arg1}": "{arg2}") +/// Warning: Unable to compile class "{arg0}". ("{arg1}": "{arg2}") /// [Event(106, Message = "Unable to compile class \"{0}\". (\"{1}\": \"{2}\")", Level = EventLevel.Warning)] public void GenericUnableToCompileError(string arg0, string arg1, string arg2) => WriteEvent(106, arg0, arg1, arg2); @@ -156,7 +156,7 @@ partial class DiagnosticEventSource /// The 'DuplicateResourceName' diagnostic. /// /// -/// Skipping resource (name clash): "{arg0}" +/// Warning: Skipping resource (name clash): "{arg0}" /// [Event(107, Message = "Skipping resource (name clash): \"{0}\"", Level = EventLevel.Warning)] public void DuplicateResourceName(string arg0) => WriteEvent(107, arg0); @@ -165,7 +165,7 @@ partial class DiagnosticEventSource /// The 'SkippingReferencedClass' diagnostic. /// /// -/// Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") +/// Warning: Skipping class: "{arg0}". (class is already available in referenced assembly "{arg1}") /// [Event(109, Message = "Skipping class: \"{0}\". (class is already available in referenced assembly \"{1}\")", Level = EventLevel.Warning)] public void SkippingReferencedClass(string arg0, string arg1) => WriteEvent(109, arg0, arg1); @@ -174,7 +174,7 @@ partial class DiagnosticEventSource /// The 'NoJniRuntime' diagnostic. /// /// -/// Unable to load runtime JNI assembly. +/// Warning: Unable to load runtime JNI assembly. /// [Event(110, Message = "Unable to load runtime JNI assembly.", Level = EventLevel.Warning)] public void NoJniRuntime() => WriteEvent(110); @@ -183,7 +183,7 @@ partial class DiagnosticEventSource /// The 'EmittedNoClassDefFoundError' diagnostic. /// /// -/// Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). +/// Warning: Emitted java.lang.NoClassDefFoundError in "{arg0}". ("{arg1}"). /// [Event(111, Message = "Emitted java.lang.NoClassDefFoundError in \"{0}\". (\"{1}\").", Level = EventLevel.Warning)] public void EmittedNoClassDefFoundError(string arg0, string arg1) => WriteEvent(111, arg0, arg1); @@ -192,7 +192,7 @@ partial class DiagnosticEventSource /// The 'EmittedIllegalAccessError' diagnostic. /// /// -/// Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IllegalAccessError in "{arg0}". ("{arg1}") /// [Event(112, Message = "Emitted java.lang.IllegalAccessError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedIllegalAccessError(string arg0, string arg1) => WriteEvent(112, arg0, arg1); @@ -201,7 +201,7 @@ partial class DiagnosticEventSource /// The 'EmittedInstantiationError' diagnostic. /// /// -/// Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.InstantiationError in "{arg0}". ("{arg1}") /// [Event(113, Message = "Emitted java.lang.InstantiationError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedInstantiationError(string arg0, string arg1) => WriteEvent(113, arg0, arg1); @@ -210,7 +210,7 @@ partial class DiagnosticEventSource /// The 'EmittedIncompatibleClassChangeError' diagnostic. /// /// -/// Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.IncompatibleClassChangeError in "{arg0}". ("{arg1}") /// [Event(114, Message = "Emitted java.lang.IncompatibleClassChangeError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedIncompatibleClassChangeError(string arg0, string arg1) => WriteEvent(114, arg0, arg1); @@ -219,7 +219,7 @@ partial class DiagnosticEventSource /// The 'EmittedNoSuchFieldError' diagnostic. /// /// -/// Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchFieldError in "{arg0}". ("{arg1}") /// [Event(115, Message = "Emitted java.lang.NoSuchFieldError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedNoSuchFieldError(string arg0, string arg1) => WriteEvent(115, arg0, arg1); @@ -228,7 +228,7 @@ partial class DiagnosticEventSource /// The 'EmittedAbstractMethodError' diagnostic. /// /// -/// Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.AbstractMethodError in "{arg0}". ("{arg1}") /// [Event(116, Message = "Emitted java.lang.AbstractMethodError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedAbstractMethodError(string arg0, string arg1) => WriteEvent(116, arg0, arg1); @@ -237,7 +237,7 @@ partial class DiagnosticEventSource /// The 'EmittedNoSuchMethodError' diagnostic. /// /// -/// Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.NoSuchMethodError in "{arg0}". ("{arg1}") /// [Event(117, Message = "Emitted java.lang.NoSuchMethodError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedNoSuchMethodError(string arg0, string arg1) => WriteEvent(117, arg0, arg1); @@ -246,7 +246,7 @@ partial class DiagnosticEventSource /// The 'EmittedLinkageError' diagnostic. /// /// -/// Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.LinkageError in "{arg0}". ("{arg1}") /// [Event(118, Message = "Emitted java.lang.LinkageError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedLinkageError(string arg0, string arg1) => WriteEvent(118, arg0, arg1); @@ -255,7 +255,7 @@ partial class DiagnosticEventSource /// The 'EmittedVerificationError' diagnostic. /// /// -/// Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.VerificationError in "{arg0}". ("{arg1}") /// [Event(119, Message = "Emitted java.lang.VerificationError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedVerificationError(string arg0, string arg1) => WriteEvent(119, arg0, arg1); @@ -264,7 +264,7 @@ partial class DiagnosticEventSource /// The 'EmittedClassFormatError' diagnostic. /// /// -/// Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") +/// Warning: Emitted java.lang.ClassFormatError in "{arg0}". ("{arg1}") /// [Event(120, Message = "Emitted java.lang.ClassFormatError in \"{0}\". (\"{1}\")", Level = EventLevel.Warning)] public void EmittedClassFormatError(string arg0, string arg1) => WriteEvent(120, arg0, arg1); @@ -273,7 +273,7 @@ partial class DiagnosticEventSource /// The 'InvalidCustomAttribute' diagnostic. /// /// -/// Error emitting "{arg0}" custom attribute. ("{arg1}") +/// Warning: Error emitting "{arg0}" custom attribute. ("{arg1}") /// [Event(121, Message = "Error emitting \"{0}\" custom attribute. (\"{1}\")", Level = EventLevel.Warning)] public void InvalidCustomAttribute(string arg0, string arg1) => WriteEvent(121, arg0, arg1); @@ -282,7 +282,7 @@ partial class DiagnosticEventSource /// The 'IgnoredCustomAttribute' diagnostic. /// /// -/// Custom attribute "{arg0}" was ignored. ("{arg1}") +/// Warning: Custom attribute "{arg0}" was ignored. ("{arg1}") /// [Event(122, Message = "Custom attribute \"{0}\" was ignored. (\"{1}\")", Level = EventLevel.Warning)] public void IgnoredCustomAttribute(string arg0, string arg1) => WriteEvent(122, arg0, arg1); @@ -291,7 +291,7 @@ partial class DiagnosticEventSource /// The 'AssumeAssemblyVersionMatch' diagnostic. /// /// -/// Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy +/// Warning: Assuming assembly reference "{arg0}" matches "{arg1}", you may need to supply runtime policy /// [Event(123, Message = "Assuming assembly reference \"{0}\" matches \"{1}\", you may need to supply runtime p" + "olicy", Level = EventLevel.Warning)] @@ -301,7 +301,7 @@ partial class DiagnosticEventSource /// The 'InvalidDirectoryInLibOptionPath' diagnostic. /// /// -/// Directory "{arg0}" specified in -lib option is not valid. +/// Warning: Directory "{arg0}" specified in -lib option is not valid. /// [Event(124, Message = "Directory \"{0}\" specified in -lib option is not valid.", Level = EventLevel.Warning)] public void InvalidDirectoryInLibOptionPath(string arg0) => WriteEvent(124, arg0); @@ -310,7 +310,7 @@ partial class DiagnosticEventSource /// The 'InvalidDirectoryInLibEnvironmentPath' diagnostic. /// /// -/// Directory "{arg0}" specified in LIB environment is not valid. +/// Warning: Directory "{arg0}" specified in LIB environment is not valid. /// [Event(125, Message = "Directory \"{0}\" specified in LIB environment is not valid.", Level = EventLevel.Warning)] public void InvalidDirectoryInLibEnvironmentPath(string arg0) => WriteEvent(125, arg0); @@ -319,7 +319,7 @@ partial class DiagnosticEventSource /// The 'LegacySearchRule' diagnostic. /// /// -/// Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. +/// Warning: Found assembly "{arg0}" using legacy search rule, please append '.dll' to the reference. /// [Event(126, Message = "Found assembly \"{0}\" using legacy search rule, please append \'.dll\' to the refere" + "nce.", Level = EventLevel.Warning)] @@ -329,7 +329,7 @@ partial class DiagnosticEventSource /// The 'AssemblyLocationIgnored' diagnostic. /// /// -/// Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". +/// Warning: Assembly "{arg0}" is ignored as previously loaded assembly "{arg1}" has the same identity "{arg2}". /// [Event(127, Message = "Assembly \"{0}\" is ignored as previously loaded assembly \"{1}\" has the same identi" + "ty \"{2}\".", Level = EventLevel.Warning)] @@ -339,7 +339,7 @@ partial class DiagnosticEventSource /// The 'InterfaceMethodCantBeInternal' diagnostic. /// /// -/// Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") +/// Warning: Ignoring @ikvm.lang.Internal annotation on interface method. ("{arg0}.{arg1}{arg2}") /// [Event(128, Message = "Ignoring @ikvm.lang.Internal annotation on interface method. (\"{0}.{1}{2}\")", Level = EventLevel.Warning)] public void InterfaceMethodCantBeInternal(string arg0, string arg1, string arg2) => WriteEvent(128, arg0, arg1, arg2); @@ -348,7 +348,7 @@ partial class DiagnosticEventSource /// The 'DuplicateAssemblyReference' diagnostic. /// /// -/// Duplicate assembly reference "{arg0}" +/// Warning: Duplicate assembly reference "{arg0}" /// [Event(132, Message = "Duplicate assembly reference \"{0}\"", Level = EventLevel.Warning)] public void DuplicateAssemblyReference(string arg0) => WriteEvent(132, arg0); @@ -357,7 +357,7 @@ partial class DiagnosticEventSource /// The 'UnableToResolveType' diagnostic. /// /// -/// Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. +/// Warning: Reference in "{arg0}" to type "{arg1}" claims it is defined in "{arg2}", but it could not be found. /// [Event(133, Message = "Reference in \"{0}\" to type \"{1}\" claims it is defined in \"{2}\", but it could not " + "be found.", Level = EventLevel.Warning)] @@ -367,7 +367,7 @@ partial class DiagnosticEventSource /// The 'StubsAreDeprecated' diagnostic. /// /// -/// Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. +/// Warning: Compiling stubs is deprecated. Please add a reference to assembly "{arg0}" instead. /// [Event(134, Message = "Compiling stubs is deprecated. Please add a reference to assembly \"{0}\" instead.", Level = EventLevel.Warning)] public void StubsAreDeprecated(string arg0) => WriteEvent(134, arg0); @@ -376,7 +376,7 @@ partial class DiagnosticEventSource /// The 'WrongClassName' diagnostic. /// /// -/// Unable to compile "{arg0}" (wrong name: "{arg1}") +/// Warning: Unable to compile "{arg0}" (wrong name: "{arg1}") /// [Event(135, Message = "Unable to compile \"{0}\" (wrong name: \"{1}\")", Level = EventLevel.Warning)] public void WrongClassName(string arg0, string arg1) => WriteEvent(135, arg0, arg1); @@ -385,7 +385,7 @@ partial class DiagnosticEventSource /// The 'ReflectionCallerClassRequiresCallerID' diagnostic. /// /// -/// Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") +/// Warning: Reflection.getCallerClass() called from non-CallerID method. ("{arg0}.{arg1}{arg2}") /// [Event(136, Message = "Reflection.getCallerClass() called from non-CallerID method. (\"{0}.{1}{2}\")", Level = EventLevel.Warning)] public void ReflectionCallerClassRequiresCallerID(string arg0, string arg1, string arg2) => WriteEvent(136, arg0, arg1, arg2); @@ -394,7 +394,7 @@ partial class DiagnosticEventSource /// The 'LegacyAssemblyAttributesFound' diagnostic. /// /// -/// Legacy assembly attributes container found. Please use the -assemblyattributes: option. +/// Warning: Legacy assembly attributes container found. Please use the -assemblyattributes: option. /// [Event(137, Message = "Legacy assembly attributes container found. Please use the -assemblyattributes: option.", Level = EventLevel.Warning)] @@ -404,7 +404,7 @@ partial class DiagnosticEventSource /// The 'UnableToCreateLambdaFactory' diagnostic. /// /// -/// Unable to create static lambda factory. +/// Warning: Unable to create static lambda factory. /// [Event(138, Message = "Unable to create static lambda factory.", Level = EventLevel.Warning)] public void UnableToCreateLambdaFactory() => WriteEvent(138); @@ -413,7 +413,7 @@ partial class DiagnosticEventSource /// The 'UnknownWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// [Event(999, Message = "{0}", Level = EventLevel.Warning)] public void UnknownWarning(string arg0) => WriteEvent(999, arg0); @@ -422,7 +422,7 @@ partial class DiagnosticEventSource /// The 'DuplicateIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// [Event(139, Message = "Ignoring duplicate ikvm.lang.Property annotation on {0}.{1}.", Level = EventLevel.Warning)] public void DuplicateIkvmLangProperty(string arg0, string arg1) => WriteEvent(139, arg0, arg1); @@ -431,7 +431,7 @@ partial class DiagnosticEventSource /// The 'MalformedIkvmLangProperty' diagnostic. /// /// -/// Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. +/// Warning: Ignoring duplicate ikvm.lang.Property annotation on {arg0}.{arg1}. /// [Event(140, Message = "Ignoring duplicate ikvm.lang.Property annotation on {0}.{1}.", Level = EventLevel.Warning)] public void MalformedIkvmLangProperty(string arg0, string arg1) => WriteEvent(140, arg0, arg1); @@ -440,7 +440,7 @@ partial class DiagnosticEventSource /// The 'GenericCompilerWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// [Event(141, Message = "{0}", Level = EventLevel.Warning)] public void GenericCompilerWarning(string arg0) => WriteEvent(141, arg0); @@ -449,7 +449,7 @@ partial class DiagnosticEventSource /// The 'GenericClassLoadingWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// [Event(142, Message = "{0}", Level = EventLevel.Warning)] public void GenericClassLoadingWarning(string arg0) => WriteEvent(142, arg0); @@ -458,7 +458,7 @@ partial class DiagnosticEventSource /// The 'GenericVerifierWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// [Event(143, Message = "{0}", Level = EventLevel.Warning)] public void GenericVerifierWarning(string arg0) => WriteEvent(143, arg0); @@ -467,7 +467,7 @@ partial class DiagnosticEventSource /// The 'GenericRuntimeWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// [Event(144, Message = "{0}", Level = EventLevel.Warning)] public void GenericRuntimeWarning(string arg0) => WriteEvent(144, arg0); @@ -476,7 +476,7 @@ partial class DiagnosticEventSource /// The 'GenericJniWarning' diagnostic. /// /// -/// {arg0} +/// Warning: {arg0} /// [Event(145, Message = "{0}", Level = EventLevel.Warning)] public void GenericJniWarning(string arg0) => WriteEvent(145, arg0); @@ -485,7 +485,7 @@ partial class DiagnosticEventSource /// The 'UnableToCreateProxy' diagnostic. /// /// -/// Unable to create proxy "{arg0}". ("{arg1}") +/// Error: Unable to create proxy "{arg0}". ("{arg1}") /// [Event(4001, Message = "Unable to create proxy \"{0}\". (\"{1}\")", Level = EventLevel.Error)] public void UnableToCreateProxy(string arg0, string arg1) => WriteEvent(4001, arg0, arg1); @@ -494,7 +494,7 @@ partial class DiagnosticEventSource /// The 'DuplicateProxy' diagnostic. /// /// -/// Duplicate proxy "{arg0}". +/// Error: Duplicate proxy "{arg0}". /// [Event(4002, Message = "Duplicate proxy \"{0}\".", Level = EventLevel.Error)] public void DuplicateProxy(string arg0) => WriteEvent(4002, arg0); @@ -503,7 +503,7 @@ partial class DiagnosticEventSource /// The 'MapXmlUnableToResolveOpCode' diagnostic. /// /// -/// Unable to resolve opcode in remap file: {arg0}. +/// Error: Unable to resolve opcode in remap file: {arg0}. /// [Event(4003, Message = "Unable to resolve opcode in remap file: {0}.", Level = EventLevel.Error)] public void MapXmlUnableToResolveOpCode(string arg0) => WriteEvent(4003, arg0); @@ -512,7 +512,7 @@ partial class DiagnosticEventSource /// The 'MapXmlError' diagnostic. /// /// -/// Error in remap file: {arg0}. +/// Error: Error in remap file: {arg0}. /// [Event(4004, Message = "Error in remap file: {0}.", Level = EventLevel.Error)] public void MapXmlError(string arg0) => WriteEvent(4004, arg0); @@ -521,7 +521,7 @@ partial class DiagnosticEventSource /// The 'InputFileNotFound' diagnostic. /// /// -/// Source file '{arg0}' not found. +/// Error: Source file '{arg0}' not found. /// [Event(4005, Message = "Source file \'{0}\' not found.", Level = EventLevel.Error)] public void InputFileNotFound(string arg0) => WriteEvent(4005, arg0); @@ -530,7 +530,7 @@ partial class DiagnosticEventSource /// The 'UnknownFileType' diagnostic. /// /// -/// Unknown file type: {arg0}. +/// Error: Unknown file type: {arg0}. /// [Event(4006, Message = "Unknown file type: {0}.", Level = EventLevel.Error)] public void UnknownFileType(string arg0) => WriteEvent(4006, arg0); @@ -539,7 +539,7 @@ partial class DiagnosticEventSource /// The 'UnknownElementInMapFile' diagnostic. /// /// -/// Unknown element {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown element {arg0} in remap file, line {arg1}, column {arg2}. /// [Event(4007, Message = "Unknown element {0} in remap file, line {1}, column {2}.", Level = EventLevel.Error)] public void UnknownElementInMapFile(string arg0, string arg1, string arg2) => WriteEvent(4007, arg0, arg1, arg2); @@ -548,7 +548,7 @@ partial class DiagnosticEventSource /// The 'UnknownAttributeInMapFile' diagnostic. /// /// -/// Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. +/// Error: Unknown attribute {arg0} in remap file, line {arg1}, column {arg2}. /// [Event(4008, Message = "Unknown attribute {0} in remap file, line {1}, column {2}.", Level = EventLevel.Error)] public void UnknownAttributeInMapFile(string arg0, string arg1, string arg2) => WriteEvent(4008, arg0, arg1, arg2); @@ -557,7 +557,7 @@ partial class DiagnosticEventSource /// The 'InvalidMemberNameInMapFile' diagnostic. /// /// -/// Invalid {arg0} name '{arg1}' in remap file in class {arg2}. +/// Error: Invalid {arg0} name '{arg1}' in remap file in class {arg2}. /// [Event(4009, Message = "Invalid {0} name \'{1}\' in remap file in class {2}.", Level = EventLevel.Error)] public void InvalidMemberNameInMapFile(string arg0, string arg1, string arg2) => WriteEvent(4009, arg0, arg1, arg2); @@ -566,7 +566,7 @@ partial class DiagnosticEventSource /// The 'InvalidMemberSignatureInMapFile' diagnostic. /// /// -/// Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. +/// Error: Invalid {arg0} signature '{arg3}' in remap file for {arg0} {arg1}.{arg2}. /// [Event(4010, Message = "Invalid {0} signature \'{3}\' in remap file for {0} {1}.{2}.", Level = EventLevel.Error)] public void InvalidMemberSignatureInMapFile(string arg0, string arg1, string arg2, string arg3) => WriteEvent(4010, arg0, arg1, arg2, arg3); @@ -575,7 +575,7 @@ partial class DiagnosticEventSource /// The 'InvalidPropertyNameInMapFile' diagnostic. /// /// -/// Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} name '{arg3}' in remap file for property {arg1}.{arg2}. /// [Event(4011, Message = "Invalid property {0} name \'{3}\' in remap file for property {1}.{2}.", Level = EventLevel.Error)] public void InvalidPropertyNameInMapFile(string arg0, string arg1, string arg2, string arg3) => WriteEvent(4011, arg0, arg1, arg2, arg3); @@ -584,7 +584,7 @@ partial class DiagnosticEventSource /// The 'InvalidPropertySignatureInMapFile' diagnostic. /// /// -/// Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. +/// Error: Invalid property {arg0} signature '{arg3}' in remap file for property {arg1}.{arg2}. /// [Event(4012, Message = "Invalid property {0} signature \'{3}\' in remap file for property {1}.{2}.", Level = EventLevel.Error)] public void InvalidPropertySignatureInMapFile(string arg0, string arg1, string arg2, string arg3) => WriteEvent(4012, arg0, arg1, arg2, arg3); @@ -593,7 +593,7 @@ partial class DiagnosticEventSource /// The 'NonPrimaryAssemblyReference' diagnostic. /// /// -/// Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. +/// Error: Referenced assembly "{arg0}" is not the primary assembly of a shared class loader group, please reference primary assembly "{arg1}" instead. /// [Event(4013, Message = "Referenced assembly \"{0}\" is not the primary assembly of a shared class loader gr" + "oup, please reference primary assembly \"{1}\" instead.", Level = EventLevel.Error)] @@ -603,7 +603,7 @@ partial class DiagnosticEventSource /// The 'MissingType' diagnostic. /// /// -/// Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. +/// Error: Reference to type "{arg0}" claims it is defined in "{arg1}", but it could not be found. /// [Event(4014, Message = "Reference to type \"{0}\" claims it is defined in \"{1}\", but it could not be found." + "", Level = EventLevel.Error)] @@ -613,7 +613,7 @@ partial class DiagnosticEventSource /// The 'MissingReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. +/// Error: The type '{arg0}' is defined in an assembly that is notResponseFileDepthExceeded referenced. You must add a reference to assembly '{arg1}'. /// [Event(4015, Message = "The type \'{0}\' is defined in an assembly that is notResponseFileDepthExceeded ref" + "erenced. You must add a reference to assembly \'{1}\'.", Level = EventLevel.Error)] @@ -623,7 +623,7 @@ partial class DiagnosticEventSource /// The 'CallerSensitiveOnUnsupportedMethod' diagnostic. /// /// -/// CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") +/// Error: CallerSensitive annotation on unsupported method. ("{arg0}.{arg1}{arg2}") /// [Event(4016, Message = "CallerSensitive annotation on unsupported method. (\"{0}.{1}{2}\")", Level = EventLevel.Error)] public void CallerSensitiveOnUnsupportedMethod(string arg0, string arg1, string arg2) => WriteEvent(4016, arg0, arg1, arg2); @@ -632,7 +632,7 @@ partial class DiagnosticEventSource /// The 'RemappedTypeMissingDefaultInterfaceMethod' diagnostic. /// /// -/// {arg0} does not implement default interface method {arg1}. +/// Error: {arg0} does not implement default interface method {arg1}. /// [Event(4017, Message = "{0} does not implement default interface method {1}.", Level = EventLevel.Error)] public void RemappedTypeMissingDefaultInterfaceMethod(string arg0, string arg1) => WriteEvent(4017, arg0, arg1); @@ -641,7 +641,7 @@ partial class DiagnosticEventSource /// The 'GenericCompilerError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// [Event(4018, Message = "{0}", Level = EventLevel.Error)] public void GenericCompilerError(string arg0) => WriteEvent(4018, arg0); @@ -650,7 +650,7 @@ partial class DiagnosticEventSource /// The 'GenericClassLoadingError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// [Event(4019, Message = "{0}", Level = EventLevel.Error)] public void GenericClassLoadingError(string arg0) => WriteEvent(4019, arg0); @@ -659,7 +659,7 @@ partial class DiagnosticEventSource /// The 'GenericVerifierError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// [Event(4020, Message = "{0}", Level = EventLevel.Error)] public void GenericVerifierError(string arg0) => WriteEvent(4020, arg0); @@ -668,7 +668,7 @@ partial class DiagnosticEventSource /// The 'GenericRuntimeError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// [Event(4021, Message = "{0}", Level = EventLevel.Error)] public void GenericRuntimeError(string arg0) => WriteEvent(4021, arg0); @@ -677,7 +677,7 @@ partial class DiagnosticEventSource /// The 'GenericJniError' diagnostic. /// /// -/// {arg0} +/// Error: {arg0} /// [Event(4022, Message = "{0}", Level = EventLevel.Error)] public void GenericJniError(string arg0) => WriteEvent(4022, arg0); @@ -686,7 +686,7 @@ partial class DiagnosticEventSource /// The 'ExportingImportsNotSupported' diagnostic. /// /// -/// Exporting previously imported assemblies is not supported. +/// Error: Exporting previously imported assemblies is not supported. /// [Event(4023, Message = "Exporting previously imported assemblies is not supported.", Level = EventLevel.Error)] public void ExportingImportsNotSupported() => WriteEvent(4023); @@ -695,7 +695,7 @@ partial class DiagnosticEventSource /// The 'ResponseFileDepthExceeded' diagnostic. /// /// -/// Response file nesting depth exceeded. +/// Fatal: Response file nesting depth exceeded. /// [Event(5000, Message = "Response file nesting depth exceeded.", Level = EventLevel.Critical)] public void ResponseFileDepthExceeded() => WriteEvent(5000); @@ -704,7 +704,7 @@ partial class DiagnosticEventSource /// The 'ErrorReadingFile' diagnostic. /// /// -/// Unable to read file: {arg0}. ({arg1}) +/// Fatal: Unable to read file: {arg0}. ({arg1}) /// [Event(5001, Message = "Unable to read file: {0}. ({1})", Level = EventLevel.Critical)] public void ErrorReadingFile(string arg0, string arg1) => WriteEvent(5001, arg0, arg1); @@ -713,7 +713,7 @@ partial class DiagnosticEventSource /// The 'NoTargetsFound' diagnostic. /// /// -/// No targets found +/// Fatal: No targets found /// [Event(5002, Message = "No targets found", Level = EventLevel.Critical)] public void NoTargetsFound() => WriteEvent(5002); @@ -722,7 +722,7 @@ partial class DiagnosticEventSource /// The 'FileFormatLimitationExceeded' diagnostic. /// /// -/// File format limitation exceeded: {arg0}. +/// Fatal: File format limitation exceeded: {arg0}. /// [Event(5003, Message = "File format limitation exceeded: {0}.", Level = EventLevel.Critical)] public void FileFormatLimitationExceeded(string arg0) => WriteEvent(5003, arg0); @@ -731,7 +731,7 @@ partial class DiagnosticEventSource /// The 'CannotSpecifyBothKeyFileAndContainer' diagnostic. /// /// -/// You cannot specify both a key file and container. +/// Fatal: You cannot specify both a key file and container. /// [Event(5004, Message = "You cannot specify both a key file and container.", Level = EventLevel.Critical)] public void CannotSpecifyBothKeyFileAndContainer() => WriteEvent(5004); @@ -740,7 +740,7 @@ partial class DiagnosticEventSource /// The 'DelaySignRequiresKey' diagnostic. /// /// -/// You cannot delay sign without a key file or container. +/// Fatal: You cannot delay sign without a key file or container. /// [Event(5005, Message = "You cannot delay sign without a key file or container.", Level = EventLevel.Critical)] public void DelaySignRequiresKey() => WriteEvent(5005); @@ -749,7 +749,7 @@ partial class DiagnosticEventSource /// The 'InvalidStrongNameKeyPair' diagnostic. /// /// -/// Invalid key {arg0} specified. ("{arg1}") +/// Fatal: Invalid key {arg0} specified. ("{arg1}") /// [Event(5006, Message = "Invalid key {0} specified. (\"{1}\")", Level = EventLevel.Critical)] public void InvalidStrongNameKeyPair(string arg0, string arg1) => WriteEvent(5006, arg0, arg1); @@ -758,7 +758,7 @@ partial class DiagnosticEventSource /// The 'ReferenceNotFound' diagnostic. /// /// -/// Reference not found: {arg0} +/// Fatal: Reference not found: {arg0} /// [Event(5007, Message = "Reference not found: {0}", Level = EventLevel.Critical)] public void ReferenceNotFound(string arg0) => WriteEvent(5007, arg0); @@ -767,7 +767,7 @@ partial class DiagnosticEventSource /// The 'OptionsMustPreceedChildLevels' diagnostic. /// /// -/// You can only specify options before any child levels. +/// Fatal: You can only specify options before any child levels. /// [Event(5008, Message = "You can only specify options before any child levels.", Level = EventLevel.Critical)] public void OptionsMustPreceedChildLevels() => WriteEvent(5008); @@ -776,7 +776,7 @@ partial class DiagnosticEventSource /// The 'UnrecognizedTargetType' diagnostic. /// /// -/// Invalid value '{arg0}' for -target option. +/// Fatal: Invalid value '{arg0}' for -target option. /// [Event(5009, Message = "Invalid value \'{0}\' for -target option.", Level = EventLevel.Critical)] public void UnrecognizedTargetType(string arg0) => WriteEvent(5009, arg0); @@ -785,7 +785,7 @@ partial class DiagnosticEventSource /// The 'UnrecognizedPlatform' diagnostic. /// /// -/// Invalid value '{arg0}' for -platform option. +/// Fatal: Invalid value '{arg0}' for -platform option. /// [Event(5010, Message = "Invalid value \'{0}\' for -platform option.", Level = EventLevel.Critical)] public void UnrecognizedPlatform(string arg0) => WriteEvent(5010, arg0); @@ -794,7 +794,7 @@ partial class DiagnosticEventSource /// The 'UnrecognizedApartment' diagnostic. /// /// -/// Invalid value '{arg0}' for -apartment option. +/// Fatal: Invalid value '{arg0}' for -apartment option. /// [Event(5011, Message = "Invalid value \'{0}\' for -apartment option.", Level = EventLevel.Critical)] public void UnrecognizedApartment(string arg0) => WriteEvent(5011, arg0); @@ -803,7 +803,7 @@ partial class DiagnosticEventSource /// The 'MissingFileSpecification' diagnostic. /// /// -/// Missing file specification for '{arg0}' option. +/// Fatal: Missing file specification for '{arg0}' option. /// [Event(5012, Message = "Missing file specification for \'{0}\' option.", Level = EventLevel.Critical)] public void MissingFileSpecification(string arg0) => WriteEvent(5012, arg0); @@ -812,7 +812,7 @@ partial class DiagnosticEventSource /// The 'PathTooLong' diagnostic. /// /// -/// Path too long: {arg0}. +/// Fatal: Path too long: {arg0}. /// [Event(5013, Message = "Path too long: {0}.", Level = EventLevel.Critical)] public void PathTooLong(string arg0) => WriteEvent(5013, arg0); @@ -821,7 +821,7 @@ partial class DiagnosticEventSource /// The 'PathNotFound' diagnostic. /// /// -/// Path not found: {arg0}. +/// Fatal: Path not found: {arg0}. /// [Event(5014, Message = "Path not found: {0}.", Level = EventLevel.Critical)] public void PathNotFound(string arg0) => WriteEvent(5014, arg0); @@ -830,7 +830,7 @@ partial class DiagnosticEventSource /// The 'InvalidPath' diagnostic. /// /// -/// Invalid path: {arg0}. +/// Fatal: Invalid path: {arg0}. /// [Event(5015, Message = "Invalid path: {0}.", Level = EventLevel.Critical)] public void InvalidPath(string arg0) => WriteEvent(5015, arg0); @@ -839,7 +839,7 @@ partial class DiagnosticEventSource /// The 'InvalidOptionSyntax' diagnostic. /// /// -/// Invalid option: {arg0}. +/// Fatal: Invalid option: {arg0}. /// [Event(5016, Message = "Invalid option: {0}.", Level = EventLevel.Critical)] public void InvalidOptionSyntax(string arg0) => WriteEvent(5016, arg0); @@ -848,7 +848,7 @@ partial class DiagnosticEventSource /// The 'ExternalResourceNotFound' diagnostic. /// /// -/// External resource file does not exist: {arg0}. +/// Fatal: External resource file does not exist: {arg0}. /// [Event(5017, Message = "External resource file does not exist: {0}.", Level = EventLevel.Critical)] public void ExternalResourceNotFound(string arg0) => WriteEvent(5017, arg0); @@ -857,7 +857,7 @@ partial class DiagnosticEventSource /// The 'ExternalResourceNameInvalid' diagnostic. /// /// -/// External resource file may not include path specification: {arg0}. +/// Fatal: External resource file may not include path specification: {arg0}. /// [Event(5018, Message = "External resource file may not include path specification: {0}.", Level = EventLevel.Critical)] public void ExternalResourceNameInvalid(string arg0) => WriteEvent(5018, arg0); @@ -866,7 +866,7 @@ partial class DiagnosticEventSource /// The 'InvalidVersionFormat' diagnostic. /// /// -/// Invalid version specified: {arg0}. +/// Fatal: Invalid version specified: {arg0}. /// [Event(5019, Message = "Invalid version specified: {0}.", Level = EventLevel.Critical)] public void InvalidVersionFormat(string arg0) => WriteEvent(5019, arg0); @@ -875,7 +875,7 @@ partial class DiagnosticEventSource /// The 'InvalidFileAlignment' diagnostic. /// /// -/// Invalid value '{arg0}' for -filealign option. +/// Fatal: Invalid value '{arg0}' for -filealign option. /// [Event(5020, Message = "Invalid value \'{0}\' for -filealign option.", Level = EventLevel.Critical)] public void InvalidFileAlignment(string arg0) => WriteEvent(5020, arg0); @@ -884,7 +884,7 @@ partial class DiagnosticEventSource /// The 'ErrorWritingFile' diagnostic. /// /// -/// Unable to write file: {arg0}. ({arg1}) +/// Fatal: Unable to write file: {arg0}. ({arg1}) /// [Event(5021, Message = "Unable to write file: {0}. ({1})", Level = EventLevel.Critical)] public void ErrorWritingFile(string arg0, string arg1) => WriteEvent(5021, arg0, arg1); @@ -893,7 +893,7 @@ partial class DiagnosticEventSource /// The 'UnrecognizedOption' diagnostic. /// /// -/// Unrecognized option: {arg0}. +/// Fatal: Unrecognized option: {arg0}. /// [Event(5022, Message = "Unrecognized option: {0}.", Level = EventLevel.Critical)] public void UnrecognizedOption(string arg0) => WriteEvent(5022, arg0); @@ -902,7 +902,7 @@ partial class DiagnosticEventSource /// The 'NoOutputFileSpecified' diagnostic. /// /// -/// No output file specified. +/// Fatal: No output file specified. /// [Event(5023, Message = "No output file specified.", Level = EventLevel.Critical)] public void NoOutputFileSpecified() => WriteEvent(5023); @@ -911,7 +911,7 @@ partial class DiagnosticEventSource /// The 'SharedClassLoaderCannotBeUsedOnModuleTarget' diagnostic. /// /// -/// Incompatible options: -target:module and -sharedclassloader cannot be combined. +/// Fatal: Incompatible options: -target:module and -sharedclassloader cannot be combined. /// [Event(5024, Message = "Incompatible options: -target:module and -sharedclassloader cannot be combined.", Level = EventLevel.Critical)] public void SharedClassLoaderCannotBeUsedOnModuleTarget() => WriteEvent(5024); @@ -920,7 +920,7 @@ partial class DiagnosticEventSource /// The 'RuntimeNotFound' diagnostic. /// /// -/// Unable to load runtime assembly. +/// Fatal: Unable to load runtime assembly. /// [Event(5025, Message = "Unable to load runtime assembly.", Level = EventLevel.Critical)] public void RuntimeNotFound() => WriteEvent(5025); @@ -929,7 +929,7 @@ partial class DiagnosticEventSource /// The 'MainClassRequiresExe' diagnostic. /// /// -/// Main class cannot be specified for library or module. +/// Fatal: Main class cannot be specified for library or module. /// [Event(5026, Message = "Main class cannot be specified for library or module.", Level = EventLevel.Critical)] public void MainClassRequiresExe() => WriteEvent(5026); @@ -938,7 +938,7 @@ partial class DiagnosticEventSource /// The 'ExeRequiresMainClass' diagnostic. /// /// -/// No main method found. +/// Fatal: No main method found. /// [Event(5027, Message = "No main method found.", Level = EventLevel.Critical)] public void ExeRequiresMainClass() => WriteEvent(5027); @@ -947,7 +947,7 @@ partial class DiagnosticEventSource /// The 'PropertiesRequireExe' diagnostic. /// /// -/// Properties cannot be specified for library or module. +/// Fatal: Properties cannot be specified for library or module. /// [Event(5028, Message = "Properties cannot be specified for library or module.", Level = EventLevel.Critical)] public void PropertiesRequireExe() => WriteEvent(5028); @@ -956,7 +956,7 @@ partial class DiagnosticEventSource /// The 'ModuleCannotHaveClassLoader' diagnostic. /// /// -/// Cannot specify assembly class loader for modules. +/// Fatal: Cannot specify assembly class loader for modules. /// [Event(5029, Message = "Cannot specify assembly class loader for modules.", Level = EventLevel.Critical)] public void ModuleCannotHaveClassLoader() => WriteEvent(5029); @@ -965,7 +965,7 @@ partial class DiagnosticEventSource /// The 'ErrorParsingMapFile' diagnostic. /// /// -/// Unable to parse remap file: {arg0}. ({arg1}) +/// Fatal: Unable to parse remap file: {arg0}. ({arg1}) /// [Event(5030, Message = "Unable to parse remap file: {0}. ({1})", Level = EventLevel.Critical)] public void ErrorParsingMapFile(string arg0, string arg1) => WriteEvent(5030, arg0, arg1); @@ -974,7 +974,7 @@ partial class DiagnosticEventSource /// The 'BootstrapClassesMissing' diagnostic. /// /// -/// Bootstrap classes missing and core assembly not found. +/// Fatal: Bootstrap classes missing and core assembly not found. /// [Event(5031, Message = "Bootstrap classes missing and core assembly not found.", Level = EventLevel.Critical)] public void BootstrapClassesMissing() => WriteEvent(5031); @@ -983,7 +983,7 @@ partial class DiagnosticEventSource /// The 'StrongNameRequiresStrongNamedRefs' diagnostic. /// /// -/// All referenced assemblies must be strong named, to be able to sign the output assembly. +/// Fatal: All referenced assemblies must be strong named, to be able to sign the output assembly. /// [Event(5032, Message = "All referenced assemblies must be strong named, to be able to sign the output ass" + "embly.", Level = EventLevel.Critical)] @@ -993,7 +993,7 @@ partial class DiagnosticEventSource /// The 'MainClassNotFound' diagnostic. /// /// -/// Main class not found. +/// Fatal: Main class not found. /// [Event(5033, Message = "Main class not found.", Level = EventLevel.Critical)] public void MainClassNotFound() => WriteEvent(5033); @@ -1002,7 +1002,7 @@ partial class DiagnosticEventSource /// The 'MainMethodNotFound' diagnostic. /// /// -/// Main method not found. +/// Fatal: Main method not found. /// [Event(5034, Message = "Main method not found.", Level = EventLevel.Critical)] public void MainMethodNotFound() => WriteEvent(5034); @@ -1011,7 +1011,7 @@ partial class DiagnosticEventSource /// The 'UnsupportedMainMethod' diagnostic. /// /// -/// Redirected main method not supported. +/// Fatal: Redirected main method not supported. /// [Event(5035, Message = "Redirected main method not supported.", Level = EventLevel.Critical)] public void UnsupportedMainMethod() => WriteEvent(5035); @@ -1020,7 +1020,7 @@ partial class DiagnosticEventSource /// The 'ExternalMainNotAccessible' diagnostic. /// /// -/// External main method must be public and in a public class. +/// Fatal: External main method must be public and in a public class. /// [Event(5036, Message = "External main method must be public and in a public class.", Level = EventLevel.Critical)] public void ExternalMainNotAccessible() => WriteEvent(5036); @@ -1029,7 +1029,7 @@ partial class DiagnosticEventSource /// The 'ClassLoaderNotFound' diagnostic. /// /// -/// Custom assembly class loader class not found. +/// Fatal: Custom assembly class loader class not found. /// [Event(5037, Message = "Custom assembly class loader class not found.", Level = EventLevel.Critical)] public void ClassLoaderNotFound() => WriteEvent(5037); @@ -1038,7 +1038,7 @@ partial class DiagnosticEventSource /// The 'ClassLoaderNotAccessible' diagnostic. /// /// -/// Custom assembly class loader class is not accessible. +/// Fatal: Custom assembly class loader class is not accessible. /// [Event(5038, Message = "Custom assembly class loader class is not accessible.", Level = EventLevel.Critical)] public void ClassLoaderNotAccessible() => WriteEvent(5038); @@ -1047,7 +1047,7 @@ partial class DiagnosticEventSource /// The 'ClassLoaderIsAbstract' diagnostic. /// /// -/// Custom assembly class loader class is abstract. +/// Fatal: Custom assembly class loader class is abstract. /// [Event(5039, Message = "Custom assembly class loader class is abstract.", Level = EventLevel.Critical)] public void ClassLoaderIsAbstract() => WriteEvent(5039); @@ -1056,7 +1056,7 @@ partial class DiagnosticEventSource /// The 'ClassLoaderNotClassLoader' diagnostic. /// /// -/// Custom assembly class loader class does not extend java.lang.ClassLoader. +/// Fatal: Custom assembly class loader class does not extend java.lang.ClassLoader. /// [Event(5040, Message = "Custom assembly class loader class does not extend java.lang.ClassLoader.", Level = EventLevel.Critical)] public void ClassLoaderNotClassLoader() => WriteEvent(5040); @@ -1065,7 +1065,7 @@ partial class DiagnosticEventSource /// The 'ClassLoaderConstructorMissing' diagnostic. /// /// -/// Custom assembly class loader constructor is missing. +/// Fatal: Custom assembly class loader constructor is missing. /// [Event(5041, Message = "Custom assembly class loader constructor is missing.", Level = EventLevel.Critical)] public void ClassLoaderConstructorMissing() => WriteEvent(5041); @@ -1074,7 +1074,7 @@ partial class DiagnosticEventSource /// The 'MapFileTypeNotFound' diagnostic. /// /// -/// Type '{arg0}' referenced in remap file was not found. +/// Fatal: Type '{arg0}' referenced in remap file was not found. /// [Event(5042, Message = "Type \'{0}\' referenced in remap file was not found.", Level = EventLevel.Critical)] public void MapFileTypeNotFound(string arg0) => WriteEvent(5042, arg0); @@ -1083,7 +1083,7 @@ partial class DiagnosticEventSource /// The 'MapFileClassNotFound' diagnostic. /// /// -/// Class '{arg0}' referenced in remap file was not found. +/// Fatal: Class '{arg0}' referenced in remap file was not found. /// [Event(5043, Message = "Class \'{0}\' referenced in remap file was not found.", Level = EventLevel.Critical)] public void MapFileClassNotFound(string arg0) => WriteEvent(5043, arg0); @@ -1092,7 +1092,7 @@ partial class DiagnosticEventSource /// The 'MaximumErrorCountReached' diagnostic. /// /// -/// Maximum error count reached. +/// Fatal: Maximum error count reached. /// [Event(5044, Message = "Maximum error count reached.", Level = EventLevel.Critical)] public void MaximumErrorCountReached() => WriteEvent(5044); @@ -1101,7 +1101,7 @@ partial class DiagnosticEventSource /// The 'LinkageError' diagnostic. /// /// -/// Link error: {arg0} +/// Fatal: Link error: {arg0} /// [Event(5045, Message = "Link error: {0}", Level = EventLevel.Critical)] public void LinkageError(string arg0) => WriteEvent(5045, arg0); @@ -1110,7 +1110,7 @@ partial class DiagnosticEventSource /// The 'RuntimeMismatch' diagnostic. /// /// -/// Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} +/// Fatal: Referenced assembly {referencedAssemblyPath} was compiled with an incompatible IKVM.Runtime version. Current runtime: {runtimeAssemblyName}. Referenced assembly runtime: {referencedAssemblyName} /// [Event(5046, Message = "Referenced assembly {0} was compiled with an incompatible IKVM.Runtime version. C" + "urrent runtime: {1}. Referenced assembly runtime: {2}", Level = EventLevel.Critical)] @@ -1120,7 +1120,7 @@ partial class DiagnosticEventSource /// The 'RuntimeMismatchStrongName' diagnostic. /// /// -/// +/// Fatal: /// [Event(5047, Message = "", Level = EventLevel.Critical)] public void RuntimeMismatchStrongName() => WriteEvent(5047); @@ -1129,7 +1129,7 @@ partial class DiagnosticEventSource /// The 'CoreClassesMissing' diagnostic. /// /// -/// Failed to find core classes in core library. +/// Fatal: Failed to find core classes in core library. /// [Event(5048, Message = "Failed to find core classes in core library.", Level = EventLevel.Critical)] public void CoreClassesMissing() => WriteEvent(5048); @@ -1138,7 +1138,7 @@ partial class DiagnosticEventSource /// The 'CriticalClassNotFound' diagnostic. /// /// -/// Unable to load critical class '{arg0}'. +/// Fatal: Unable to load critical class '{arg0}'. /// [Event(5049, Message = "Unable to load critical class \'{0}\'.", Level = EventLevel.Critical)] public void CriticalClassNotFound(string arg0) => WriteEvent(5049, arg0); @@ -1147,7 +1147,7 @@ partial class DiagnosticEventSource /// The 'AssemblyContainsDuplicateClassNames' diagnostic. /// /// -/// Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) +/// Fatal: Type '{arg0}' and '{arg1}' both map to the same name '{arg2}'. ({arg3}) /// [Event(5050, Message = "Type \'{0}\' and \'{1}\' both map to the same name \'{2}\'. ({3})", Level = EventLevel.Critical)] public void AssemblyContainsDuplicateClassNames(string arg0, string arg1, string arg2, string arg3) => WriteEvent(5050, arg0, arg1, arg2, arg3); @@ -1156,7 +1156,7 @@ partial class DiagnosticEventSource /// The 'CallerIDRequiresHasCallerIDAnnotation' diagnostic. /// /// -/// CallerID.getCallerID() requires a HasCallerID annotation. +/// Fatal: CallerID.getCallerID() requires a HasCallerID annotation. /// [Event(5051, Message = "CallerID.getCallerID() requires a HasCallerID annotation.", Level = EventLevel.Critical)] public void CallerIDRequiresHasCallerIDAnnotation() => WriteEvent(5051); @@ -1165,7 +1165,7 @@ partial class DiagnosticEventSource /// The 'UnableToResolveInterface' diagnostic. /// /// -/// Unable to resolve interface '{arg0}' on type '{arg1}'. +/// Fatal: Unable to resolve interface '{arg0}' on type '{arg1}'. /// [Event(5052, Message = "Unable to resolve interface \'{0}\' on type \'{1}\'.", Level = EventLevel.Critical)] public void UnableToResolveInterface(string arg0, string arg1) => WriteEvent(5052, arg0, arg1); @@ -1174,7 +1174,7 @@ partial class DiagnosticEventSource /// The 'MissingBaseType' diagnostic. /// /// -/// The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. +/// Fatal: The base class or interface '{arg0}' in assembly '{arg1}' referenced by type '{arg2}' in '{arg3}' could not be resolved. /// [Event(5053, Message = "The base class or interface \'{0}\' in assembly \'{1}\' referenced by type \'{2}\' in \'" + "{3}\' could not be resolved.", Level = EventLevel.Critical)] @@ -1184,7 +1184,7 @@ partial class DiagnosticEventSource /// The 'MissingBaseTypeReference' diagnostic. /// /// -/// The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. +/// Fatal: The type '{arg0}' is defined in an assembly that is not referenced. You must add a reference to assembly '{arg1}'. /// [Event(5054, Message = "The type \'{0}\' is defined in an assembly that is not referenced. You must add a r" + "eference to assembly \'{1}\'.", Level = EventLevel.Critical)] @@ -1194,7 +1194,7 @@ partial class DiagnosticEventSource /// The 'FileNotFound' diagnostic. /// /// -/// File not found: {arg0}. +/// Fatal: File not found: {arg0}. /// [Event(5055, Message = "File not found: {0}.", Level = EventLevel.Critical)] public void FileNotFound(string arg0) => WriteEvent(5055, arg0); @@ -1203,7 +1203,7 @@ partial class DiagnosticEventSource /// The 'RuntimeMethodMissing' diagnostic. /// /// -/// Runtime method '{arg0}' not found. +/// Fatal: Runtime method '{arg0}' not found. /// [Event(5056, Message = "Runtime method \'{0}\' not found.", Level = EventLevel.Critical)] public void RuntimeMethodMissing(string arg0) => WriteEvent(5056, arg0); @@ -1212,7 +1212,7 @@ partial class DiagnosticEventSource /// The 'MapFileFieldNotFound' diagnostic. /// /// -/// Field '{arg0}' referenced in remap file was not found in class '{arg1}'. +/// Fatal: Field '{arg0}' referenced in remap file was not found in class '{arg1}'. /// [Event(5057, Message = "Field \'{0}\' referenced in remap file was not found in class \'{1}\'.", Level = EventLevel.Critical)] public void MapFileFieldNotFound(string arg0, string arg1) => WriteEvent(5057, arg0, arg1); @@ -1221,7 +1221,7 @@ partial class DiagnosticEventSource /// The 'GhostInterfaceMethodMissing' diagnostic. /// /// -/// Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) +/// Fatal: Remapped class '{arg0}' does not implement ghost interface method. ({arg1}.{arg2}{arg3}) /// [Event(5058, Message = "Remapped class \'{0}\' does not implement ghost interface method. ({1}.{2}{3})", Level = EventLevel.Critical)] public void GhostInterfaceMethodMissing(string arg0, string arg1, string arg2, string arg3) => WriteEvent(5058, arg0, arg1, arg2, arg3); @@ -1230,7 +1230,7 @@ partial class DiagnosticEventSource /// The 'ModuleInitializerMethodRequirements' diagnostic. /// /// -/// Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. +/// Fatal: Method '{arg1}.{arg2}{arg3}' does not meet the requirements of a module initializer. /// [Event(5059, Message = "Method \'{0}.{1}{2}\' does not meet the requirements of a module initializer.", Level = EventLevel.Critical)] public void ModuleInitializerMethodRequirements(string arg1, string arg2, string arg3) => WriteEvent(5059, arg1, arg2, arg3); @@ -1239,7 +1239,7 @@ partial class DiagnosticEventSource /// The 'InvalidZip' diagnostic. /// /// -/// Invalid zip: {name}. +/// Fatal: Invalid zip: {name}. /// [Event(5060, Message = "Invalid zip: {0}.", Level = EventLevel.Critical)] public void InvalidZip(string name) => WriteEvent(5060, name); @@ -1248,7 +1248,7 @@ partial class DiagnosticEventSource /// The 'CoreAssemblyVersionMismatch' diagnostic. /// /// -/// Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. +/// Fatal: Unable to load assembly '{0}' as it depends on a higher version of {1} than the one currently loaded. /// [Event(5061, Message = "Unable to load assembly \'{-1}\' as it depends on a higher version of {-1} than the" + " one currently loaded.", Level = EventLevel.Critical)] @@ -1258,7 +1258,7 @@ partial class DiagnosticEventSource /// The 'GenericRuntimeTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// [Event(6000, Message = "{0}", Level = EventLevel.Verbose)] public void GenericRuntimeTrace(string arg0) => WriteEvent(6000, arg0); @@ -1267,7 +1267,7 @@ partial class DiagnosticEventSource /// The 'GenericJniTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// [Event(6001, Message = "{0}", Level = EventLevel.Verbose)] public void GenericJniTrace(string arg0) => WriteEvent(6001, arg0); @@ -1276,7 +1276,7 @@ partial class DiagnosticEventSource /// The 'GenericCompilerTrace' diagnostic. /// /// -/// {arg0} +/// Trace: {arg0} /// [Event(6002, Message = "{0}", Level = EventLevel.Verbose)] public void GenericCompilerTrace(string arg0) => WriteEvent(6002, arg0); diff --git a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt index 3e266cf33e..c689e2f47c 100644 --- a/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt +++ b/src/IKVM.CoreLib/Diagnostics/Tracing/DiagnosticEventSource.g.tt @@ -61,7 +61,7 @@ foreach (var kvp in DiagnosticFile.Read(Host.ResolvePath(Path.Combine("..", "Dia /// <#= desc #> /// /// -<#= Util.ToCommentString(kvp.Value.Message) #> +<#= Util.ToCommentString(kvp.Value) #> /// [Event(<#= kvp.Value.Id #>, Message = <#= Util.ToStringLiteral(string.Join("", message)) #>, Level = EventLevel.<#= level #>)] public void <#= kvp.Key #>(<#= string.Join(", ", argDecl) #>) => WriteEvent(<#= string.Join(", ", argList) #>); diff --git a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs index fab9546036..b14842d29f 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs @@ -7,12 +7,6 @@ interface ISymbolResolver { - /// - /// Gets the known core assembly. - /// - /// - IAssemblySymbol ResolveCoreAssembly(); - /// /// Resolves the named type from the core assembly. /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs index dcfdb68ad0..c582d13005 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs @@ -242,9 +242,7 @@ public void MarkLabel(ILabel loc) /// public void MarkSequencePoint(ISymbolDocumentWriter document, int startLine, int startColumn, int endLine, int endColumn) { -#if NETFRAMEWORK _il.MarkSequencePoint(document, startLine, startColumn, endLine, endColumn); -#endif } /// diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index a54bacb1fa..09ab282415 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -152,7 +152,7 @@ class AttributeHelper ITypeSymbol TypeOfConstantPoolAttribute => typeofConstantPoolAttribute ??= context.Resolver.ResolveRuntimeType(typeof(ConstantPoolAttribute).FullName); - ITypeSymbol TypeOfDebuggableAttribute => typeofDebuggableAttribute ??= context.Resolver.ResolveCoreType(typeof(DebuggableAttribute).FullName); + ITypeSymbol TypeOfDebuggableAttribute => typeofDebuggableAttribute ??= context.Resolver.ResolveSystemType(typeof(DebuggableAttribute).FullName); ITypeSymbol TypeOfCustomAssemblyClassLoaderAttribute => typeofCustomAssemblyClassLoaderAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.CustomAssemblyClassLoaderAttribute).FullName); @@ -179,7 +179,7 @@ object ParseValue(RuntimeClassLoader loader, RuntimeJavaType tw, string val) } else if (tw.IsUnloadable) { - throw new FatalCompilerErrorException(DiagnosticEvent.MapFileTypeNotFound(tw.Name)); + throw new DiagnosticEventException(DiagnosticEvent.MapFileTypeNotFound(tw.Name)); } else if (tw.TypeAsTBD.IsEnum) { @@ -374,8 +374,8 @@ ICustomAttributeBuilder GetEditorBrowsableNever() { if (editorBrowsableNever == null) { - var typeofEditorBrowsableAttribute = context.Resolver.ResolveType(typeof(EditorBrowsableAttribute).FullName); - var typeofEditorBrowsableState = context.Resolver.ResolveType(typeof(EditorBrowsableState).FullName); + var typeofEditorBrowsableAttribute = context.Resolver.ResolveSystemType(typeof(EditorBrowsableAttribute).FullName); + var typeofEditorBrowsableState = context.Resolver.ResolveSystemType(typeof(EditorBrowsableState).FullName); var ctor = typeofEditorBrowsableAttribute.GetConstructor([typeofEditorBrowsableState]); editorBrowsableNever = context.Resolver.Symbols.CreateCustomAttribute(ctor, [EditorBrowsableState.Never]); } @@ -385,13 +385,13 @@ ICustomAttributeBuilder GetEditorBrowsableNever() internal void SetCompilerGenerated(ITypeSymbolBuilder tb) { - compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); + compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); tb.SetCustomAttribute(compilerGeneratedAttribute); } internal void SetCompilerGenerated(IMethodBaseSymbolBuilder mb) { - compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); + compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); mb.SetCustomAttribute(compilerGeneratedAttribute); } @@ -412,25 +412,25 @@ internal void SetEditorBrowsableNever(IPropertySymbolBuilder pb) internal void SetDeprecatedAttribute(IMethodBaseSymbolBuilder mb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); mb.SetCustomAttribute(deprecatedAttribute); } internal void SetDeprecatedAttribute(ITypeSymbolBuilder tb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); tb.SetCustomAttribute(deprecatedAttribute); } internal void SetDeprecatedAttribute(IFieldSymbolBuilder fb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); fb.SetCustomAttribute(deprecatedAttribute); } internal void SetDeprecatedAttribute(IPropertySymbolBuilder pb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); + deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); pb.SetCustomAttribute(deprecatedAttribute); } @@ -438,7 +438,7 @@ internal void SetThrowsAttribute(IMethodBaseSymbolBuilder mb, string[] exception { if (exceptions != null && exceptions.Length != 0) { - throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); + throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor([context.Types.String.MakeArrayType()]); exceptions = UnicodeUtil.EscapeInvalidSurrogates(exceptions); mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(throwsAttribute, [exceptions])); } @@ -548,7 +548,7 @@ internal void SetImplementsAttribute(ITypeSymbolBuilder typeBuilder, RuntimeJava interfaces[i] = UnicodeUtil.EscapeInvalidSurrogates(ifaceWrappers[i].Name); if (implementsAttribute == null) - implementsAttribute = TypeOfImplementsAttribute.GetConstructor([context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]); + implementsAttribute = TypeOfImplementsAttribute.GetConstructor([context.Types.String.MakeArrayType()]); typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(implementsAttribute, [interfaces])); } @@ -1024,7 +1024,7 @@ internal AssemblyNameInfo[] GetInternalsVisibleToAttributes(IAssemblySymbol asse foreach (var cad in assembly.GetCustomAttributes()) { - if (cad.Constructor.DeclaringType == context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName)) + if (cad.Constructor.DeclaringType == context.Resolver.ResolveSystemType(typeof(InternalsVisibleToAttribute).FullName)) { try { diff --git a/src/IKVM.Runtime/BigEndianBinaryReader.cs b/src/IKVM.Runtime/BigEndianBinaryReader.cs index 826c4e215c..e58d009cb8 100644 --- a/src/IKVM.Runtime/BigEndianBinaryReader.cs +++ b/src/IKVM.Runtime/BigEndianBinaryReader.cs @@ -205,7 +205,7 @@ internal unsafe string ReadString(string classFile, int majorVersion) fixed (byte* p = buf.Slice(pos, len).Span) s = Encoding.ASCII.GetString(p, buf.Length); #else - var s = Encoding.ASCII.GetString(buf.Slice(pos, len).Span); + var s = Encoding.ASCII.GetString(buf.Slice(pos, len).Span); #endif pos += len; return s; diff --git a/src/IKVM.Runtime/BootstrapClassLoader.cs b/src/IKVM.Runtime/BootstrapClassLoader.cs index 758fab3740..a5cec2c115 100644 --- a/src/IKVM.Runtime/BootstrapClassLoader.cs +++ b/src/IKVM.Runtime/BootstrapClassLoader.cs @@ -39,7 +39,7 @@ sealed class BootstrapClassLoader : RuntimeAssemblyClassLoader /// Initializes a new instance. /// internal BootstrapClassLoader(RuntimeContext context) : - base(context, context.Resolver.ResolveBaseAssembly(), [typeof(object).Assembly.FullName, typeof(Uri).Assembly.FullName]) + base(context, context.Resolver.GetBaseAssembly(), [typeof(object).Assembly.FullName, typeof(Uri).Assembly.FullName]) { #if FIRST_PASS == false && IMPORTER == false && EXPORTER == false RegisterNativeLibrary(LibJava.Instance.Handle); diff --git a/src/IKVM.Runtime/ByteCodeHelper.cs b/src/IKVM.Runtime/ByteCodeHelper.cs index 337d16c351..07730aceac 100644 --- a/src/IKVM.Runtime/ByteCodeHelper.cs +++ b/src/IKVM.Runtime/ByteCodeHelper.cs @@ -630,7 +630,7 @@ private static bool IsPrimitiveArrayType(Type type) #if FIRST_PASS throw new NotImplementedException(); #else - return type.IsArray && IsPrimitiveArrayType(JVM.Context.Resolver.ImportType(type.GetElementType())); + return type.IsArray && IsPrimitiveArrayType(JVM.Context.Resolver.GetSymbol(type.GetElementType())); #endif } @@ -1049,7 +1049,7 @@ public static void InitializeModule(Module module) throw new ArgumentOutOfRangeException(); // check for InitializeModule method present on classloader - var classLoader = JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.ImportAssembly(asm)).GetJavaClassLoader(); + var classLoader = JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.GetSymbol(asm)).GetJavaClassLoader(); if (classLoader != null) { var init = (Action)Delegate.CreateDelegate(typeof(Action), classLoader, "InitializeModule", false, false); diff --git a/src/IKVM.Runtime/ByteCodeHelperMethods.cs b/src/IKVM.Runtime/ByteCodeHelperMethods.cs index fffd0b72bc..583021b745 100644 --- a/src/IKVM.Runtime/ByteCodeHelperMethods.cs +++ b/src/IKVM.Runtime/ByteCodeHelperMethods.cs @@ -172,7 +172,7 @@ static IMethodSymbol GetHelper(ITypeSymbol type, string method, ITypeSymbol[] pa var mi = parameters == null ? type.GetMethod(method) : type.GetMethod(method, parameters); if (mi == null) #if IMPORTER - throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeMethodMissing(method)); + throw new DiagnosticEventException(DiagnosticEvent.RuntimeMethodMissing(method)); #else throw new InternalException("Missing ByteCodeHelper method in runtime."); #endif diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index 4f0c6d73e9..a74869d2ce 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -61,11 +61,11 @@ public CodeEmitterFactory(RuntimeContext context) public IMethodSymbol VerboseCastFailureMethod => verboseCastFailure ??= JVM.SafeGetEnvironmentVariable("IKVM_VERBOSE_CAST") == null ? null : context.ByteCodeHelperMethods.VerboseCastFailure; - public IMethodSymbol MonitorEnterMethod => monitorEnter ??= context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); + public IMethodSymbol MonitorEnterMethod => monitorEnter ??= context.Resolver.ResolveSystemType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); - public IMethodSymbol MonitorExitMethod => monitorExit ??= context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); + public IMethodSymbol MonitorExitMethod => monitorExit ??= context.Resolver.ResolveSystemType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static, [context.Types.Object]); - public IMethodSymbol MemoryBarrierMethod => memoryBarrier ??= context.Resolver.ResolveType(typeof(System.Threading.Thread).FullName).GetMethod("MemoryBarrier", []); + public IMethodSymbol MemoryBarrierMethod => memoryBarrier ??= context.Resolver.ResolveSystemType(typeof(System.Threading.Thread).FullName).GetMethod("MemoryBarrier", []); public bool ExperimentalOptimizations = JVM.SafeGetEnvironmentVariable("IKVM_EXPERIMENTAL_OPTIMIZATIONS") != null; diff --git a/src/IKVM.Runtime/DynamicCallerIDProvider.cs b/src/IKVM.Runtime/DynamicCallerIDProvider.cs index a1ead52906..41b9eb6356 100644 --- a/src/IKVM.Runtime/DynamicCallerIDProvider.cs +++ b/src/IKVM.Runtime/DynamicCallerIDProvider.cs @@ -36,7 +36,10 @@ sealed class DynamicCallerIDProvider // method to be public without giving untrusted code the ability to forge a CallerID token internal static readonly DynamicCallerIDProvider Instance = new DynamicCallerIDProvider(); - private DynamicCallerIDProvider() { } + private DynamicCallerIDProvider() + { + + } internal ikvm.@internal.CallerID GetCallerID() { @@ -56,7 +59,7 @@ internal ikvm.@internal.CallerID GetCallerID() continue; } - var caller = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(method.DeclaringType); + var caller = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(method.DeclaringType)); return CreateCallerID(caller.Host ?? caller); } #endif diff --git a/src/IKVM.Runtime/ExceptionHelper.cs b/src/IKVM.Runtime/ExceptionHelper.cs index 20ab5b79a4..0cbf5dc621 100644 --- a/src/IKVM.Runtime/ExceptionHelper.cs +++ b/src/IKVM.Runtime/ExceptionHelper.cs @@ -381,7 +381,7 @@ int GetLineNumber(StackFrame frame) var mb = frame.GetMethod(); if (mb != null && mb.DeclaringType != null) { - var mbs = context.Resolver.ImportMethodBase(mb); + var mbs = context.Resolver.GetSymbol(mb); if (context.ClassLoaderFactory.IsRemappedType(mbs.DeclaringType)) return -1; @@ -399,7 +399,7 @@ string GetFileName(StackFrame frame) var mb = frame.GetMethod(); if (mb != null && mb.DeclaringType != null) { - var mbs = context.Resolver.ImportMethodBase(mb); + var mbs = context.Resolver.GetSymbol(mb); if (context.ClassLoaderFactory.IsRemappedType(mbs.DeclaringType)) return null; diff --git a/src/IKVM.Runtime/GhostTag.cs b/src/IKVM.Runtime/GhostTag.cs index 8bf1e289a1..c79e706c18 100644 --- a/src/IKVM.Runtime/GhostTag.cs +++ b/src/IKVM.Runtime/GhostTag.cs @@ -40,7 +40,7 @@ internal static void SetTag(object obj, RuntimeTypeHandle typeHandle) #if FIRST_PASS || IMPORTER throw new NotImplementedException(); #else - SetTag(obj, JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(Type.GetTypeFromHandle(typeHandle))); + SetTag(obj, JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(Type.GetTypeFromHandle(typeHandle)))); #endif } @@ -74,7 +74,7 @@ internal static bool IsGhostArrayInstance(object obj, RuntimeTypeHandle typeHand var tw1 = GhostTag.GetTag(obj); if (tw1 != null) { - var tw2 = tw1.Context.ClassLoaderFactory.GetJavaTypeFromType(Type.GetTypeFromHandle(typeHandle)).MakeArrayType(rank); + var tw2 = tw1.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(Type.GetTypeFromHandle(typeHandle))).MakeArrayType(rank); return tw1.IsAssignableTo(tw2); } diff --git a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs index c3ae1c1767..7a5874bc9c 100644 --- a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs +++ b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs @@ -29,94 +29,122 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// ISymbolContext Symbols { get; } + /// + /// Resolves the named type from any of the known System assemblies. + /// + /// + /// + ITypeSymbol? ResolveSystemType(string typeName); + /// /// Gets the known runtime assembly. /// /// - IAssemblySymbol ResolveRuntimeAssembly(); + IAssemblySymbol? GetRuntimeAssembly(); /// /// Resolves the named type from the IKVM runtime assembly. /// /// /// - ITypeSymbol ResolveRuntimeType(string typeName); + ITypeSymbol? ResolveRuntimeType(string typeName); /// /// Resolves the known Java base assembly. /// /// - IAssemblySymbol ResolveBaseAssembly(); + IAssemblySymbol? GetBaseAssembly(); /// /// Resolves the named type from the IKVM Java assembly. /// /// /// - ITypeSymbol ResolveBaseType(string typeName); + ITypeSymbol? ResolveBaseType(string typeName); /// /// Gets the associated with the specified assembly. /// /// /// - IAssemblySymbol ImportAssembly(Assembly assembly); + IAssemblySymbol GetSymbol(Assembly assembly); /// /// Gets the associated with the specified assembly. /// /// /// - IAssemblySymbolBuilder?ImportAssembly(AssemblyBuilder assembly); + IAssemblySymbolBuilder GetSymbol(AssemblyBuilder assembly); /// /// Gets the associated with the specified module. /// /// /// - IModuleSymbol ImportModule(Module module); + IModuleSymbol GetSymbol(Module module); /// /// Gets the associated with the specified module. /// /// /// - IModuleSymbolBuilder ImportModule(ModuleBuilder module); + IModuleSymbolBuilder GetSymbol(ModuleBuilder module); /// - /// Gets the associated with the specified type. + /// Gets the associated with the specified member. /// - /// + /// /// - ITypeSymbol ImportType(Type type); + IMemberSymbol GetSymbol(MemberInfo memberInfo); /// - /// Gets the associated with the specified member. + /// Gets the associated with the specified type. /// - /// + /// /// - IMemberSymbol ImportMember(MemberInfo memberInfo); + ITypeSymbol GetSymbol(Type type); /// /// Gets the associated with the specified method. /// /// /// - IMethodBaseSymbol ImportMethodBase(MethodBase type); + IMethodBaseSymbol GetSymbol(MethodBase type); /// - /// Gets the associated with the specified method. + /// Gets the associated with the specified constructor. /// /// /// - IConstructorSymbol ImportConstructor(ConstructorInfo ctor); + IConstructorSymbol GetSymbol(ConstructorInfo ctor); /// /// Gets the associated with the specified method. /// /// /// - IMethodSymbol ImportMethod(MethodInfo method); + IMethodSymbol GetSymbol(MethodInfo method); + + /// + /// Gets the associated with the specified field. + /// + /// + /// + IFieldSymbol GetSymbol(FieldInfo field); + + /// + /// Gets the associated with the specified property. + /// + /// + /// + IPropertySymbol GetSymbol(PropertyInfo property); + + /// + /// Gets the associated with the specified event. + /// + /// + /// + IEventSymbol GetSymbol(EventInfo @event); } diff --git a/src/IKVM.Runtime/JNI/JNIEnv.cs b/src/IKVM.Runtime/JNI/JNIEnv.cs index 51a0c46f15..6daad51be8 100644 --- a/src/IKVM.Runtime/JNI/JNIEnv.cs +++ b/src/IKVM.Runtime/JNI/JNIEnv.cs @@ -628,9 +628,9 @@ static nint AllocObjectImpl(JNIEnv* pEnv, RuntimeJavaType wrapper) wrapper.Finish(); #if NETFRAMEWORK - return pEnv->MakeLocalRef(FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType)); + return pEnv->MakeLocalRef(FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection())); #else - return pEnv->MakeLocalRef(RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType)); + return pEnv->MakeLocalRef(RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection())); #endif } catch (RetargetableJavaException e) @@ -709,7 +709,7 @@ static object InvokeHelper(JNIEnv* pEnv, nint objHandle, nint methodID, JValue* // possible with remapped types throw new NotSupportedException($"Remapped type {mw.DeclaringType.Name} doesn't support constructor invocation on an existing instance"); } - else if (!mb.DeclaringType.IsInstanceOfType(obj)) + else if (!mb.DeclaringType.AsReflection().IsInstanceOfType(obj)) { // we're trying to initialize an existing instance of a remapped type throw new NotSupportedException($"Unable to partially construct object of type {obj.GetType().FullName} to type {mb.DeclaringType.FullName}"); @@ -734,10 +734,10 @@ static object InvokeNonVirtual(JNIEnvContext env, RuntimeJavaMethod mw, object o if (mw.HasCallerID || mw.IsDynamicOnly) throw new NotSupportedException(); - if (mw.DeclaringType.IsRemapped && !mw.DeclaringType.TypeAsBaseType.IsInstanceOfType(obj)) + if (mw.DeclaringType.IsRemapped && !mw.DeclaringType.TypeAsBaseType.AsReflection().IsInstanceOfType(obj)) return mw.InvokeNonvirtualRemapped(obj, argarray); - var del = (Delegate)Activator.CreateInstance(mw.GetDelegateType(), new object[] { obj, mw.GetMethod().MethodHandle.GetFunctionPointer() }); + var del = (Delegate)Activator.CreateInstance(mw.GetDelegateType().AsReflection(), [obj, mw.GetMethod().AsReflection().MethodHandle.GetFunctionPointer()]); try { return del.DynamicInvoke(argarray); @@ -2157,7 +2157,7 @@ internal static nint NewObjectArray(JNIEnv* pEnv, jsize len, nint clazz, nint in try { // we want to support (non-primitive) value types so we can't cast to object[] - var a = Array.CreateInstance(RuntimeJavaType.FromClass((java.lang.Class)pEnv->UnwrapRef(clazz)).TypeAsArrayType, len); + var a = Array.CreateInstance(RuntimeJavaType.FromClass((java.lang.Class)pEnv->UnwrapRef(clazz)).TypeAsArrayType.AsReflection(), len); var o = pEnv->UnwrapRef(init); if (o != null) for (int i = 0; i < a.Length; i++) @@ -2776,7 +2776,7 @@ internal static jint RegisterNatives(JNIEnv* pEnv, nint clazz, JNINativeMethod* // don't allow dotted names! if (methodSig.IndexOf('.') < 0) - fi = wrapper.TypeAsTBD.GetField(METHOD_PTR_FIELD_PREFIX + methodName + methodSig, BindingFlags.Static | BindingFlags.NonPublic); + fi = wrapper.TypeAsTBD.GetField(METHOD_PTR_FIELD_PREFIX + methodName + methodSig, BindingFlags.Static | BindingFlags.NonPublic).AsReflection(); if (fi == null) { diff --git a/src/IKVM.Runtime/JVM.Internal.cs b/src/IKVM.Runtime/JVM.Internal.cs index 4d8c83ea92..543cf847f9 100644 --- a/src/IKVM.Runtime/JVM.Internal.cs +++ b/src/IKVM.Runtime/JVM.Internal.cs @@ -5,16 +5,6 @@ using IKVM.Runtime.Accessors.Java.Lang; using IKVM.Runtime.Vfs; -#if IMPORTER || EXPORTER -using IKVM.Reflection; -using Type = IKVM.Reflection.Type; -#else -#endif - -#if IMPORTER -using IKVM.Tools.Importer; -#endif - namespace IKVM.Runtime { @@ -34,8 +24,12 @@ internal static class Internal #if FIRST_PASS == false && IMPORTER == false && EXPORTER == false - internal static readonly RuntimeContextOptions contextOptions = new RuntimeContextOptions(); - internal static readonly RuntimeContext context = new RuntimeContext(contextOptions, DiagnosticEventSource.Instance, new Resolver(), false); +#if NETFRAMEWORK + internal static readonly RuntimeContextOptions contextOptions = new RuntimeContextOptions(dynamicAssemblySuffixAndPublicKey: RuntimeContextOptions.SignedDefaultDynamicAssemblySuffixAndPublicKey); +#else + internal static readonly RuntimeContextOptions contextOptions = new RuntimeContextOptions(dynamicAssemblySuffixAndPublicKey: RuntimeContextOptions.UnsignedDefaultDynamicAssemblySuffixAndPublicKey); +#endif + internal static readonly RuntimeContext context = new RuntimeContext(contextOptions, DiagnosticEventSource.Instance, new Resolver()); internal static readonly VfsTable vfs = VfsTable.BuildDefaultTable(new VfsRuntimeContext(context), Properties.HomePath); internal static readonly Lazy systemThreadGroup = new Lazy(() => ThreadGroupAccessor.Init()); internal static readonly Lazy mainThreadGroup = new Lazy(() => ThreadGroupAccessor.Init(null, SystemThreadGroup, "main")); @@ -44,7 +38,7 @@ internal static class Internal static ThreadGroupAccessor threadGroupAccessor; static SystemAccessor systemAccessor; - internal static AccessorCache BaseAccessors => AccessorCache.Get(ref baseAccessors, context.Resolver.ResolveBaseAssembly().AsReflection()); + internal static AccessorCache BaseAccessors => AccessorCache.Get(ref baseAccessors, context.Resolver.GetBaseAssembly().AsReflection()); internal static ThreadGroupAccessor ThreadGroupAccessor => BaseAccessors.Get(ref threadGroupAccessor); diff --git a/src/IKVM.Runtime/JVM.Properties.cs b/src/IKVM.Runtime/JVM.Properties.cs index b33ea8db21..c026416ed9 100644 --- a/src/IKVM.Runtime/JVM.Properties.cs +++ b/src/IKVM.Runtime/JVM.Properties.cs @@ -259,7 +259,7 @@ static void InitSystemProperties(Dictionary p) p["java.ext.dirs"] = Path.Combine(HomePath, "lib", "ext"); p["java.endorsed.dirs"] = Path.Combine(HomePath, "lib", "endorsed"); p["sun.boot.library.path"] = GetBootLibraryPath(); - p["sun.boot.class.path"] = VfsTable.GetAssemblyClassesPath(Vfs.Context, Context.Resolver.ResolveBaseAssembly().AsReflection(), HomePath); + p["sun.boot.class.path"] = VfsTable.GetAssemblyClassesPath(Vfs.Context, Context.Resolver.GetBaseAssembly().AsReflection(), HomePath); p["sun.cds.enableSharedLookupCache"] = "false"; // unlimited direct memory diff --git a/src/IKVM.Runtime/JVM.Resolver.cs b/src/IKVM.Runtime/JVM.Resolver.cs index 6174d0a9c2..188121ae76 100644 --- a/src/IKVM.Runtime/JVM.Resolver.cs +++ b/src/IKVM.Runtime/JVM.Resolver.cs @@ -4,15 +4,13 @@ using System.ComponentModel; using System.Linq; using System.Reflection; +using System.Reflection.Emit; using System.Runtime.CompilerServices; using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols.Reflection; -#if IMPORTER || EXPORTER -using Type = IKVM.Reflection.Type; -#endif - namespace IKVM.Runtime { @@ -31,7 +29,7 @@ internal class Resolver : IRuntimeSymbolResolver /// Gets the set of assemblies from which to load core types. /// /// - static IEnumerable GetCoreAssemblies() + static IEnumerable GetSystemAssemblies() { yield return typeof(object).Assembly; yield return typeof(RuntimeCompatibilityAttribute).Assembly; @@ -43,58 +41,206 @@ static IEnumerable GetCoreAssemblies() yield return typeof(Environment).Assembly; } - readonly static Assembly[] coreAssemblies = GetCoreAssemblies().Distinct().ToArray(); + readonly ReflectionSymbolContext _symbols = new(); + + IAssemblySymbol _coreAssembly; + readonly ConcurrentDictionary _coreTypeCache = new(); - readonly ReflectionSymbolContext _context = new(); - readonly IAssemblySymbol[] _coreAssemblies; - readonly ConcurrentDictionary _typeCache = new(); + IAssemblySymbol[] _systemAssemblies; + readonly ConcurrentDictionary _systemTypeCache = new(); + + IAssemblySymbol _runtimeAssembly; + readonly ConcurrentDictionary _runtimeTypeCache = new(); + + IAssemblySymbol _baseAssembly; + readonly ConcurrentDictionary _baseTypeCache = new(); /// /// Initializes a new instance. /// public Resolver() { - _coreAssemblies = coreAssemblies.Select(_context.GetOrCreateAssemblySymbol).ToArray(); + _systemAssemblies = GetSystemAssemblies().Distinct().ToArray().Select(GetSymbol).ToArray(); + _runtimeAssembly = GetSymbol(typeof(JVM).Assembly); } + /// + public ISymbolContext Symbols => _symbols; + /// public IAssemblySymbol ResolveAssembly(string assemblyName) { - return Assembly.Load(assemblyName) is { } a ? _context.GetOrCreateAssemblySymbol(a) : null; + return GetSymbol(Assembly.Load(assemblyName)); } /// - public IAssemblySymbol ResolveBaseAssembly() + public IAssemblySymbol GetCoreAssembly() { - return _context.GetOrCreateAssemblySymbol(typeof(java.lang.Object).Assembly); + return _coreAssembly ??= GetSymbol(typeof(object).Assembly); } /// public ITypeSymbol ResolveCoreType(string typeName) { - return _typeCache.GetOrAdd(typeName, ResolveCoreTypeImpl); + return _coreTypeCache.GetOrAdd(typeName, ResolveCoreTypeImpl); } + /// + /// Resolves the specified core type. + /// + /// + /// ITypeSymbol ResolveCoreTypeImpl(string typeName) { - // loop over core assemblies searching for type - foreach (var assembly in _coreAssemblies) + return _coreAssembly.GetType(typeName); + } + + /// + public ITypeSymbol ResolveSystemType(string typeName) + { + return _systemTypeCache.GetOrAdd(typeName, ResolveSystemTypeImpl); + } + + /// + /// Resolves the specified system type. + /// + /// + /// + ITypeSymbol ResolveSystemTypeImpl(string typeName) + { + foreach (var assembly in _systemAssemblies) if (assembly.GetType(typeName) is ITypeSymbol t) return t; return null; } + /// + public IAssemblySymbol GetRuntimeAssembly() + { + return _runtimeAssembly; + } + /// public ITypeSymbol ResolveRuntimeType(string typeName) { - return typeof(Resolver).Assembly.GetType(typeName) is { } t ? _context.GetOrCreateTypeSymbol(t) : null; + return _runtimeTypeCache.GetOrAdd(typeName, ResolveRuntimeTypeImpl); + } + + /// + /// Resolves the specified system type. + /// + /// + /// + ITypeSymbol ResolveRuntimeTypeImpl(string typeName) + { + return _runtimeAssembly.GetType(typeName); + } + + /// + public IAssemblySymbol GetBaseAssembly() + { + return _baseAssembly; + } + + /// + public ITypeSymbol ResolveBaseType(string typeName) + { + return _baseAssembly.GetType(typeName); + } + + /// + public ITypeSymbol ResolveType(string typeName) + { + foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies()) + if (assembly.GetType(typeName) is Type t) + return GetSymbol(t); + + return null; + } + + /// + public IAssemblySymbol GetSymbol(Assembly assembly) + { + return _symbols.GetOrCreateAssemblySymbol(assembly); + } + + /// + public IAssemblySymbolBuilder GetSymbol(AssemblyBuilder assembly) + { + return _symbols.GetOrCreateAssemblySymbol(assembly); + } + + /// + public IModuleSymbol GetSymbol(Module module) + { + return _symbols.GetOrCreateModuleSymbol(module); + } + + /// + public IModuleSymbolBuilder GetSymbol(ModuleBuilder module) + { + return _symbols.GetOrCreateModuleSymbol(module); + } + + /// + public ITypeSymbol GetSymbol(Type type) + { + return _symbols.GetOrCreateTypeSymbol(type); + } + + /// + public IMemberSymbol GetSymbol(MemberInfo member) + { + return member switch + { + MethodBase method => GetSymbol(method), + FieldInfo field => GetSymbol(field), + PropertyInfo property => GetSymbol(property), + EventInfo @event => GetSymbol(@event), + _ => throw new InvalidOperationException(), + }; + } + + /// + public IMethodBaseSymbol GetSymbol(MethodBase method) + { + return method switch + { + ConstructorInfo ctor => GetSymbol(ctor), + MethodInfo mi => GetSymbol(mi), + _ => throw new InvalidOperationException(), + }; + } + + /// + public IConstructorSymbol GetSymbol(ConstructorInfo ctor) + { + return _symbols.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IMethodSymbol GetSymbol(MethodInfo method) + { + return _symbols.GetOrCreateMethodSymbol(method); + } + + /// + public IFieldSymbol GetSymbol(FieldInfo field) + { + return _symbols.GetOrCreateFieldSymbol(field); + } + + /// + public IPropertySymbol GetSymbol(PropertyInfo property) + { + return _symbols.GetOrCreatePropertySymbol(property); } /// - public ITypeSymbol ImportType(Type type) + public IEventSymbol GetSymbol(EventInfo @event) { - return type is { } t ? _context.GetOrCreateTypeSymbol(t) : null; + return _symbols.GetOrCreateEventSymbol(@event); } } diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs index b8735c4d1d..6dc9ffc64e 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs @@ -50,7 +50,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, return ghostType; var t = o.GetType(); - var ts = context.Resolver.ImportType(t); + var ts = context.Resolver.GetSymbol(t); if (t.IsPrimitive || context.ClassLoaderFactory.IsRemappedType(ts) && !ts.IsSealed) return context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts); @@ -73,7 +73,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, throw new NotImplementedException(); #else var t = Type.GetTypeFromHandle(handle); - var ts = JVM.Context.Resolver.ImportType(t); + var ts = JVM.Context.Resolver.GetSymbol(t); if (t.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || t == typeof(void)) return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).ClassObject; @@ -94,7 +94,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, throw new NotImplementedException(); #else var t = Type.GetTypeFromHandle(handle); - var ts = JVM.Context.Resolver.ImportType(t); + var ts = JVM.Context.Resolver.GetSymbol(t); if (ts.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || ts == typeof(void)) return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).MakeArrayType(rank).ClassObject; @@ -114,7 +114,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, #if FIRST_PASS throw new NotImplementedException(); #else - var ts = JVM.Context.Resolver.ImportType(type); + var ts = JVM.Context.Resolver.GetSymbol(type); int rank = 0; while (ReflectUtil.IsVector(ts)) diff --git a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs index 22ba987616..abe35f9526 100644 --- a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs +++ b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs @@ -21,9 +21,9 @@ Jeroen Frijters jeroen@frijters.net */ -using System; -using System.Reflection; using IKVM.Runtime; +using IKVM.CoreLib.Symbols; + #if !NO_REF_EMIT using System.Reflection.Emit; @@ -177,41 +177,46 @@ public static bool hasStaticInitializer(global::java.lang.Class cl) #if !FIRST_PASS && !NO_REF_EMIT - private sealed class FastFieldReflector : global::ikvm.@internal.FieldReflectorBase + sealed class FastFieldReflector : global::ikvm.@internal.FieldReflectorBase { - private static readonly MethodInfo ReadByteMethod = typeof(IOHelpers).GetMethod("ReadByte"); - private static readonly MethodInfo ReadBooleanMethod = typeof(IOHelpers).GetMethod("ReadBoolean"); - private static readonly MethodInfo ReadCharMethod = typeof(IOHelpers).GetMethod("ReadChar"); - private static readonly MethodInfo ReadShortMethod = typeof(IOHelpers).GetMethod("ReadShort"); - private static readonly MethodInfo ReadIntMethod = typeof(IOHelpers).GetMethod("ReadInt"); - private static readonly MethodInfo ReadFloatMethod = typeof(IOHelpers).GetMethod("ReadFloat"); - private static readonly MethodInfo ReadLongMethod = typeof(IOHelpers).GetMethod("ReadLong"); - private static readonly MethodInfo ReadDoubleMethod = typeof(IOHelpers).GetMethod("ReadDouble"); - private static readonly MethodInfo WriteByteMethod = typeof(IOHelpers).GetMethod("WriteByte"); - private static readonly MethodInfo WriteBooleanMethod = typeof(IOHelpers).GetMethod("WriteBoolean"); - private static readonly MethodInfo WriteCharMethod = typeof(IOHelpers).GetMethod("WriteChar"); - private static readonly MethodInfo WriteShortMethod = typeof(IOHelpers).GetMethod("WriteShort"); - private static readonly MethodInfo WriteIntMethod = typeof(IOHelpers).GetMethod("WriteInt"); - private static readonly MethodInfo WriteFloatMethod = typeof(IOHelpers).GetMethod("WriteFloat"); - private static readonly MethodInfo WriteLongMethod = typeof(IOHelpers).GetMethod("WriteLong"); - private static readonly MethodInfo WriteDoubleMethod = typeof(IOHelpers).GetMethod("WriteDouble"); - private delegate void ObjFieldGetterSetter(object obj, object[] objarr); - private delegate void PrimFieldGetterSetter(object obj, byte[] objarr); - private static readonly ObjFieldGetterSetter objDummy = new ObjFieldGetterSetter(Dummy); - private static readonly PrimFieldGetterSetter primDummy = new PrimFieldGetterSetter(Dummy); - private global::java.io.ObjectStreamField[] fields; - private ObjFieldGetterSetter objFieldGetter; - private PrimFieldGetterSetter primFieldGetter; - private ObjFieldGetterSetter objFieldSetter; - private PrimFieldGetterSetter primFieldSetter; - - private static void Dummy(object obj, object[] objarr) + delegate void ObjFieldGetterSetter(object obj, object[] objarr); + delegate void PrimFieldGetterSetter(object obj, byte[] objarr); + + static readonly IMethodSymbol ReadByteMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadByte")); + static readonly IMethodSymbol ReadBooleanMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadBoolean")); + static readonly IMethodSymbol ReadCharMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadChar")); + static readonly IMethodSymbol ReadShortMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadShort")); + static readonly IMethodSymbol ReadIntMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadInt")); + static readonly IMethodSymbol ReadFloatMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadFloat")); + static readonly IMethodSymbol ReadLongMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadLong")); + static readonly IMethodSymbol ReadDoubleMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("ReadDouble")); + static readonly IMethodSymbol WriteByteMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteByte")); + static readonly IMethodSymbol WriteBooleanMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteBoolean")); + static readonly IMethodSymbol WriteCharMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteChar")); + static readonly IMethodSymbol WriteShortMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteShort")); + static readonly IMethodSymbol WriteIntMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteInt")); + static readonly IMethodSymbol WriteFloatMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteFloat")); + static readonly IMethodSymbol WriteLongMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteLong")); + static readonly IMethodSymbol WriteDoubleMethod = JVM.Context.Resolver.GetSymbol(typeof(IOHelpers).GetMethod("WriteDouble")); + + static readonly ObjFieldGetterSetter objDummy = new ObjFieldGetterSetter(Dummy); + static readonly PrimFieldGetterSetter primDummy = new PrimFieldGetterSetter(Dummy); + + global::java.io.ObjectStreamField[] fields; + ObjFieldGetterSetter objFieldGetter; + PrimFieldGetterSetter primFieldGetter; + ObjFieldGetterSetter objFieldSetter; + PrimFieldGetterSetter primFieldSetter; + + static void Dummy(object obj, object[] objarr) { + } - private static void Dummy(object obj, byte[] barr) + static void Dummy(object obj, byte[] barr) { + } internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) @@ -220,7 +225,7 @@ internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) RuntimeJavaType tw = null; foreach (global::java.io.ObjectStreamField field in fields) { - RuntimeJavaField fw = GetFieldWrapper(field); + var fw = GetFieldWrapper(field); if (fw != null) { if (tw == null) @@ -234,6 +239,7 @@ internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) } } } + if (tw == null) { objFieldGetter = objFieldSetter = objDummy; @@ -250,10 +256,10 @@ internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) throw x.ToJava(); } - var dmObjGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType, true, null, new Type[] { typeof(object), typeof(object[]) }); - var dmPrimGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType, true, null, new Type[] { typeof(object), typeof(byte[]) }); - var dmObjSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType, true, null, new Type[] { typeof(object), typeof(object[]) }); - var dmPrimSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType, true, null, new Type[] { typeof(object), typeof(byte[]) }); + var dmObjGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(object[])]); + var dmPrimGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(byte[])]); + var dmObjSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(object[])]); + var dmPrimSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(byte[])]); var ilgenObjGetter = JVM.Context.CodeEmitterFactory.Create(dmObjGetter); var ilgenPrimGetter = JVM.Context.CodeEmitterFactory.Create(dmPrimGetter); var ilgenObjSetter = JVM.Context.CodeEmitterFactory.Create(dmObjSetter); @@ -272,13 +278,12 @@ internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) foreach (global::java.io.ObjectStreamField field in fields) { - RuntimeJavaField fw = GetFieldWrapper(field); + var fw = GetFieldWrapper(field); if (fw == null) - { continue; - } + fw.ResolveField(); - RuntimeJavaType fieldType = fw.FieldTypeWrapper; + var fieldType = fw.FieldTypeWrapper; try { fieldType = fieldType.EnsureLoadable(tw.ClassLoader); @@ -288,6 +293,7 @@ internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) { throw x.ToJava(); } + if (fieldType.IsPrimitive) { // Getter diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs index cab514262d..e7c9d49e86 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs @@ -72,7 +72,7 @@ static class Class var type = Type.GetType(name); if (type != null) - tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.ImportType(type)); + tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(type)); if (tw == null) { diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs b/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs index ce41e7611b..e98641d5fb 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs @@ -48,7 +48,7 @@ static void LazyInitSystemPackages() if (systemPackages == null) { var dict = new Dictionary(); - var path = Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, JVM.Context.Resolver.ResolveBaseAssembly().AsReflection(), JVM.Properties.HomePath), "resources.jar"); + var path = Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, JVM.Context.Resolver.GetBaseAssembly().AsReflection(), JVM.Properties.HomePath), "resources.jar"); foreach (var pkgs in JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().GetPackageInfo()) foreach (var pkg in pkgs.Value) dict[pkg.Replace('.', '/') + "/"] = path; diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Proxy.cs b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Proxy.cs index e7d5bade40..9b4827c764 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Proxy.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Proxy.cs @@ -41,42 +41,34 @@ public static object defineClass0(global::java.lang.ClassLoader classLoader, str #if FIRST_PASS throw new NotImplementedException(); #else - RuntimeAssemblyClassLoader acl = JVM.Context.ClassLoaderFactory.GetClassLoaderWrapper(classLoader) as RuntimeAssemblyClassLoader; + var acl = JVM.Context.ClassLoaderFactory.GetClassLoaderWrapper(classLoader) as RuntimeAssemblyClassLoader; if (acl == null) - { return null; - } - RuntimeJavaType[] wrappers = new RuntimeJavaType[interfaces.Length]; + + var wrappers = new RuntimeJavaType[interfaces.Length]; for (int i = 0; i < wrappers.Length; i++) - { wrappers[i] = RuntimeJavaType.FromClass(interfaces[i]); - } + // TODO support multi assembly class loaders - Type type = acl.MainAssembly.GetType(TypeNameUtil.GetProxyName(wrappers)); + var type = acl.MainAssembly.GetType(TypeNameUtil.GetProxyName(wrappers)); if (type == null) - { return null; - } - RuntimeJavaType tw = JVM.Context.ManagedByteCodeJavaTypeFactory.newInstance(proxyName, type); - RuntimeJavaType tw2 = acl.RegisterInitiatingLoader(tw); + + var tw = JVM.Context.ManagedByteCodeJavaTypeFactory.newInstance(proxyName, type); + var tw2 = acl.RegisterInitiatingLoader(tw); if (tw != tw2) - { return null; - } + // we need to explicitly register the type, because the type isn't visible by normal means JVM.Context.ClassLoaderFactory.SetWrapperForType(type, tw); - RuntimeJavaType[] wrappers2 = tw.Interfaces; + var wrappers2 = tw.Interfaces; if (wrappers.Length != wrappers.Length) - { return null; - } + for (int i = 0; i < wrappers.Length; i++) - { if (wrappers[i] != wrappers2[i]) - { return null; - } - } + return tw.ClassObject; #endif } diff --git a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs index 3997dd1f83..ab9c1a1b17 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs @@ -31,6 +31,7 @@ Jeroen Frijters using System.Runtime.Serialization; using System.Security; +using IKVM.CoreLib.Symbols; using IKVM.Runtime; using IKVM.Runtime.Accessors.Java.Lang; using IKVM.Runtime.Util.Java.Security; @@ -261,7 +262,7 @@ sealed class SerializationConstructorAccessorImpl : global::sun.reflect.Construc { readonly RuntimeJavaMethod mw; - readonly Type type; + readonly ITypeSymbol type; /// /// Initializes a new instance. @@ -285,9 +286,9 @@ internal SerializationConstructorAccessorImpl(global::java.lang.reflect.Construc public object newInstance(object[] args) { #if NETFRAMEWORK - var obj = FormatterServices.GetUninitializedObject(type); + var obj = FormatterServices.GetUninitializedObject(type.AsReflection()); #else - var obj = RuntimeHelpers.GetUninitializedObject(type); + var obj = RuntimeHelpers.GetUninitializedObject(type.AsReflection()); #endif if (mw != null) mw.Invoke(obj, ConvertArgs(mw.DeclaringType.ClassLoader, mw.GetParameters(), args)); @@ -302,38 +303,38 @@ public object newInstance(object[] args) sealed class BoxUtil { - static readonly MethodInfo valueOfByte = typeof(global::java.lang.Byte).GetMethod("valueOf", new Type[] { typeof(byte) }); - static readonly MethodInfo valueOfBoolean = typeof(global::java.lang.Boolean).GetMethod("valueOf", new Type[] { typeof(bool) }); - static readonly MethodInfo valueOfChar = typeof(global::java.lang.Character).GetMethod("valueOf", new Type[] { typeof(char) }); - static readonly MethodInfo valueOfShort = typeof(global::java.lang.Short).GetMethod("valueOf", new Type[] { typeof(short) }); - static readonly MethodInfo valueOfInt = typeof(global::java.lang.Integer).GetMethod("valueOf", new Type[] { typeof(int) }); - static readonly MethodInfo valueOfFloat = typeof(global::java.lang.Float).GetMethod("valueOf", new Type[] { typeof(float) }); - static readonly MethodInfo valueOfLong = typeof(global::java.lang.Long).GetMethod("valueOf", new Type[] { typeof(long) }); - static readonly MethodInfo valueOfDouble = typeof(global::java.lang.Double).GetMethod("valueOf", new Type[] { typeof(double) }); - static readonly MethodInfo byteValue = typeof(global::java.lang.Byte).GetMethod("byteValue", []); - static readonly MethodInfo booleanValue = typeof(global::java.lang.Boolean).GetMethod("booleanValue", []); - static readonly MethodInfo charValue = typeof(global::java.lang.Character).GetMethod("charValue", []); - static readonly MethodInfo shortValue = typeof(global::java.lang.Short).GetMethod("shortValue", []); - static readonly MethodInfo intValue = typeof(global::java.lang.Integer).GetMethod("intValue", []); - static readonly MethodInfo floatValue = typeof(global::java.lang.Float).GetMethod("floatValue", []); - static readonly MethodInfo longValue = typeof(global::java.lang.Long).GetMethod("longValue", []); - static readonly MethodInfo doubleValue = typeof(global::java.lang.Double).GetMethod("doubleValue", []); + static readonly IMethodSymbol valueOfByte = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Byte)).GetMethod("valueOf", [JVM.Context.Types.Byte]); + static readonly IMethodSymbol valueOfBoolean = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Boolean)).GetMethod("valueOf", [JVM.Context.Types.Boolean]); + static readonly IMethodSymbol valueOfChar = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Character)).GetMethod("valueOf", [JVM.Context.Types.Char]); + static readonly IMethodSymbol valueOfShort = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Short)).GetMethod("valueOf", [JVM.Context.Types.Int16]); + static readonly IMethodSymbol valueOfInt = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Integer)).GetMethod("valueOf", [JVM.Context.Types.Int32]); + static readonly IMethodSymbol valueOfFloat = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Float)).GetMethod("valueOf", [JVM.Context.Types.Single]); + static readonly IMethodSymbol valueOfLong = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Long)).GetMethod("valueOf", [JVM.Context.Types.Int64]); + static readonly IMethodSymbol valueOfDouble = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Double)).GetMethod("valueOf", [JVM.Context.Types.Double]); + static readonly IMethodSymbol byteValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Byte)).GetMethod("byteValue", []); + static readonly IMethodSymbol booleanValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Boolean)).GetMethod("booleanValue", []); + static readonly IMethodSymbol charValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Character)).GetMethod("charValue", []); + static readonly IMethodSymbol shortValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Short)).GetMethod("shortValue", []); + static readonly IMethodSymbol intValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Integer)).GetMethod("intValue", []); + static readonly IMethodSymbol floatValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Float)).GetMethod("floatValue", []); + static readonly IMethodSymbol longValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Long)).GetMethod("longValue", []); + static readonly IMethodSymbol doubleValue = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Double)).GetMethod("doubleValue", []); internal static void EmitUnboxArg(CodeEmitter ilgen, RuntimeJavaType type) { if (type == ilgen.Context.PrimitiveJavaTypeFactory.BYTE) { - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Byte)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Byte))); ilgen.Emit(OpCodes.Call, byteValue); } else if (type == ilgen.Context.PrimitiveJavaTypeFactory.BOOLEAN) { - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Boolean)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Boolean))); ilgen.Emit(OpCodes.Call, booleanValue); } else if (type == ilgen.Context.PrimitiveJavaTypeFactory.CHAR) { - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Character)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Character))); ilgen.Emit(OpCodes.Call, charValue); } else if (type == ilgen.Context.PrimitiveJavaTypeFactory.SHORT @@ -343,10 +344,10 @@ internal static void EmitUnboxArg(CodeEmitter ilgen, RuntimeJavaType type) || type == ilgen.Context.PrimitiveJavaTypeFactory.DOUBLE) { ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, typeof(global::java.lang.Byte)); + ilgen.Emit(OpCodes.Isinst, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Byte))); CodeEmitterLabel next = ilgen.DefineLabel(); ilgen.EmitBrfalse(next); - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Byte)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Byte))); ilgen.Emit(OpCodes.Call, byteValue); ilgen.Emit(OpCodes.Conv_I1); Expand(ilgen, type); @@ -355,77 +356,77 @@ internal static void EmitUnboxArg(CodeEmitter ilgen, RuntimeJavaType type) ilgen.MarkLabel(next); if (type == ilgen.Context.PrimitiveJavaTypeFactory.SHORT) { - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Short)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Short))); ilgen.Emit(OpCodes.Call, shortValue); } else { ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, typeof(global::java.lang.Short)); + ilgen.Emit(OpCodes.Isinst, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Short))); next = ilgen.DefineLabel(); ilgen.EmitBrfalse(next); - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Short)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Short))); ilgen.Emit(OpCodes.Call, shortValue); Expand(ilgen, type); ilgen.EmitBr(done); ilgen.MarkLabel(next); ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, typeof(global::java.lang.Character)); + ilgen.Emit(OpCodes.Isinst, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Character))); next = ilgen.DefineLabel(); ilgen.EmitBrfalse(next); - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Character)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Character))); ilgen.Emit(OpCodes.Call, charValue); Expand(ilgen, type); ilgen.EmitBr(done); ilgen.MarkLabel(next); if (type == ilgen.Context.PrimitiveJavaTypeFactory.INT) { - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Integer)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Integer))); ilgen.Emit(OpCodes.Call, intValue); } else { ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, typeof(global::java.lang.Integer)); + ilgen.Emit(OpCodes.Isinst, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Integer))); next = ilgen.DefineLabel(); ilgen.EmitBrfalse(next); - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Integer)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Integer))); ilgen.Emit(OpCodes.Call, intValue); Expand(ilgen, type); ilgen.EmitBr(done); ilgen.MarkLabel(next); if (type == ilgen.Context.PrimitiveJavaTypeFactory.LONG) { - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Long)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Long))); ilgen.Emit(OpCodes.Call, longValue); } else { ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, typeof(global::java.lang.Long)); + ilgen.Emit(OpCodes.Isinst, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Long))); next = ilgen.DefineLabel(); ilgen.EmitBrfalse(next); - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Long)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Long))); ilgen.Emit(OpCodes.Call, longValue); Expand(ilgen, type); ilgen.EmitBr(done); ilgen.MarkLabel(next); if (type == ilgen.Context.PrimitiveJavaTypeFactory.FLOAT) { - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Float)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Float))); ilgen.Emit(OpCodes.Call, floatValue); } else if (type == ilgen.Context.PrimitiveJavaTypeFactory.DOUBLE) { ilgen.Emit(OpCodes.Dup); - ilgen.Emit(OpCodes.Isinst, typeof(global::java.lang.Float)); + ilgen.Emit(OpCodes.Isinst, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Float))); next = ilgen.DefineLabel(); ilgen.EmitBrfalse(next); - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Float)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Float))); ilgen.Emit(OpCodes.Call, floatValue); ilgen.EmitBr(done); ilgen.MarkLabel(next); - ilgen.Emit(OpCodes.Castclass, typeof(global::java.lang.Double)); + ilgen.Emit(OpCodes.Castclass, JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.Double))); ilgen.Emit(OpCodes.Call, doubleValue); } else @@ -506,13 +507,13 @@ static void Expand(CodeEmitter ilgen, RuntimeJavaType type) sealed class FastMethodAccessorImpl : global::sun.reflect.MethodAccessor { - internal static readonly ConstructorInfo nullPointerExceptionCtor; - internal static readonly ConstructorInfo nullPointerExceptionWithMessageCtor; - internal static readonly ConstructorInfo illegalArgumentExceptionCtor; - internal static readonly ConstructorInfo illegalArgumentExceptionWithMessageCtor; - internal static readonly ConstructorInfo illegalArgumentExceptionWithMessageAndCauseCtor; - internal static readonly ConstructorInfo illegalArgumentExceptionWithCauseCtor; - internal static readonly ConstructorInfo invocationTargetExceptionWithCauseCtor; + internal static readonly IConstructorSymbol nullPointerExceptionCtor; + internal static readonly IConstructorSymbol nullPointerExceptionWithMessageCtor; + internal static readonly IConstructorSymbol illegalArgumentExceptionCtor; + internal static readonly IConstructorSymbol illegalArgumentExceptionWithMessageCtor; + internal static readonly IConstructorSymbol illegalArgumentExceptionWithMessageAndCauseCtor; + internal static readonly IConstructorSymbol illegalArgumentExceptionWithCauseCtor; + internal static readonly IConstructorSymbol invocationTargetExceptionWithCauseCtor; delegate object Invoker(object obj, object[] args, global::ikvm.@internal.CallerID callerID); Invoker invoker; @@ -522,13 +523,13 @@ sealed class FastMethodAccessorImpl : global::sun.reflect.MethodAccessor /// static FastMethodAccessorImpl() { - nullPointerExceptionCtor = typeof(global::java.lang.NullPointerException).GetConstructor([]); - nullPointerExceptionWithMessageCtor = typeof(global::java.lang.NullPointerException).GetConstructor(new[] { typeof(string) }); - illegalArgumentExceptionCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor([]); - illegalArgumentExceptionWithMessageCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor(new[] { typeof(string) }); - illegalArgumentExceptionWithMessageAndCauseCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor(new[] { typeof(string), typeof(Exception) }); - illegalArgumentExceptionWithCauseCtor = typeof(global::java.lang.IllegalArgumentException).GetConstructor(new[] { typeof(Exception) }); - invocationTargetExceptionWithCauseCtor = typeof(global::java.lang.reflect.InvocationTargetException).GetConstructor(new[] { typeof(Exception) }); + nullPointerExceptionCtor = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.NullPointerException)).GetConstructor([]); + nullPointerExceptionWithMessageCtor = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.NullPointerException)).GetConstructor([JVM.Context.Types.String]); + illegalArgumentExceptionCtor = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.IllegalArgumentException)).GetConstructor([]); + illegalArgumentExceptionWithMessageCtor = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.IllegalArgumentException)).GetConstructor([JVM.Context.Types.String]); + illegalArgumentExceptionWithMessageAndCauseCtor = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.IllegalArgumentException)).GetConstructor([JVM.Context.Types.String, JVM.Context.Types.Exception]); + illegalArgumentExceptionWithCauseCtor = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.IllegalArgumentException)).GetConstructor([JVM.Context.Types.Exception]); + invocationTargetExceptionWithCauseCtor = JVM.Context.Resolver.GetSymbol(typeof(global::java.lang.reflect.InvocationTargetException)).GetConstructor([JVM.Context.Types.Exception]); } sealed class RunClassInit @@ -586,7 +587,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) // generate new dynamic method var np = !mw.IsPublic || !mw.DeclaringType.IsPublic; - var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsBaseType, np, typeof(object), new[] { typeof(object), typeof(object[]), typeof(global::ikvm.@internal.CallerID) }); + var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsBaseType.AsReflection(), np, typeof(object), new[] { typeof(object), typeof(object[]), typeof(global::ikvm.@internal.CallerID) }); var il = JVM.Context.CodeEmitterFactory.Create(dm); // labels @@ -614,7 +615,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) il.MarkLabel(endIsNullLabel); // temporary variables - var e = il.AllocTempLocal(typeof(Exception)); + var e = il.AllocTempLocal(il.Context.Types.Exception); // cast target to appropriate type var endConvSelf = il.DefineLabel(); @@ -626,7 +627,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) il.EmitLeave(endConvSelf); // catch InvalidCastException, store, add message, and wrap with IllegalArgumentException - il.BeginCatchBlock(typeof(InvalidCastException)); + il.BeginCatchBlock(il.Context.Resolver.GetSymbol(typeof(InvalidCastException))); il.Emit(OpCodes.Stloc, e); il.Emit(OpCodes.Ldstr, "object is not an instance of declaring class"); il.Emit(OpCodes.Ldloc, e); @@ -634,7 +635,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) il.Emit(OpCodes.Throw); // catch Exception, wrap with IllegalArgumentException - il.BeginCatchBlock(typeof(Exception)); + il.BeginCatchBlock(il.Context.Types.Exception); il.Emit(OpCodes.Newobj, illegalArgumentExceptionWithCauseCtor); il.Emit(OpCodes.Throw); @@ -685,7 +686,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) var o = p[n++] = il.AllocTempLocal(tw.TypeAsSignatureType); // temporary variable for exceptions - var e = il.AllocTempLocal(typeof(Exception)); + var e = il.AllocTempLocal(il.Context.Types.Exception); // load and convert argument var endConvArgn = il.DefineLabel(); @@ -699,7 +700,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) il.EmitLeave(endConvArgn); // catch InvalidCastException, store, add message, and wrap with IllegalArgumentException - il.BeginCatchBlock(typeof(InvalidCastException)); + il.BeginCatchBlock(il.Context.Resolver.GetSymbol(typeof(InvalidCastException))); il.Emit(OpCodes.Stloc, e); il.Emit(OpCodes.Ldstr, $"argument type mismatch on parameter {i}"); il.Emit(OpCodes.Ldloc, e); @@ -707,7 +708,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) il.Emit(OpCodes.Throw); // catch Exception, wrap with IllegalArgumentException - il.BeginCatchBlock(typeof(Exception)); + il.BeginCatchBlock(il.Context.Types.Exception); il.Emit(OpCodes.Stloc, e); il.Emit(OpCodes.Ldstr, $"exception on parameter {i}"); il.Emit(OpCodes.Ldloc, e); @@ -721,7 +722,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) } // storage for return value - var rt = il.AllocTempLocal(typeof(object)); + var rt = il.AllocTempLocal(il.Context.Types.Object); // call method and convert result il.BeginExceptionBlock(); @@ -758,7 +759,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) il.EmitLeave(postLabel); // catch exception from call and wrap - il.BeginCatchBlock(typeof(Exception)); + il.BeginCatchBlock(il.Context.Types.Exception); il.Emit(OpCodes.Ldc_I4_0); il.Emit(OpCodes.Call, il.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(il.Context.Types.Exception)); il.Emit(OpCodes.Newobj, invocationTargetExceptionWithCauseCtor); @@ -830,7 +831,7 @@ internal FastConstructorAccessorImpl(global::java.lang.reflect.Constructor const // resolve the runtime method info mw.ResolveMethod(); var np = !mw.IsPublic || !mw.DeclaringType.IsPublic; - var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsTBD, np, typeof(object), new[] { typeof(object[]) }); + var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsTBD.AsReflection(), np, typeof(object), new[] { typeof(object[]) }); var il = JVM.Context.CodeEmitterFactory.Create(dm); // labels @@ -881,7 +882,7 @@ internal FastConstructorAccessorImpl(global::java.lang.reflect.Constructor const var o = p[n++] = il.AllocTempLocal(tw.TypeAsSignatureType); // temporary variable for exceptions - var e = il.AllocTempLocal(typeof(Exception)); + var e = il.AllocTempLocal(il.Context.Types.Exception); // load and convert argument var endConvArgn = il.DefineLabel(); @@ -895,7 +896,7 @@ internal FastConstructorAccessorImpl(global::java.lang.reflect.Constructor const il.EmitLeave(endConvArgn); // catch InvalidCastException, store, add message, and wrap with IllegalArgumentException - il.BeginCatchBlock(typeof(InvalidCastException)); + il.BeginCatchBlock(il.Context.Resolver.GetSymbol(typeof(InvalidCastException))); il.Emit(OpCodes.Stloc, e); il.Emit(OpCodes.Ldstr, $"argument type mismatch on parameter {i}"); il.Emit(OpCodes.Ldloc, e); @@ -903,7 +904,7 @@ internal FastConstructorAccessorImpl(global::java.lang.reflect.Constructor const il.Emit(OpCodes.Throw); // catch Exception, wrap with IllegalArgumentException - il.BeginCatchBlock(typeof(Exception)); + il.BeginCatchBlock(il.Context.Types.Exception); il.Emit(OpCodes.Stloc, e); il.Emit(OpCodes.Ldstr, $"exception on parameter {i}"); il.Emit(OpCodes.Ldloc, e); @@ -927,13 +928,13 @@ internal FastConstructorAccessorImpl(global::java.lang.reflect.Constructor const } // call constructor - var rt = il.AllocTempLocal(typeof(object)); + var rt = il.AllocTempLocal(il.Context.Types.Object); mw.EmitNewobj(il); il.Emit(OpCodes.Stloc, rt); il.EmitLeave(postLabel); // catch exception from call and wrap - il.BeginCatchBlock(typeof(Exception)); + il.BeginCatchBlock(il.Context.Types.Exception); il.Emit(OpCodes.Ldc_I4_0); il.Emit(OpCodes.Call, il.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(il.Context.Types.Exception)); il.Emit(OpCodes.Newobj, FastMethodAccessorImpl.invocationTargetExceptionWithCauseCtor); @@ -975,28 +976,29 @@ public object newInstance(object[] args) sealed class FastSerializationConstructorAccessorImpl : global::sun.reflect.ConstructorAccessor { - static readonly MethodInfo GetTypeFromHandleMethod = typeof(Type).GetMethod(nameof(Type.GetTypeFromHandle), new[] { typeof(RuntimeTypeHandle) }); + static readonly IMethodSymbol GetTypeFromHandleMethod = JVM.Context.Types.Type.GetMethod(nameof(Type.GetTypeFromHandle), [JVM.Context.Types.RuntimeTypeHandle]); #if NETFRAMEWORK - static readonly MethodInfo GetUninitializedObjectMethod = typeof(FormatterServices).GetMethod(nameof(FormatterServices.GetUninitializedObject), new[] { typeof(Type) }); + static readonly IMethodSymbol GetUninitializedObjectMethod = JVM.Context.Resolver.GetSymbol(typeof(FormatterServices)).GetMethod(nameof(FormatterServices.GetUninitializedObject), [JVM.Context.Types.Type]); #else - static readonly MethodInfo GetUninitializedObjectMethod = typeof(RuntimeHelpers).GetMethod(nameof(RuntimeHelpers.GetUninitializedObject), new[] { typeof(Type) }); + static readonly IMethodSymbol GetUninitializedObjectMethod = JVM.Context.Resolver.GetSymbol(typeof(RuntimeHelpers)).GetMethod(nameof(RuntimeHelpers.GetUninitializedObject), [JVM.Context.Types.Type]); #endif + delegate object InvokeCtor(); InvokeCtor invoker; internal FastSerializationConstructorAccessorImpl(global::java.lang.reflect.Constructor constructorToCall, global::java.lang.Class classToInstantiate) { - RuntimeJavaMethod constructor = RuntimeJavaMethod.FromExecutable(constructorToCall); + var constructor = RuntimeJavaMethod.FromExecutable(constructorToCall); if (constructor.GetParameters().Length != 0) - { throw new NotImplementedException("Serialization constructor cannot have parameters"); - } + constructor.Link(); constructor.ResolveMethod(); - Type type; + + ITypeSymbol type; try { - RuntimeJavaType wrapper = RuntimeJavaType.FromClass(classToInstantiate); + var wrapper = RuntimeJavaType.FromClass(classToInstantiate); wrapper.Finish(); type = wrapper.TypeAsBaseType; } @@ -1004,15 +1006,16 @@ internal FastSerializationConstructorAccessorImpl(global::java.lang.reflect.Cons { throw x.ToJava(); } - DynamicMethod dm = DynamicMethodUtil.Create("__", constructor.DeclaringType.TypeAsBaseType, true, typeof(object), null); - CodeEmitter ilgen = JVM.Context.CodeEmitterFactory.Create(dm); - ilgen.Emit(OpCodes.Ldtoken, type); - ilgen.Emit(OpCodes.Call, GetTypeFromHandleMethod); - ilgen.Emit(OpCodes.Call, GetUninitializedObjectMethod); - ilgen.Emit(OpCodes.Dup); - constructor.EmitCall(ilgen); - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); + + var dm = DynamicMethodUtil.Create("__", constructor.DeclaringType.TypeAsBaseType.AsReflection(), true, typeof(object), null); + var il = JVM.Context.CodeEmitterFactory.Create(dm); + il.Emit(OpCodes.Ldtoken, type); + il.Emit(OpCodes.Call, GetTypeFromHandleMethod); + il.Emit(OpCodes.Call, GetUninitializedObjectMethod); + il.Emit(OpCodes.Dup); + constructor.EmitCall(il); + il.Emit(OpCodes.Ret); + il.DoEmit(); invoker = (InvokeCtor)dm.CreateDelegate(typeof(InvokeCtor)); } @@ -1035,7 +1038,7 @@ public object newInstance(object[] args) sealed class ActivatorConstructorAccessor : global::sun.reflect.ConstructorAccessor { - private readonly Type type; + readonly ITypeSymbol type; internal ActivatorConstructorAccessor(RuntimeJavaMethod mw) { @@ -1049,7 +1052,7 @@ public object newInstance(object[] objarr) try { - return Activator.CreateInstance(type); + return Activator.CreateInstance(type.AsReflection()); } catch (TargetInvocationException x) { @@ -1316,7 +1319,7 @@ private T lazyGet(object obj) { throw GetIllegalArgumentException(obj); } - else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.IsInstanceOfType(obj)) + else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.AsReflection().IsInstanceOfType(obj)) { throw GetUnsupportedRemappedFieldException(obj); } @@ -1361,7 +1364,7 @@ private void lazySet(object obj, T value) { throw SetIllegalArgumentException(obj); } - else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.IsInstanceOfType(obj)) + else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.AsReflection().IsInstanceOfType(obj)) { throw GetUnsupportedRemappedFieldException(obj); } @@ -2049,9 +2052,11 @@ protected sealed override object JavaBox(object value) } #if !NO_REF_EMIT + private Delegate GenerateFastGetter(Type delegateType, Type fieldType, RuntimeJavaField fw) { RuntimeJavaType fieldTypeWrapper; + try { fieldTypeWrapper = fw.FieldTypeWrapper.EnsureLoadable(fw.DeclaringType.ClassLoader); @@ -2062,36 +2067,38 @@ private Delegate GenerateFastGetter(Type delegateType, Type fieldType, RuntimeJa { throw x.ToJava(); } + fw.ResolveField(); - DynamicMethod dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType, !fw.IsPublic || !fw.DeclaringType.IsPublic, fieldType, new Type[] { typeof(IReflectionException), typeof(object), typeof(object) }); - CodeEmitter ilgen = JVM.Context.CodeEmitterFactory.Create(dm); + + var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.AsReflection(), !fw.IsPublic || !fw.DeclaringType.IsPublic, fieldType, [typeof(IReflectionException), typeof(object), typeof(object)]); + var il = JVM.Context.CodeEmitterFactory.Create(dm); if (fw.IsStatic) { - fw.EmitGet(ilgen); - fieldTypeWrapper.EmitConvSignatureTypeToStackType(ilgen); + fw.EmitGet(il); + fieldTypeWrapper.EmitConvSignatureTypeToStackType(il); } else { - ilgen.BeginExceptionBlock(); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Castclass, fw.DeclaringType.TypeAsBaseType); - fw.EmitGet(ilgen); - fieldTypeWrapper.EmitConvSignatureTypeToStackType(ilgen); - CodeEmitterLocal local = ilgen.DeclareLocal(fieldType); - ilgen.Emit(OpCodes.Stloc, local); - CodeEmitterLabel label = ilgen.DefineLabel(); - ilgen.EmitLeave(label); - ilgen.BeginCatchBlock(typeof(InvalidCastException)); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Callvirt, typeof(IReflectionException).GetMethod("GetIllegalArgumentException")); - ilgen.Emit(OpCodes.Throw); - ilgen.EndExceptionBlock(); - ilgen.MarkLabel(label); - ilgen.Emit(OpCodes.Ldloc, local); - } - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); + il.BeginExceptionBlock(); + il.Emit(OpCodes.Ldarg_1); + il.Emit(OpCodes.Castclass, fw.DeclaringType.TypeAsBaseType); + fw.EmitGet(il); + fieldTypeWrapper.EmitConvSignatureTypeToStackType(il); + CodeEmitterLocal local = il.DeclareLocal(il.Context.Resolver.GetSymbol(fieldType)); + il.Emit(OpCodes.Stloc, local); + CodeEmitterLabel label = il.DefineLabel(); + il.EmitLeave(label); + il.BeginCatchBlock(il.Context.Resolver.GetSymbol(typeof(InvalidCastException))); + il.Emit(OpCodes.Ldarg_0); + il.Emit(OpCodes.Ldarg_1); + il.Emit(OpCodes.Callvirt, il.Context.Resolver.GetSymbol(typeof(IReflectionException)).GetMethod("GetIllegalArgumentException")); + il.Emit(OpCodes.Throw); + il.EndExceptionBlock(); + il.MarkLabel(label); + il.Emit(OpCodes.Ldloc, local); + } + il.Emit(OpCodes.Ret); + il.DoEmit(); return dm.CreateDelegate(delegateType, this); } @@ -2108,58 +2115,59 @@ private Delegate GenerateFastSetter(Type delegateType, Type fieldType, RuntimeJa { throw x.ToJava(); } + fw.ResolveField(); - DynamicMethod dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType, !fw.IsPublic || !fw.DeclaringType.IsPublic, null, new Type[] { typeof(IReflectionException), typeof(object), fieldType, typeof(object) }); - CodeEmitter ilgen = JVM.Context.CodeEmitterFactory.Create(dm); + + var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.AsReflection(), !fw.IsPublic || !fw.DeclaringType.IsPublic, null, [typeof(IReflectionException), typeof(object), fieldType, typeof(object)]); + var il = JVM.Context.CodeEmitterFactory.Create(dm); if (fw.IsStatic) { if (fieldType == typeof(object)) { - ilgen.BeginExceptionBlock(); - ilgen.Emit(OpCodes.Ldarg_2); - fieldTypeWrapper.EmitCheckcast(ilgen); - fieldTypeWrapper.EmitConvStackTypeToSignatureType(ilgen, null); - fw.EmitSet(ilgen); - CodeEmitterLabel label = ilgen.DefineLabel(); - ilgen.EmitLeave(label); - ilgen.BeginCatchBlock(typeof(InvalidCastException)); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Callvirt, typeof(IReflectionException).GetMethod("SetIllegalArgumentException")); - ilgen.Emit(OpCodes.Throw); - ilgen.EndExceptionBlock(); - ilgen.MarkLabel(label); + il.BeginExceptionBlock(); + il.Emit(OpCodes.Ldarg_2); + fieldTypeWrapper.EmitCheckcast(il); + fieldTypeWrapper.EmitConvStackTypeToSignatureType(il, null); + fw.EmitSet(il); + CodeEmitterLabel label = il.DefineLabel(); + il.EmitLeave(label); + il.BeginCatchBlock(il.Context.Resolver.GetSymbol(typeof(InvalidCastException))); + il.Emit(OpCodes.Ldarg_0); + il.Emit(OpCodes.Ldarg_1); + il.Emit(OpCodes.Callvirt, il.Context.Resolver.GetSymbol(typeof(IReflectionException)).GetMethod("SetIllegalArgumentException")); + il.Emit(OpCodes.Throw); + il.EndExceptionBlock(); + il.MarkLabel(label); } else { - ilgen.Emit(OpCodes.Ldarg_2); - fw.EmitSet(ilgen); + il.Emit(OpCodes.Ldarg_2); + fw.EmitSet(il); } } else { - ilgen.BeginExceptionBlock(); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Castclass, fw.DeclaringType.TypeAsBaseType); - ilgen.Emit(OpCodes.Ldarg_2); + il.BeginExceptionBlock(); + il.Emit(OpCodes.Ldarg_1); + il.Emit(OpCodes.Castclass, fw.DeclaringType.TypeAsBaseType); + il.Emit(OpCodes.Ldarg_2); if (fieldType == typeof(object)) - { - fieldTypeWrapper.EmitCheckcast(ilgen); - } - fieldTypeWrapper.EmitConvStackTypeToSignatureType(ilgen, null); - fw.EmitSet(ilgen); - CodeEmitterLabel label = ilgen.DefineLabel(); - ilgen.EmitLeave(label); - ilgen.BeginCatchBlock(typeof(InvalidCastException)); - ilgen.Emit(OpCodes.Ldarg_0); - ilgen.Emit(OpCodes.Ldarg_1); - ilgen.Emit(OpCodes.Callvirt, typeof(IReflectionException).GetMethod("SetIllegalArgumentException")); - ilgen.Emit(OpCodes.Throw); - ilgen.EndExceptionBlock(); - ilgen.MarkLabel(label); - } - ilgen.Emit(OpCodes.Ret); - ilgen.DoEmit(); + fieldTypeWrapper.EmitCheckcast(il); + + fieldTypeWrapper.EmitConvStackTypeToSignatureType(il, null); + fw.EmitSet(il); + var label = il.DefineLabel(); + il.EmitLeave(label); + il.BeginCatchBlock(il.Context.Resolver.GetSymbol(typeof(InvalidCastException))); + il.Emit(OpCodes.Ldarg_0); + il.Emit(OpCodes.Ldarg_1); + il.Emit(OpCodes.Callvirt, il.Context.Resolver.GetSymbol(typeof(IReflectionException)).GetMethod("SetIllegalArgumentException")); + il.Emit(OpCodes.Throw); + il.EndExceptionBlock(); + il.MarkLabel(label); + } + il.Emit(OpCodes.Ret); + il.DoEmit(); return dm.CreateDelegate(delegateType, this); } #endif // !NO_REF_EMIT diff --git a/src/IKVM.Runtime/MethodAnalyzer.cs b/src/IKVM.Runtime/MethodAnalyzer.cs index b6a1652c05..65643053b1 100644 --- a/src/IKVM.Runtime/MethodAnalyzer.cs +++ b/src/IKVM.Runtime/MethodAnalyzer.cs @@ -2856,37 +2856,27 @@ private RuntimeJavaType SigTypeToClassName(RuntimeJavaType type, RuntimeJavaType private int AllocErrorMessage(string message) { - if (errorMessages == null) - { - errorMessages = new List(); - } - int index = errorMessages.Count; + errorMessages ??= []; + var index = errorMessages.Count; errorMessages.Add(message); return index; } - private string CheckLoaderConstraints(ClassFile.ConstantPoolItemMI cpi, RuntimeJavaMethod mw) + string CheckLoaderConstraints(ClassFile.ConstantPoolItemMI cpi, RuntimeJavaMethod mw) { -#if NETFRAMEWORK if (cpi.GetRetType() != mw.ReturnType && !cpi.GetRetType().IsUnloadable && !mw.ReturnType.IsUnloadable) -#else - if (cpi.GetRetType() != mw.ReturnType && cpi.GetRetType().Name != mw.ReturnType.Name && !cpi.GetRetType().IsUnloadable && !mw.ReturnType.IsUnloadable) -#endif { #if IMPORTER StaticCompiler.LinkageError("Method \"{2}.{3}{4}\" has a return type \"{0}\" instead of type \"{1}\" as expected by \"{5}\"", mw.ReturnType, cpi.GetRetType(), cpi.GetClassType().Name, cpi.Name, cpi.Signature, classFile.Name); #endif return "Loader constraints violated (return type): " + mw.DeclaringType.Name + "." + mw.Name + mw.Signature; } - RuntimeJavaType[] here = cpi.GetArgTypes(); - RuntimeJavaType[] there = mw.GetParameters(); + + var here = cpi.GetArgTypes(); + var there = mw.GetParameters(); for (int i = 0; i < here.Length; i++) { -#if NETFRAMEWORK if (here[i] != there[i] && !here[i].IsUnloadable && !there[i].IsUnloadable) -#else - if (here[i] != there[i] && here[i].Name != there[i].Name && !here[i].IsUnloadable && !there[i].IsUnloadable) -#endif { #if IMPORTER StaticCompiler.LinkageError("Method \"{2}.{3}{4}\" has a argument type \"{0}\" instead of type \"{1}\" as expected by \"{5}\"", there[i], here[i], cpi.GetClassType().Name, cpi.Name, cpi.Signature, classFile.Name); @@ -2903,9 +2893,7 @@ ClassFile.ConstantPoolItemInvokeDynamic GetInvokeDynamic(int index) { var item = classFile.GetInvokeDynamic(new InvokeDynamicConstantHandle(checked((ushort)index))); if (item != null) - { return item; - } } catch (OverflowException) { diff --git a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs index d44636cb65..d3fd060a55 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs @@ -28,13 +28,15 @@ Jeroen Frijters using System.Reflection.Emit; using System.Runtime.CompilerServices; +using IKVM.CoreLib.Symbols; + namespace IKVM.Runtime { partial class MethodHandleUtil { - internal Type GetMemberWrapperDelegateType(global::java.lang.invoke.MethodType type) + internal ITypeSymbol GetMemberWrapperDelegateType(global::java.lang.invoke.MethodType type) { #if FIRST_PASS throw new NotImplementedException(); @@ -45,7 +47,7 @@ internal Type GetMemberWrapperDelegateType(global::java.lang.invoke.MethodType t #if FIRST_PASS == false - Type CreateMethodHandleDelegateType(java.lang.invoke.MethodType type) + ITypeSymbol CreateMethodHandleDelegateType(java.lang.invoke.MethodType type) { var args = new RuntimeJavaType[type.parameterCount()]; for (int i = 0; i < args.Length; i++) @@ -58,20 +60,20 @@ Type CreateMethodHandleDelegateType(java.lang.invoke.MethodType type) return CreateMethodHandleDelegateType(args, ret); } - static Type[] GetParameterTypes(MethodBase mb) + static ITypeSymbol[] GetParameterTypes(IMethodBaseSymbol mb) { var pi = mb.GetParameters(); - var args = new Type[pi.Length]; + var args = new ITypeSymbol[pi.Length]; for (int i = 0; i < args.Length; i++) args[i] = pi[i].ParameterType; return args; } - internal static Type[] GetParameterTypes(Type thisType, MethodBase mb) + internal static ITypeSymbol[] GetParameterTypes(ITypeSymbol thisType, IMethodBaseSymbol mb) { var pi = mb.GetParameters(); - var args = new Type[pi.Length + 1]; + var args = new ITypeSymbol[pi.Length + 1]; args[0] = thisType; for (int i = 1; i < args.Length; i++) args[i] = pi[i - 1].ParameterType; @@ -79,7 +81,7 @@ internal static Type[] GetParameterTypes(Type thisType, MethodBase mb) return args; } - internal java.lang.invoke.MethodType GetDelegateMethodType(Type type) + internal java.lang.invoke.MethodType GetDelegateMethodType(ITypeSymbol type) { java.lang.Class[] types; var mi = GetDelegateInvokeMethod(type); @@ -124,13 +126,13 @@ internal sealed class DynamicMethodBuilder readonly RuntimeContext context; readonly java.lang.invoke.MethodType type; readonly int firstArg; - readonly Type delegateType; + readonly ITypeSymbol delegateType; readonly object firstBoundValue; readonly object secondBoundValue; - readonly Type container; + readonly ITypeSymbol container; readonly DynamicMethod dm; readonly CodeEmitter ilgen; - readonly Type packedArgType; + readonly ITypeSymbol packedArgType; readonly int packedArgPos; sealed class Container @@ -159,7 +161,7 @@ public Container(T1 target, T2 value) /// /// /// - DynamicMethodBuilder(RuntimeContext context, string name, java.lang.invoke.MethodType type, Type container, object target, object value, Type owner, bool useBasicTypes) + DynamicMethodBuilder(RuntimeContext context, string name, java.lang.invoke.MethodType type, ITypeSymbol container, object target, object value, ITypeSymbol owner, bool useBasicTypes) { this.context = context ?? throw new ArgumentNullException(nameof(context)); this.type = type; @@ -171,7 +173,7 @@ public Container(T1 target, T2 value) var mi = context.MethodHandleUtil.GetDelegateInvokeMethod(delegateType); - Type[] paramTypes; + ITypeSymbol[] paramTypes; if (container != null) { firstArg = 1; @@ -180,17 +182,17 @@ public Container(T1 target, T2 value) else if (target != null) { firstArg = 1; - paramTypes = GetParameterTypes(target.GetType(), mi); + paramTypes = GetParameterTypes(context.Resolver.GetSymbol(target.GetType()), mi); } else { paramTypes = GetParameterTypes(mi); } - if (!ReflectUtil.CanOwnDynamicMethod(owner)) - owner = typeof(DynamicMethodBuilder); + if (!ReflectUtil.CanOwnDynamicMethod(owner.AsReflection())) + owner = context.Resolver.GetSymbol(typeof(DynamicMethodBuilder)); - dm = new DynamicMethod(name, mi.ReturnType, paramTypes, owner, true); + dm = new DynamicMethod(name, mi.ReturnType.AsReflection(), paramTypes.AsReflection(), owner.AsReflection(), true); ilgen = context.CodeEmitterFactory.Create(dm); if (type.parameterCount() > MaxArity) @@ -211,9 +213,9 @@ internal static Delegate CreateVoidAdapter(RuntimeContext context, global::java. var targetDelegateType = context.MethodHandleUtil.GetMemberWrapperDelegateType(type); dm.Ldarg(0); dm.EmitCheckcast(context.JavaBase.TypeOfJavaLangInvokeMethodHandle); - dm.ilgen.Emit(OpCodes.Ldfld, typeof(global::java.lang.invoke.MethodHandle).GetField(METHOD_HANDLE_FORM_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); - dm.ilgen.Emit(OpCodes.Ldfld, typeof(global::java.lang.invoke.LambdaForm).GetField(LAMBDA_FORM_VMENTRY_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); - dm.ilgen.Emit(OpCodes.Ldfld, typeof(global::java.lang.invoke.MemberName).GetField(MEMBER_NAME_VMTARGET_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); + dm.ilgen.Emit(OpCodes.Ldfld, context.Resolver.GetSymbol(typeof(global::java.lang.invoke.MethodHandle)).GetField(METHOD_HANDLE_FORM_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); + dm.ilgen.Emit(OpCodes.Ldfld, context.Resolver.GetSymbol(typeof(global::java.lang.invoke.LambdaForm)).GetField(LAMBDA_FORM_VMENTRY_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); + dm.ilgen.Emit(OpCodes.Ldfld, context.Resolver.GetSymbol(typeof(global::java.lang.invoke.MemberName)).GetField(MEMBER_NAME_VMTARGET_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); dm.ilgen.Emit(OpCodes.Castclass, targetDelegateType); for (int i = 0; i < type.parameterCount(); i++) dm.Ldarg(i); @@ -229,15 +231,15 @@ internal static DynamicMethod CreateInvokeExact(RuntimeContext context, global:: { FinishTypes(type); - var dm = new DynamicMethodBuilder(context, "InvokeExact", type, typeof(java.lang.invoke.MethodHandle), null, null, null, false); + var dm = new DynamicMethodBuilder(context, "InvokeExact", type, context.Resolver.GetSymbol(typeof(java.lang.invoke.MethodHandle)), null, null, null, false); var targetDelegateType = context.MethodHandleUtil.GetMemberWrapperDelegateType(type.insertParameterTypes(0, context.JavaBase.TypeOfJavaLangInvokeMethodHandle.ClassObject)); dm.ilgen.Emit(OpCodes.Ldarg_0); - dm.ilgen.Emit(OpCodes.Ldfld, typeof(global::java.lang.invoke.MethodHandle).GetField(METHOD_HANDLE_FORM_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); - dm.ilgen.Emit(OpCodes.Ldfld, typeof(global::java.lang.invoke.LambdaForm).GetField(LAMBDA_FORM_VMENTRY_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); + dm.ilgen.Emit(OpCodes.Ldfld, context.Resolver.GetSymbol(typeof(global::java.lang.invoke.MethodHandle)).GetField(METHOD_HANDLE_FORM_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); + dm.ilgen.Emit(OpCodes.Ldfld, context.Resolver.GetSymbol(typeof(global::java.lang.invoke.LambdaForm)).GetField(LAMBDA_FORM_VMENTRY_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); if (type.returnType() == java.lang.Void.TYPE) - dm.ilgen.Emit(OpCodes.Call, typeof(MethodHandleUtil).GetMethod(nameof(GetVoidAdapter), BindingFlags.Static | BindingFlags.NonPublic)); + dm.ilgen.Emit(OpCodes.Call, context.Resolver.GetSymbol(typeof(MethodHandleUtil)).GetMethod(nameof(GetVoidAdapter), BindingFlags.Static | BindingFlags.NonPublic)); else - dm.ilgen.Emit(OpCodes.Ldfld, typeof(java.lang.invoke.MemberName).GetField(MEMBER_NAME_VMTARGET_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); + dm.ilgen.Emit(OpCodes.Ldfld, context.Resolver.GetSymbol(typeof(java.lang.invoke.MemberName)).GetField(MEMBER_NAME_VMTARGET_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); dm.ilgen.Emit(OpCodes.Castclass, targetDelegateType); dm.ilgen.Emit(OpCodes.Ldarg_0); @@ -273,8 +275,8 @@ internal static Delegate CreateMethodHandleLinkTo(RuntimeContext context, java.l var delegateType = context.MethodHandleUtil.GetMemberWrapperDelegateType(type.dropParameterTypes(type.parameterCount() - 1, type.parameterCount())); var dm = new DynamicMethodBuilder(context, "DirectMethodHandle." + mn.getName() + type, type, null, null, null, null, true); dm.Ldarg(type.parameterCount() - 1); - dm.ilgen.EmitCastclass(typeof(java.lang.invoke.MemberName)); - dm.ilgen.Emit(OpCodes.Ldfld, typeof(java.lang.invoke.MemberName).GetField(MEMBER_NAME_VMTARGET_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); + dm.ilgen.EmitCastclass(context.Resolver.GetSymbol(typeof(java.lang.invoke.MemberName))); + dm.ilgen.Emit(OpCodes.Ldfld, context.Resolver.GetSymbol(typeof(java.lang.invoke.MemberName)).GetField(MEMBER_NAME_VMTARGET_FIELD, BindingFlags.Instance | BindingFlags.NonPublic)); dm.ilgen.Emit(OpCodes.Castclass, delegateType); for (int i = 0, count = type.parameterCount() - 1; i < count; i++) dm.Ldarg(i); @@ -288,7 +290,7 @@ internal static Delegate CreateMethodHandleInvoke(RuntimeContext context, java.l { var type = mn.getMethodType().insertParameterTypes(0, mn.getDeclaringClass()); var targetDelegateType = context.MethodHandleUtil.GetMemberWrapperDelegateType(type); - var dm = new DynamicMethodBuilder(context, "DirectMethodHandle." + mn.getName() + type, type, typeof(Container<,>).MakeGenericType(typeof(object), typeof(IKVM.Runtime.InvokeCache<>).MakeGenericType(targetDelegateType)), null, null, null, true); + var dm = new DynamicMethodBuilder(context, "DirectMethodHandle." + mn.getName() + type, type, context.Resolver.GetSymbol(typeof(Container<,>)).MakeGenericType(context.Types.Object, context.Resolver.GetSymbol(typeof(IKVM.Runtime.InvokeCache<>)).MakeGenericType(targetDelegateType)), null, null, null, true); dm.Ldarg(0); dm.EmitCheckcast(context.JavaBase.TypeOfJavaLangInvokeMethodHandle); switch (mn.getName()) @@ -332,7 +334,7 @@ internal static Delegate CreateDynamicOnly(RuntimeContext context, RuntimeJavaMe dm.Ldarg(0); dm.BoxArgs(1); } - dm.Callvirt(typeof(RuntimeJavaMethod).GetMethod("Invoke", BindingFlags.Instance | BindingFlags.NonPublic)); + dm.Callvirt(context.Resolver.GetSymbol(typeof(RuntimeJavaMethod)).GetMethod("Invoke", BindingFlags.Instance | BindingFlags.NonPublic)); dm.UnboxReturnValue(); dm.Ret(); @@ -439,12 +441,12 @@ internal static Delegate CreateMemberName(RuntimeContext context, RuntimeJavaMet return dm.CreateDelegate(); } - internal void Call(MethodInfo method) + internal void Call(IMethodSymbol method) { ilgen.Emit(OpCodes.Call, method); } - internal void Callvirt(MethodInfo method) + internal void Callvirt(IMethodSymbol method) { ilgen.Emit(OpCodes.Callvirt, method); } @@ -459,7 +461,7 @@ internal void Callvirt(RuntimeJavaMethod mw) mw.EmitCallvirt(ilgen); } - internal void CallDelegate(Type delegateType) + internal void CallDelegate(ITypeSymbol delegateType) { context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } @@ -512,8 +514,8 @@ internal Delegate CreateDelegate() //ilgen.DumpMethod(); ilgen.DoEmit(); return ValidateDelegate(firstArg == 0 - ? dm.CreateDelegate(delegateType) - : dm.CreateDelegate(delegateType, container == null ? firstBoundValue : Activator.CreateInstance(container, firstBoundValue, secondBoundValue))); + ? dm.CreateDelegate(delegateType.AsReflection()) + : dm.CreateDelegate(delegateType.AsReflection(), container == null ? firstBoundValue : Activator.CreateInstance(container.AsReflection(), firstBoundValue, secondBoundValue))); } internal void BoxArgs(int start) @@ -578,14 +580,14 @@ internal void EmitCheckcast(RuntimeJavaType tw) tw.EmitCheckcast(ilgen); } - internal void EmitCastclass(Type type) + internal void EmitCastclass(ITypeSymbol type) { ilgen.EmitCastclass(type); } internal void EmitWriteLine() { - ilgen.Emit(OpCodes.Call, typeof(Console).GetMethod("WriteLine", new Type[] { typeof(object) })); + ilgen.Emit(OpCodes.Call, context.Resolver.GetSymbol(typeof(Console)).GetMethod("WriteLine", [context.Types.Object])); } internal void CastByte() @@ -627,10 +629,10 @@ static Delegate ValidateDelegate(Delegate d) return d; } - internal Type GetDelegateTypeForInvokeExact(global::java.lang.invoke.MethodType type) + internal ITypeSymbol GetDelegateTypeForInvokeExact(global::java.lang.invoke.MethodType type) { - type._invokeExactDelegateType ??= CreateMethodHandleDelegateType(type); - return type._invokeExactDelegateType; + type._invokeExactDelegateType ??= CreateMethodHandleDelegateType(type).AsReflection(); + return context.Resolver.GetSymbol(type._invokeExactDelegateType); } internal T GetDelegateForInvokeExact(global::java.lang.invoke.MethodHandle mh) @@ -640,13 +642,13 @@ internal T GetDelegateForInvokeExact(global::java.lang.invoke.MethodHandle mh if (mh._invokeExactDelegate == null) { type._invokeExactDynamicMethod ??= DynamicMethodBuilder.CreateInvokeExact(context, type); - mh._invokeExactDelegate = type._invokeExactDynamicMethod.CreateDelegate(GetDelegateTypeForInvokeExact(type), mh); + mh._invokeExactDelegate = type._invokeExactDynamicMethod.CreateDelegate(GetDelegateTypeForInvokeExact(type).AsReflection(), mh); var del = mh._invokeExactDelegate as T; if (del != null) return del; } - throw java.lang.invoke.Invokers.newWrongMethodTypeException(GetDelegateMethodType(typeof(T)), type); + throw java.lang.invoke.Invokers.newWrongMethodTypeException(GetDelegateMethodType(context.Resolver.GetSymbol(typeof(T))), type); } /// @@ -668,7 +670,7 @@ internal static object GetVoidAdapter(java.lang.invoke.MemberName mn) return type.voidAdapter; } - internal void LoadPackedArg(CodeEmitter ilgen, int index, int firstArg, int packedArgPos, Type packedArgType) + internal void LoadPackedArg(CodeEmitter ilgen, int index, int firstArg, int packedArgPos, ITypeSymbol packedArgType) { index += firstArg; if (index >= packedArgPos) diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index 9869a856ed..d064ee8dfd 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -705,7 +705,7 @@ internal virtual RuntimeJavaType GetJavaTypeFromAssemblyType(ITypeSymbol type) if (javaType.TypeAsTBD != type && (!javaType.IsRemapped || javaType.TypeAsBaseType != type)) { #if IMPORTER - throw new FatalCompilerErrorException(DiagnosticEvent.AssemblyContainsDuplicateClassNames(type.FullName, javaType.TypeAsTBD.FullName, javaType.Name, type.Assembly.FullName)); + throw new DiagnosticEventException(DiagnosticEvent.AssemblyContainsDuplicateClassNames(type.FullName, javaType.TypeAsTBD.FullName, javaType.Name, type.Assembly.FullName)); #else throw new InternalException($"\nType \"{type.FullName}\" and \"{javaType.TypeAsTBD.FullName}\" both map to the same name \"{javaType.Name}\"."); #endif diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index 6c26b41fc3..a300dae6ed 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -1661,11 +1661,11 @@ public JniBuilder(RuntimeContext context) IMethodSymbol UnwrapLocalRefMethod => LocalRefStructType.GetMethod("UnwrapLocalRef"); - IMethodSymbol WriteLineMethod => context.Resolver.ResolveType(typeof(Console).FullName).GetMethod("WriteLine", [context.Types.Object]); + IMethodSymbol WriteLineMethod => context.Resolver.ResolveSystemType(typeof(Console).FullName).GetMethod("WriteLine", [context.Types.Object]); - IMethodSymbol MonitorEnterMethod => context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", [context.Types.Object]); + IMethodSymbol MonitorEnterMethod => context.Resolver.ResolveSystemType(typeof(System.Threading.Monitor).FullName).GetMethod("Enter", [context.Types.Object]); - IMethodSymbol MonitorExitMethod => context.Resolver.ResolveType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", [context.Types.Object]); + IMethodSymbol MonitorExitMethod => context.Resolver.ResolveSystemType(typeof(System.Threading.Monitor).FullName).GetMethod("Exit", [context.Types.Object]); internal void Generate(RuntimeByteCodeJavaType.FinishContext context, CodeEmitter ilGenerator, RuntimeByteCodeJavaType wrapper, RuntimeJavaMethod mw, ITypeSymbolBuilder typeBuilder, ClassFile classFile, ClassFile.Method m, RuntimeJavaType[] args, bool thruProxy) { @@ -1896,7 +1896,7 @@ void EmitCallerIDStub(RuntimeJavaMethod mw, string[] parameterNames) } ilgen.Emit(OpCodes.Ldc_I4_1); ilgen.Emit(OpCodes.Ldc_I4_0); - ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveType(typeof(StackFrame).FullName).GetConstructor([context.Types.Int32, context.Types.Boolean])); + ilgen.Emit(OpCodes.Newobj, context.Resolver.ResolveSystemType(typeof(StackFrame).FullName).GetConstructor([context.Types.Int32, context.Types.Boolean])); var callerID = context.JavaBase.TypeOfIkvmInternalCallerID.GetMethodWrapper("create", "(Lcli.System.Diagnostics.StackFrame;)Likvm.internal.CallerID;", false); callerID.Link(); callerID.EmitCall(ilgen); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index ea1dadac63..3c960048f2 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -88,9 +88,9 @@ private static void CheckMissing(RuntimeJavaType prev, RuntimeJavaType tw) { var mt = ReflectUtil.GetMissingType(missing.MissingType); if (mt.Assembly.IsMissing) - throw new FatalCompilerErrorException(DiagnosticEvent.MissingBaseTypeReference(mt.FullName, mt.Assembly.FullName)); + throw new DiagnosticEventException(DiagnosticEvent.MissingBaseTypeReference(mt.FullName, mt.Assembly.FullName)); - throw new FatalCompilerErrorException(DiagnosticEvent.MissingBaseType(mt.FullName, mt.Assembly.FullName, prev.TypeAsBaseType.FullName, prev.TypeAsBaseType.Module.Name)); + throw new DiagnosticEventException(DiagnosticEvent.MissingBaseType(mt.FullName, mt.Assembly.FullName, prev.TypeAsBaseType.FullName, prev.TypeAsBaseType.Module.Name)); } foreach (RuntimeJavaType iface in tw.Interfaces) @@ -657,7 +657,7 @@ private bool IsPInvokeMethod(ClassFile.Method m) { if (method.Attributes != null) foreach (IKVM.Tools.Importer.MapXml.Attribute attr in method.Attributes) - if (Context.StaticCompiler.GetType(classLoader, attr.Type) == Context.Resolver.ResolveCoreType(typeof(System.Runtime.InteropServices.DllImportAttribute).FullName)) + if (Context.StaticCompiler.GetType(classLoader, attr.Type) == Context.Resolver.ResolveSystemType(typeof(System.Runtime.InteropServices.DllImportAttribute).FullName)) return true; break; diff --git a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs index 27f07f5dbf..6e564b1660 100644 --- a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs @@ -102,17 +102,17 @@ internal void LoadRemappedTypes() // if we're compiling the base assembly, we won't be able to resolve one if (context.Options.Bootstrap == false && remappedTypes.Count == 0) { - var baseAssembly = context.Resolver.ResolveBaseAssembly(); + var baseAssembly = context.Resolver.GetBaseAssembly(); var remapped = context.AttributeHelper.GetRemappedClasses(baseAssembly); if (remapped.Length > 0) { foreach (var r in remapped) - remappedTypes.Add(context.Resolver.ImportType(r.RemappedType), r.Name); + remappedTypes.Add(context.Resolver.GetSymbol(r.RemappedType), r.Name); } else { #if IMPORTER - throw new FatalCompilerErrorException(DiagnosticEvent.CoreClassesMissing()); + throw new DiagnosticEventException(DiagnosticEvent.CoreClassesMissing()); #else throw new InternalException("Failed to find core classes in core library."); #endif @@ -283,7 +283,7 @@ internal RuntimeJavaType LoadClassCritical(string name) #if IMPORTER var wrapper = GetBootstrapClassLoader().TryLoadClassByName(name); if (wrapper == null) - throw new FatalCompilerErrorException(DiagnosticEvent.CriticalClassNotFound(name)); + throw new DiagnosticEventException(DiagnosticEvent.CriticalClassNotFound(name)); return wrapper; #else @@ -384,9 +384,9 @@ internal RuntimeClassLoader GetAssemblyClassLoaderByName(string name) return GetGenericClassLoaderByName(name); #if NETFRAMEWORK - return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ImportAssembly( Assembly.Load(name))); + return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.GetSymbol(Assembly.Load(name))); #else - return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ImportAssembly(AssemblyLoadContext.GetLoadContext(typeof(RuntimeClassLoader).Assembly).LoadFromAssemblyName(new AssemblyName(name)))); + return context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.GetSymbol(AssemblyLoadContext.GetLoadContext(typeof(RuntimeClassLoader).Assembly).LoadFromAssemblyName(new AssemblyName(name)))); #endif } diff --git a/src/IKVM.Runtime/RuntimeContextOptions.cs b/src/IKVM.Runtime/RuntimeContextOptions.cs index 159bef8308..20f1f047c6 100644 --- a/src/IKVM.Runtime/RuntimeContextOptions.cs +++ b/src/IKVM.Runtime/RuntimeContextOptions.cs @@ -4,11 +4,8 @@ internal class RuntimeContextOptions { -#if NETFRAMEWORK - internal const string DefaultDynamicAssemblySuffixAndPublicKey = "-ikvm-runtime-injected, PublicKey=00240000048000009400000006020000002400005253413100040000010001009D674F3D63B8D7A4C428BD7388341B025C71AA61C6224CD53A12C21330A3159D300051FE2EED154FE30D70673A079E4529D0FD78113DCA771DA8B0C1EF2F77B73651D55645B0A4294F0AF9BF7078432E13D0F46F951D712C2FCF02EB15552C0FE7817FC0AED58E0984F86661BF64D882F29B619899DD264041E7D4992548EB9E"; -#else - internal const string DefaultDynamicAssemblySuffixAndPublicKey = "-ikvm-runtime-injected"; -#endif + internal const string SignedDefaultDynamicAssemblySuffixAndPublicKey = "-ikvm-runtime-injected, PublicKey=00240000048000009400000006020000002400005253413100040000010001009D674F3D63B8D7A4C428BD7388341B025C71AA61C6224CD53A12C21330A3159D300051FE2EED154FE30D70673A079E4529D0FD78113DCA771DA8B0C1EF2F77B73651D55645B0A4294F0AF9BF7078432E13D0F46F951D712C2FCF02EB15552C0FE7817FC0AED58E0984F86661BF64D882F29B619899DD264041E7D4992548EB9E"; + internal const string UnsignedDefaultDynamicAssemblySuffixAndPublicKey = "-ikvm-runtime-injected"; readonly bool bootstrap; readonly string dynamicAssemblySuffixAndPublicKey; @@ -21,7 +18,7 @@ internal class RuntimeContextOptions public RuntimeContextOptions(bool bootstrap = false, string dynamicAssemblySuffixAndPublicKey = null) { this.bootstrap = bootstrap; - this.dynamicAssemblySuffixAndPublicKey = dynamicAssemblySuffixAndPublicKey ?? DefaultDynamicAssemblySuffixAndPublicKey; + this.dynamicAssemblySuffixAndPublicKey = dynamicAssemblySuffixAndPublicKey ?? UnsignedDefaultDynamicAssemblySuffixAndPublicKey; } /// diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 6fb940ce16..c127cf3607 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -302,7 +302,7 @@ internal static RuntimeJavaType FromClass(java.lang.Class clazz) return FromClass(clazz); } - var symbol = JVM.Context.Resolver.ImportType(type); + var symbol = JVM.Context.Resolver.GetSymbol(type); if (type == typeof(void) || type.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(symbol)) tw = JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(symbol); else diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs index ca2fb0d06d..bf52e19ed7 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaType.cs @@ -58,7 +58,7 @@ internal RemappedJavaType(RuntimeContext context, string name, ITypeSymbol type) base(context, name, type) { var attr = Context.AttributeHelper.GetRemappedType(type) ?? throw new InvalidOperationException(); - remappedType = Context.Resolver.ImportType(attr.Type); + remappedType = Context.Resolver.GetSymbol(attr.Type); } internal override ITypeSymbol TypeAsTBD => remappedType; diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index cce2864319..840ebdc54b 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -137,7 +137,7 @@ static RuntimeJavaType GetBaseTypeWrapper(RuntimeContext context, ITypeSymbol ty var attr = context.AttributeHelper.GetRemappedType(type); if (attr != null) { - if (context.Resolver.ImportType(attr.Type) == context.Types.Object) + if (context.Resolver.GetSymbol(attr.Type) == context.Types.Object) return null; else return context.JavaBase.TypeOfJavaLangObject; @@ -312,7 +312,7 @@ private RuntimeJavaType[] GetInterfaces() if (interfaceWrappers[i] == null) { #if IMPORTER - throw new FatalCompilerErrorException(DiagnosticEvent.UnableToResolveInterface(interfaceNames[i], ToString())); + throw new DiagnosticEventException(DiagnosticEvent.UnableToResolveInterface(interfaceNames[i], ToString())); #else throw new InternalException($"Unable to resolve interface {interfaceNames[i]} on type {this}"); #endif @@ -1183,7 +1183,7 @@ internal sealed class CompiledAnnotation : Annotation internal CompiledAnnotation(RuntimeContext context, ITypeSymbol type) { this.context = context ?? throw new ArgumentNullException(nameof(context)); - constructor = type.GetConstructor([context.Resolver.ResolveCoreType(typeof(object).FullName).MakeArrayType()]); + constructor = type.GetConstructor([context.Types.Object.MakeArrayType()]); } private ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) @@ -1254,7 +1254,7 @@ internal override ITypeSymbol EnumType internal override string GetSourceFileName() { - var attr = type.GetCustomAttribute(Context.Resolver.ImportType(typeof(SourceFileAttribute))); + var attr = type.GetCustomAttribute(Context.Resolver.GetSymbol(typeof(SourceFileAttribute))); if (attr != null && attr.Value.ConstructorArguments.Length > 0) return (string)attr.Value.ConstructorArguments[0].Value; @@ -1264,7 +1264,7 @@ internal override string GetSourceFileName() if (IsNestedTypeAnonymousOrLocalClass(type)) return Context.ClassLoaderFactory.GetJavaTypeFromType(type.DeclaringType).GetSourceFileName(); - if (type.Module.IsDefined(Context.Resolver.ImportType(typeof(SourceFileAttribute)), false)) + if (type.Module.IsDefined(Context.Resolver.GetSymbol(typeof(SourceFileAttribute)), false)) return type.Name + ".java"; return null; @@ -1272,7 +1272,7 @@ internal override string GetSourceFileName() internal override int GetSourceLineNumber(IMethodBaseSymbol mb, int ilOffset) { - var attr = type.GetCustomAttribute(Context.Resolver.ImportType(typeof(LineNumberTableAttribute))); + var attr = type.GetCustomAttribute(Context.Resolver.GetSymbol(typeof(LineNumberTableAttribute))); if (attr != null && attr.Value.Constructor != null) return ((LineNumberTableAttribute)attr.Value.Constructor.AsReflection().Invoke(attr.Value.ConstructorArguments.Cast().ToArray())).GetLineNumber(ilOffset); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs index ae41f128c7..b762ef1011 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs @@ -71,7 +71,7 @@ internal AttributeAnnotationJavaType(RuntimeContext context, string name, ITypeS #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetAttributeType(attributeType); #elif !FIRST_PASS - this.fakeType = context.Resolver.ImportType(typeof(ikvm.@internal.AttributeAnnotation<>)).MakeGenericType(attributeType); + this.fakeType = context.Resolver.GetSymbol(typeof(ikvm.@internal.AttributeAnnotation<>)).MakeGenericType(attributeType); #endif this.attributeType = attributeType; } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs index f3703bba64..0173a94b4d 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.DelegateInnerClassJavaType.cs @@ -53,7 +53,7 @@ internal DelegateInnerClassJavaType(RuntimeContext context, string name, ITypeSy #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetDelegateType(delegateType); #elif !FIRST_PASS - this.fakeType = context.Resolver.ImportType(typeof(ikvm.@internal.DelegateInterface<>)).MakeGenericType(delegateType); + this.fakeType = context.Resolver.GetSymbol(typeof(ikvm.@internal.DelegateInterface<>)).MakeGenericType(delegateType); #endif var invoke = delegateType.GetMethod("Invoke"); var parameters = invoke.GetParameters(); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs index b9765c9522..709b007046 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs @@ -56,7 +56,7 @@ internal EnumEnumJavaType(RuntimeContext context, string name, ITypeSymbol enumT #if IMPORTER || EXPORTER this.fakeType = context.FakeTypes.GetEnumType(enumType); #elif !FIRST_PASS - this.fakeType = context.Resolver.ImportType(typeof(ikvm.@internal.EnumEnum<>)).MakeGenericType(enumType); + this.fakeType = context.Resolver.GetSymbol(typeof(ikvm.@internal.EnumEnum<>)).MakeGenericType(enumType); #endif } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index 758e61747f..7b20b06a86 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -541,7 +541,7 @@ protected override void LazyPublishMembers() #if !IMPORTER && !EXPORTER && !FIRST_PASS // support serializing .NET exceptions (by replacing them with a placeholder exception) - if (Context.Types.Exception.IsAssignableFrom(type) && Context.Resolver.ImportType(typeof(java.io.Serializable.__Interface)).IsAssignableFrom(type) == false && methodsList.ContainsKey("writeReplace()Ljava.lang.Object;") == false) + if (Context.Types.Exception.IsAssignableFrom(type) && Context.Resolver.GetSymbol(typeof(java.io.Serializable.__Interface)).IsAssignableFrom(type) == false && methodsList.ContainsKey("writeReplace()Ljava.lang.Object;") == false) methodsList.Add("writeReplace()Ljava.lang.Object;", new ExceptionWriteReplaceJavaMethod(this)); #endif diff --git a/src/IKVM.Runtime/StubGen/StubGenerator.cs b/src/IKVM.Runtime/StubGen/StubGenerator.cs index 51d7f48332..2706d4c187 100644 --- a/src/IKVM.Runtime/StubGen/StubGenerator.cs +++ b/src/IKVM.Runtime/StubGen/StubGenerator.cs @@ -329,7 +329,7 @@ void AddExceptionsAttribute(ClassFileBuilder builder, RuntimeJavaType type, Runt if (throws.types != null) foreach (var ex in throws.types) - e.Class(builder.Constants.GetOrAddClass(context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ImportType(ex)).Name.Replace('.', '/'))); + e.Class(builder.Constants.GetOrAddClass(context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.GetSymbol(ex)).Name.Replace('.', '/'))); }); } } @@ -580,7 +580,7 @@ bool EncodeAnnotations(ClassFileBuilder builder, ref AnnotationTableEncoder enco #if !FIRST_PASS && !EXPORTER if (source != null) { - foreach (var cad in CustomAttributeData.GetCustomAttributes(source)) + foreach (var cad in source.GetCustomAttributes()) { var ann = GetAnnotation(cad); if (ann != null) @@ -615,7 +615,7 @@ bool EncodeParameterAnnotations(ClassFileBuilder builder, ref ParameterAnnotatio { encoder.ParameterAnnotation(e2 => { - foreach (var cad in CustomAttributeData.GetCustomAttributes(parameters[i])) + foreach (var cad in parameters[i].GetCustomAttributes()) { var ann = GetAnnotation(cad); if (ann != null) @@ -913,12 +913,12 @@ public PackageConstantHandle Map(PackageConstantHandle handle) object[] GetAnnotation(CustomAttribute cad) { // attribute is either a AnnotationAttributeBase or a DynamicAnnotationAttribute with a single object[] in our internal annotation format - if (cad.ConstructorArguments.Count == 1 && cad.ConstructorArguments[0].ArgumentType == typeof(object[]) && (cad.Constructor.DeclaringType.BaseType == typeof(ikvm.@internal.AnnotationAttributeBase) || cad.Constructor.DeclaringType == typeof(DynamicAnnotationAttribute))) + if (cad.ConstructorArguments.Length == 1 && cad.ConstructorArguments[0].ArgumentType == context.Types.Object.MakeArrayType() && (cad.Constructor.DeclaringType.BaseType == context.Resolver.ResolveBaseType(typeof(ikvm.@internal.AnnotationAttributeBase).FullName) || cad.Constructor.DeclaringType == context.Resolver.ResolveBaseType(typeof(DynamicAnnotationAttribute).FullName))) { return UnpackArray((IList)cad.ConstructorArguments[0].Value); } - if (cad.Constructor.DeclaringType.BaseType == typeof(ikvm.@internal.AnnotationAttributeBase)) + if (cad.Constructor.DeclaringType.BaseType == context.Resolver.ResolveBaseType(typeof(ikvm.@internal.AnnotationAttributeBase).FullName)) { var annotationType = GetAnnotationInterface(cad); if (annotationType != null) @@ -948,12 +948,12 @@ object[] GetAnnotation(CustomAttribute cad) return null; } - string GetAnnotationInterface(CustomAttributeData cad) + string GetAnnotationInterface(CustomAttribute cad) { - var attr = cad.Constructor.DeclaringType.GetCustomAttributes(typeof(IKVM.Attributes.ImplementsAttribute), false); - if (attr.Length == 1) + var attr = cad.Constructor.DeclaringType.GetCustomAttribute(context.Resolver.ResolveRuntimeType(typeof(ImplementsAttribute).FullName), false); + if (attr != null) { - var interfaces = ((IKVM.Attributes.ImplementsAttribute)attr[0]).Interfaces; + var interfaces = (string[])attr.Value.ConstructorArguments[0].Value; if (interfaces.Length == 1) return interfaces[0]; } @@ -974,11 +974,11 @@ object GetAnnotationValue(CustomAttributeTypedArgument arg) { // if GetWrapperFromType returns null, we've got an ikvmc synthesized .NET enum nested inside a Java enum var tw = context.ClassLoaderFactory.GetJavaTypeFromType(arg.ArgumentType) ?? context.ClassLoaderFactory.GetJavaTypeFromType(arg.ArgumentType.DeclaringType); - return new object[] { IKVM.Attributes.AnnotationDefaultAttribute.TAG_ENUM, EncodeTypeName(tw), Enum.GetName(arg.ArgumentType, arg.Value) }; + return new object[] { IKVM.Attributes.AnnotationDefaultAttribute.TAG_ENUM, EncodeTypeName(tw), arg.ArgumentType.GetEnumName(arg.Value) }; } // argument is directly a type, so we encode it as a TAG_CLASS - if (arg.Value is Type type) + if (arg.Value is ITypeSymbol type) { return new object[] { IKVM.Attributes.AnnotationDefaultAttribute.TAG_CLASS, EncodeTypeName(context.ClassLoaderFactory.GetJavaTypeFromType(type)) }; } diff --git a/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs b/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs index bb0d5d136b..355ca04473 100644 --- a/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs +++ b/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs @@ -29,10 +29,10 @@ using System; using System.Collections.Generic; -using System.Reflection; using System.Reflection.Emit; using IKVM.Attributes; +using IKVM.CoreLib.Symbols; using java.lang.invoke; @@ -63,11 +63,11 @@ public static MemberName generateCustomizedCode(LambdaForm form, MethodType invo readonly RuntimeContext context; readonly java.lang.invoke.LambdaForm lambdaForm; readonly java.lang.invoke.MethodType invokerType; - readonly Type delegateType; + readonly ITypeSymbol delegateType; readonly DynamicMethod dm; readonly CodeEmitter ilgen; readonly int packedArgPos; - readonly Type packedArgType; + readonly ITypeSymbol packedArgType; readonly CodeEmitterLocal[] locals; readonly List constants = new List(); @@ -112,10 +112,10 @@ internal BailoutException(Bailout reason, object data) this.delegateType = context.MethodHandleUtil.GetMemberWrapperDelegateType(invokerType); var mi = context.MethodHandleUtil.GetDelegateInvokeMethod(delegateType); - var paramTypes = MethodHandleUtil.GetParameterTypes(typeof(object[]), mi); + var paramTypes = MethodHandleUtil.GetParameterTypes(context.Types.Object.MakeArrayType(), mi); // HACK the code we generate is not verifiable (known issue: locals aren't typed correctly), so we stick the DynamicMethod into mscorlib (a security critical assembly) - this.dm = new DynamicMethod(lambdaForm.debugName, mi.ReturnType, paramTypes, typeof(object).Module, true); + this.dm = new DynamicMethod(lambdaForm.debugName, mi.ReturnType.AsReflection(), paramTypes.AsReflection(), typeof(object).Module, true); this.ilgen = context.CodeEmitterFactory.Create(this.dm); if (invokerType.parameterCount() > MethodHandleUtil.MaxArity) { @@ -124,7 +124,7 @@ internal BailoutException(Bailout reason, object data) } else { - this.packedArgPos = Int32.MaxValue; + this.packedArgPos = int.MaxValue; } locals = new CodeEmitterLocal[lambdaForm.names.Length]; @@ -334,7 +334,7 @@ public AnonymousClass(RuntimeContext context) : internal override RuntimeClassLoader ClassLoader => Context.ClassLoaderFactory.GetBootstrapClassLoader(); - internal override Type TypeAsTBD + internal override ITypeSymbol TypeAsTBD { get { throw new InvalidOperationException(); } } @@ -439,7 +439,7 @@ private Delegate generateCustomizedCodeBytes() emitReturn(onStack); ilgen.DoEmit(); - return dm.CreateDelegate(delegateType, constants.ToArray()); + return dm.CreateDelegate(delegateType.AsReflection(), constants.ToArray()); } void emitArrayLoad(Name name) @@ -816,12 +816,12 @@ private Name emitGuardWithCatch(int pos) ilgen.EmitLeave(L_done); // Exceptional case - ilgen.BeginCatchBlock(typeof(Exception)); + ilgen.BeginCatchBlock(context.Types.Exception); // [IKVM] map the exception and store it in a local and exit the handler ilgen.EmitLdc_I4(0); - ilgen.Emit(OpCodes.Call, context.ByteCodeHelperMethods.MapException.MakeGenericMethod(typeof(Exception))); - CodeEmitterLocal exception = ilgen.DeclareLocal(typeof(Exception)); + ilgen.Emit(OpCodes.Call, context.ByteCodeHelperMethods.MapException.MakeGenericMethod(context.Types.Exception)); + CodeEmitterLocal exception = ilgen.DeclareLocal(context.Types.Exception); ilgen.Emit(OpCodes.Stloc, exception); ilgen.EmitLeave(L_handler); ilgen.EndExceptionBlock(); diff --git a/src/IKVM.Runtime/atomic.cs b/src/IKVM.Runtime/atomic.cs index 42f2af31c0..7c7b282c8e 100644 --- a/src/IKVM.Runtime/atomic.cs +++ b/src/IKVM.Runtime/atomic.cs @@ -143,7 +143,7 @@ public InterlockedMethods(RuntimeContext context) { this.context = context; - var type = context.Resolver.ResolveType(typeof(System.Threading.Interlocked).FullName); + var type = context.Resolver.ResolveSystemType(typeof(System.Threading.Interlocked).FullName); AddInt32 = type.GetMethod("Add", [context.Types.Int32.MakeByRefType(), context.Types.Int32]); CompareExchangeInt32 = type.GetMethod("CompareExchange", [context.Types.Int32.MakeByRefType(), context.Types.Int32, context.Types.Int32]); CompareExchangeInt64 = type.GetMethod("CompareExchange", [context.Types.Int64.MakeByRefType(), context.Types.Int64, context.Types.Int64]); diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index b2da6523b3..bc17ee9d9c 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -1743,7 +1743,7 @@ void Compile(Block block, int startIndex) } case NormalizedByteCode.__multianewarray: { - var localArray = ilGenerator.UnsafeAllocTempLocal(finish.Context.Resolver.ResolveCoreType(typeof(int).FullName).MakeArrayType()); + var localArray = ilGenerator.UnsafeAllocTempLocal(finish.Context.Types.Int32.MakeArrayType()); var localInt = ilGenerator.UnsafeAllocTempLocal(finish.Context.Types.Int32); ilGenerator.EmitLdc_I4(instr.Arg2); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Newarr, finish.Context.Types.Int32); @@ -3439,24 +3439,25 @@ internal override void EmitCall(CodeEmitter ilgen) internal static void EmitLinkToCall(RuntimeContext context, CodeEmitter ilgen, RuntimeJavaType[] args, RuntimeJavaType retType) { #if !FIRST_PASS && !IMPORTER - CodeEmitterLocal[] temps = new CodeEmitterLocal[args.Length]; + var temps = new CodeEmitterLocal[args.Length]; for (int i = args.Length - 1; i > 0; i--) { temps[i] = ilgen.DeclareLocal(context.MethodHandleUtil.AsBasicType(args[i])); ToBasic(args[i], ilgen); ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } + temps[0] = ilgen.DeclareLocal(args[0].TypeAsSignatureType); ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[0]); Array.Resize(ref args, args.Length - 1); - Type delegateType = context.MethodHandleUtil.CreateMemberWrapperDelegateType(args, retType); + + var delegateType = context.MethodHandleUtil.CreateMemberWrapperDelegateType(args, retType); ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[args.Length]); - ilgen.Emit(System.Reflection.Emit.OpCodes.Ldfld, typeof(java.lang.invoke.MemberName).GetField("vmtarget", BindingFlags.Instance | BindingFlags.NonPublic)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldfld, context.Resolver.ResolveBaseType(typeof(java.lang.invoke.MemberName).FullName).GetField("vmtarget", BindingFlags.Instance | BindingFlags.NonPublic)); ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, delegateType); for (int i = 0; i < args.Length; i++) - { ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); - } + context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); FromBasic(retType, ilgen); #else @@ -3464,7 +3465,7 @@ internal static void EmitLinkToCall(RuntimeContext context, CodeEmitter ilgen, R #endif } - private void EmitInvokeExact(CodeEmitter ilgen) + void EmitInvokeExact(CodeEmitter ilgen) { var args = cpi.GetArgTypes(); var temps = new CodeEmitterLocal[args.Length]; @@ -3494,7 +3495,7 @@ private void EmitInvokeExact(CodeEmitter ilgen) ilgen.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } - private void EmitInvokeMaxArity(CodeEmitter ilgen) + void EmitInvokeMaxArity(CodeEmitter ilgen) { RuntimeJavaType[] args = cpi.GetArgTypes(); CodeEmitterLocal[] temps = new CodeEmitterLocal[args.Length]; @@ -3510,9 +3511,8 @@ private void EmitInvokeMaxArity(CodeEmitter ilgen) var mi = compiler.finish.Context.ByteCodeHelperMethods.GetDelegateForInvokeExact.MakeGenericMethod(delegateType); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) - { ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); - } + compiler.finish.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } @@ -3553,15 +3553,14 @@ void EmitInvoke(CodeEmitter ilgen) ilgen.Emit(System.Reflection.Emit.OpCodes.Ldsflda, fb); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) - { ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); - } + compiler.finish.Context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } - private void EmitInvokeBasic(CodeEmitter ilgen) + void EmitInvokeBasic(CodeEmitter ilgen) { - RuntimeJavaType retType = cpi.GetRetType(); + var retType = cpi.GetRetType(); EmitInvokeBasic(wrapper.Context, ilgen, cpi.GetArgTypes(), retType, true); FromBasic(retType, ilgen); } @@ -3574,21 +3573,20 @@ internal static void EmitInvokeBasic(RuntimeContext context, CodeEmitter ilgen, { temps[i] = ilgen.DeclareLocal(context.MethodHandleUtil.AsBasicType(args[i])); if (toBasic) - { ToBasic(args[i], ilgen); - } + ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[i]); } temps[0] = ilgen.DeclareLocal(args[0].TypeAsSignatureType); ilgen.Emit(System.Reflection.Emit.OpCodes.Stloc, temps[0]); + var delegateType = context.MethodHandleUtil.CreateMemberWrapperDelegateType(args, retType); var mi = context.ByteCodeHelperMethods.GetDelegateForInvokeBasic.MakeGenericMethod(delegateType); ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[0]); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); for (int i = 0; i < args.Length; i++) - { ilgen.Emit(System.Reflection.Emit.OpCodes.Ldloc, temps[i]); - } + context.MethodHandleUtil.EmitCallDelegateInvokeMethod(ilgen, delegateType); } @@ -3614,12 +3612,13 @@ internal override void EmitNewobj(CodeEmitter ilgen) { throw new InvalidOperationException(); } + } - private sealed class DynamicFieldBinder + sealed class DynamicFieldBinder { - private IMethodSymbol method; + IMethodSymbol method; internal void Emit(Compiler compiler, ClassFile.ConstantPoolItemFieldref cpi, MethodHandleKind kind) { @@ -3659,7 +3658,7 @@ private static IMethodSymbol CreateMethod(Compiler compiler, ClassFile.ConstantP } } - private sealed class DynamicBinder + sealed class DynamicBinder { RuntimeJavaMethod mw; diff --git a/src/IKVM.Runtime/intrinsics.cs b/src/IKVM.Runtime/intrinsics.cs index 14f5c24ff0..ef29d314f7 100644 --- a/src/IKVM.Runtime/intrinsics.cs +++ b/src/IKVM.Runtime/intrinsics.cs @@ -370,7 +370,7 @@ private static bool CallerID_getCallerID(EmitIntrinsicContext eic) } else { - throw new FatalCompilerErrorException(DiagnosticEvent.CallerIDRequiresHasCallerIDAnnotation()); + throw new DiagnosticEventException(DiagnosticEvent.CallerIDRequiresHasCallerIDAnnotation()); } } diff --git a/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatter.cs b/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatter.cs index e92a766240..abd2d80b66 100644 --- a/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/ConsoleDiagnosticFormatter.cs @@ -31,9 +31,19 @@ public ConsoleDiagnosticFormatter(ConsoleDiagnosticFormatterOptions options) _options = options ?? throw new ArgumentNullException(nameof(options)); } + /// + public bool CanWrite(in DiagnosticEvent @event) + { + return true; + } + /// public void Write(in DiagnosticEvent @event) { + // skip events we cannot write + if (CanWrite(@event) == false) + return; + try { WriteDiagnosticEvent(@event); @@ -50,7 +60,7 @@ public void Write(in DiagnosticEvent @event) /// /// /// - protected virtual Markup WriteDiagnosticLevel(DiagnosticLevel level) + protected virtual Markup GetDiagnosticLevelMarkup(DiagnosticLevel level) { return level switch { @@ -63,12 +73,23 @@ protected virtual Markup WriteDiagnosticLevel(DiagnosticLevel level) }; } + /// + /// Returns the output text for the given . + /// + /// + /// + /// + protected virtual void WriteDiagnosticLevel(DiagnosticLevel level) + { + AnsiConsole.Write(GetDiagnosticLevelMarkup(level)); + } + /// /// Formats the output text for the given diagnostic code. /// /// /// - protected virtual void WriteDiagnosticCode(int code) + protected virtual void WriteDiagnosticCode(DiagnosticLevel level, int code) { AnsiConsole.Write("IKVM"); AnsiConsole.Write($"{code:D4}"); @@ -79,7 +100,7 @@ protected virtual void WriteDiagnosticCode(int code) /// /// /// - protected virtual void WriteDiagnosticMessage(string message, ReadOnlySpan args) + protected virtual void WriteDiagnosticMessage(DiagnosticLevel level, string message, ReadOnlySpan args) { AnsiConsole.MarkupInterpolated(FormattableStringFactory.Create(message, args.ToArray())); } @@ -92,9 +113,9 @@ protected virtual void WriteDiagnosticEvent(in DiagnosticEvent @event) { WriteDiagnosticLevel(@event.Diagnostic.Level); AnsiConsole.Write(" "); - WriteDiagnosticCode(@event.Diagnostic.Id); + WriteDiagnosticCode(@event.Diagnostic.Level, @event.Diagnostic.Id); AnsiConsole.Write(": "); - WriteDiagnosticMessage(@event.Diagnostic.Message, @event.Args); + WriteDiagnosticMessage(@event.Diagnostic.Level, @event.Diagnostic.Message, @event.Args); AnsiConsole.WriteLine(); if (@event.Exception != null) diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs index f407ef8c05..ceeb1488ad 100644 --- a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelFormatter.cs @@ -26,14 +26,36 @@ public DiagnosticChannelFormatter(TOptions options) /// public TOptions Options => _options; + /// + public bool CanWrite(in DiagnosticEvent @event) + { + // filter out nowarn + if (@event.Diagnostic.Level is DiagnosticLevel.Warning) + { + if (Options.NoWarn) + return false; + else if (Options.NoWarnDiagnostics.Contains(@event.Diagnostic)) + return false; + } + + // any unknown diagnostic can be written + return @event.Diagnostic.Level is not DiagnosticLevel.Unknown; + } + /// public void Write(in DiagnosticEvent @event) { var level = @event.Diagnostic.Level; - if (level is DiagnosticLevel.Warning && Options.WarnAsError) - level = DiagnosticLevel.Error; - if (level is DiagnosticLevel.Warning && Options.WarnAsErrorDiagnostics.Contains(@event.Diagnostic)) - level = DiagnosticLevel.Error; + if (CanWrite(@event) == false) + return; + + if (level is DiagnosticLevel.Warning) + { + if (Options.WarnAsError) + level = DiagnosticLevel.Error; + else if (Options.WarnAsErrorDiagnostics.Contains(@event.Diagnostic)) + level = DiagnosticLevel.Error; + } // find the writer for the event's level var channel = level switch diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs index fef86d45bc..4d2fd5930a 100644 --- a/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticServiceCollectionExtensions.cs @@ -19,6 +19,7 @@ public static IServiceCollection AddToolsDiagnostics(this IServiceCollection ser services.AddSingleton(); services.AddSingleton(); services.AddSingleton(); + services.AddSingleton(); services.AddSingleton(); return services; } diff --git a/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs b/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs index 02dfebe0a4..007eadce4c 100644 --- a/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs +++ b/src/IKVM.Tools.Core/Diagnostics/IDiagnosticFormatter.cs @@ -6,6 +6,13 @@ namespace IKVM.Tools.Core.Diagnostics interface IDiagnosticFormatter { + /// + /// Returns true if the given event should be written. + /// + /// + /// + bool CanWrite(in DiagnosticEvent @event); + /// /// Writes the event. /// diff --git a/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj b/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj index e08766661c..5205a8c686 100644 --- a/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj +++ b/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj @@ -11,7 +11,7 @@ - + @@ -23,5 +23,9 @@ + + + + diff --git a/src/IKVM.Tools.Exporter/ExportImpl.cs b/src/IKVM.Tools.Exporter/ExportImpl.cs index b7e4b327b5..09494ee741 100644 --- a/src/IKVM.Tools.Exporter/ExportImpl.cs +++ b/src/IKVM.Tools.Exporter/ExportImpl.cs @@ -146,12 +146,11 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(true), diagnostics, new ManagedTypeResolver(symbols, universe, runtimeAssembly, null), compiler); + context = new RuntimeContext(new RuntimeContextOptions(true), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols), compiler); context.ClassLoaderFactory.SetBootstrapClassLoader(new RuntimeBootstrapClassLoader(context)); } else { - var runtimeAssemblyPath = references.FirstOrDefault(i => Path.GetFileNameWithoutExtension(i) == "IKVM.Runtime"); if (runtimeAssemblyPath != null) runtimeAssembly = assemblyResolver.LoadFile(runtimeAssemblyPath); @@ -173,10 +172,10 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ManagedTypeResolver(symbols, universe, runtimeAssembly, baseAssembly), compiler); + context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols), compiler); } - if (context.AttributeHelper.IsJavaModule(context.Resolver.ImportModule(assembly.ManifestModule))) + if (context.AttributeHelper.IsJavaModule(context.Resolver.GetSymbol(assembly.ManifestModule))) { diagnostics.ExportingImportsNotSupported(); return 1; @@ -368,7 +367,7 @@ bool ExportNamespace(IList namespaces, ITypeSymbol type) int ProcessTypes(RuntimeContext context, Type[] types) { int rc = 0; - foreach (var t in types.Select(context.Resolver.ImportType)) + foreach (var t in types.Select(context.Resolver.GetSymbol)) { if ((t.IsPublic || options.IncludeNonPublicTypes) && ExportNamespace(options.Namespaces, t) && !t.IsGenericTypeDefinition && !context.AttributeHelper.IsHideFromJava(t) && (!t.IsGenericType || !context.AttributeHelper.IsJavaModule(t.Module))) { diff --git a/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs new file mode 100644 index 0000000000..cb41963e35 --- /dev/null +++ b/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs @@ -0,0 +1,287 @@ +/* + Copyright (C) 2002-2014 Jeroen Frijters + + This software is provided 'as-is', without any express or implied + warranty. In no event will the authors be held liable for any damages + arising from the use of this software. + + Permission is granted to anyone to use this software for any purpose, + including commercial applications, and to alter it and redistribute it + freely, subject to the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not + claim that you wrote the original software. If you use this software + in a product, an acknowledgment in the product documentation would be + appreciated but is not required. + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + 3. This notice may not be removed or altered from any source distribution. + + Jeroen Frijters + jeroen@frijters.net + +*/ +#nullable enable + +using System; +using System.Collections.Concurrent; +using System.Collections.Generic; +using System.Linq; + +using IKVM.CoreLib.Diagnostics; +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.IkvmReflection; +using IKVM.Reflection; +using IKVM.Reflection.Emit; +using IKVM.Runtime; + +using Type = IKVM.Reflection.Type; + +namespace IKVM.Tools.Exporter +{ + + class ExportRuntimeSymbolResolver : IRuntimeSymbolResolver + { + + /// + /// Gets the set of types from which to discover system assemblies. + /// + /// + static IEnumerable GetSystemTypeNames() + { + yield return "System.Object"; + yield return "System.Runtime.CompilerServices.RuntimeCompatibilityAttribute"; + yield return "System.Console"; + yield return "System.Threading.Interlocked"; + yield return "System.ComponentModel.EditorBrowsableAttribute"; + yield return "System.Collections.IEnumerable"; + yield return "System.Collections.Generic.IEnumerable`1"; + yield return "System.Environment"; + } + + readonly IDiagnosticHandler _diagnostics; + readonly Universe _universe; + readonly IkvmReflectionSymbolContext _symbols; + + IAssemblySymbol? _coreAssembly; + readonly ConcurrentDictionary _coreTypeCache = new(); + + IAssemblySymbol[]? _systemAssemblies; + readonly ConcurrentDictionary _systemTypeCache = new(); + + IAssemblySymbol? _runtimeAssembly; + readonly ConcurrentDictionary _runtimeTypeCache = new(); + + IAssemblySymbol? _baseAssembly; + readonly ConcurrentDictionary _baseTypeCache = new(); + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ExportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols) + { + _diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); + _universe = universe ?? throw new ArgumentNullException(nameof(universe)); + _symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); + } + + /// + public ISymbolContext Symbols => _symbols; + + /// + public IAssemblySymbol GetCoreAssembly() + { + return (_coreAssembly ??= GetSymbol(_universe.CoreLib)) ?? throw new DiagnosticEventException(DiagnosticEvent.CoreClassesMissing()); + } + + /// + public IAssemblySymbol GetRuntimeAssembly() + { + return (_runtimeAssembly ??= FindRuntimeAssembly()) ?? throw new DiagnosticEventException(DiagnosticEvent.RuntimeNotFound()); + } + + /// + /// Attempts to load the runtime assembly. + /// + IAssemblySymbol? FindRuntimeAssembly() + { + foreach (var assembly in _universe.GetAssemblies()) + if (assembly.GetType("IKVM.Runtime.JVM") is Type) + return GetSymbol(assembly); + + return null; + } + + /// + public IAssemblySymbol GetBaseAssembly() + { + return (_baseAssembly ??= FindBaseAssembly()) ?? throw new DiagnosticEventException(DiagnosticEvent.BootstrapClassesMissing()); + } + + /// + /// Attempts to load the base assembly. + /// + IAssemblySymbol? FindBaseAssembly() + { + foreach (var assembly in _universe.GetAssemblies()) + if (assembly.GetType("java.lang.Object") is Type) + return GetSymbol(assembly); + + return null; + } + + /// + public ITypeSymbol ResolveCoreType(string typeName) + { + return _coreTypeCache.GetOrAdd(typeName, _ => GetCoreAssembly().GetType(_)) ?? throw new DiagnosticEventException(DiagnosticEvent.CoreClassesMissing()); + } + + /// + /// Resolves the set of system assemblies. + /// + /// + IAssemblySymbol[] ResolveSystemAssemblies() + { + return _systemAssemblies ??= ResolveSystemAssembliesIter().Distinct().ToArray(); + } + + /// + /// Resolves the set of system assemblies that contain the system types. + /// + /// + IEnumerable ResolveSystemAssembliesIter() + { + foreach (var assembly in _universe.GetAssemblies()) + foreach (var typeName in GetSystemTypeNames()) + if (assembly.GetType(typeName) is Type t) + yield return GetSymbol(assembly); + } + + /// + public ITypeSymbol ResolveSystemType(string typeName) + { + return _systemTypeCache.GetOrAdd(typeName, FindSystemType) ?? throw new DiagnosticEventException(DiagnosticEvent.ClassNotFound(typeName)); + } + + /// + /// Attempts to load the specified system type. + /// + /// + /// + ITypeSymbol? FindSystemType(string typeName) + { + foreach (var assembly in ResolveSystemAssemblies()) + if (assembly.GetType(typeName) is { } t) + return t; + + return null; + } + + /// + public ITypeSymbol? ResolveRuntimeType(string typeName) + { + return GetRuntimeAssembly().GetType(typeName); + } + + /// + public ITypeSymbol? ResolveBaseType(string typeName) + { + return GetBaseAssembly().GetType(typeName); + } + + /// + public IAssemblySymbol? ResolveAssembly(string assemblyName) + { + return _universe.Load(assemblyName) is { } a ? GetSymbol(a) : null; + } + + /// + public ITypeSymbol? ResolveType(string typeName) + { + foreach (var assembly in _universe.GetAssemblies()) + if (assembly.GetType(typeName) is Type t) + return GetSymbol(t); + + return null; + } + + /// + public IAssemblySymbol GetSymbol(Assembly assembly) + { + return _symbols.GetOrCreateAssemblySymbol(assembly); + } + + /// + public IAssemblySymbolBuilder GetSymbol(AssemblyBuilder assembly) + { + return _symbols.GetOrCreateAssemblySymbol(assembly); + } + + /// + public IModuleSymbol GetSymbol(Module module) + { + return _symbols.GetOrCreateModuleSymbol(module); + } + + /// + public IModuleSymbolBuilder GetSymbol(ModuleBuilder module) + { + return _symbols.GetOrCreateModuleSymbol(module); + } + + /// + public ITypeSymbol GetSymbol(Type type) + { + return _symbols.GetOrCreateTypeSymbol(type); + } + + /// + public IMemberSymbol GetSymbol(MemberInfo memberInfo) + { + return _symbols.GetOrCreateMemberSymbol(memberInfo); + } + + /// + public IMethodBaseSymbol GetSymbol(MethodBase type) + { + return _symbols.GetOrCreateMethodBaseSymbol(type); + } + + /// + public IConstructorSymbol GetSymbol(ConstructorInfo ctor) + { + return _symbols.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IMethodSymbol GetSymbol(MethodInfo method) + { + return _symbols.GetOrCreateMethodSymbol(method); + } + + /// + public IFieldSymbol GetSymbol(FieldInfo field) + { + return _symbols.GetOrCreateFieldSymbol(field); + } + + /// + public IPropertySymbol GetSymbol(PropertyInfo property) + { + return _symbols.GetOrCreatePropertySymbol(property); + } + + /// + public IEventSymbol GetSymbol(EventInfo @event) + { + return _symbols.GetOrCreateEventSymbol(@event); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.Tools.Exporter/ExportTool.cs b/src/IKVM.Tools.Exporter/ExportTool.cs index 2a6eb04b65..b8e3ae086d 100644 --- a/src/IKVM.Tools.Exporter/ExportTool.cs +++ b/src/IKVM.Tools.Exporter/ExportTool.cs @@ -60,7 +60,7 @@ static Task ExecuteImplAsync(ExportOptions options, Func(); - services.AddSingleton(); + services.AddSingleton(); services.AddSingleton(); using var provider = services.BuildServiceProvider(); var exporter = provider.GetRequiredService(); diff --git a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs b/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs deleted file mode 100644 index 55d36cceaa..0000000000 --- a/src/IKVM.Tools.Exporter/ManagedTypeResolver.cs +++ /dev/null @@ -1,163 +0,0 @@ -#nullable enable - -using System; - -using IKVM.CoreLib.Symbols; -using IKVM.CoreLib.Symbols.Emit; -using IKVM.CoreLib.Symbols.IkvmReflection; -using IKVM.Reflection; -using IKVM.Reflection.Emit; -using IKVM.Runtime; - -using Type = IKVM.Reflection.Type; - -namespace IKVM.Tools.Exporter -{ - - class ManagedTypeResolver : IRuntimeSymbolResolver - { - - readonly Universe universe; - readonly Assembly runtimeAssembly; - readonly Assembly baseAssembly; - readonly IkvmReflectionSymbolContext symbols; - - /// - /// Initializes a new instance. - /// - /// - /// - public ManagedTypeResolver(IkvmReflectionSymbolContext symbols, Universe universe, Assembly runtimeAssembly, Assembly baseAssembly) - { - this.symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); - this.universe = universe ?? throw new ArgumentNullException(nameof(universe)); - this.runtimeAssembly = runtimeAssembly ?? throw new ArgumentNullException(nameof(runtimeAssembly)); - this.baseAssembly = baseAssembly; - } - - /// - public ISymbolContext Symbols => symbols; - - /// - public IAssemblySymbol ResolveCoreAssembly() - { - return ImportAssembly(universe.CoreLib); - } - - /// - public ITypeSymbol ResolveCoreType(string typeName) - { - return ResolveCoreAssembly().GetType(typeName) ?? throw new InvalidOperationException(); - } - - /// - public IAssemblySymbol ResolveRuntimeAssembly() - { - return ImportAssembly(runtimeAssembly); - } - - /// - public ITypeSymbol ResolveRuntimeType(string typeName) - { - return ResolveRuntimeAssembly().GetType(typeName) ?? throw new InvalidOperationException(); - } - - /// - public IAssemblySymbol ResolveBaseAssembly() - { - return ImportAssembly(baseAssembly); - } - - /// - public ITypeSymbol ResolveBaseType(string typeName) - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol? ResolveType(string typeName) - { - throw new NotImplementedException(); - } - - /// - public IAssemblySymbol ResolveAssembly(string assemblyName) - { - return ImportAssembly(universe.Load(assemblyName)); - } - - /// - public IAssemblySymbol ImportAssembly(Assembly assembly) - { - return symbols.GetOrCreateAssemblySymbol(assembly); - } - - /// - public IAssemblySymbolBuilder ImportAssembly(AssemblyBuilder assembly) - { - return symbols.GetOrCreateAssemblySymbol(assembly); - } - - /// - public IModuleSymbol ImportModule(Module module) - { - return symbols.GetOrCreateModuleSymbol(module); - } - - /// - public IModuleSymbolBuilder ImportModule(ModuleBuilder module) - { - return symbols.GetOrCreateModuleSymbol(module); - } - - /// - public ITypeSymbol ImportType(Type type) - { - return symbols.GetOrCreateTypeSymbol(type) ; - } - - /// - public ITypeSymbolBuilder ResolveType(TypeBuilder type) - { - return symbols.GetOrCreateTypeSymbol(type); - } - - /// - public IMemberSymbol ImportMember(MemberInfo module) - { - return symbols.GetOrCreateMemberSymbol(module); - } - - /// - public IMethodBaseSymbol ImportMethodBase(MethodBase method) - { - return symbols.GetOrCreateMethodBaseSymbol(method); - } - - /// - public IConstructorSymbol ImportConstructor(ConstructorInfo ctor) - { - return symbols.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IConstructorSymbolBuilder ResolveConstructor(ConstructorBuilder ctor) - { - return symbols.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IMethodSymbol ImportMethod(MethodInfo method) - { - return symbols.GetOrCreateMethodSymbol(method); - } - - /// - public IMethodSymbolBuilder ResolveMethod(MethodBuilder method) - { - return symbols.GetOrCreateMethodSymbol(method); - } - - } - -} diff --git a/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs b/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs index 4814a786d8..b51a8be78b 100644 --- a/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs +++ b/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs @@ -87,7 +87,7 @@ public ImportAssemblyResolver(Universe universe, ImportOptions options, IDiagnos /// /// /// - /// + /// internal Assembly LoadFile(string path) { string ex = null; @@ -101,7 +101,7 @@ internal Assembly LoadFile(string path) // to avoid problems (i.e. weird exceptions), we don't allow assemblies to load that reference a newer version of the corelib foreach (var asmref in module.GetReferencedAssemblies()) if (asmref.Name == universe.CoreLibName && asmref.Version > coreLibVersion) - throw new FatalCompilerErrorException(DiagnosticEvent.CoreAssemblyVersionMismatch(asmref.Name, universe.CoreLibName)); + throw new DiagnosticEventException(DiagnosticEvent.CoreAssemblyVersionMismatch(asmref.Name, universe.CoreLibName)); } var asm = universe.LoadAssembly(module); diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index b889c289c6..908069f170 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -165,7 +165,7 @@ internal IModuleSymbolBuilder CreateModuleBuilder() name.Version = state.version; // define a dynamic assembly and module - assemblyBuilder = Context.Resolver.ImportAssembly(Context.StaticCompiler.Universe.DefineDynamicAssembly(name, AssemblyBuilderAccess.ReflectionOnly, assemblyDir)); + assemblyBuilder = Context.Resolver.GetSymbol(Context.StaticCompiler.Universe.DefineDynamicAssembly(name, AssemblyBuilderAccess.ReflectionOnly, assemblyDir)); var moduleBuilder = assemblyBuilder.DefineModule(assemblyName, assemblyFile, EmitSymbols); // if configured to emit stack trace info set source file @@ -631,11 +631,11 @@ void Save() } catch (IOException x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorWritingFile(GetTypeWrapperFactory().ModuleBuilder.FullyQualifiedName, x.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorWritingFile(GetTypeWrapperFactory().ModuleBuilder.FullyQualifiedName, x.Message)); } catch (UnauthorizedAccessException x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorWritingFile(GetTypeWrapperFactory().ModuleBuilder.FullyQualifiedName, x.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorWritingFile(GetTypeWrapperFactory().ModuleBuilder.FullyQualifiedName, x.Message)); } } else @@ -648,11 +648,11 @@ void Save() } catch (IOException x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorWritingFile(Path.Combine(assemblyDir, assemblyFile), x.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorWritingFile(Path.Combine(assemblyDir, assemblyFile), x.Message)); } catch (UnauthorizedAccessException x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorWritingFile(Path.Combine(assemblyDir, assemblyFile), x.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorWritingFile(Path.Combine(assemblyDir, assemblyFile), x.Message)); } } } @@ -674,7 +674,7 @@ void AddJavaModuleAttribute(IModuleSymbolBuilder mb) } list = UnicodeUtil.EscapeInvalidSurrogates(list); - var cab = Context.Resolver.Symbols.CreateCustomAttribute(typeofJavaModuleAttribute.GetConstructor([Context.Resolver.ResolveCoreType(typeof(string).FullName).MakeArrayType()]), [list], propInfos, propValues); + var cab = Context.Resolver.Symbols.CreateCustomAttribute(typeofJavaModuleAttribute.GetConstructor([Context.Types.String.MakeArrayType()]), [list], propInfos, propValues); mb.SetCustomAttribute(cab); } else @@ -897,7 +897,7 @@ internal RemapperTypeWrapper(RuntimeContext context, ImportClassLoader classLoad this.baseTypeWrapper = GetBaseWrapper(context, c); classDef = c; bool baseIsSealed = false; - shadowType = context.Resolver.ImportType(context.StaticCompiler.Universe.GetType(c.Shadows, true)); + shadowType = context.Resolver.GetSymbol(context.StaticCompiler.Universe.GetType(c.Shadows, true)); classLoader.SetRemappedType(shadowType, this); var baseType = shadowType; ITypeSymbol baseInterface = null; @@ -1757,7 +1757,7 @@ private void EmitRedirect(ITypeSymbol baseType, CodeEmitter ilgen) // type specified, or class missing, assume loading .NET type if (m.Redirect.Type != null || m.Redirect.Class == null) { - var type = m.Redirect.Type != null ? DeclaringType.Context.Resolver.ImportType(DeclaringType.Context.StaticCompiler.Universe.GetType(m.Redirect.Type, true)) : baseType; + var type = m.Redirect.Type != null ? DeclaringType.Context.Resolver.GetSymbol(DeclaringType.Context.StaticCompiler.Universe.GetType(m.Redirect.Type, true)) : baseType; var redirParamTypes = classLoader.ArgTypeListFromSig(redirSig); var mi = type.GetMethod(m.Redirect.Name, redirParamTypes) ?? throw new InvalidOperationException(); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, mi); @@ -2301,7 +2301,7 @@ internal void Emit(MapXml.CodeGenContext context, CodeEmitter ilgen) for (int i = 0; i < map.Length; i++) { ilgen.Emit(System.Reflection.Emit.OpCodes.Dup); - ilgen.Emit(System.Reflection.Emit.OpCodes.Ldtoken, rcontext.Resolver.ResolveCoreType(map[i].Source)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Ldtoken, rcontext.Resolver.ResolveType(map[i].Source)); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, rcontext.CompilerFactory.GetTypeFromHandleMethod); ilgen.Emit(System.Reflection.Emit.OpCodes.Ceq); var label = ilgen.DefineLabel(); @@ -2593,7 +2593,7 @@ internal static int Compile(RuntimeContext context, StaticCompiler compiler, IDi } catch (FileFormatLimitationExceededException e) { - throw new FatalCompilerErrorException(DiagnosticEvent.FileFormatLimitationExceeded(e.Message)); + throw new DiagnosticEventException(DiagnosticEvent.FileFormatLimitationExceeded(e.Message)); } return 0; @@ -2604,7 +2604,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag diagnostics.GenericCompilerInfo($"JVM.Compile path: {import.path}, assembly: {import.assembly}"); // locate specified runtime assembly - var runtimeAssembly = context.Resolver.ResolveRuntimeAssembly(); + var runtimeAssembly = context.Resolver.GetRuntimeAssembly(); var allReferencesAreStrongNamed = IsSigned(runtimeAssembly); var references = new List(); @@ -2625,12 +2625,12 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag { // TODO we really should support binding redirects here to allow different revisions to be mixed if (asmref.FullName != runtimeAssembly.FullName) - throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); + throw new DiagnosticEventException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); } else { if (asmref.PublicKeyOrToken.IsEmpty == false) - throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); + throw new DiagnosticEventException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); } } } @@ -2744,10 +2744,10 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag import.target = IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll; if (import.target != IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && import.mainClass == null) - throw new FatalCompilerErrorException(DiagnosticEvent.ExeRequiresMainClass()); + throw new DiagnosticEventException(DiagnosticEvent.ExeRequiresMainClass()); if (import.target == IKVM.CoreLib.Symbols.Emit.PEFileKinds.Dll && import.props.Count != 0) - throw new FatalCompilerErrorException(DiagnosticEvent.PropertiesRequireExe()); + throw new DiagnosticEventException(DiagnosticEvent.PropertiesRequireExe()); if (import.path == null) { @@ -2767,7 +2767,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag if (import.targetIsModule) { if (import.classLoader != null) - throw new FatalCompilerErrorException(DiagnosticEvent.ModuleCannotHaveClassLoader()); + throw new DiagnosticEventException(DiagnosticEvent.ModuleCannotHaveClassLoader()); // TODO if we're overwriting a user specified assembly name, we need to emit a warning import.assembly = import.path.Name; @@ -2801,7 +2801,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag } catch (Exception e) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(import.remapfile.FullName, e.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorReadingFile(import.remapfile.FullName, e.Message)); } try @@ -2814,7 +2814,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag } catch (MapXml.MapXmlException x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorParsingMapFile(import.remapfile.FullName, x.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorParsingMapFile(import.remapfile.FullName, x.Message)); } if (loader.ValidateAndSetMap(map) == false) @@ -2831,13 +2831,13 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag if (import.bootstrap == false) { - allReferencesAreStrongNamed &= IsSigned(context.Resolver.ResolveBaseAssembly()); - loader.AddReference(context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.ResolveBaseAssembly())); + allReferencesAreStrongNamed &= IsSigned(context.Resolver.GetBaseAssembly()); + loader.AddReference(context.AssemblyClassLoaderFactory.FromAssembly(context.Resolver.GetBaseAssembly())); } if ((import.keyPair != null || import.publicKey != null) && !allReferencesAreStrongNamed) { - throw new FatalCompilerErrorException(DiagnosticEvent.StrongNameRequiresStrongNamedRefs()); + throw new DiagnosticEventException(DiagnosticEvent.StrongNameRequiresStrongNamedRefs()); } if (loader.map != null) @@ -2848,7 +2848,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag if (import.bootstrap == false) { loader.fakeTypes = context.FakeTypes; - loader.fakeTypes.Load(context.Resolver.ResolveBaseAssembly()); + loader.fakeTypes.Load(context.Resolver.GetBaseAssembly()); } return 0; @@ -2960,22 +2960,22 @@ int CompilePass3() } if (wrapper == null) { - throw new FatalCompilerErrorException(DiagnosticEvent.MainClassNotFound()); + throw new DiagnosticEventException(DiagnosticEvent.MainClassNotFound()); } var mw = wrapper.GetMethodWrapper("main", "([Ljava.lang.String;)V", false); if (mw == null || !mw.IsStatic) - throw new FatalCompilerErrorException(DiagnosticEvent.MainMethodNotFound()); + throw new DiagnosticEventException(DiagnosticEvent.MainMethodNotFound()); mw.Link(); var method = mw.GetMethod() as IMethodSymbol; if (method == null) - throw new FatalCompilerErrorException(DiagnosticEvent.UnsupportedMainMethod()); + throw new DiagnosticEventException(DiagnosticEvent.UnsupportedMainMethod()); if (!ReflectUtil.IsFromAssembly(method.DeclaringType, assemblyBuilder) && (!method.IsPublic || !method.DeclaringType.IsPublic)) { - throw new FatalCompilerErrorException(DiagnosticEvent.ExternalMainNotAccessible()); + throw new DiagnosticEventException(DiagnosticEvent.ExternalMainNotAccessible()); } var apartmentAttributeType = state.apartment switch @@ -3001,7 +3001,7 @@ int CompilePass3() } catch (IKVM.Reflection.MissingMemberException x) { - Context.StaticCompiler.IssueMissingTypeMessage((ITypeSymbol)Context.Resolver.ImportMember(x.MemberInfo)); + Context.StaticCompiler.IssueMissingTypeMessage((ITypeSymbol)Context.Resolver.GetSymbol(x.MemberInfo)); return 1; } } @@ -3046,20 +3046,20 @@ int CompilePass3() } if (classLoaderType == null) - throw new FatalCompilerErrorException(DiagnosticEvent.ClassLoaderNotFound()); + throw new DiagnosticEventException(DiagnosticEvent.ClassLoaderNotFound()); if (classLoaderType.IsPublic == false && ReflectUtil.IsFromAssembly(classLoaderType.TypeAsBaseType, assemblyBuilder) == false) - throw new FatalCompilerErrorException(DiagnosticEvent.ClassLoaderNotAccessible()); + throw new DiagnosticEventException(DiagnosticEvent.ClassLoaderNotAccessible()); if (classLoaderType.IsAbstract) - throw new FatalCompilerErrorException(DiagnosticEvent.ClassLoaderIsAbstract()); + throw new DiagnosticEventException(DiagnosticEvent.ClassLoaderIsAbstract()); if (classLoaderType.IsAssignableTo(Context.ClassLoaderFactory.LoadClassCritical("java.lang.ClassLoader")) == false) - throw new FatalCompilerErrorException(DiagnosticEvent.ClassLoaderNotClassLoader()); + throw new DiagnosticEventException(DiagnosticEvent.ClassLoaderNotClassLoader()); var classLoaderInitMethod = classLoaderType.GetMethodWrapper("", "(Lcli.System.Reflection.Assembly;)V", false); if (classLoaderInitMethod == null) - throw new FatalCompilerErrorException(DiagnosticEvent.ClassLoaderConstructorMissing()); + throw new DiagnosticEventException(DiagnosticEvent.ClassLoaderConstructorMissing()); // apply custom attribute specifying custom class loader Context.AttributeHelper.SetCustomAssemblyClassLoaderAttribute(assemblyBuilder, classLoaderType.TypeAsTBD); diff --git a/src/IKVM.Tools.Importer/ImportCommand.cs b/src/IKVM.Tools.Importer/ImportCommand.cs index b2e088a8d7..dd5706f712 100644 --- a/src/IKVM.Tools.Importer/ImportCommand.cs +++ b/src/IKVM.Tools.Importer/ImportCommand.cs @@ -294,36 +294,6 @@ public ImportCommand(bool root = true) ResourceOption.AddValidator(ValidateResource); } - /// - /// Parse an option set of Diagnostic ID values. - /// - /// - /// - Diagnostic[]? ParseDiagnosticArray(ArgumentResult result) - { - List? l = null; - - foreach (var i in result.Tokens) - { - foreach (var j in i.Value.Split(LIST_SEPARATOR, StringSplitOptions.RemoveEmptyEntries)) - { - if (int.TryParse(j, out var id) && Diagnostic.GetById(id) is { } diagnostic) - { - l ??= new(); - l.Add(diagnostic); - } - - if (j.StartsWith("IKVM", StringComparison.OrdinalIgnoreCase) && int.TryParse(j["IKVM".Length..], out var id2) && Diagnostic.GetById(id2) is { } diagnostic2) - { - l ??= new(); - l.Add(diagnostic2); - } - } - } - - return l?.ToArray(); - } - /// /// Parses an optional string option. An optional string argument represents three states: not present (null), /// empty (present with no values) or specified (present with values). diff --git a/src/IKVM.Tools.Importer/ImportContextFactory.cs b/src/IKVM.Tools.Importer/ImportContextFactory.cs index b151d670a9..40c8f58d91 100644 --- a/src/IKVM.Tools.Importer/ImportContextFactory.cs +++ b/src/IKVM.Tools.Importer/ImportContextFactory.cs @@ -73,7 +73,7 @@ public List Create(ImportOptions options) /// /// /// - /// + /// void Create(ImportOptions options, ImportContext import, List targets) { if (options.Output != null) @@ -102,7 +102,7 @@ void Create(ImportOptions options, ImportContext import, List tar import.guessFileKind = false; break; default: - throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedTargetType(options.Target.ToString())); + throw new DiagnosticEventException(DiagnosticEvent.UnrecognizedTargetType(options.Target.ToString())); } switch (options.Platform) @@ -132,7 +132,7 @@ void Create(ImportOptions options, ImportContext import, List tar import.imageFileMachine = IKVM.CoreLib.Symbols.ImageFileMachine.Unknown; break; default: - throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedPlatform(options.Platform.ToString())); + throw new DiagnosticEventException(DiagnosticEvent.UnrecognizedPlatform(options.Platform.ToString())); } switch (options.Apartment) @@ -147,7 +147,7 @@ void Create(ImportOptions options, ImportContext import, List tar import.apartment = ApartmentState.Unknown; break; default: - throw new FatalCompilerErrorException(DiagnosticEvent.UnrecognizedApartment(options.Apartment.ToString())); + throw new DiagnosticEventException(DiagnosticEvent.UnrecognizedApartment(options.Apartment.ToString())); } if (options.NoGlobbing) @@ -218,20 +218,20 @@ void Create(ImportOptions options, ImportContext import, List tar } catch (PathTooLongException) { - throw new FatalCompilerErrorException(DiagnosticEvent.PathTooLong(spec)); + throw new DiagnosticEventException(DiagnosticEvent.PathTooLong(spec)); } catch (DirectoryNotFoundException) { - throw new FatalCompilerErrorException(DiagnosticEvent.PathNotFound(spec)); + throw new DiagnosticEventException(DiagnosticEvent.PathNotFound(spec)); } catch (ArgumentException) { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(spec)); + throw new DiagnosticEventException(DiagnosticEvent.InvalidPath(spec)); } } if (!found) - throw new FatalCompilerErrorException(DiagnosticEvent.FileNotFound(spec)); + throw new DiagnosticEventException(DiagnosticEvent.FileNotFound(spec)); } foreach (var kvp in options.Resources) @@ -244,9 +244,9 @@ void Create(ImportOptions options, ImportContext import, List tar foreach (var kvp in options.ExternalResources) { if (!File.Exists(kvp.Value.FullName)) - throw new FatalCompilerErrorException(DiagnosticEvent.ExternalResourceNotFound(kvp.Value.FullName)); + throw new DiagnosticEventException(DiagnosticEvent.ExternalResourceNotFound(kvp.Value.FullName)); if (Path.GetFileName(kvp.Value.FullName) != kvp.Value.FullName) - throw new FatalCompilerErrorException(DiagnosticEvent.ExternalResourceNameInvalid(kvp.Value.FullName)); + throw new DiagnosticEventException(DiagnosticEvent.ExternalResourceNameInvalid(kvp.Value.FullName)); // TODO resource name clashes should be tested import.externalResources ??= new Dictionary(); @@ -346,7 +346,7 @@ void Create(ImportOptions options, ImportContext import, List tar if (options.FileAlign != null) { if (!uint.TryParse(options.FileAlign, out var filealign) || filealign < 512 || filealign > 8192 || (filealign & (filealign - 1)) != 0) - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidFileAlignment(options.FileAlign)); + throw new DiagnosticEventException(DiagnosticEvent.InvalidFileAlignment(options.FileAlign)); import.fileAlignment = filealign; } @@ -397,7 +397,7 @@ void Create(ImportOptions options, ImportContext import, List tar import.bootstrap = true; if (import.targetIsModule && import.sharedclassloader != null) - throw new FatalCompilerErrorException(DiagnosticEvent.SharedClassLoaderCannotBeUsedOnModuleTarget()); + throw new DiagnosticEventException(DiagnosticEvent.SharedClassLoaderCannotBeUsedOnModuleTarget()); ReadFiles(import, options.Inputs.Select(i => i.FullName).ToList()); @@ -414,7 +414,7 @@ void Create(ImportOptions options, ImportContext import, List tar { var basename = import.path == null ? import.defaultAssemblyName : import.path.Name; if (basename == null) - throw new FatalCompilerErrorException(DiagnosticEvent.NoOutputFileSpecified()); + throw new DiagnosticEventException(DiagnosticEvent.NoOutputFileSpecified()); int idx = basename.LastIndexOf('.'); if (idx > 0) @@ -446,7 +446,7 @@ void Create(ImportOptions options, ImportContext import, List tar /// Resolves the intra-peer references in the list of imports. /// /// - /// + /// void ResolveReferences(List imports) { var cache = new Dictionary(); @@ -474,12 +474,12 @@ void ResolveReferences(List imports) } if (resolver.ResolveReference(cache, refs, reference) == false) - throw new FatalCompilerErrorException(DiagnosticEvent.ReferenceNotFound(reference)); + throw new DiagnosticEventException(DiagnosticEvent.ReferenceNotFound(reference)); } // transform references into symbols foreach (var a in refs) - import.references.Add(runtime.Resolver.ImportAssembly(a)); + import.references.Add(runtime.Resolver.GetSymbol(a)); } } @@ -510,16 +510,16 @@ void ResolveReferences(List imports) /// Resolves any strong name keys. /// /// - /// + /// void ResolveStrongNameKeys(List targets) { foreach (var options in targets) { if (options.keyfile != null && options.keycontainer != null) - throw new FatalCompilerErrorException(DiagnosticEvent.CannotSpecifyBothKeyFileAndContainer()); + throw new DiagnosticEventException(DiagnosticEvent.CannotSpecifyBothKeyFileAndContainer()); if (options.keyfile == null && options.keycontainer == null && options.delaysign) - throw new FatalCompilerErrorException(DiagnosticEvent.DelaySignRequiresKey()); + throw new DiagnosticEventException(DiagnosticEvent.DelaySignRequiresKey()); if (options.keyfile != null) { @@ -563,7 +563,7 @@ static internal byte[] ReadAllBytes(FileInfo path) } catch (Exception x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(path.ToString(), x.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorReadingFile(path.ToString(), x.Message)); } } @@ -575,26 +575,26 @@ static internal FileInfo GetFileInfo(string path) if (fileInfo.Directory == null) { // this happens with an incorrect unc path (e.g. "\\foo\bar") - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + throw new DiagnosticEventException(DiagnosticEvent.InvalidPath(path)); } return fileInfo; } catch (ArgumentException) { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + throw new DiagnosticEventException(DiagnosticEvent.InvalidPath(path)); } catch (NotSupportedException) { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + throw new DiagnosticEventException(DiagnosticEvent.InvalidPath(path)); } catch (PathTooLongException) { - throw new FatalCompilerErrorException(DiagnosticEvent.PathTooLong(path)); + throw new DiagnosticEventException(DiagnosticEvent.PathTooLong(path)); } catch (UnauthorizedAccessException) { // this exception does not appear to be possible - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidPath(path)); + throw new DiagnosticEventException(DiagnosticEvent.InvalidPath(path)); } } @@ -714,7 +714,7 @@ void SetStrongNameKeyPair(ref StrongNameKeyPair strongNameKeyPair, FileInfo keyF } catch (Exception e) { - throw new FatalCompilerErrorException(DiagnosticEvent.InvalidStrongNameKeyPair(keyFile != null ? "file" : "container", e.Message)); + throw new DiagnosticEventException(DiagnosticEvent.InvalidStrongNameKeyPair(keyFile != null ? "file" : "container", e.Message)); } } @@ -861,7 +861,7 @@ bool ProcessZipFile(ImportContext import, string file, Predicate annotations, string filename) } catch (Exception x) { - throw new FatalCompilerErrorException(DiagnosticEvent.ErrorReadingFile(filename, x.Message)); + throw new DiagnosticEventException(DiagnosticEvent.ErrorReadingFile(filename, x.Message)); } } diff --git a/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs b/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs index 09a816b42b..53d32a8a19 100644 --- a/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs +++ b/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs @@ -30,8 +30,8 @@ public ImportDiagnosticHandler(ImportOptions options, string spec, DiagnosticFor /// public override bool IsEnabled(Diagnostic diagnostic) { - if (diagnostic.Level is DiagnosticLevel.Trace or DiagnosticLevel.Info) - return false; + //if (diagnostic.Level is DiagnosticLevel.Trace or DiagnosticLevel.Info) + // return false; if (diagnostic.Level == DiagnosticLevel.Warning && _options.NoWarn.Any(i => i.Id == diagnostic.Id)) return false; diff --git a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs index 927dbfc67b..87799b0642 100644 --- a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs +++ b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs @@ -21,9 +21,12 @@ Jeroen Frijters jeroen@frijters.net */ +#nullable enable + using System; -using System.IO; -using System.Threading; +using System.Collections.Concurrent; +using System.Collections.Generic; +using System.Linq; using IKVM.CoreLib.Diagnostics; using IKVM.CoreLib.Symbols; @@ -41,12 +44,37 @@ namespace IKVM.Tools.Importer class ImportRuntimeSymbolResolver : IRuntimeSymbolResolver { - readonly IDiagnosticHandler diagnostics; - readonly Universe universe; - readonly IkvmReflectionSymbolContext symbols; - readonly ImportOptions options; - IAssemblySymbol runtimeAssembly; - IAssemblySymbol baseAssembly; + /// + /// Gets the set of types from which to discover system assemblies. + /// + /// + static IEnumerable GetSystemTypeNames() + { + yield return "System.Object"; + yield return "System.Runtime.CompilerServices.RuntimeCompatibilityAttribute"; + yield return "System.Console"; + yield return "System.Threading.Interlocked"; + yield return "System.ComponentModel.EditorBrowsableAttribute"; + yield return "System.Collections.IEnumerable"; + yield return "System.Collections.Generic.IEnumerable`1"; + yield return "System.Environment"; + } + + readonly IDiagnosticHandler _diagnostics; + readonly Universe _universe; + readonly IkvmReflectionSymbolContext _symbols; + + IAssemblySymbol? _coreAssembly; + readonly ConcurrentDictionary _coreTypeCache = new(); + + IAssemblySymbol[]? _systemAssemblies; + readonly ConcurrentDictionary _systemTypeCache = new(); + + IAssemblySymbol? _runtimeAssembly; + readonly ConcurrentDictionary _runtimeTypeCache = new(); + + IAssemblySymbol? _baseAssembly; + readonly ConcurrentDictionary _baseTypeCache = new(); /// /// Initializes a new instance. @@ -54,165 +82,206 @@ class ImportRuntimeSymbolResolver : IRuntimeSymbolResolver /// /// /// - /// /// - public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols, ImportOptions options) + public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols) { - this.diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); - this.universe = universe ?? throw new ArgumentNullException(nameof(universe)); - this.symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); - this.options = options ?? throw new ArgumentNullException(nameof(options)); + _diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); + _universe = universe ?? throw new ArgumentNullException(nameof(universe)); + _symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); } /// - public ISymbolContext Symbols => symbols; + public ISymbolContext Symbols => _symbols; /// - public IAssemblySymbol ResolveCoreAssembly() + public IAssemblySymbol GetCoreAssembly() { - try - { - if (ImportAssembly(universe.CoreLib) is { } a) - return a; - } - catch (FileNotFoundException) - { - - } - - throw new FatalCompilerErrorException(DiagnosticEvent.CoreClassesMissing()); + return (_coreAssembly ??= GetSymbol(_universe.CoreLib)) ?? throw new DiagnosticEventException(DiagnosticEvent.CoreClassesMissing()); } /// - public IAssemblySymbol ResolveRuntimeAssembly() + public IAssemblySymbol GetRuntimeAssembly() { - if (runtimeAssembly == null) - Interlocked.CompareExchange(ref runtimeAssembly, LoadRuntimeAssembly(), null); - - return runtimeAssembly; + return (_runtimeAssembly ??= FindRuntimeAssembly()) ?? throw new DiagnosticEventException(DiagnosticEvent.RuntimeNotFound()); } /// /// Attempts to load the runtime assembly. /// - /// - IAssemblySymbol LoadRuntimeAssembly() + IAssemblySymbol? FindRuntimeAssembly() { - foreach (var assembly in universe.GetAssemblies()) + foreach (var assembly in _universe.GetAssemblies()) if (assembly.GetType("IKVM.Runtime.JVM") is Type) - return ImportAssembly(assembly); + return GetSymbol(assembly); - throw new FatalCompilerErrorException(DiagnosticEvent.RuntimeNotFound()); + return null; } /// - public IAssemblySymbol ResolveBaseAssembly() + public IAssemblySymbol GetBaseAssembly() { - if (baseAssembly == null) - Interlocked.CompareExchange(ref baseAssembly, LoadBaseAssembly(), null); - - return baseAssembly; + return (_baseAssembly ??= FindBaseAssembly()) ?? throw new DiagnosticEventException(DiagnosticEvent.BootstrapClassesMissing()); } /// /// Attempts to load the base assembly. /// - IAssemblySymbol LoadBaseAssembly() + IAssemblySymbol? FindBaseAssembly() { - foreach (var assembly in universe.GetAssemblies()) + foreach (var assembly in _universe.GetAssemblies()) if (assembly.GetType("java.lang.Object") is Type) - return ImportAssembly(assembly); + return GetSymbol(assembly); - throw new Exception(); + return null; } /// public ITypeSymbol ResolveCoreType(string typeName) { - return ResolveCoreAssembly().GetType(typeName); + return _coreTypeCache.GetOrAdd(typeName, _ => GetCoreAssembly().GetType(_)) ?? throw new DiagnosticEventException(DiagnosticEvent.CoreClassesMissing()); + } + + /// + /// Resolves the set of system assemblies. + /// + /// + IAssemblySymbol[] ResolveSystemAssemblies() + { + return _systemAssemblies ??= ResolveSystemAssembliesIter().Distinct().ToArray(); + } + + /// + /// Resolves the set of system assemblies that contain the system types. + /// + /// + IEnumerable ResolveSystemAssembliesIter() + { + foreach (var assembly in _universe.GetAssemblies()) + foreach (var typeName in GetSystemTypeNames()) + if (assembly.GetType(typeName) is Type t) + yield return GetSymbol(assembly); } /// - public ITypeSymbol ResolveRuntimeType(string typeName) + public ITypeSymbol ResolveSystemType(string typeName) { - return ResolveRuntimeAssembly().GetType(typeName); + return _systemTypeCache.GetOrAdd(typeName, FindSystemType) ?? throw new DiagnosticEventException(DiagnosticEvent.ClassNotFound(typeName)); + } + + /// + /// Attempts to load the specified system type. + /// + /// + /// + ITypeSymbol? FindSystemType(string typeName) + { + foreach (var assembly in ResolveSystemAssemblies()) + if (assembly.GetType(typeName) is { } t) + return t; + + return null; + } + + /// + public ITypeSymbol? ResolveRuntimeType(string typeName) + { + return GetRuntimeAssembly().GetType(typeName); } /// - public ITypeSymbol ResolveBaseType(string typeName) + public ITypeSymbol? ResolveBaseType(string typeName) { - return ResolveBaseAssembly().GetType(typeName); + return GetBaseAssembly().GetType(typeName); } /// - public IAssemblySymbol ResolveAssembly(string assemblyName) + public IAssemblySymbol? ResolveAssembly(string assemblyName) { - return universe.Load(assemblyName) is { } a ? symbols.GetOrCreateAssemblySymbol(a) : null; + return _universe.Load(assemblyName) is { } a ? GetSymbol(a) : null; } /// - public ITypeSymbol ResolveType(string typeName) + public ITypeSymbol? ResolveType(string typeName) { - foreach (var assembly in universe.GetAssemblies()) + foreach (var assembly in _universe.GetAssemblies()) if (assembly.GetType(typeName) is Type t) - return ImportType(t); + return GetSymbol(t); return null; } /// - public IAssemblySymbol ImportAssembly(Assembly assembly) + public IAssemblySymbol GetSymbol(Assembly assembly) { - return symbols.GetOrCreateAssemblySymbol(assembly); + return _symbols.GetOrCreateAssemblySymbol(assembly); } /// - public IAssemblySymbolBuilder ImportAssembly(AssemblyBuilder assembly) + public IAssemblySymbolBuilder GetSymbol(AssemblyBuilder assembly) { - return symbols.GetOrCreateAssemblySymbol(assembly); + return _symbols.GetOrCreateAssemblySymbol(assembly); } /// - public IModuleSymbol ImportModule(Module module) + public IModuleSymbol GetSymbol(Module module) { - return symbols.GetOrCreateModuleSymbol(module); + return _symbols.GetOrCreateModuleSymbol(module); } /// - public IModuleSymbolBuilder ImportModule(ModuleBuilder module) + public IModuleSymbolBuilder GetSymbol(ModuleBuilder module) { - return symbols.GetOrCreateModuleSymbol(module); + return _symbols.GetOrCreateModuleSymbol(module); } /// - public ITypeSymbol ImportType(Type type) + public ITypeSymbol GetSymbol(Type type) { - return symbols.GetOrCreateTypeSymbol(type); + return _symbols.GetOrCreateTypeSymbol(type); } /// - public IMemberSymbol ImportMember(MemberInfo memberInfo) + public IMemberSymbol GetSymbol(MemberInfo memberInfo) { - return symbols.GetOrCreateMemberSymbol(memberInfo); + return _symbols.GetOrCreateMemberSymbol(memberInfo); } /// - public IMethodBaseSymbol ImportMethodBase(MethodBase type) + public IMethodBaseSymbol GetSymbol(MethodBase type) { - return symbols.GetOrCreateMethodBaseSymbol(type); + return _symbols.GetOrCreateMethodBaseSymbol(type); } /// - public IConstructorSymbol ImportConstructor(ConstructorInfo ctor) + public IConstructorSymbol GetSymbol(ConstructorInfo ctor) { - return symbols.GetOrCreateConstructorSymbol(ctor); + return _symbols.GetOrCreateConstructorSymbol(ctor); } /// - public IMethodSymbol ImportMethod(MethodInfo method) + public IMethodSymbol GetSymbol(MethodInfo method) { - return symbols.GetOrCreateMethodSymbol(method); + return _symbols.GetOrCreateMethodSymbol(method); } + + /// + public IFieldSymbol GetSymbol(FieldInfo field) + { + return _symbols.GetOrCreateFieldSymbol(field); + } + + /// + public IPropertySymbol GetSymbol(PropertyInfo property) + { + return _symbols.GetOrCreatePropertySymbol(property); + } + + /// + public IEventSymbol GetSymbol(EventInfo @event) + { + return _symbols.GetOrCreateEventSymbol(@event); + } + } } \ No newline at end of file diff --git a/src/IKVM.Tools.Importer/ImportTool.cs b/src/IKVM.Tools.Importer/ImportTool.cs index 5690e4466c..6dd53d2323 100644 --- a/src/IKVM.Tools.Importer/ImportTool.cs +++ b/src/IKVM.Tools.Importer/ImportTool.cs @@ -7,6 +7,7 @@ using System.IO; using System.Reflection.Metadata; using System.Reflection.PortableExecutable; +using System.Runtime.ExceptionServices; using System.Threading; using System.Threading.Tasks; @@ -70,7 +71,7 @@ async Task ExecuteImplAsync(ImportOptions options, CancellationToken cancel services.AddSingleton(p => p.GetRequiredService().Universe); services.AddSingleton(); services.AddSingleton(); - services.AddSingleton(p => new RuntimeContextOptions(p.GetRequiredService().Bootstrap)); + services.AddSingleton(p => CreateContextOptions(p)); services.AddSingleton(); services.AddSingleton(); services.AddSingleton(); @@ -78,28 +79,34 @@ async Task ExecuteImplAsync(ImportOptions options, CancellationToken cancel try { - // convert options to imports - var imports = provider.GetRequiredService().Create(options); - if (imports.Count == 0) - throw new FatalCompilerErrorException(DiagnosticEvent.NoTargetsFound()); - - // execute the compiler - return await Task.Run(() => Execute( - provider.GetRequiredService(), - provider.GetRequiredService(), - provider.GetRequiredService(), - imports)); + try + { + // convert options to imports + var imports = provider.GetRequiredService().Create(options); + if (imports.Count == 0) + throw new DiagnosticEventException(DiagnosticEvent.NoTargetsFound()); + + // execute the compiler + return await Task.Run(() => Execute( + provider.GetRequiredService(), + provider.GetRequiredService(), + provider.GetRequiredService(), + imports)); + } + catch (DiagnosticEventException e) + { + ExceptionDispatchInfo.Capture(e).Throw(); + throw; + } + catch (Exception e) + { + throw new DiagnosticEventException(DiagnosticEvent.GenericCompilerError(e.Message)); + } } - catch (FatalCompilerErrorException e) + catch (DiagnosticEventException e) { provider.GetRequiredService().Report(e.Event); return e.Event.Diagnostic.Id; - - } - catch (Exception e) - { - provider.GetRequiredService().GenericCompilerError(e.Message); - return Diagnostic.GenericCompilerError.Id; } } @@ -270,6 +277,19 @@ static DiagnosticOptions GetDiagnosticOptions(IServiceProvider services, ImportO }; } + /// + /// Creates the . + /// + /// + /// + static RuntimeContextOptions CreateContextOptions(IServiceProvider services) + { + var u = services.GetRequiredService(); + var isNetFX = u.CoreLibName == "mscorlib"; + var dynamicSuffix = isNetFX ? RuntimeContextOptions.SignedDefaultDynamicAssemblySuffixAndPublicKey : RuntimeContextOptions.UnsignedDefaultDynamicAssemblySuffixAndPublicKey; + return new RuntimeContextOptions(services.GetRequiredService().Bootstrap, dynamicSuffix); + } + /// /// Initializes a new instance. /// diff --git a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs index 0cad9fc1fb..13b650c2ef 100644 --- a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs +++ b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs @@ -696,7 +696,7 @@ protected override void FinishGhost(ITypeSymbolBuilder typeBuilder, RuntimeJavaM if (methods[i].IsAbstract) { // This should only happen for remapped types (defined in map.xml), because normally you'd get a miranda method. - throw new FatalCompilerErrorException(DiagnosticEvent.GhostInterfaceMethodMissing(implementers[j].Name, Name, methods[i].Name, methods[i].Signature)); + throw new DiagnosticEventException(DiagnosticEvent.GhostInterfaceMethodMissing(implementers[j].Name, Name, methods[i].Name, methods[i].Signature)); } // We're inheriting a default method ilgen.Emit(OpCodes.Pop); diff --git a/src/IKVM.Tools.Importer/StaticCompiler.cs b/src/IKVM.Tools.Importer/StaticCompiler.cs index 52f8d526ca..ab413e256a 100644 --- a/src/IKVM.Tools.Importer/StaticCompiler.cs +++ b/src/IKVM.Tools.Importer/StaticCompiler.cs @@ -80,19 +80,19 @@ internal IAssemblySymbol LoadFile(string path) internal ITypeSymbol GetTypeForMapXml(RuntimeClassLoader loader, string name) { - return GetType(loader, name) ?? throw new FatalCompilerErrorException(DiagnosticEvent.MapFileTypeNotFound(name)); + return GetType(loader, name) ?? throw new DiagnosticEventException(DiagnosticEvent.MapFileTypeNotFound(name)); } internal RuntimeJavaType GetClassForMapXml(RuntimeClassLoader loader, string name) { - return loader.TryLoadClassByName(name) ?? throw new FatalCompilerErrorException(DiagnosticEvent.MapFileClassNotFound(name)); + return loader.TryLoadClassByName(name) ?? throw new DiagnosticEventException(DiagnosticEvent.MapFileClassNotFound(name)); } internal RuntimeJavaField GetFieldForMapXml(RuntimeClassLoader loader, string clazz, string name, string sig) { var fw = GetClassForMapXml(loader, clazz).GetFieldWrapper(name, sig); if (fw == null) - throw new FatalCompilerErrorException(DiagnosticEvent.MapFileFieldNotFound(name, clazz)); + throw new DiagnosticEventException(DiagnosticEvent.MapFileFieldNotFound(name, clazz)); fw.Link(); return fw; @@ -116,7 +116,7 @@ internal static void LinkageError(string msg, RuntimeJavaType actualType, Runtim str += string.Format("\n\t(Please add a reference to {0})", expectedType.TypeAsBaseType.Assembly.Location); } - throw new FatalCompilerErrorException(DiagnosticEvent.LinkageError(str)); + throw new DiagnosticEventException(DiagnosticEvent.LinkageError(str)); } static string AssemblyQualifiedName(RuntimeJavaType javaType) diff --git a/src/ikvmc/Properties/launchSettings.json b/src/ikvmc/Properties/launchSettings.json index a472b2cdaf..31d9cf8012 100644 --- a/src/ikvmc/Properties/launchSettings.json +++ b/src/ikvmc/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmc": { "commandName": "Project", - "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net472\\IKVM.Java.ikvmc.rsp" + "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net8.0\\IKVM.Java.ikvmc.rsp" } } } diff --git a/src/ikvmc/ikvmc.csproj b/src/ikvmc/ikvmc.csproj index 2be36ac434..ae6f133e10 100644 --- a/src/ikvmc/ikvmc.csproj +++ b/src/ikvmc/ikvmc.csproj @@ -1,7 +1,7 @@  Exe - net472;net8.0;;net6.0; + net8.0;net472;;net6.0; $(_SupportedToolRuntimes) true true diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json index c08101f8e5..64fa8dc5e7 100644 --- a/src/ikvmstub/Properties/launchSettings.json +++ b/src/ikvmstub/Properties/launchSettings.json @@ -1,8 +1,8 @@ { "profiles": { "ikvmstub": { - "commandName": "Project", - "commandLineArgs": "--bootstrap --skiperror --nostdlib --parameters --lib:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\" --reference:\"D:\\ikvm\\src\\IKVM.Java-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"C:\\Users\\jhaltom\\System.Threading.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Threading.dll\"" + "commandName": "Project", + "commandLineArgs": "--bootstrap --nostdlib --skiperror --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.Win32.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Collections.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.InteropServices.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net8.0\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"C:\\Users\\jhaltom\\System.Net.Primitives.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Primitives.dll\"" } } } \ No newline at end of file From 1e14f735db527eeacfcae9dc25b119d52af86f98 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 27 Sep 2024 19:55:03 -0500 Subject: [PATCH 16/59] More. --- .../IkvmReflection/IkvmReflectionSymbol.cs | 1 + src/IKVM.Runtime/Accessors/FieldAccessor.cs | 28 ++++---- src/IKVM.Runtime/Accessors/MethodAccessor.cs | 19 +++--- .../Accessors/PropertyAccessor.cs | 12 ++-- src/IKVM.Runtime/AttributeHelper.cs | 3 +- src/IKVM.Runtime/ExceptionHelper.cs | 2 +- .../Java/Externs/ikvm/internal/CallerID.cs | 6 +- .../runtime/AppDomainAssemblyClassLoader.cs | 4 +- .../ikvm/runtime/AssemblyClassLoader.cs | 10 +-- .../Java/Externs/ikvm/runtime/Launcher.cs | 2 +- .../Java/Externs/ikvm/runtime/Startup.cs | 2 +- .../Java/Externs/ikvm/runtime/Util.cs | 4 +- .../Java/Externs/java/lang/SecurityManager.cs | 2 +- .../java/lang/invoke/MethodHandleNatives.cs | 9 +-- .../Java/Externs/java/lang/reflect/Array.cs | 65 ++++++++++--------- .../Externs/java/security/AccessController.cs | 2 +- .../Java/Externs/sun/misc/MiscHelper.cs | 4 +- .../Java/Externs/sun/misc/Unsafe.cs | 8 +-- src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs | 6 +- .../sun/net/www/protocol/ikvmres/Handler.cs | 2 +- .../Java/Externs/sun/reflect/Reflection.cs | 4 +- src/IKVM.Runtime/Launcher.cs | 4 +- .../MethodHandleUtil.jniexport.cs | 24 +++---- src/IKVM.Runtime/MethodHandleUtil.root.cs | 8 +-- src/IKVM.Runtime/ReflectUtil.cs | 2 + .../RuntimeAssemblyClassLoaderFactory.cs | 3 +- src/IKVM.Runtime/RuntimeClassLoader.cs | 2 +- ...tionJavaType.MultipleAnnotationJavaType.cs | 2 +- ...ntimeManagedJavaType.EnumWrapJavaMethod.cs | 2 +- .../Vfs/VfsAssemblyClassDirectory.cs | 10 +-- src/ikvmc/ikvmc.csproj | 2 +- src/ikvmstub/Properties/launchSettings.json | 2 +- src/ikvmstub/ikvmstub.csproj | 2 +- 33 files changed, 128 insertions(+), 130 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index 68f30b47dd..b766fd03e3 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -508,6 +508,7 @@ public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(IKVM.Ref { return value switch { + IList aa => ResolveCustomAttributeTypedArguments(aa), Type v => ResolveTypeSymbol(v), _ => value }; diff --git a/src/IKVM.Runtime/Accessors/FieldAccessor.cs b/src/IKVM.Runtime/Accessors/FieldAccessor.cs index 40a44cf98c..8b8ab657c9 100644 --- a/src/IKVM.Runtime/Accessors/FieldAccessor.cs +++ b/src/IKVM.Runtime/Accessors/FieldAccessor.cs @@ -102,11 +102,10 @@ Func MakeGetter() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Type.Name.Replace(".", "_")}__{Field.Name}", Type, false, typeof(TField), Array.Empty()); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(OpCodes.Ldsfld, Field); il.Emit(OpCodes.Ret); - il.DoEmit(); return (Func)dm.CreateDelegate(typeof(Func)); #endif @@ -123,12 +122,11 @@ Action MakeSetter() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Type.Name.Replace(".", "_")}__{Field.Name}", Type, false, typeof(void), new[] { typeof(TField) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(OpCodes.Ldarg_0); il.Emit(OpCodes.Stsfld, Field); il.Emit(OpCodes.Ret); - il.DoEmit(); return (Action)dm.CreateDelegate(typeof(Action)); #endif @@ -231,13 +229,12 @@ GetterDelegate MakeGetter() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Field.DeclaringType.Name.Replace(".", "_")}__{Field.Name}", Type, false, typeof(TField), new[] { typeof(TObject) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(OpCodes.Ldarg_0); il.Emit(OpCodes.Castclass, Type); il.Emit(OpCodes.Ldfld, Field); il.Emit(OpCodes.Ret); - il.DoEmit(); return (GetterDelegate)dm.CreateDelegate(typeof(GetterDelegate)); #endif @@ -253,14 +250,13 @@ SetterDelegate MakeSetter() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Field.DeclaringType.Name.Replace(".", "_")}__{Field.Name}", Type, false, typeof(void), new[] { typeof(TObject), typeof(TField) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(OpCodes.Ldarg_0); il.Emit(OpCodes.Castclass, Type); il.Emit(OpCodes.Ldarg_1); il.Emit(OpCodes.Stfld, Field); il.Emit(OpCodes.Ret); - il.DoEmit(); return (SetterDelegate)dm.CreateDelegate(typeof(SetterDelegate)); #endif @@ -276,12 +272,12 @@ ExchangeDelegate MakeExchange() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Field.DeclaringType.Name.Replace(".", "_")}__{Field.Name}", Type, false, typeof(TField), new[] { typeof(TObject), typeof(TField) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); - il.EmitLdarg(0); + il.Emit(OpCodes.Ldarg_0); il.Emit(OpCodes.Castclass, Type); il.Emit(Field.IsStatic ? OpCodes.Ldsflda: OpCodes.Ldflda, Field); - il.EmitLdarg(1); + il.Emit(OpCodes.Ldarg_1); switch (typeof(TField)) { @@ -305,7 +301,6 @@ ExchangeDelegate MakeExchange() } il.Emit(OpCodes.Ret); - il.DoEmit(); return (ExchangeDelegate)dm.CreateDelegate(typeof(ExchangeDelegate)); #endif @@ -321,13 +316,13 @@ CompareExchangeDelegate MakeCompareExchange() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Field.DeclaringType.Name.Replace(".", "_")}__{Field.Name}", Type, false, typeof(TField), new[] { typeof(TObject), typeof(TField), typeof(TField) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); - il.EmitLdarg(0); + il.Emit(OpCodes.Ldarg_0); il.Emit(OpCodes.Castclass, Type); il.Emit(Field.IsStatic ? OpCodes.Ldsflda : OpCodes.Ldflda, Field); - il.EmitLdarg(1); - il.EmitLdarg(2); + il.Emit(OpCodes.Ldarg_1); + il.Emit(OpCodes.Ldarg_2); switch (typeof(TField)) { @@ -351,7 +346,6 @@ CompareExchangeDelegate MakeCompareExchange() } il.Emit(OpCodes.Ret); - il.DoEmit(); return (CompareExchangeDelegate)dm.CreateDelegate(typeof(CompareExchangeDelegate)); #endif diff --git a/src/IKVM.Runtime/Accessors/MethodAccessor.cs b/src/IKVM.Runtime/Accessors/MethodAccessor.cs index 0e0088ab14..09446acec6 100644 --- a/src/IKVM.Runtime/Accessors/MethodAccessor.cs +++ b/src/IKVM.Runtime/Accessors/MethodAccessor.cs @@ -139,7 +139,7 @@ TDelegate MakeInvoker() // generate new dynamic method var dm = DynamicMethodUtil.Create($"____{Type.Name.Replace(".", "_")}__{Method.Name}", Type, false, delegateReturnType, delegateParameterTypes); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); // advance through each argument var n = 0; @@ -147,34 +147,33 @@ TDelegate MakeInvoker() // load first argument, which is the instance if non-static if (Method.IsStatic == false && Method.IsConstructor == false) { - il.EmitLdarg(n++); + il.Emit(OpCodes.Ldarg, n++); if (delegateParameterTypes[0] != Type) - il.EmitCastclass(Type); + il.Emit(OpCodes.Castclass, Type); } // emit conversion code for the remainder of the arguments for (var i = 0; i < parameters.Length; i++) { var delegateParameterType = delegateParameterTypes[n]; - il.EmitLdarg(n++); + il.Emit(OpCodes.Ldarg, n++); if (parameters[i].ParameterType != delegateParameterType) - il.EmitCastclass(parameters[i].ParameterType); + il.Emit(OpCodes.Castclass, parameters[i].ParameterType); } if (Method.IsConstructor) - il.Emit(OpCodes.Newobj, Method); + il.Emit(OpCodes.Newobj, (ConstructorInfo)Method); else if (Method.IsStatic || Method.IsVirtual == false) - il.Emit(OpCodes.Call, Method); + il.Emit(OpCodes.Call, (MethodInfo)Method); else - il.Emit(OpCodes.Callvirt, Method); + il.Emit(OpCodes.Callvirt, (MethodInfo)Method); // convert to delegate value if (delegateReturnType != typeof(void)) if (Method.IsConstructor && delegateReturnType != Type || Method.IsConstructor == false && delegateReturnType != ((MethodInfo)Method).ReturnType) - il.EmitCastclass(delegateReturnType); + il.Emit(OpCodes.Castclass, delegateReturnType); il.Emit(OpCodes.Ret); - il.DoEmit(); return (TDelegate)dm.CreateDelegate(typeof(TDelegate)); #endif diff --git a/src/IKVM.Runtime/Accessors/PropertyAccessor.cs b/src/IKVM.Runtime/Accessors/PropertyAccessor.cs index 88aee410dd..c078d1ae53 100644 --- a/src/IKVM.Runtime/Accessors/PropertyAccessor.cs +++ b/src/IKVM.Runtime/Accessors/PropertyAccessor.cs @@ -101,11 +101,10 @@ Func MakeGetter() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Type.Name.Replace(".", "_")}__{Property.Name}", Type, false, typeof(TProperty), Array.Empty()); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(Property.GetMethod.IsVirtual ? OpCodes.Callvirt : OpCodes.Call, Property.GetMethod); il.Emit(OpCodes.Ret); - il.DoEmit(); return (Func)dm.CreateDelegate(typeof(Func)); #endif @@ -122,12 +121,11 @@ Action MakeSetter() throw new NotImplementedException(); #else var dm = DynamicMethodUtil.Create($"____{Type.Name.Replace(".", "_")}__{Property.Name}", Type, false, typeof(void), new[] { typeof(TProperty) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(OpCodes.Ldarg_0); il.Emit(Property.SetMethod.IsVirtual ? OpCodes.Callvirt : OpCodes.Call, Property.SetMethod); il.Emit(OpCodes.Ret); - il.DoEmit(); return (Action)dm.CreateDelegate(typeof(Action)); #endif @@ -204,13 +202,12 @@ Func MakeGetter() throw new InternalException($"Property {Property.Name} cannot be read."); var dm = DynamicMethodUtil.Create($"____{Property.DeclaringType.Name.Replace(".", "_")}__{Property.Name}", Type, false, typeof(TProperty), new[] { typeof(TObject) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(OpCodes.Ldarg_0); il.Emit(OpCodes.Castclass, Type); il.Emit(Property.GetMethod.IsVirtual ? OpCodes.Callvirt : OpCodes.Call, Property.GetMethod); il.Emit(OpCodes.Ret); - il.DoEmit(); return (Func)dm.CreateDelegate(typeof(Func)); #endif @@ -229,14 +226,13 @@ Action MakeSetter() throw new InternalException($"Property {Property.Name} cannot be written."); var dm = DynamicMethodUtil.Create($"____{Property.DeclaringType.Name.Replace(".", "_")}__{Property.Name}", Type, false, typeof(void), new[] { typeof(TObject), typeof(TProperty) }); - var il = JVM.Context.CodeEmitterFactory.Create(dm); + var il = dm.GetILGenerator(); il.Emit(OpCodes.Ldarg_0); il.Emit(OpCodes.Castclass, Type); il.Emit(OpCodes.Ldarg_1); il.Emit(Property.SetMethod.IsVirtual ? OpCodes.Callvirt : OpCodes.Call, Property.SetMethod); il.Emit(OpCodes.Ret); - il.DoEmit(); return (Action)dm.CreateDelegate(typeof(Action)); #endif diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index 09ab282415..ebdec4ceb6 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -23,6 +23,7 @@ Jeroen Frijters */ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.ComponentModel; using System.Diagnostics; using System.Reflection; @@ -876,7 +877,7 @@ internal NameSigAttribute GetNameSig(IMemberSymbol member) internal T[] DecodeArray(IKVM.CoreLib.Symbols.CustomAttributeTypedArgument arg) { - var elems = (IKVM.CoreLib.Symbols.CustomAttributeTypedArgument[])arg.Value; + var elems = (ImmutableArray)arg.Value; var arr = new T[elems.Length]; for (int i = 0; i < arr.Length; i++) arr[i] = (T)elems[i].Value; diff --git a/src/IKVM.Runtime/ExceptionHelper.cs b/src/IKVM.Runtime/ExceptionHelper.cs index 0cbf5dc621..01ce0199e4 100644 --- a/src/IKVM.Runtime/ExceptionHelper.cs +++ b/src/IKVM.Runtime/ExceptionHelper.cs @@ -256,7 +256,7 @@ internal static void Append(ExceptionHelper exceptionHelper, List /// /// - static global::java.util.jar.Manifest GetManifestForAssemblyJar(Assembly assembly, string resourceName) + static global::java.util.jar.Manifest GetManifestForAssemblyJar(IAssemblySymbol assembly, string resourceName) { if (assembly is null) throw new ArgumentNullException(nameof(assembly)); @@ -262,7 +262,7 @@ public static string toString(global::java.lang.ClassLoader _this) #else // note that we don't do a security check here, because if you have the Assembly object, // you can already get at all the types in it. - return JVM.Context.AssemblyClassLoaderFactory.FromAssembly(asm).GetJavaClassLoader(); + return JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.GetSymbol(asm)).GetJavaClassLoader(); #endif } diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Launcher.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Launcher.cs index 1b1271ea54..20c6267e58 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Launcher.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Launcher.cs @@ -32,7 +32,7 @@ public static int run(Type main, string[] args, string jvmArgPrefix, global::jav // statically compiled entry points need to be explicitly added to the classpath // this is sort of a hack and should be removed with a better class loader hierarchy if (main != null && main.Assembly.IsDynamic == false) - JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().AddDelegate(JVM.Context.AssemblyClassLoaderFactory.FromAssembly(main.Assembly)); + JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().AddDelegate(JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.GetSymbol(main.Assembly))); // copy properties to a CLR type var p = new Dictionary(); diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Startup.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Startup.cs index f8a297f710..2a710d59e0 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Startup.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Startup.cs @@ -17,7 +17,7 @@ public static void addBootClassPathAssembly(Assembly asm) #if FIRST_PASS throw new NotImplementedException(); #else - JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().AddDelegate(JVM.Context.AssemblyClassLoaderFactory.FromAssembly(asm)); + JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().AddDelegate(JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.GetSymbol(asm))); #endif } diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs index 6dc9ffc64e..f765da0e7f 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs @@ -77,7 +77,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, if (t.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || t == typeof(void)) return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).ClassObject; - if (!IsVisibleAsClass(ts)) + if (!IsVisibleAsClass(t)) return null; var tw = JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(ts); @@ -140,7 +140,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, #endif } - private static bool IsVisibleAsClass(ITypeSymbol type) + private static bool IsVisibleAsClass(Type type) { while (type.HasElementType) { diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/SecurityManager.cs b/src/IKVM.Runtime/Java/Externs/java/lang/SecurityManager.cs index 36c28392f6..0a2a4180cd 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/SecurityManager.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/SecurityManager.cs @@ -53,7 +53,7 @@ static class SecurityManager if (type == typeof(global::java.lang.SecurityManager)) continue; - stack.Add(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(type).ClassObject); + stack.Add(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(type)).ClassObject); } return stack.ToArray(); diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs b/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs index 18a662b403..db53ee23ab 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs @@ -366,18 +366,19 @@ static Delegate CreateMemberNameDelegate(RuntimeJavaMethod mw, global::java.lang mw = thisType.Context.JavaBase.TypeOfjavaLangThrowable.GetMethodWrapper(mw.Name, mw.Signature, true); } } - RuntimeJavaType tw = mw.DeclaringType; + + var tw = mw.DeclaringType; tw.Finish(); mw.Link(); mw.ResolveMethod(); - MethodInfo mi = mw.GetMethod() as MethodInfo; + var mi = mw.GetMethod() as MethodInfo; if (mi != null && !mw.HasCallerID && mw.IsStatic && tw.Context.MethodHandleUtil.HasOnlyBasicTypes(mw.GetParameters(), mw.ReturnType) && type.parameterCount() <= MethodHandleUtil.MaxArity) { - return Delegate.CreateDelegate(tw.Context.MethodHandleUtil.CreateMemberWrapperDelegateType(mw.GetParameters(), mw.ReturnType), mi); + return Delegate.CreateDelegate(tw.Context.MethodHandleUtil.CreateMemberWrapperDelegateType(mw.GetParameters(), mw.ReturnType).AsReflection(), mi); } else { @@ -465,7 +466,7 @@ public static object staticFieldBase(global::java.lang.invoke.MemberName self) internal static void InitializeCallSite(global::java.lang.invoke.CallSite site) { - var type = typeof(IKVM.Runtime.IndyCallSite<>).MakeGenericType(JVM.Context.MethodHandleUtil.GetDelegateTypeForInvokeExact(site.type())); + var type = typeof(IKVM.Runtime.IndyCallSite<>).MakeGenericType(JVM.Context.MethodHandleUtil.GetDelegateTypeForInvokeExact(site.type()).AsReflection()); var ics = (IKVM.Runtime.IIndyCallSite)Activator.CreateInstance(type, true); Interlocked.CompareExchange(ref site.ics, ics, null); } diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs index 4f4f70548c..90d288d490 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs @@ -23,6 +23,7 @@ Jeroen Frijters */ using System; +using IKVM.CoreLib.Reflection; using IKVM.Runtime; namespace IKVM.Java.Externs.java.lang.reflect @@ -353,52 +354,60 @@ public static void set(object arrayObj, int index, object value) { throw new global::java.lang.NullPointerException(); } - Type type = arrayObj.GetType(); - if (ReflectUtil.IsVector(type) && JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(type.GetElementType()).IsPrimitive) + + var type = arrayObj.GetType(); + if (type.IsSZArray() && JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(type).GetElementType()).IsPrimitive) { - global::java.lang.Boolean booleanValue = value as global::java.lang.Boolean; + var booleanValue = value as global::java.lang.Boolean; if (booleanValue != null) { setBoolean(arrayObj, index, booleanValue.booleanValue()); return; } - global::java.lang.Byte byteValue = value as global::java.lang.Byte; + + var byteValue = value as global::java.lang.Byte; if (byteValue != null) { setByte(arrayObj, index, byteValue.byteValue()); return; } - global::java.lang.Character charValue = value as global::java.lang.Character; + + var charValue = value as global::java.lang.Character; if (charValue != null) { setChar(arrayObj, index, charValue.charValue()); return; } - global::java.lang.Short shortValue = value as global::java.lang.Short; + + var shortValue = value as global::java.lang.Short; if (shortValue != null) { setShort(arrayObj, index, shortValue.shortValue()); return; } - global::java.lang.Integer intValue = value as global::java.lang.Integer; + + var intValue = value as global::java.lang.Integer; if (intValue != null) { setInt(arrayObj, index, intValue.intValue()); return; } - global::java.lang.Float floatValue = value as global::java.lang.Float; + + var floatValue = value as global::java.lang.Float; if (floatValue != null) { setFloat(arrayObj, index, floatValue.floatValue()); return; } - global::java.lang.Long longValue = value as global::java.lang.Long; + + var longValue = value as global::java.lang.Long; if (longValue != null) { setLong(arrayObj, index, longValue.longValue()); return; } - global::java.lang.Double doubleValue = value as global::java.lang.Double; + + var doubleValue = value as global::java.lang.Double; if (doubleValue != null) { setDouble(arrayObj, index, doubleValue.doubleValue()); @@ -422,16 +431,14 @@ public static void set(object arrayObj, int index, object value) public static void setBoolean(object arrayObj, int index, bool value) { if (arrayObj == null) - { throw new global::java.lang.NullPointerException(); - } - bool[] arr = arrayObj as bool[]; + + var arr = arrayObj as bool[]; if (arr != null) { if (index < 0 || index >= arr.Length) - { throw new global::java.lang.ArrayIndexOutOfBoundsException(); - } + arr[index] = value; } else @@ -443,16 +450,14 @@ public static void setBoolean(object arrayObj, int index, bool value) public static void setByte(object arrayObj, int index, byte value) { if (arrayObj == null) - { throw new global::java.lang.NullPointerException(); - } - byte[] arr = arrayObj as byte[]; + + var arr = arrayObj as byte[]; if (arr != null) { if (index < 0 || index >= arr.Length) - { throw new global::java.lang.ArrayIndexOutOfBoundsException(); - } + arr[index] = value; } else @@ -464,16 +469,14 @@ public static void setByte(object arrayObj, int index, byte value) public static void setChar(object arrayObj, int index, char value) { if (arrayObj == null) - { throw new global::java.lang.NullPointerException(); - } - char[] arr = arrayObj as char[]; + + var arr = arrayObj as char[]; if (arr != null) { if (index < 0 || index >= arr.Length) - { throw new global::java.lang.ArrayIndexOutOfBoundsException(); - } + arr[index] = value; } else @@ -603,9 +606,9 @@ public static object newArray(global::java.lang.Class componentType, int length) } try { - RuntimeJavaType wrapper = RuntimeJavaType.FromClass(componentType); + var wrapper = RuntimeJavaType.FromClass(componentType); wrapper.Finish(); - object obj = global::System.Array.CreateInstance(wrapper.TypeAsArrayType, length); + object obj = global::System.Array.CreateInstance(wrapper.TypeAsArrayType.AsReflection(), length); if (wrapper.IsGhost || wrapper.IsGhostArray) { IKVM.Runtime.GhostTag.SetTag(obj, wrapper.MakeArrayType(1)); @@ -640,13 +643,13 @@ public static object multiNewArray(global::java.lang.Class componentType, int[] } try { - RuntimeJavaType wrapper = RuntimeJavaType.FromClass(componentType).MakeArrayType(dimensions.Length); + var wrapper = RuntimeJavaType.FromClass(componentType).MakeArrayType(dimensions.Length); wrapper.Finish(); - object obj = IKVM.Runtime.ByteCodeHelper.multianewarray(wrapper.TypeAsArrayType.TypeHandle, dimensions); + + var obj = IKVM.Runtime.ByteCodeHelper.multianewarray(wrapper.TypeAsArrayType.AsReflection().TypeHandle, dimensions); if (wrapper.IsGhostArray) - { IKVM.Runtime.GhostTag.SetTag(obj, wrapper); - } + return obj; } catch (RetargetableJavaException x) diff --git a/src/IKVM.Runtime/Java/Externs/java/security/AccessController.cs b/src/IKVM.Runtime/Java/Externs/java/security/AccessController.cs index 99d89c98f6..3001f87849 100644 --- a/src/IKVM.Runtime/Java/Externs/java/security/AccessController.cs +++ b/src/IKVM.Runtime/Java/Externs/java/security/AccessController.cs @@ -117,7 +117,7 @@ static object CreateAccessControlContext(List)arrayRefCache.GetValue(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(array.GetType().GetElementType()), _ => new ArrayDelegateRef(_)).VolatileGetter)(array, offset); + return ((Func)arrayRefCache.GetValue(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(array.GetType()).GetElementType()), _ => new ArrayDelegateRef(_)).VolatileGetter)(array, offset); } catch (Exception e) { @@ -1957,7 +1957,7 @@ static void PutArrayObjectVolatile(object[] array, long offset, object value) #else try { - ((Action)arrayRefCache.GetValue(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(array.GetType().GetElementType()), _ => new ArrayDelegateRef(_)).VolatilePutter)(array, offset, value); + ((Action)arrayRefCache.GetValue(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(array.GetType()).GetElementType()), _ => new ArrayDelegateRef(_)).VolatilePutter)(array, offset, value); } catch (Exception e) { @@ -2499,7 +2499,7 @@ static object CompareAndSwapArray(T[] o, long offset, T value, T comparand) #if FIRST_PASS throw new NotImplementedException(); #else - return Interlocked.CompareExchange(ref o[offset / ArrayIndexScale(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(o.GetType()))], value, comparand); + return Interlocked.CompareExchange(ref o[offset / ArrayIndexScale(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(o.GetType())))], value, comparand); #endif } @@ -2520,7 +2520,7 @@ static object CompareAndSwapObjectArray(object[] o, long offset, object value, o #else try { - return ((Func)arrayRefCache.GetValue(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(o.GetType().GetElementType()), _ => new ArrayDelegateRef(_)).CompareExchange)(o, offset, value, expected); + return ((Func)arrayRefCache.GetValue(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(o.GetType()).GetElementType()), _ => new ArrayDelegateRef(_)).CompareExchange)(o, offset, value, expected); } catch (Exception e) { diff --git a/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs b/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs index ad2eaaef57..02e611e845 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs @@ -59,12 +59,12 @@ public static void initialize() if (global::IKVM.Java.Externs.sun.reflect.Reflection.IsHideFromStackWalk(m)) continue; - if (m.DeclaringType != null && JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(m.DeclaringType) is RuntimeJavaType tw and not null) + if (m.DeclaringType != null && JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(m.DeclaringType)) is { } tw) { - // check that the assembly isn't java.base or the IKVM runtime + // check that the assembly isn't the .NET corelib or the IKVM runtime var clw = tw.ClassLoader; if (clw is RuntimeAssemblyClassLoader acl) - if (acl.GetAssembly(tw) == typeof(object).Assembly || acl.GetAssembly(tw) == typeof(VM).Assembly) + if (acl.GetAssembly(tw) == JVM.Context.Types.Object.Assembly || acl.GetAssembly(tw).AsReflection() == typeof(VM).Assembly) continue; // associated Java class loader is our nearest diff --git a/src/IKVM.Runtime/Java/Externs/sun/net/www/protocol/ikvmres/Handler.cs b/src/IKVM.Runtime/Java/Externs/sun/net/www/protocol/ikvmres/Handler.cs index 8a726ac707..673d6fb337 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/net/www/protocol/ikvmres/Handler.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/net/www/protocol/ikvmres/Handler.cs @@ -87,7 +87,7 @@ public static object LoadClassFromAssembly(Assembly asm, string className) #if FIRST_PASS throw new NotImplementedException(); #else - var tw = JVM.Context.AssemblyClassLoaderFactory.FromAssembly(asm).TryLoadClassByName(className); + var tw = JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.GetSymbol(asm)).TryLoadClassByName(className); if (tw != null) return tw.ClassObject; diff --git a/src/IKVM.Runtime/Java/Externs/sun/reflect/Reflection.cs b/src/IKVM.Runtime/Java/Externs/sun/reflect/Reflection.cs index ad244fe425..c555bc66a0 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/reflect/Reflection.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/reflect/Reflection.cs @@ -61,7 +61,7 @@ static HideFromJavaFlags GetHideFromJavaFlagsImpl(MethodBase mb) #if FIRST_PASS throw new NotImplementedException(); #else - return mb.Name.StartsWith("__<", StringComparison.Ordinal) ? HideFromJavaFlags.All : JVM.Context.AttributeHelper.GetHideFromJavaFlags(mb); + return mb.Name.StartsWith("__<", StringComparison.Ordinal) ? HideFromJavaFlags.All : JVM.Context.AttributeHelper.GetHideFromJavaFlags(JVM.Context.Resolver.GetSymbol(mb)); #endif } @@ -118,7 +118,7 @@ internal static bool IsHideFromStackWalk(MethodBase mb) continue; if (--realFramesToSkip == 0) - return JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(method.DeclaringType).ClassObject; + return JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Resolver.GetSymbol(method.DeclaringType)).ClassObject; } #endif } diff --git a/src/IKVM.Runtime/Launcher.cs b/src/IKVM.Runtime/Launcher.cs index 18bfbc8286..12618d9491 100644 --- a/src/IKVM.Runtime/Launcher.cs +++ b/src/IKVM.Runtime/Launcher.cs @@ -240,7 +240,7 @@ static void AddBootClassPathAssembly(Assembly assembly) #if FIRST_PASS || IMPORTER throw new NotImplementedException(); #else - JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().AddDelegate(JVM.Context.AssemblyClassLoaderFactory.FromAssembly(assembly)); + JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().AddDelegate(JVM.Context.AssemblyClassLoaderFactory.FromAssembly(JVM.Context.Resolver.GetSymbol(assembly))); #endif } @@ -518,7 +518,7 @@ public static int Run(Assembly assembly, string main, bool jar, string[] args, s SystemAccessor.InvokeSetProperty("sun.java.command", initialize["sun.java.command"]); // find the main method and ensure it is accessible - var method = ClassAccessor.InvokeGetMethod(clazz, "main", ClassAccessor.InitArray(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(typeof(string[])).ClassObject), CallerIDAccessor.InvokeCreate(typeof(Launcher).TypeHandle)); + var method = ClassAccessor.InvokeGetMethod(clazz, "main", ClassAccessor.InitArray(JVM.Context.ClassLoaderFactory.GetJavaTypeFromType(JVM.Context.Types.String.MakeArrayType()).ClassObject), CallerIDAccessor.InvokeCreate(typeof(Launcher).TypeHandle)); MethodAccessor.InvokeSetAccessible(method, true); try diff --git a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs index d3fd060a55..9a6044702d 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs @@ -22,6 +22,7 @@ Jeroen Frijters */ #if IMPORTER == false + using System; using System.Diagnostics; using System.Reflection; @@ -47,7 +48,7 @@ internal ITypeSymbol GetMemberWrapperDelegateType(global::java.lang.invoke.Metho #if FIRST_PASS == false - ITypeSymbol CreateMethodHandleDelegateType(java.lang.invoke.MethodType type) + Type CreateMethodHandleDelegateType(java.lang.invoke.MethodType type) { var args = new RuntimeJavaType[type.parameterCount()]; for (int i = 0; i < args.Length; i++) @@ -57,7 +58,8 @@ ITypeSymbol CreateMethodHandleDelegateType(java.lang.invoke.MethodType type) } var ret = RuntimeJavaType.FromClass(type.returnType()); ret.Finish(); - return CreateMethodHandleDelegateType(args, ret); + + return CreateMethodHandleDelegateType(args, ret).AsReflection(); } static ITypeSymbol[] GetParameterTypes(IMethodBaseSymbol mb) @@ -81,10 +83,10 @@ internal static ITypeSymbol[] GetParameterTypes(ITypeSymbol thisType, IMethodBas return args; } - internal java.lang.invoke.MethodType GetDelegateMethodType(ITypeSymbol type) + internal java.lang.invoke.MethodType GetDelegateMethodType(Type type) { java.lang.Class[] types; - var mi = GetDelegateInvokeMethod(type); + var mi = GetDelegateInvokeMethod(context.Resolver.GetSymbol(type)); var pi = mi.GetParameters(); if (pi.Length > 0 && IsPackedArgsContainer(pi[pi.Length - 1].ParameterType)) { @@ -161,7 +163,7 @@ public Container(T1 target, T2 value) /// /// /// - DynamicMethodBuilder(RuntimeContext context, string name, java.lang.invoke.MethodType type, ITypeSymbol container, object target, object value, ITypeSymbol owner, bool useBasicTypes) + DynamicMethodBuilder(RuntimeContext context, string name, java.lang.invoke.MethodType type, ITypeSymbol container, object target, object value, Type owner, bool useBasicTypes) { this.context = context ?? throw new ArgumentNullException(nameof(context)); this.type = type; @@ -189,10 +191,10 @@ public Container(T1 target, T2 value) paramTypes = GetParameterTypes(mi); } - if (!ReflectUtil.CanOwnDynamicMethod(owner.AsReflection())) - owner = context.Resolver.GetSymbol(typeof(DynamicMethodBuilder)); + if (!ReflectUtil.CanOwnDynamicMethod(owner)) + owner = typeof(DynamicMethodBuilder); - dm = new DynamicMethod(name, mi.ReturnType.AsReflection(), paramTypes.AsReflection(), owner.AsReflection(), true); + dm = new DynamicMethod(name, mi.ReturnType.AsReflection(), paramTypes.AsReflection(), owner, true); ilgen = context.CodeEmitterFactory.Create(dm); if (type.parameterCount() > MaxArity) @@ -346,7 +348,7 @@ internal static Delegate CreateMemberName(RuntimeContext context, RuntimeJavaMet FinishTypes(type); var tw = mw.DeclaringType; - var owner = tw.TypeAsBaseType; + var owner = tw.TypeAsBaseType.AsReflection(); var dm = new DynamicMethodBuilder(context, "MemberName:" + mw.DeclaringType.Name + "::" + mw.Name + mw.Signature, type, null, mw.HasCallerID ? DynamicCallerIDProvider.Instance : null, null, owner, true); for (int i = 0, count = type.parameterCount(); i < count; i++) { @@ -631,7 +633,7 @@ static Delegate ValidateDelegate(Delegate d) internal ITypeSymbol GetDelegateTypeForInvokeExact(global::java.lang.invoke.MethodType type) { - type._invokeExactDelegateType ??= CreateMethodHandleDelegateType(type).AsReflection(); + type._invokeExactDelegateType ??= CreateMethodHandleDelegateType(type); return context.Resolver.GetSymbol(type._invokeExactDelegateType); } @@ -648,7 +650,7 @@ internal T GetDelegateForInvokeExact(global::java.lang.invoke.MethodHandle mh return del; } - throw java.lang.invoke.Invokers.newWrongMethodTypeException(GetDelegateMethodType(context.Resolver.GetSymbol(typeof(T))), type); + throw java.lang.invoke.Invokers.newWrongMethodTypeException(GetDelegateMethodType(typeof(T)), type); } /// diff --git a/src/IKVM.Runtime/MethodHandleUtil.root.cs b/src/IKVM.Runtime/MethodHandleUtil.root.cs index 414420e073..5cd878bb5b 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.root.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.root.cs @@ -47,7 +47,7 @@ public MethodHandleUtil(RuntimeContext context) this.context = context ?? throw new ArgumentNullException(nameof(context)); typeofMHA = context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHA`8"); - typeofMHV = new[] { + typeofMHV = [ context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV"), context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`1"), context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`2"), @@ -57,8 +57,8 @@ public MethodHandleUtil(RuntimeContext context) context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`6"), context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`7"), context.Resolver.ResolveRuntimeType("IKVM.Runtime.MHV`8"), - }; - typeofMH = new[] { + ]; + typeofMH = [ null, context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`1"), context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`2"), @@ -69,7 +69,7 @@ public MethodHandleUtil(RuntimeContext context) context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`7"), context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`8"), context.Resolver.ResolveRuntimeType("IKVM.Runtime.MH`9"), - }; + ]; } internal bool IsPackedArgsContainer(ITypeSymbol type) diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index 96cce87e57..beca070d4d 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -27,6 +27,8 @@ Jeroen Frijters using IKVM.CoreLib.Symbols.Emit; using System.Collections.Immutable; +using IKVM.CoreLib.Reflection; + #if IMPORTER || EXPORTER diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs index c0b9bf7283..d64bfe1591 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoaderFactory.cs @@ -112,7 +112,8 @@ RuntimeAssemblyClassLoader Create(IAssemblySymbol assembly) context.ClassLoaderFactory.LoadRemappedTypes(); #endif - if (assembly.IsDefined(context.Resolver.ResolveRuntimeType("IKVM.Attributes.RemappedClassAttribute"), false)) + var baseAssembly = context.Resolver.GetBaseAssembly(); + if (baseAssembly == assembly) { // This cast is necessary for ikvmc and a no-op for the runtime. // Note that the cast cannot fail, because ikvmc will only return a non AssemblyClassLoader diff --git a/src/IKVM.Runtime/RuntimeClassLoader.cs b/src/IKVM.Runtime/RuntimeClassLoader.cs index e2d095ec17..faa45eb106 100644 --- a/src/IKVM.Runtime/RuntimeClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeClassLoader.cs @@ -910,7 +910,7 @@ public override string ToString() if (javaClassLoader == null) return "null"; else - return string.Format("{0}@{1:X}", Context.ClassLoaderFactory.GetJavaTypeFromType(javaClassLoader.GetType()).Name, javaClassLoader.GetHashCode()); + return string.Format("{0}@{1:X}", Context.ClassLoaderFactory.GetJavaTypeFromType(Context.Resolver.GetSymbol(javaClassLoader.GetType())).Name, javaClassLoader.GetHashCode()); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs index c288ba1d32..cc600578c1 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs @@ -55,7 +55,7 @@ internal MultipleAnnotationJavaType(RuntimeContext context, AttributeAnnotationJ #if IMPORTER || EXPORTER this.annotationType = context.FakeTypes.GetAttributeMultipleType(declaringType.attributeType); #elif !FIRST_PASS - this.annotationType = typeof(ikvm.@internal.AttributeAnnotationMultiple<>).MakeGenericType(declaringType.attributeType); + this.annotationType = context.Resolver.GetSymbol(typeof(ikvm.@internal.AttributeAnnotationMultiple<>)).MakeGenericType(declaringType.attributeType); #endif this.declaringType = declaringType; } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs index a350429529..b412e502e8 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs @@ -67,7 +67,7 @@ internal override void EmitCall(CodeEmitter ilgen) internal override object Invoke(object obj, object[] args) { - return Enum.ToObject(DeclaringType.TypeAsTBD, args[0]); + return Enum.ToObject(DeclaringType.TypeAsTBD.AsReflection(), args[0]); } #endif diff --git a/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs b/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs index 5e8cb20fc6..60599a5cad 100644 --- a/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs +++ b/src/IKVM.Runtime/Vfs/VfsAssemblyClassDirectory.cs @@ -67,7 +67,7 @@ RuntimeJavaType TryLoadType(JavaTypeName className) #if FIRST_PASS || IMPORTER || EXPORTER throw new NotImplementedException(); #else - var acl = Context.Context.AssemblyClassLoaderFactory.FromAssembly(assembly); + var acl = Context.Context.AssemblyClassLoaderFactory.FromAssembly(Context.Context.Resolver.GetSymbol(assembly)); try { @@ -124,7 +124,7 @@ VfsEntry GetPackageEntry(JavaPackageName packageName) #if FIRST_PASS || IMPORTER || EXPORTER throw new PlatformNotSupportedException(); #else - var acl = Context.Context.AssemblyClassLoaderFactory.FromAssembly(assembly); + var acl = Context.Context.AssemblyClassLoaderFactory.FromAssembly(Context.Context.Resolver.GetSymbol(assembly)); if (acl == null) throw new InvalidOperationException("Could not locate assembly loader."); @@ -132,7 +132,7 @@ VfsEntry GetPackageEntry(JavaPackageName packageName) foreach (var type in GetAssemblyTypes()) { // attempt to find Java type name - var name = acl.GetTypeNameAndType(type, out var isJavaType); + var name = acl.GetTypeNameAndType(Context.Context.Resolver.GetSymbol(type), out var isJavaType); if (name is null) continue; @@ -162,14 +162,14 @@ public override string[] List() #else var lst = new HashSet(); - var acl = Context.Context.AssemblyClassLoaderFactory.FromAssembly(assembly); + var acl = Context.Context.AssemblyClassLoaderFactory.FromAssembly(Context.Context.Resolver.GetSymbol(assembly)); if (acl == null) throw new InvalidOperationException("Could not locate assembly loader."); // search for any type that would be within the package foreach (var type in GetAssemblyTypes()) { - var name = acl.GetTypeNameAndType(type, out var isJavaType); + var name = acl.GetTypeNameAndType(Context.Context.Resolver.GetSymbol(type), out var isJavaType); if (name is null) continue; diff --git a/src/ikvmc/ikvmc.csproj b/src/ikvmc/ikvmc.csproj index ae6f133e10..042fb47cee 100644 --- a/src/ikvmc/ikvmc.csproj +++ b/src/ikvmc/ikvmc.csproj @@ -1,7 +1,7 @@  Exe - net8.0;net472;;net6.0; + net472;net6.0;net8.0 $(_SupportedToolRuntimes) true true diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json index 64fa8dc5e7..c0011c6008 100644 --- a/src/ikvmstub/Properties/launchSettings.json +++ b/src/ikvmstub/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmstub": { "commandName": "Project", - "commandLineArgs": "--bootstrap --nostdlib --skiperror --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.Win32.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Collections.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.InteropServices.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net8.0\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"C:\\Users\\jhaltom\\System.Net.Primitives.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Primitives.dll\"" + "commandLineArgs": "--bootstrap --nostdlib --skiperror --non-public-types --parameters --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\mscorlib.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Configuration.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Core.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Numerics.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Security.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Xml.dll\" --reference:\"C:\\Program Files\\dotnet\\sdk\\NuGetFallbackFolder\\system.numerics.vectors\\4.5.0\\ref\\net46\\System.Numerics.Vectors.dll\" --reference:\"C:\\Program Files\\dotnet\\sdk\\NuGetFallbackFolder\\system.valuetuple\\4.5.0\\ref\\net47\\System.ValueTuple.dll\" --reference:\"D:\\ikvm\\src\\IKVM.CoreLib\\bin\\Debug\\net472\\IKVM.CoreLib.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net472\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Reflection\\obj\\Debug\\net472\\ref\\IKVM.Reflection.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net472\\ref\\IKVM.Runtime.dll\" --reference:\"D:\\packages\\NuGet\\cache\\ikvm.bytecode\\9.1.3\\lib\\net472\\IKVM.ByteCode.dll\" --reference:\"D:\\packages\\NuGet\\cache\\microsoft.bcl.asyncinterfaces\\8.0.0\\lib\\net462\\Microsoft.Bcl.AsyncInterfaces.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.buffers\\4.5.1\\ref\\net45\\System.Buffers.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.collections.immutable\\8.0.0\\lib\\net462\\System.Collections.Immutable.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.io.pipelines\\8.0.0\\lib\\net462\\System.IO.Pipelines.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.memory\\4.5.5\\lib\\net461\\System.Memory.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.reflection.metadata\\8.0.0\\lib\\net462\\System.Reflection.Metadata.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.reflection.typeextensions\\4.7.0\\ref\\net472\\System.Reflection.TypeExtensions.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.runtime.compilerservices.unsafe\\6.0.0\\lib\\net461\\System.Runtime.CompilerServices.Unsafe.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.encodings.web\\8.0.0\\lib\\net462\\System.Text.Encodings.Web.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.json\\8.0.4\\lib\\net462\\System.Text.Json.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.threading.tasks.extensions\\4.5.4\\lib\\net461\\System.Threading.Tasks.Extensions.dll\" --out:\"IKVM.Runtime.jar\" \"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net472\\ref\\IKVM.Runtime.dll\"" } } } \ No newline at end of file diff --git a/src/ikvmstub/ikvmstub.csproj b/src/ikvmstub/ikvmstub.csproj index 15e796a6b8..1d89f5a4df 100644 --- a/src/ikvmstub/ikvmstub.csproj +++ b/src/ikvmstub/ikvmstub.csproj @@ -1,7 +1,7 @@  Exe - net8.0;net472;net6.0 + net472;net6.0;net8.0 $(_SupportedToolRuntimes) true true From a9a3232734da8cbe520ea7fe80cb28c68b58e45d Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 27 Sep 2024 21:10:51 -0500 Subject: [PATCH 17/59] 111 --- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 8 +- src/IKVM.Runtime/InstructionState.cs | 1 + .../Java/Externs/java/lang/reflect/Array.cs | 6 +- src/IKVM.Runtime/RuntimeJavaType.cs | 9 +- .../RuntimeManagedByteCodeJavaType.cs | 4 +- ...tionJavaType.MultipleAnnotationJavaType.cs | 2 +- src/IKVM.Tools.Exporter/ExportImpl.cs | 4 +- .../ExportRuntimeSymbolResolver.cs | 110 +++++++++--------- src/IKVM.Tools.Importer/ImportClassLoader.cs | 2 +- .../ImportRuntimeSymbolResolver.cs | 36 ++---- 10 files changed, 86 insertions(+), 96 deletions(-) diff --git a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs index 7a5874bc9c..3d89c7c9a6 100644 --- a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs +++ b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs @@ -34,20 +34,20 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// /// /// - ITypeSymbol? ResolveSystemType(string typeName); + ITypeSymbol ResolveSystemType(string typeName); /// /// Gets the known runtime assembly. /// /// - IAssemblySymbol? GetRuntimeAssembly(); + IAssemblySymbol GetRuntimeAssembly(); /// /// Resolves the named type from the IKVM runtime assembly. /// /// /// - ITypeSymbol? ResolveRuntimeType(string typeName); + ITypeSymbol ResolveRuntimeType(string typeName); /// /// Resolves the known Java base assembly. @@ -60,7 +60,7 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// /// /// - ITypeSymbol? ResolveBaseType(string typeName); + ITypeSymbol ResolveBaseType(string typeName); /// /// Gets the associated with the specified assembly. diff --git a/src/IKVM.Runtime/InstructionState.cs b/src/IKVM.Runtime/InstructionState.cs index 27312c3aff..6c0b043e2a 100644 --- a/src/IKVM.Runtime/InstructionState.cs +++ b/src/IKVM.Runtime/InstructionState.cs @@ -382,6 +382,7 @@ internal static RuntimeJavaType FindCommonBaseType(RuntimeContext context, Runti { baseType = FindCommonBaseTypeHelper(context, elem1, elem2); } + return baseType.MakeArrayType(rank); } return FindCommonBaseTypeHelper(context, type1, type2); diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs index 90d288d490..f19c102feb 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs @@ -608,11 +608,11 @@ public static object newArray(global::java.lang.Class componentType, int length) { var wrapper = RuntimeJavaType.FromClass(componentType); wrapper.Finish(); - object obj = global::System.Array.CreateInstance(wrapper.TypeAsArrayType.AsReflection(), length); + + var obj = global::System.Array.CreateInstance(wrapper.TypeAsArrayType.AsReflection(), length); if (wrapper.IsGhost || wrapper.IsGhostArray) - { IKVM.Runtime.GhostTag.SetTag(obj, wrapper.MakeArrayType(1)); - } + return obj; } catch (RetargetableJavaException x) diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index c127cf3607..4b5e967458 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -137,7 +137,7 @@ ITypeSymbol GetClassLiteralType() while (tw.IsArray) tw = tw.ElementTypeWrapper; - return tw.TypeAsTBD.MakeArrayType(rank); + return rank == 1 ? tw.TypeAsTBD.MakeArrayType() : tw.TypeAsTBD.MakeArrayType(rank); } else { @@ -1029,16 +1029,17 @@ internal RuntimeJavaType ElementTypeWrapper internal RuntimeJavaType MakeArrayType(int rank) { Debug.Assert(rank != 0); + // NOTE this call to LoadClassByDottedNameFast can never fail and will not trigger a class load - return ClassLoader.TryLoadClassByName(new String('[', rank) + this.SigName); + return ClassLoader.TryLoadClassByName(new string('[', rank) + SigName); } internal bool ImplementsInterface(RuntimeJavaType interfaceWrapper) { - RuntimeJavaType typeWrapper = this; + var typeWrapper = this; while (typeWrapper != null) { - RuntimeJavaType[] interfaces = typeWrapper.Interfaces; + var interfaces = typeWrapper.Interfaces; for (int i = 0; i < interfaces.Length; i++) { if (interfaces[i] == interfaceWrapper) diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index 840ebdc54b..b789061404 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -953,10 +953,10 @@ static RuntimeJavaType TypeWrapperFromModOpt(RuntimeContext context, ITypeSymbol tw = context.ClassLoaderFactory.GetJavaTypeFromType(type); } } + if (rank != 0) - { tw = tw.MakeArrayType(rank); - } + return tw; } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs index cc600578c1..4b33a804d5 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.MultipleAnnotationJavaType.cs @@ -62,7 +62,7 @@ internal MultipleAnnotationJavaType(RuntimeContext context, AttributeAnnotationJ protected override void LazyPublishMembers() { - RuntimeJavaType tw = declaringType.MakeArrayType(1); + var tw = declaringType.MakeArrayType(1); SetMethods([new DynamicOnlyJavaMethod(this, "value", "()" + tw.SigName, tw, [], MemberFlags.None)]); SetFields([]); } diff --git a/src/IKVM.Tools.Exporter/ExportImpl.cs b/src/IKVM.Tools.Exporter/ExportImpl.cs index 09494ee741..1c506da3a9 100644 --- a/src/IKVM.Tools.Exporter/ExportImpl.cs +++ b/src/IKVM.Tools.Exporter/ExportImpl.cs @@ -146,7 +146,7 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(true), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols), compiler); + context = new RuntimeContext(new RuntimeContextOptions(true), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols, options.Bootstrap), compiler); context.ClassLoaderFactory.SetBootstrapClassLoader(new RuntimeBootstrapClassLoader(context)); } else @@ -172,7 +172,7 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols), compiler); + context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols, options.Bootstrap), compiler); } if (context.AttributeHelper.IsJavaModule(context.Resolver.GetSymbol(assembly.ManifestModule))) diff --git a/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs index cb41963e35..d994169864 100644 --- a/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs +++ b/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs @@ -1,27 +1,4 @@ -/* - Copyright (C) 2002-2014 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - -*/ -#nullable enable +#nullable enable using System; using System.Collections.Concurrent; @@ -63,6 +40,7 @@ static IEnumerable GetSystemTypeNames() readonly IDiagnosticHandler _diagnostics; readonly Universe _universe; readonly IkvmReflectionSymbolContext _symbols; + readonly bool _bootstrap; IAssemblySymbol? _coreAssembly; readonly ConcurrentDictionary _coreTypeCache = new(); @@ -82,12 +60,14 @@ static IEnumerable GetSystemTypeNames() /// /// /// + /// /// - public ExportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols) + public ExportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols, bool bootstrap) { _diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); _universe = universe ?? throw new ArgumentNullException(nameof(universe)); _symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); + _bootstrap = bootstrap; } /// @@ -99,6 +79,27 @@ public IAssemblySymbol GetCoreAssembly() return (_coreAssembly ??= GetSymbol(_universe.CoreLib)) ?? throw new DiagnosticEventException(DiagnosticEvent.CoreClassesMissing()); } + /// + /// Resolves the set of system assemblies. + /// + /// + IAssemblySymbol[] FindSystemAssemblies() + { + return _systemAssemblies ??= ResolveSystemAssembliesIter().Distinct().ToArray(); + } + + /// + /// Resolves the set of system assemblies that contain the system types. + /// + /// + IEnumerable ResolveSystemAssembliesIter() + { + foreach (var assembly in _universe.GetAssemblies()) + foreach (var typeName in GetSystemTypeNames()) + if (assembly.GetType(typeName) is Type t) + yield return GetSymbol(assembly); + } + /// public IAssemblySymbol GetRuntimeAssembly() { @@ -118,8 +119,12 @@ public IAssemblySymbol GetRuntimeAssembly() } /// - public IAssemblySymbol GetBaseAssembly() + public IAssemblySymbol? GetBaseAssembly() { + // bootstrap mode is used for builing the main assembly, and thus should not return the existing base assembly + if (_bootstrap) + return null; + return (_baseAssembly ??= FindBaseAssembly()) ?? throw new DiagnosticEventException(DiagnosticEvent.BootstrapClassesMissing()); } @@ -138,60 +143,59 @@ public IAssemblySymbol GetBaseAssembly() /// public ITypeSymbol ResolveCoreType(string typeName) { - return _coreTypeCache.GetOrAdd(typeName, _ => GetCoreAssembly().GetType(_)) ?? throw new DiagnosticEventException(DiagnosticEvent.CoreClassesMissing()); + return _coreTypeCache.GetOrAdd(typeName, _ => GetCoreAssembly().GetType(_)) ?? throw new DiagnosticEventException(DiagnosticEvent.CriticalClassNotFound(typeName)); } - /// - /// Resolves the set of system assemblies. - /// - /// - IAssemblySymbol[] ResolveSystemAssemblies() + /// + public ITypeSymbol ResolveSystemType(string typeName) { - return _systemAssemblies ??= ResolveSystemAssembliesIter().Distinct().ToArray(); + return _systemTypeCache.GetOrAdd(typeName, FindSystemType) ?? throw new DiagnosticEventException(DiagnosticEvent.CriticalClassNotFound(typeName)); } /// - /// Resolves the set of system assemblies that contain the system types. + /// Attempts to load the specified system type. /// + /// /// - IEnumerable ResolveSystemAssembliesIter() + ITypeSymbol? FindSystemType(string typeName) { - foreach (var assembly in _universe.GetAssemblies()) - foreach (var typeName in GetSystemTypeNames()) - if (assembly.GetType(typeName) is Type t) - yield return GetSymbol(assembly); + foreach (var assembly in FindSystemAssemblies()) + if (assembly.GetType(typeName) is { } t) + return t; + + return null; } /// - public ITypeSymbol ResolveSystemType(string typeName) + public ITypeSymbol ResolveRuntimeType(string typeName) { - return _systemTypeCache.GetOrAdd(typeName, FindSystemType) ?? throw new DiagnosticEventException(DiagnosticEvent.ClassNotFound(typeName)); + return _runtimeTypeCache.GetOrAdd(typeName, FindRuntimeType) ?? throw new DiagnosticEventException(DiagnosticEvent.CriticalClassNotFound(typeName)); } /// - /// Attempts to load the specified system type. + /// Attempts to load the specified runtime type. /// /// /// - ITypeSymbol? FindSystemType(string typeName) + ITypeSymbol? FindRuntimeType(string typeName) { - foreach (var assembly in ResolveSystemAssemblies()) - if (assembly.GetType(typeName) is { } t) - return t; - - return null; + return GetRuntimeAssembly()?.GetType(typeName); } /// - public ITypeSymbol? ResolveRuntimeType(string typeName) + public ITypeSymbol ResolveBaseType(string typeName) { - return GetRuntimeAssembly().GetType(typeName); + return _baseTypeCache.GetOrAdd(typeName, FindBaseType) ?? throw new DiagnosticEventException(DiagnosticEvent.CriticalClassNotFound(typeName)); } - /// - public ITypeSymbol? ResolveBaseType(string typeName) + /// + /// Attempts to find the base type. + /// + /// + /// + ITypeSymbol? FindBaseType(string typeName) { - return GetBaseAssembly().GetType(typeName); + return GetBaseAssembly()?.GetType(typeName); } /// diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index 908069f170..56a8c26c7b 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -517,7 +517,7 @@ void SetMain(RuntimeJavaType type, IKVM.CoreLib.Symbols.Emit.PEFileKinds target, throw new ArgumentNullException(nameof(properties)); // global main method decorated with appropriate apartment type - var mainMethodProxy = GetTypeWrapperFactory().ModuleBuilder.DefineGlobalMethod("Main", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static, Context.Types.Int32, new[] { Context.Types.String.MakeArrayType() }); + var mainMethodProxy = GetTypeWrapperFactory().ModuleBuilder.DefineGlobalMethod("Main", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static, Context.Types.Int32, [Context.Types.String.MakeArrayType()]); if (apartmentAttributeType != null) mainMethodProxy.SetCustomAttribute(Context.Resolver.Symbols.CreateCustomAttribute(apartmentAttributeType.GetConstructor([]), [])); diff --git a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs index 87799b0642..321178fefe 100644 --- a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs +++ b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs @@ -1,27 +1,4 @@ -/* - Copyright (C) 2002-2014 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - -*/ -#nullable enable +#nullable enable using System; using System.Collections.Concurrent; @@ -63,6 +40,7 @@ static IEnumerable GetSystemTypeNames() readonly IDiagnosticHandler _diagnostics; readonly Universe _universe; readonly IkvmReflectionSymbolContext _symbols; + readonly bool _bootstrap; IAssemblySymbol? _coreAssembly; readonly ConcurrentDictionary _coreTypeCache = new(); @@ -82,12 +60,14 @@ static IEnumerable GetSystemTypeNames() /// /// /// + /// /// - public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols) + public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols, bool bootstrap) { _diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); _universe = universe ?? throw new ArgumentNullException(nameof(universe)); _symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); + _bootstrap = bootstrap; } /// @@ -118,8 +98,12 @@ public IAssemblySymbol GetRuntimeAssembly() } /// - public IAssemblySymbol GetBaseAssembly() + public IAssemblySymbol? GetBaseAssembly() { + // bootstrap mode is used for builing the main assembly, and thus should not return the existing base assembly + if (_bootstrap) + return null; + return (_baseAssembly ??= FindBaseAssembly()) ?? throw new DiagnosticEventException(DiagnosticEvent.BootstrapClassesMissing()); } From 28f1c037aaaea2c4eff40b326887fe8a9711d722 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sat, 28 Sep 2024 10:54:11 -0500 Subject: [PATCH 18/59] Restore MakeArray, since it doesn't do multidims. --- src/IKVM.Runtime/ByteCodeHelper.cs | 2 +- src/IKVM.Runtime/MethodHandleUtil.compiler.cs | 5 +--- src/IKVM.Runtime/RuntimeArrayJavaType.cs | 24 +++++++++++++++++++ src/IKVM.Runtime/RuntimeByteCodeJavaType.cs | 5 +--- src/IKVM.Runtime/RuntimeJavaType.cs | 2 +- src/IKVM.Runtime/compiler.cs | 4 ++-- .../ImportRuntimeSymbolResolver.cs | 6 ++--- .../RuntimeImportByteCodeJavaType.cs | 2 +- src/ikvmstub/Properties/launchSettings.json | 2 +- src/ikvmstub/ikvmstub.csproj | 2 +- 10 files changed, 36 insertions(+), 18 deletions(-) diff --git a/src/IKVM.Runtime/ByteCodeHelper.cs b/src/IKVM.Runtime/ByteCodeHelper.cs index 07730aceac..942f28550e 100644 --- a/src/IKVM.Runtime/ByteCodeHelper.cs +++ b/src/IKVM.Runtime/ByteCodeHelper.cs @@ -106,7 +106,7 @@ public static object multianewarray_ghost(RuntimeTypeHandle typeHandle, int[] le type = type.GetElementType(); } - var obj = multianewarray(typeof(object).MakeArrayType(rank).TypeHandle, lengths); + var obj = multianewarray(RuntimeArrayJavaType.MakeArrayType(typeof(object), rank).TypeHandle, lengths); GhostTag.SetTag(obj, typeHandle); return obj; } diff --git a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs index 5015c8972e..606793ebff 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs @@ -84,10 +84,7 @@ ITypeSymbol TypeWrapperToTypeForLoadConstant(RuntimeJavaType tw) while (tw.IsArray) tw = tw.ElementTypeWrapper; - if (dims == 1) - return tw.TypeAsSignatureType.MakeArrayType(); - else - return tw.TypeAsSignatureType.MakeArrayType(dims); + return RuntimeArrayJavaType.MakeArrayType(tw.TypeAsSignatureType, dims); } else { diff --git a/src/IKVM.Runtime/RuntimeArrayJavaType.cs b/src/IKVM.Runtime/RuntimeArrayJavaType.cs index 4d681af32c..4ee9687a92 100644 --- a/src/IKVM.Runtime/RuntimeArrayJavaType.cs +++ b/src/IKVM.Runtime/RuntimeArrayJavaType.cs @@ -180,6 +180,30 @@ internal override RuntimeJavaType GetUltimateElementTypeWrapper() return ultimateElementTypeWrapper; } + internal static ITypeSymbol MakeArrayType(ITypeSymbol type, int dims) + { + // NOTE this is not just an optimization, but it is also required to + // make sure that ReflectionOnly types stay ReflectionOnly types + // (in particular instantiations of generic types from mscorlib that + // have ReflectionOnly type parameters). + for (int i = 0; i < dims; i++) + type = type.MakeArrayType(); + + return type; + } + + internal static Type MakeArrayType(Type type, int dims) + { + // NOTE this is not just an optimization, but it is also required to + // make sure that ReflectionOnly types stay ReflectionOnly types + // (in particular instantiations of generic types from mscorlib that + // have ReflectionOnly type parameters). + for (int i = 0; i < dims; i++) + type = type.MakeArrayType(); + + return type; + } + } } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs index 3c960048f2..05d752cd0d 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.cs @@ -933,10 +933,7 @@ static ITypeSymbol GetModOptHelper(RuntimeJavaType tw) if (tw.IsArray) { - if (tw.ArrayRank == 1) - return GetModOptHelper(tw.GetUltimateElementTypeWrapper()).MakeArrayType(); - else - return GetModOptHelper(tw.GetUltimateElementTypeWrapper()).MakeArrayType(tw.ArrayRank); + return RuntimeArrayJavaType.MakeArrayType(GetModOptHelper(tw.GetUltimateElementTypeWrapper()), tw.ArrayRank); } else if (tw.IsGhost) { diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 4b5e967458..197ad18ce1 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -137,7 +137,7 @@ ITypeSymbol GetClassLiteralType() while (tw.IsArray) tw = tw.ElementTypeWrapper; - return rank == 1 ? tw.TypeAsTBD.MakeArrayType() : tw.TypeAsTBD.MakeArrayType(rank); + return RuntimeArrayJavaType.MakeArrayType(tw.TypeAsTBD, rank); } else { diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index bc17ee9d9c..4bb8d9c889 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -1770,7 +1770,7 @@ void Compile(Block block, int startIndex) while (tw.IsArray) tw = tw.ElementTypeWrapper; - ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, wrapper.ArrayRank == 1 ? tw.TypeAsTBD.MakeArrayType() : tw.TypeAsTBD.MakeArrayType(wrapper.ArrayRank)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, RuntimeArrayJavaType.MakeArrayType(tw.TypeAsTBD, wrapper.ArrayRank)); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldloc, localArray); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.multianewarray_ghost); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Castclass, wrapper.TypeAsArrayType); @@ -1811,7 +1811,7 @@ void Compile(Block block, int startIndex) tw = tw.ElementTypeWrapper; var rank = wrapper.ArrayRank + 1; - ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, rank == 1 ? tw.TypeAsTBD.MakeArrayType() : tw.TypeAsTBD.MakeArrayType(rank)); + ilGenerator.Emit(System.Reflection.Emit.OpCodes.Ldtoken, RuntimeArrayJavaType.MakeArrayType(tw.TypeAsTBD, wrapper.ArrayRank + 1)); ilGenerator.Emit(System.Reflection.Emit.OpCodes.Call, finish.Context.ByteCodeHelperMethods.anewarray_ghost.MakeGenericMethod(wrapper.TypeAsArrayType)); } else diff --git a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs index 321178fefe..eed6535111 100644 --- a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs +++ b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs @@ -60,14 +60,14 @@ static IEnumerable GetSystemTypeNames() /// /// /// - /// + /// /// - public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols, bool bootstrap) + public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe universe, IkvmReflectionSymbolContext symbols, ImportOptions options) { _diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); _universe = universe ?? throw new ArgumentNullException(nameof(universe)); _symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); - _bootstrap = bootstrap; + _bootstrap = options.Bootstrap; } /// diff --git a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs index 13b650c2ef..0915471e32 100644 --- a/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs +++ b/src/IKVM.Tools.Importer/RuntimeImportByteCodeJavaType.cs @@ -995,7 +995,7 @@ internal override void EmitCheckcast(CodeEmitter ilgen) } ilgen.EmitLdc_I4(rank); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, ghostCastArrayMethod); - ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, rank == 1 ? Context.Types.Object.MakeArrayType() : Context.Types.Object.MakeArrayType(rank)); + ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(Context.Types.Object, rank)); } else { diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json index c0011c6008..338a877ef6 100644 --- a/src/ikvmstub/Properties/launchSettings.json +++ b/src/ikvmstub/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmstub": { "commandName": "Project", - "commandLineArgs": "--bootstrap --nostdlib --skiperror --non-public-types --parameters --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\mscorlib.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Configuration.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Core.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Numerics.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Security.dll\" --reference:\"C:\\Program Files (x86)\\Reference Assemblies\\Microsoft\\Framework\\.NETFramework\\v4.7.2\\System.Xml.dll\" --reference:\"C:\\Program Files\\dotnet\\sdk\\NuGetFallbackFolder\\system.numerics.vectors\\4.5.0\\ref\\net46\\System.Numerics.Vectors.dll\" --reference:\"C:\\Program Files\\dotnet\\sdk\\NuGetFallbackFolder\\system.valuetuple\\4.5.0\\ref\\net47\\System.ValueTuple.dll\" --reference:\"D:\\ikvm\\src\\IKVM.CoreLib\\bin\\Debug\\net472\\IKVM.CoreLib.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net472\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Reflection\\obj\\Debug\\net472\\ref\\IKVM.Reflection.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net472\\ref\\IKVM.Runtime.dll\" --reference:\"D:\\packages\\NuGet\\cache\\ikvm.bytecode\\9.1.3\\lib\\net472\\IKVM.ByteCode.dll\" --reference:\"D:\\packages\\NuGet\\cache\\microsoft.bcl.asyncinterfaces\\8.0.0\\lib\\net462\\Microsoft.Bcl.AsyncInterfaces.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.buffers\\4.5.1\\ref\\net45\\System.Buffers.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.collections.immutable\\8.0.0\\lib\\net462\\System.Collections.Immutable.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.io.pipelines\\8.0.0\\lib\\net462\\System.IO.Pipelines.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.memory\\4.5.5\\lib\\net461\\System.Memory.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.reflection.metadata\\8.0.0\\lib\\net462\\System.Reflection.Metadata.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.reflection.typeextensions\\4.7.0\\ref\\net472\\System.Reflection.TypeExtensions.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.runtime.compilerservices.unsafe\\6.0.0\\lib\\net461\\System.Runtime.CompilerServices.Unsafe.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.encodings.web\\8.0.0\\lib\\net462\\System.Text.Encodings.Web.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.json\\8.0.4\\lib\\net462\\System.Text.Json.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.threading.tasks.extensions\\4.5.4\\lib\\net461\\System.Threading.Tasks.Extensions.dll\" --out:\"IKVM.Runtime.jar\" \"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net472\\ref\\IKVM.Runtime.dll\"" + "commandLineArgs": "--bootstrap --nostdlib --skiperror --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.Win32.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Collections.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.NameResolution.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.InteropServices.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net8.0\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"System.Net.NameResolution.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.NameResolution.dll\"" } } } \ No newline at end of file diff --git a/src/ikvmstub/ikvmstub.csproj b/src/ikvmstub/ikvmstub.csproj index 1d89f5a4df..4b9e31015c 100644 --- a/src/ikvmstub/ikvmstub.csproj +++ b/src/ikvmstub/ikvmstub.csproj @@ -1,7 +1,7 @@  Exe - net472;net6.0;net8.0 + net8.0;net472;net6.0; $(_SupportedToolRuntimes) true true From a0331c90e77ff8f7b003e6baa4d466fa62079328 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sat, 28 Sep 2024 16:46:27 -0500 Subject: [PATCH 19/59] Turn off skiperrors. Fix resolver. --- .../targets/IKVM.Java.Core.NoTasks.targets | 1 - src/IKVM.Runtime/JVM.Resolver.cs | 4 +++- src/IKVM.Runtime/JVM.cs | 1 - .../Java/Externs/ikvm/runtime/Util.cs | 2 +- .../Diagnostics/DiagnosticOptions.cs | 4 ++-- src/IKVM.Tools.Importer/ImportClassLoader.cs | 20 +++++++++---------- src/ikvmc/Properties/launchSettings.json | 2 +- src/ikvmc/ikvmc.csproj | 2 +- src/ikvmstub/Properties/launchSettings.json | 2 +- src/ikvmstub/ikvmstub.csproj | 2 +- src/javac-ref/Properties/launchSettings.json | 2 +- src/javac-ref/javac-ref.csproj | 2 +- 12 files changed, 21 insertions(+), 23 deletions(-) diff --git a/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets b/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets index 5d20169208..15b39348c9 100644 --- a/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets +++ b/src/IKVM.NET.Sdk/targets/IKVM.Java.Core.NoTasks.targets @@ -137,7 +137,6 @@ Value = b.ToString(); <_IkvmExporterArgs Remove="@(_IkvmExporterArgs)" /> <_IkvmExporterArgs Include="--bootstrap" Condition=" '%(ReferenceExport.Bootstrap)' == 'true' " /> <_IkvmExporterArgs Include="--nostdlib" Condition=" '%(ReferenceExport.NoStdLib)' == 'true' " /> - <_IkvmExporterArgs Include="--skiperror" /> <_IkvmExporterArgs Include="--non-public-types" Condition=" '%(ReferenceExport.IncludeNonPublicTypes)' == 'true' " /> <_IkvmExporterArgs Include="--non-public-interfaces" Condition=" '%(ReferenceExport.IncludeNonPublicInterfaces)' == 'true' " /> <_IkvmExporterArgs Include="--non-public-members" Condition=" '%(ReferenceExport.IncludeNonPublicMembers)' == 'true' " /> diff --git a/src/IKVM.Runtime/JVM.Resolver.cs b/src/IKVM.Runtime/JVM.Resolver.cs index 188121ae76..83d23d67b8 100644 --- a/src/IKVM.Runtime/JVM.Resolver.cs +++ b/src/IKVM.Runtime/JVM.Resolver.cs @@ -60,8 +60,10 @@ static IEnumerable GetSystemAssemblies() /// public Resolver() { + _coreAssembly = GetSymbol(typeof(object).Assembly); _systemAssemblies = GetSystemAssemblies().Distinct().ToArray().Select(GetSymbol).ToArray(); _runtimeAssembly = GetSymbol(typeof(JVM).Assembly); + _baseAssembly = GetSymbol(typeof(java.lang.Object).Assembly); } /// @@ -76,7 +78,7 @@ public IAssemblySymbol ResolveAssembly(string assemblyName) /// public IAssemblySymbol GetCoreAssembly() { - return _coreAssembly ??= GetSymbol(typeof(object).Assembly); + return _coreAssembly; } /// diff --git a/src/IKVM.Runtime/JVM.cs b/src/IKVM.Runtime/JVM.cs index f287af1c92..159f7aadf5 100644 --- a/src/IKVM.Runtime/JVM.cs +++ b/src/IKVM.Runtime/JVM.cs @@ -6,7 +6,6 @@ using System.Text; using System.Threading; -using IKVM.CoreLib.Diagnostics.Tracing; using IKVM.Runtime.Vfs; namespace IKVM.Runtime diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs index f765da0e7f..5d50f9c5b6 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs @@ -95,7 +95,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, #else var t = Type.GetTypeFromHandle(handle); var ts = JVM.Context.Resolver.GetSymbol(t); - if (ts.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || ts == typeof(void)) + if (ts.IsPrimitive || JVM.Context.ClassLoaderFactory.IsRemappedType(ts) || ts == JVM.Context.Types.Void) return JVM.Context.ManagedJavaTypeFactory.GetJavaTypeFromManagedType(ts).MakeArrayType(rank).ClassObject; if (!IsVisibleAsClass(t)) diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs index 9870c9356a..7f804f637e 100644 --- a/src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticOptions.cs @@ -16,7 +16,7 @@ class DiagnosticOptions /// /// Gets or sets whether the specified diagnostics should be suppressed. /// - public ImmutableArray NoWarnDiagnostics { get; set; } + public ImmutableArray NoWarnDiagnostics { get; set; } = []; /// /// Gets or sets whether all warnings should be promoted to errors. @@ -26,7 +26,7 @@ class DiagnosticOptions /// /// Gets or sets whether the specified diagnostics should be promoted to errors. /// - public ImmutableArray WarnAsErrorDiagnostics { get; set; } + public ImmutableArray WarnAsErrorDiagnostics { get; set; } = []; } diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index 56a8c26c7b..f7894b03ca 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -1131,11 +1131,11 @@ internal override void Finish() var paramTypes = this.GetParametersForDefineMethod(); - var cbCore = GetMethod() as IMethodSymbolBuilder; - + var cbCore = GetMethod() as IConstructorSymbolBuilder; if (cbCore != null) { - CodeEmitter ilgen = DeclaringType.Context.CodeEmitterFactory.Create(cbCore); + var ilgen = DeclaringType.Context.CodeEmitterFactory.Create(cbCore); + // TODO we need to support ghost (and other funky?) parameter types if (m.Body != null) { @@ -1146,9 +1146,8 @@ internal override void Finish() { ilgen.Emit(System.Reflection.Emit.OpCodes.Ldarg_0); for (int i = 0; i < paramTypes.Length; i++) - { ilgen.EmitLdarg(i + 1); - } + if (m.Redirect != null) { throw new NotImplementedException(); @@ -1157,19 +1156,18 @@ internal override void Finish() { var baseCon = DeclaringType.TypeAsTBD.GetConstructor(paramTypes); if (baseCon == null) - { - // TODO better error handling throw new InvalidOperationException("base class constructor not found: " + DeclaringType.Name + "." + m.Sig); - } + ilgen.Emit(System.Reflection.Emit.OpCodes.Call, baseCon); } + ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); } + ilgen.DoEmit(); - if (this.DeclaringType.ClassLoader.EmitStackTraceInfo) - { + + if (DeclaringType.ClassLoader.EmitStackTraceInfo) ilgen.EmitLineNumberTable(cbCore); - } } if (mbHelper != null) diff --git a/src/ikvmc/Properties/launchSettings.json b/src/ikvmc/Properties/launchSettings.json index 31d9cf8012..02b8e637e6 100644 --- a/src/ikvmc/Properties/launchSettings.json +++ b/src/ikvmc/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmc": { "commandName": "Project", - "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net8.0\\IKVM.Java.ikvmc.rsp" + "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java.runtime.win\\obj\\Debug\\net8.0\\IKVM.Java.runtime.win.ikvmc.rsp" } } } diff --git a/src/ikvmc/ikvmc.csproj b/src/ikvmc/ikvmc.csproj index 042fb47cee..939ff4bbc3 100644 --- a/src/ikvmc/ikvmc.csproj +++ b/src/ikvmc/ikvmc.csproj @@ -1,7 +1,7 @@  Exe - net472;net6.0;net8.0 + net8.0;net472;net6.0 $(_SupportedToolRuntimes) true true diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json index 338a877ef6..7b5a3610e7 100644 --- a/src/ikvmstub/Properties/launchSettings.json +++ b/src/ikvmstub/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmstub": { "commandName": "Project", - "commandLineArgs": "--bootstrap --nostdlib --skiperror --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.Win32.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Collections.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.NameResolution.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.InteropServices.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net8.0\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"System.Net.NameResolution.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.NameResolution.dll\"" + "commandLineArgs": "--bootstrap --nostdlib --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Numerics.Vectors.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.Intrinsics.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"System.Runtime.Intrinsics.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.Intrinsics.dll\"" } } } \ No newline at end of file diff --git a/src/ikvmstub/ikvmstub.csproj b/src/ikvmstub/ikvmstub.csproj index 4b9e31015c..e66f94dc41 100644 --- a/src/ikvmstub/ikvmstub.csproj +++ b/src/ikvmstub/ikvmstub.csproj @@ -1,7 +1,7 @@  Exe - net8.0;net472;net6.0; + net8.0;net6.0;net472; $(_SupportedToolRuntimes) true true diff --git a/src/javac-ref/Properties/launchSettings.json b/src/javac-ref/Properties/launchSettings.json index 889072b99e..1118a90760 100644 --- a/src/javac-ref/Properties/launchSettings.json +++ b/src/javac-ref/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "javac": { "commandName": "Project", - "commandLineArgs": "@C:\\dev\\ikvm\\src\\javadoc\\obj\\Debug\\net8.0\\osx-arm64\\javadoc.javac.rsp", + "commandLineArgs": "", "environmentVariables": { } diff --git a/src/javac-ref/javac-ref.csproj b/src/javac-ref/javac-ref.csproj index 4b232be5d7..105dc9c6b5 100644 --- a/src/javac-ref/javac-ref.csproj +++ b/src/javac-ref/javac-ref.csproj @@ -6,7 +6,7 @@ Exe javac - net8.0;net472;net6.0; + net472;net8.0;;net6.0; $(_SupportedImageRuntimes) true true From 1cbbd1139ffe5fd983ecd3797bdce14c3991cbba Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Tue, 1 Oct 2024 16:42:35 -0500 Subject: [PATCH 20/59] Unify System.Reflection version. --- .../IkvmReflectionSymbolTests.cs | 4 + .../Reflection/TypeListEqualityComparer.cs | 50 ++ .../Symbols/Emit/IModuleSymbolBuilder.cs | 4 +- .../IIkvmReflectionPropertySymbolBuilder.cs | 1 - .../IkvmReflectionAssemblySymbolBuilder.cs | 10 +- .../Emit/IkvmReflectionMemberSymbolBuilder.cs | 10 +- .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 35 +- .../IkvmReflectionParameterSymbolBuilder.cs | 10 +- .../IIkvmReflectionModuleSymbol.cs | 4 +- .../IkvmReflection/IIkvmReflectionSymbol.cs | 2 - .../IkvmReflectionAssemblySymbol.cs | 10 +- .../IkvmReflectionMemberSymbol.cs | 10 +- .../IkvmReflectionMethodTable.cs | 22 +- .../IkvmReflectionModuleSymbol.cs | 10 +- .../IkvmReflectionParameterSymbol.cs | 10 +- .../IkvmReflection/IkvmReflectionSymbol.cs | 28 +- .../IkvmReflectionTypeSymbol.cs | 2 +- .../IkvmReflection/IkvmReflectionUtil.cs | 6 +- .../Emit/IReflectionAssemblySymbolBuilder.cs | 9 +- .../IReflectionConstructorSymbolBuilder.cs | 5 +- .../Emit/IReflectionEventSymbolBuilder.cs | 5 +- .../Emit/IReflectionFieldSymbolBuilder.cs | 2 +- ...ectionGenericTypeParameterSymbolBuilder.cs | 2 +- .../Emit/IReflectionMemberSymbolBuilder.cs | 7 +- .../IReflectionMethodBaseSymbolBuilder.cs | 13 +- .../Emit/IReflectionMethodSymbolBuilder.cs | 9 +- .../Emit/IReflectionModuleSymbolBuilder.cs | 59 +- .../Emit/IReflectionParameterSymbolBuilder.cs | 2 +- .../Emit/IReflectionPropertySymbolBuilder.cs | 12 +- .../Emit/IReflectionSymbolBuilder.cs | 77 ++- .../Emit/IReflectionTypeSymbolBuilder.cs | 44 +- .../Emit/ReflectionAssemblySymbolBuilder.cs | 83 +-- .../ReflectionConstructorSymbolBuilder.cs | 13 +- .../Emit/ReflectionEventSymbolBuilder.cs | 4 +- .../Emit/ReflectionFieldSymbolBuilder.cs | 4 +- ...ectionGenericTypeParameterSymbolBuilder.cs | 485 +++++++++----- .../Emit/ReflectionMemberSymbolBuilder.cs | 352 +++++----- .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 31 +- .../Emit/ReflectionMethodSymbolBuilder.cs | 52 +- .../Emit/ReflectionModuleSymbolBuilder.cs | 381 ++++++----- .../Emit/ReflectionParameterBuilderInfo.cs | 3 +- .../Emit/ReflectionParameterSymbolBuilder.cs | 35 +- .../Emit/ReflectionPropertySymbolBuilder.cs | 31 +- .../Emit/ReflectionSymbolBuilder.cs | 12 +- .../Emit/ReflectionTypeSymbolBuilder.cs | 589 ++++++++++------ .../Reflection/IReflectionAssemblySymbol.cs | 10 - .../Reflection/IReflectionEventSymbol.cs | 8 +- .../Reflection/IReflectionMethodBaseSymbol.cs | 7 + .../Reflection/IReflectionMethodSymbol.cs | 17 +- .../Reflection/IReflectionModuleSymbol.cs | 51 +- .../Reflection/IReflectionParameterSymbol.cs | 4 +- .../Reflection/IReflectionPropertySymbol.cs | 7 + .../Symbols/Reflection/IReflectionSymbol.cs | 75 --- .../Reflection/IReflectionTypeSymbol.cs | 82 +++ .../Reflection/ReflectionAssemblySymbol.cs | 89 ++- .../Reflection/ReflectionConstructorSymbol.cs | 5 +- .../Reflection/ReflectionEventSymbol.cs | 11 +- .../Reflection/ReflectionEventTable.cs | 95 +++ .../Reflection/ReflectionFieldSymbol.cs | 9 +- .../Reflection/ReflectionFieldTable.cs | 81 +++ .../ReflectionGenericTypeParameterSymbol.cs | 465 ++++++++----- .../ReflectionGenericTypeParameterTable.cs | 78 +++ .../Reflection/ReflectionMemberSymbol.cs | 307 +++------ .../Reflection/ReflectionMethodBaseSymbol.cs | 42 +- .../Reflection/ReflectionMethodSpecTable.cs | 64 ++ .../Reflection/ReflectionMethodSymbol.cs | 30 +- .../Reflection/ReflectionMethodTable.cs | 143 ++++ .../Reflection/ReflectionModuleMetadata.cs | 488 -------------- .../Reflection/ReflectionModuleSymbol.cs | 103 +-- ...lyMetadata.cs => ReflectionModuleTable.cs} | 39 +- .../Reflection/ReflectionParameterSymbol.cs | 35 +- .../Reflection/ReflectionParameterTable.cs | 102 +++ .../Reflection/ReflectionPropertySymbol.cs | 24 +- .../Reflection/ReflectionPropertyTable.cs | 81 +++ .../Symbols/Reflection/ReflectionSymbol.cs | 69 +- .../Reflection/ReflectionSymbolContext.cs | 157 +++-- .../Symbols/Reflection/ReflectionTypeImpl.cs | 633 ------------------ .../Reflection/ReflectionTypeSpecTable.cs | 127 ++++ .../Reflection/ReflectionTypeSymbol.cs | 460 ++++++++----- .../Symbols/Reflection/ReflectionTypeTable.cs | 75 +++ .../Symbols/Reflection/ReflectionUtil.cs | 91 ++- src/IKVM.Reflection/Emit/MethodBuilder.cs | 3 +- src/IKVM.Runtime/RuntimeArrayJavaType.cs | 2 +- .../RuntimeAssemblyClassLoader.cs | 2 +- src/IKVM.Runtime/RuntimeJavaType.cs | 10 +- .../RuntimeManagedByteCodeJavaType.cs | 5 +- src/IKVM.Runtime/StubGen/StubGenerator.cs | 2 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 5 +- src/ikvmstub/Properties/launchSettings.json | 2 +- src/ikvmstub/ikvmstub.csproj | 2 +- 90 files changed, 3747 insertions(+), 2999 deletions(-) create mode 100644 src/IKVM.CoreLib/Reflection/TypeListEqualityComparer.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs rename src/IKVM.CoreLib/Symbols/Reflection/{ReflectionAssemblyMetadata.cs => ReflectionModuleTable.cs} (55%) create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index 0147fea237..ab284d995b 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -97,6 +97,8 @@ public void ArrayTypeShouldBeSame() var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); + s1.IsSZArray.Should().BeFalse(); + s2.IsSZArray.Should().BeFalse(); s1.Should().BeSameAs(s2); } @@ -106,6 +108,8 @@ public void SZArrayTypeShouldBeSame() var c = new IkvmReflectionSymbolContext(universe); var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); + s1.IsSZArray.Should().BeTrue(); + s2.IsSZArray.Should().BeTrue(); s1.Should().BeSameAs(s2); } diff --git a/src/IKVM.CoreLib/Reflection/TypeListEqualityComparer.cs b/src/IKVM.CoreLib/Reflection/TypeListEqualityComparer.cs new file mode 100644 index 0000000000..c7349923bf --- /dev/null +++ b/src/IKVM.CoreLib/Reflection/TypeListEqualityComparer.cs @@ -0,0 +1,50 @@ +using System; +using System.Collections.Generic; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Compares two array instances for equality. + /// + class TypeListEqualityComparer : IEqualityComparer + { + + public static readonly TypeListEqualityComparer Instance = new(); + + public bool Equals(Type[]? x, Type[]? y) + { + if (x == y) + return true; + + if (x == null || y == null) + return false; + + if (x.Length != y.Length) + return false; + + for (int i = 0; i < x.Length; i++) + if (x[i] != y[i]) + return false; + + return true; + } + + public int GetHashCode(Type[] obj) + { + int result = 17; + + for (int i = 0; i < obj.Length; i++) + { + unchecked + { + result = result * 41 + obj[i].GetHashCode(); + } + } + + return result; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index f030d9e2ed..1ad74cf09e 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -183,12 +183,12 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol void AddReference(IAssemblySymbol assembly); /// - /// Finishes the module. + /// Finishes the module and all types. Required before save. /// void Complete(); /// - /// Saves this module assembly to disk. + /// Saves this module assembly to disk. Module must first be completed. /// /// /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs index a4fc28e00f..b28ea70a4e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs @@ -1,5 +1,4 @@ using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection; using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs index 73594ea8c1..0d876aa823 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -240,7 +240,12 @@ public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inh /// public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingAssembly.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingAssembly.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -269,6 +274,9 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + /// + public override string ToString() => UnderlyingAssembly.ToString()!; + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs index 456507620d..b174dd069a 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs @@ -319,7 +319,12 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingMember.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -336,6 +341,9 @@ public virtual void OnComplete() } + /// + public override string ToString() => UnderlyingMember.ToString()!; + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs index 752ef4f3ec..339bb88c21 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -17,7 +17,8 @@ class IkvmReflectionModuleSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmRefl { readonly IIkvmReflectionAssemblySymbol _resolvingAssembly; - readonly ModuleBuilder _module; + Module _module; + ModuleBuilder? _builder; IkvmReflectionTypeTable _typeTable; IkvmReflectionMethodTable _methodTable; @@ -28,13 +29,14 @@ class IkvmReflectionModuleSymbolBuilder : IkvmReflectionSymbolBuilder, IIkvmRefl /// /// /// - /// + /// /// - public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionAssemblySymbol resolvingAssembly, ModuleBuilder module) : + public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionAssemblySymbol resolvingAssembly, ModuleBuilder builder) : base(context) { _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); - _module = module ?? throw new ArgumentNullException(nameof(module)); + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _module = _builder; _typeTable = new IkvmReflectionTypeTable(context, this, null); _methodTable = new IkvmReflectionMethodTable(context, this, null); @@ -42,10 +44,10 @@ public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, II } /// - public Module UnderlyingModule => UnderlyingModuleBuilder; + public Module UnderlyingModule => _module; /// - public ModuleBuilder UnderlyingModuleBuilder => _module; + public ModuleBuilder UnderlyingModuleBuilder => _builder ?? throw new InvalidOperationException(); /// public IIkvmReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; @@ -305,11 +307,20 @@ public void AddReference(IAssemblySymbol assembly) public void Complete() { UnderlyingModuleBuilder.CreateGlobalFunctions(); + + foreach (var type in GetTypes()) + if (type is IIkvmReflectionTypeSymbolBuilder t) + t.Complete(); + + _builder = null; } /// public void Save(System.Reflection.PortableExecutableKinds portableExecutableKind, IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine) { + if (IsComplete == false) + throw new InvalidOperationException("Module must be completed before Save."); + UnderlyingModuleBuilder.__Save((PortableExecutableKinds)portableExecutableKind, (IKVM.Reflection.ImageFileMachine)imageFileMachine); } @@ -336,7 +347,7 @@ public void Save(System.Reflection.PortableExecutableKinds portableExecutableKin public string ScopeName => UnderlyingModule.ScopeName; /// - public override bool IsComplete => _module == null; + public override bool IsComplete => _builder == null; /// public ulong ImageBase @@ -518,7 +529,12 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingModule.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingModule.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -529,6 +545,9 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + /// + public override string ToString() => UnderlyingModule.ToString()!; + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs index 461d75db79..f0e7aed502 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs @@ -128,7 +128,12 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingParameter.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingParameter.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -163,6 +168,9 @@ public void OnComplete() _builder = null; } + /// + public override string ToString() => UnderlyingParameter.ToString()!; + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs index 41a1252f2c..1111312ef1 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs @@ -1,6 +1,4 @@ -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; +using IKVM.Reflection; using Type = IKVM.Reflection.Type; diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs index af3369996d..d09e074b98 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs @@ -2,9 +2,7 @@ using System.Collections.Immutable; using System.Diagnostics.CodeAnalysis; -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; using IKVM.Reflection; -using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index db6ef47b76..b5c1d3dd1e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -146,7 +146,12 @@ public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inh /// public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingAssembly.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingAssembly.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -175,6 +180,9 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + /// + public override string ToString() => UnderlyingAssembly.ToString(); + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index 7da4302ba3..b9d3222320 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -192,7 +192,12 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingMember.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingMember.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -203,6 +208,9 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + /// + public override string ToString() => UnderlyingMember.ToString()!; + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs index 479dda6ac6..ec6a020171 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs @@ -23,7 +23,7 @@ struct IkvmReflectionMethodTable IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; - ConcurrentDictionary? _byName; + ConcurrentDictionary? _byToken; /// /// Initializes a new instance. @@ -54,17 +54,19 @@ public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase me throw new ArgumentException(nameof(method)); var token = method.MetadataToken; - if (token <= 0) + if (token == 0) + throw new InvalidOperationException(); + + // pseudo tokens: since IKVM.Reflection does not remove pseudo tokens after creation, we can keep using these + // but they are non-sequential per-type, so we need to use a real dictionary + if (token < 0) { // we fall back to lookup by name if there is no valid metadata token - if (_byName == null) - Interlocked.CompareExchange(ref _byName, new(), null); - - var context_ = _context; - var module_ = _module; - var type_ = _type; - var method_ = method; - return _byName.GetOrAdd(method.ToString() ?? throw new InvalidOperationException(), _ => CreateMethodBaseSymbol(context_, module_, type_, method_)); + if (_byToken == null) + Interlocked.CompareExchange(ref _byToken, new(), null); + + var value = (_context, _module, _type, method); + return _byToken.GetOrAdd(token, _ => CreateMethodBaseSymbol(value._context, value._module, value._type, value.method)); } // create lock on demand diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index e1e699c846..806f0cb7c7 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -227,7 +227,12 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingModule.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingModule.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -321,6 +326,9 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p #endregion + /// + public override string ToString() => UnderlyingModule.ToString()!; + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs index d23d839393..98fb45d390 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs @@ -93,7 +93,12 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingParameter.__GetCustomAttributes(attributeType.Unpack(), inherit).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingParameter.__GetCustomAttributes(_attributeType, inherit); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// @@ -116,6 +121,9 @@ public ITypeSymbol[] GetRequiredCustomModifiers() #endregion + /// + public override string ToString() => UnderlyingParameter.ToString()!; + } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index b766fd03e3..fb4f446f2d 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -62,7 +62,7 @@ public virtual IIkvmReflectionAssemblySymbolBuilder ResolveAssemblySymbol(Assemb /// [return: NotNullIfNotNull(nameof(assemblies))] - public virtual IIkvmReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies) + public IIkvmReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies) { if (assemblies == null) return null; @@ -96,7 +96,7 @@ public virtual IIkvmReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuil /// [return: NotNullIfNotNull(nameof(modules))] - public virtual IIkvmReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules) + public IIkvmReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules) { if (modules == null) return null; @@ -112,7 +112,7 @@ public virtual IIkvmReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuil } /// - public virtual IEnumerable ResolveModuleSymbols(IEnumerable modules) + public IEnumerable ResolveModuleSymbols(IEnumerable modules) { foreach (var module in modules) if (ResolveModuleSymbol(module) is { } symbol) @@ -140,7 +140,7 @@ public virtual IEnumerable ResolveModuleSymbols(IEn /// [return: NotNullIfNotNull(nameof(members))] - public virtual IIkvmReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? members) + public IIkvmReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? members) { if (members == null) return null; @@ -174,7 +174,7 @@ public virtual IIkvmReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder ty /// [return: NotNullIfNotNull(nameof(types))] - public virtual IIkvmReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types) + public IIkvmReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types) { if (types == null) return null; @@ -228,7 +228,7 @@ public virtual IIkvmReflectionConstructorSymbolBuilder ResolveConstructorSymbol( /// [return: NotNullIfNotNull(nameof(ctors))] - public virtual IIkvmReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors) + public IIkvmReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors) { if (ctors == null) return null; @@ -262,7 +262,7 @@ public virtual IIkvmReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuil /// [return: NotNullIfNotNull(nameof(methods))] - public virtual IIkvmReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods) + public IIkvmReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods) { if (methods == null) return null; @@ -296,7 +296,7 @@ public virtual IIkvmReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder /// [return: NotNullIfNotNull(nameof(fields))] - public virtual IIkvmReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields) + public IIkvmReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields) { if (fields == null) return null; @@ -330,7 +330,7 @@ public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Proper /// [return: NotNullIfNotNull(nameof(properties))] - public virtual IIkvmReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties) + public IIkvmReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties) { if (properties == null) return null; @@ -367,7 +367,7 @@ public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Proper /// [return: NotNullIfNotNull(nameof(events))] - public virtual IIkvmReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events) + public IIkvmReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events) { if (@events == null) return null; @@ -420,7 +420,7 @@ public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Proper /// [return: NotNullIfNotNull(nameof(parameters))] - public virtual IIkvmReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters) + public IIkvmReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters) { if (parameters == null) return null; @@ -437,7 +437,7 @@ public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Proper /// [return: NotNullIfNotNull(nameof(attributes))] - public virtual CustomAttribute[]? ResolveCustomAttributes(IList? attributes) + public CustomAttribute[]? ResolveCustomAttributes(IList? attributes) { if (attributes == null) return null; @@ -453,7 +453,7 @@ public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Proper } /// - public virtual IEnumerable ResolveCustomAttributes(IEnumerable attributes) + public IEnumerable ResolveCustomAttributes(IEnumerable attributes) { if (attributes is null) throw new ArgumentNullException(nameof(attributes)); @@ -468,7 +468,7 @@ public virtual IEnumerable ResolveCustomAttributes(IEnumerable< /// [return: NotNullIfNotNull(nameof(customAttributeData))] - public virtual CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) + public CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) { if (customAttributeData == null) return null; diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index 405b59f233..7a984642fc 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -42,7 +42,7 @@ public IkvmReflectionTypeSymbol(IkvmReflectionSymbolContext context, IIkvmReflec public Type UnderlyingType => _type; /// - public override IKVM.Reflection.MemberInfo UnderlyingMember => UnderlyingType; + public override MemberInfo UnderlyingMember => UnderlyingType; #region IIkvmReflectionTypeSymbol diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs index 7239bb3f36..5898b55e8f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -15,7 +15,7 @@ static class IkvmReflectionUtil { /// - /// Converts a to a . + /// Converts a to a . /// /// /// @@ -25,7 +25,7 @@ public static AssemblyNameInfo Pack(this AssemblyName n) } /// - /// Converts a set of to a set of . + /// Converts a set of to a set of . /// /// /// @@ -58,7 +58,7 @@ public static AssemblyName Unpack(this AssemblyNameInfo n) } /// - /// Converts a set of to a set of . + /// Converts a set of to a set of . /// /// /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs index 6652e1af14..af8639e043 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs @@ -5,7 +5,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionAssemblySymbolBuilder : IReflectionSymbolBuilder, IAssemblySymbolBuilder, IReflectionAssemblySymbol + interface IReflectionAssemblySymbolBuilder : IReflectionSymbolBuilder, IAssemblySymbolBuilder, IReflectionAssemblySymbol { /// @@ -13,6 +13,13 @@ interface IReflectionAssemblySymbolBuilder : IReflectionSymbolBuilder AssemblyBuilder UnderlyingAssemblyBuilder { get; } + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs index 0572b3bdfb..d9a2a02655 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs @@ -5,9 +5,12 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionConstructorSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder, IReflectionConstructorSymbol + interface IReflectionConstructorSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder, IReflectionConstructorSymbol { + /// + /// Gets the underlying . + /// ConstructorBuilder UnderlyingConstructorBuilder { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs index f9c48d0bec..d90955a8cf 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs @@ -5,9 +5,12 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionEventSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IEventSymbolBuilder, IReflectionEventSymbol + interface IReflectionEventSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IEventSymbolBuilder, IReflectionEventSymbol { + /// + /// Gets the underlying . + /// EventBuilder UnderlyingEventBuilder { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs index ecd263c1bd..6463e87167 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs @@ -5,7 +5,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionFieldSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IFieldSymbolBuilder, IReflectionFieldSymbol + interface IReflectionFieldSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IFieldSymbolBuilder, IReflectionFieldSymbol { FieldBuilder UnderlyingFieldBuilder { get; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs index a9cc7500f8..c02f275dda 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs @@ -5,7 +5,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionGenericTypeParameterSymbolBuilder : IReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IReflectionTypeSymbol + interface IReflectionGenericTypeParameterSymbolBuilder : IReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IReflectionTypeSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs index 4eb323b30b..f324730eb0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs @@ -3,9 +3,14 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionMemberSymbolBuilder : IReflectionSymbolBuilder, IMemberSymbolBuilder, IReflectionMemberSymbol + interface IReflectionMemberSymbolBuilder : IReflectionSymbolBuilder, IMemberSymbolBuilder, IReflectionMemberSymbol { + /// + /// Gets the resolving . + /// + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder { get; } + /// /// Invoked when the type responsible for this builder is completed. Implementations should update their /// underlying type, and optionally dispatch the OnComplete invocation to downstream elements. diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs index 0d757111d6..bdc1c996f5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs @@ -1,12 +1,19 @@ -using IKVM.CoreLib.Symbols.Emit; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionMethodBaseSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IReflectionMethodBaseSymbol + interface IReflectionMethodBaseSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IReflectionMethodBaseSymbol { - + /// + /// Gets or creates a for the given . + /// + /// + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs index cc19efa3d2..76cbe97c51 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs @@ -5,7 +5,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionMethodSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder, IReflectionMethodSymbol + interface IReflectionMethodSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder, IReflectionMethodSymbol { /// @@ -13,6 +13,13 @@ interface IReflectionMethodSymbolBuilder : IReflectionSymbolBuilder MethodBuilder UnderlyingMethodBuilder { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs index 9fbd1c7c1c..695568f4f5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs @@ -5,7 +5,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionModuleSymbolBuilder : IReflectionSymbolBuilder, IModuleSymbolBuilder, IReflectionModuleSymbol + interface IReflectionModuleSymbolBuilder : IReflectionSymbolBuilder, IModuleSymbolBuilder, IReflectionModuleSymbol { /// @@ -13,6 +13,63 @@ interface IReflectionModuleSymbolBuilder : IReflectionSymbolBuilder ModuleBuilder UnderlyingModuleBuilder { get; } + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + /// + IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs index 679ac84294..17f6fb75ea 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs @@ -5,7 +5,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionParameterSymbolBuilder : IReflectionSymbolBuilder, IParameterSymbolBuilder, IReflectionParameterSymbol + interface IReflectionParameterSymbolBuilder : IReflectionSymbolBuilder, IParameterSymbolBuilder, IReflectionParameterSymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs index 1a10c8c6cd..c010b01963 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs @@ -5,11 +5,21 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionPropertySymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IPropertySymbolBuilder, IReflectionPropertySymbol + interface IReflectionPropertySymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IPropertySymbolBuilder, IReflectionPropertySymbol { + /// + /// Gets the underlying . + /// PropertyBuilder UnderlyingPropertyBuilder { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs index 45123999fd..b7795a7d32 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs @@ -1,4 +1,7 @@ -using IKVM.CoreLib.Symbols.Emit; +using System.Diagnostics.CodeAnalysis; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -6,13 +9,77 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit interface IReflectionSymbolBuilder : ISymbolBuilder { - } + /// + /// Resolves the symbol for the specified assembly builder. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assembly))] + IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); - interface IReflectionSymbolBuilder : IReflectionSymbolBuilder, ISymbolBuilder - where TSymbol : IReflectionSymbol - { + /// + /// Resolves the symbol for the specified module. + /// + /// + /// + [return: NotNullIfNotNull(nameof(module))] + IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); + + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); + + /// + /// Resolves the symbol for the specified constructor. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctor))] + IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); + + /// + /// Resolves the symbol for the specified field. + /// + /// + /// + [return: NotNullIfNotNull(nameof(field))] + IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); + + /// + /// Resolves the symbol for the specified property. + /// + /// + /// + [return: NotNullIfNotNull(nameof(property))] + IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); + /// + /// Resolves the symbol for the specified event. + /// + /// + /// + [return: NotNullIfNotNull(nameof(@event))] + IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); + /// + /// Resolves the symbol for the specified generic type parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(genericTypeParameter))] + IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs index ee86b9734b..d5ed37b227 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs @@ -5,7 +5,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - interface IReflectionTypeSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, ITypeSymbolBuilder, IReflectionTypeSymbol + interface IReflectionTypeSymbolBuilder : IReflectionMemberSymbolBuilder, ITypeSymbolBuilder, IReflectionTypeSymbol { /// @@ -13,6 +13,48 @@ interface IReflectionTypeSymbolBuilder : IReflectionSymbolBuilder TypeBuilder UnderlyingTypeBuilder { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index b421a94c6e..1ae5eba59c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -1,6 +1,5 @@ using System; using System.Collections.Generic; -using System.Collections.Immutable; using System.IO; using System.Linq; using System.Reflection; @@ -15,7 +14,8 @@ class ReflectionAssemblySymbolBuilder : ReflectionSymbolBuilder, IReflectionAsse { readonly AssemblyBuilder _builder; - ReflectionAssemblyMetadata _metadata; + + ReflectionModuleTable _moduleTable; /// /// Initializes a new instance. @@ -26,7 +26,7 @@ public ReflectionAssemblySymbolBuilder(ReflectionSymbolContext context, Assembly base(context) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _metadata = new ReflectionAssemblyMetadata(this); + _moduleTable = new ReflectionModuleTable(context, this); } /// @@ -35,6 +35,26 @@ public ReflectionAssemblySymbolBuilder(ReflectionSymbolContext context, Assembly /// public AssemblyBuilder UnderlyingAssemblyBuilder => _builder; + #region IReflectionAssemblySymbolBuilder + + /// + public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return _moduleTable.GetOrCreateModuleSymbol(module); + } + + #endregion + + #region IReflectionAssemblySymbol + + /// + public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _moduleTable.GetOrCreateModuleSymbol(module); + } + + #endregion + #region IAssemblySymbolBuilder /// @@ -66,23 +86,13 @@ public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emit /// public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) { - _builder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingAssemblyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); } /// public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) { - _builder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } - - public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy) - { - throw new NotImplementedException(); - } - - public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, Symbols.Emit.PEFileKinds target) - { - throw new NotImplementedException(); + UnderlyingAssemblyBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } /// @@ -107,6 +117,18 @@ public void DefineVersionInfoResource() #endif } + /// + public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy) + { + throw new NotImplementedException(); + } + + /// + public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, IKVM.CoreLib.Symbols.Emit.PEFileKinds target) + { + throw new NotImplementedException(); + } + /// public void AddTypeForwarder(ITypeSymbol type) { @@ -124,7 +146,7 @@ public void AddResourceFile(string name, string fileName) } /// - public void Save(string assemblyFileName, PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine) + public void Save(string assemblyFileName, System.Reflection.PortableExecutableKinds portableExecutableKind, IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine) { #if NETFRAMEWORK UnderlyingAssemblyBuilder.Save(assemblyFileName, portableExecutableKind, (System.Reflection.ImageFileMachine)imageFileMachine); @@ -190,24 +212,13 @@ public IModuleSymbol[] GetModules(bool getResourceModules) /// public AssemblyNameInfo GetName() { - return ToAssemblyName(UnderlyingAssembly.GetName()); + return UnderlyingAssembly.GetName().Pack(); } /// public AssemblyNameInfo[] GetReferencedAssemblies() { - return UnderlyingAssembly.GetReferencedAssemblies().Select(i => ToAssemblyName(i)).ToArray(); - } - - /// - /// Transforms the to a . - /// - /// - /// - /// - AssemblyNameInfo ToAssemblyName(AssemblyName n) - { - return new AssemblyNameInfo(n.Name ?? throw new InvalidOperationException(), n.Version, n.CultureName, n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? []); + return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } /// @@ -250,7 +261,8 @@ public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inh /// public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); } /// @@ -279,17 +291,6 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion - /// - public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - return _metadata.GetOrCreateModuleSymbol(module); - } - - /// - public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) - { - return (IReflectionModuleSymbolBuilder)_metadata.GetOrCreateModuleSymbol(module); - } } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index a80569f593..ba6d7c8b83 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -23,7 +23,7 @@ class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IR /// /// /// - public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, ConstructorBuilder builder) : + public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder resolvingType, ConstructorBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); @@ -39,7 +39,7 @@ public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, IRefl /// public ConstructorBuilder UnderlyingConstructorBuilder => _builder ?? throw new InvalidOperationException(); - #region IMethodBaseSymbolBuilder + #region IConstructorSymbolBuilder /// public override void SetImplementationFlags(MethodImplAttributes attributes) @@ -50,7 +50,10 @@ public override void SetImplementationFlags(MethodImplAttributes attributes) /// public override IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) { - return ResolveParameterSymbol(UnderlyingConstructorBuilder.DefineParameter(iSequence, attributes, strParamName)); + if (iSequence <= 0) + throw new ArgumentOutOfRangeException(nameof(iSequence)); + + return ResolveParameterSymbol(this, UnderlyingConstructorBuilder.DefineParameter(iSequence, attributes, strParamName)); } /// @@ -79,10 +82,6 @@ public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAtt #endregion - #region IConstructorSymbolBuilder - - #endregion - #region IConstructorSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs index d583458d9e..0241418019 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs @@ -21,7 +21,7 @@ class ReflectionEventSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionE /// /// /// - public ReflectionEventSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, EventBuilder builder) : + public ReflectionEventSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder resolvingType, EventBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); @@ -80,7 +80,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) #region IEventSymbol /// - public EventAttributes Attributes => UnderlyingEvent.Attributes; + public System.Reflection.EventAttributes Attributes => UnderlyingEvent.Attributes; /// public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs index 5aa337c85f..1c96e8bd8b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs @@ -21,7 +21,7 @@ class ReflectionFieldSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionF /// /// /// - public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, FieldBuilder builder) : + public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType, FieldBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); @@ -94,10 +94,8 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) /// public bool IsLiteral => UnderlyingField.IsLiteral; -#pragma warning disable SYSLIB0050 // Type or member is obsolete /// public bool IsNotSerialized => UnderlyingField.IsNotSerialized; -#pragma warning restore SYSLIB0050 // Type or member is obsolete /// public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs index 2ea5707553..17651ec77a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs @@ -2,7 +2,7 @@ using System.Reflection; using System.Reflection.Emit; -using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Reflection; namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -10,28 +10,28 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit class ReflectionGenericTypeParameterSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionGenericTypeParameterSymbolBuilder { - readonly IReflectionMethodSymbol? _resolvingMethod; + readonly IReflectionMemberSymbol? _resolvingMember; GenericTypeParameterBuilder? _builder; Type _type; - ReflectionTypeImpl _impl; + + ReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. /// /// /// - /// - /// + /// /// /// - public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, IReflectionMethodSymbol? resolvingMethod, GenericTypeParameterBuilder builder) : - base(context, resolvingModule, resolvingType) + public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionMemberSymbolBuilder resolvingMember, GenericTypeParameterBuilder builder) : + base(context, resolvingModule, resolvingMember as IReflectionTypeSymbolBuilder) { - _resolvingMethod = resolvingMethod; + _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _type = _builder; - _impl = new ReflectionTypeImpl(this); + _specTable = new ReflectionTypeSpecTable(); } /// @@ -40,9 +40,125 @@ public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext conte /// public override MemberInfo UnderlyingMember => UnderlyingType; + #region IReflectionGenericTypeParameterSymbolBuilder + /// public GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder => _builder ?? throw new InvalidOperationException(); + #endregion + + #region IReflectionTypeSymbol + + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + throw new NotSupportedException(); + } + + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + throw new NotSupportedException(); + } + + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + throw new NotSupportedException(); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + throw new NotSupportedException(); + } + + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + throw new NotSupportedException(); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + throw new NotSupportedException(); + } + + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + throw new NotSupportedException(); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + throw new NotSupportedException(); + } + + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + throw new NotSupportedException(); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + throw new NotSupportedException(); + } + + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + throw new NotSupportedException(); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type type) + { + throw new NotSupportedException(); + } + + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeSymbol(GenericTypeParameterBuilder genericType) + { + throw new NotSupportedException(); + } + + /// + public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion + #region ITypeSymbolBuilder /// @@ -52,9 +168,9 @@ public void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint) } /// - public void SetGenericParameterAttributes(GenericParameterAttributes genericParameterAttributes) + public void SetGenericParameterAttributes(System.Reflection.GenericParameterAttributes genericParameterAttributes) { - UnderlyingGenericTypeParameterBuilder.SetGenericParameterAttributes(genericParameterAttributes); + UnderlyingGenericTypeParameterBuilder.SetGenericParameterAttributes((GenericParameterAttributes)genericParameterAttributes); } /// @@ -68,506 +184,525 @@ public void SetInterfaceConstraints(params ITypeSymbol[]? interfaceConstraints) #region ITypeSymbol /// - public TypeAttributes Attributes => _impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); + + /// + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IAssemblySymbol Assembly => _impl.Assembly; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? FullName => _impl.FullName; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public string? Namespace => _impl.Namespace; + public string? FullName => UnderlyingType.FullName; /// - public TypeCode TypeCode => _impl.TypeCode; + public string? Namespace => UnderlyingType.Namespace; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public bool HasElementType => UnderlyingType.HasElementType; /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsSZArray => UnderlyingType.IsSZArray(); /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsClass => UnderlyingType.IsClass; /// - public bool HasElementType => _impl.HasElementType; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsClass => _impl.IsClass; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsValueType => _impl.IsValueType; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsInterface => _impl.IsInterface; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsArray => _impl.IsArray; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsEnum => _impl.IsEnum; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsPointer => UnderlyingType.IsPointer; + +#if NET8_0_OR_GREATER /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNested => _impl.IsNested; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; + +#else /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsFunctionPointer => throw new NotImplementedException(); /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSignatureType => throw new NotImplementedException(); /// - public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + public bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public override bool IsComplete => _builder == null; + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// public int GetArrayRank() { - return _impl.GetArrayRank(); + return UnderlyingType.GetArrayRank(); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetElementType(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors() { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string[] GetEnumNames() + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumNames(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public ITypeSymbol GetEnumUnderlyingType() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumUnderlyingType(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol[] GetGenericArguments() + public ITypeSymbol? GetElementType() { - return _impl.GetGenericArguments(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string? GetEnumName(object value) { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol GetGenericTypeDefinition() + public string[] GetEnumNames() { - return _impl.GetGenericTypeDefinition(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol? GetInterface(string name) + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetInterface(name); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public Array GetEnumValues() { - return _impl.GetInterface(name, ignoreCase); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents() { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, bindingAttr); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetConstructor(types); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructors(); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name, bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol[] GetFields() + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return _impl.GetFields(); + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); } /// - public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(bindingAttr); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, types); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name, bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties() { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public bool IsAssignableFrom(ITypeSymbol? c) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.IsAssignableFrom(c); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// public bool IsEnumDefined(object value) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsEnumDefined(value); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); } /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + public ITypeSymbol MakeByRefType() { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); } /// - public ITypeSymbol MakeByRefType() + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } #endregion @@ -575,7 +710,7 @@ public ITypeSymbol MakeByRefType() /// public override void OnComplete() { - throw new NotImplementedException(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs index 8727613762..d3c13c2050 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs @@ -1,5 +1,4 @@ using System; -using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Linq; using System.Reflection; @@ -13,39 +12,8 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit abstract class ReflectionMemberSymbolBuilder : ReflectionSymbolBuilder, IReflectionMemberSymbolBuilder { - /// - /// Concatinates the list of arrays. - /// - /// - /// - static T[] Concat(List? list) - { - if (list == null) - return []; - - var c = 0; - foreach (var i in list) - c += i.Length; - - if (c == 0) - return []; - - var t = 0; - var a = new T[c]; - foreach (var i in list) - { - Array.Copy(i, 0, a, t, i.Length); - t += i.Length; - } - - return a; - } - - readonly IReflectionModuleSymbol _resolvingModule; - readonly IReflectionTypeSymbol? _resolvingType; - - CustomAttribute[]? _customAttributes; - CustomAttribute[]? _inheritedCustomAttributes; + readonly IReflectionModuleSymbolBuilder _resolvingModule; + readonly IReflectionTypeSymbolBuilder? _resolvingType; /// /// Initializes a new instance. @@ -53,14 +21,14 @@ static T[] Concat(List? list) /// /// /// - public ReflectionMemberSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : + public ReflectionMemberSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType) : base(context) { _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); _resolvingType = resolvingType; } - #region IMemberSymbol + #region IReflectionMemberSymbol /// public abstract MemberInfo UnderlyingMember { get; } @@ -69,128 +37,153 @@ public ReflectionMemberSymbolBuilder(ReflectionSymbolContext context, IReflectio public IReflectionModuleSymbol ResolvingModule => _resolvingModule; /// - public IReflectionTypeSymbol? ResolvingType => ResolvingType; + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => _resolvingModule; /// - public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + public IReflectionTypeSymbol? ResolvingType => _resolvingType; - /// - public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + #endregion - /// - public virtual MemberTypes MemberType => UnderlyingMember.MemberType; + #region IReflectionSymbolBuilder /// - public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); + [return: NotNullIfNotNull("type")] + public override IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); - /// - public virtual string Name => UnderlyingMember.Name; + if (UnderlyingMember == type) + return (IReflectionTypeSymbolBuilder)this; + + if (_resolvingType != null && type == _resolvingType.UnderlyingType) + return (IReflectionTypeSymbolBuilder)_resolvingType; + + if (type.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateTypeSymbol(type); + + return base.ResolveTypeSymbol(type); + } /// - public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) + [return: NotNullIfNotNull(nameof(ctor))] + public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) { - if (inherit) - { - // check that we've already processed this - if (_inheritedCustomAttributes != null) - return _inheritedCustomAttributes; - - var self = UnderlyingMember; - var list = default(List?); - for (; ; ) - { - if (self == null) - throw new InvalidOperationException(); - - // get attribute for current member and append to list - var attr = ResolveMemberSymbol(self)!.GetCustomAttributes(false); - if (attr.Length > 0) - { - list ??= []; - list.Add(attr); - } - - var type = self as Type; - if (type != null) - { - type = type.BaseType; - if (type == null) - return _inheritedCustomAttributes ??= Concat(list); - - self = type; - continue; - } - - var method = self as MethodInfo; - if (method != null) - { - var prev = self; - method = method.GetBaseDefinition(); - if (method == null || method == prev) - return _inheritedCustomAttributes ??= Concat(list); - - self = method; - continue; - } - - return _inheritedCustomAttributes ??= Concat(list); - } - } - - return _customAttributes ??= ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData())!; + if (ctor is null) + throw new ArgumentNullException(nameof(ctor)); + + if (UnderlyingMember == ctor) + return (IReflectionConstructorSymbolBuilder)this; + + if (ctor.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + + return base.ResolveConstructorSymbol(ctor); } /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + [return: NotNullIfNotNull(nameof(method))] + public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) { - return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + if (method is null) + throw new ArgumentNullException(nameof(method)); + + if (UnderlyingMember == method) + return (IReflectionMethodSymbolBuilder)this; + + if (method.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateMethodSymbol(method); + + return base.ResolveMethodSymbol(method); } /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + [return: NotNullIfNotNull(nameof(field))] + public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + if (field is null) + throw new ArgumentNullException(nameof(field)); + + if (UnderlyingMember == field) + return (IReflectionFieldSymbolBuilder)this; + + if (field.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateFieldSymbol(field); + + return base.ResolveFieldSymbol(field); } /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + [return: NotNullIfNotNull(nameof(property))] + public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) { - return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (UnderlyingMember == property) + return (IReflectionPropertySymbolBuilder)this; + + if (property.Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreatePropertySymbol(property); + + return base.ResolvePropertySymbol(property); } - #endregion + /// + [return: NotNullIfNotNull(nameof(@event))] + public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + + if (@event.GetModuleBuilder() == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateEventSymbol(@event); + + return base.ResolveEventSymbol(@event); + } /// - [return: NotNullIfNotNull(nameof(type))] - public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) + [return: NotNullIfNotNull(nameof(parameter))] + public override IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionMethodBaseSymbolBuilder method, ParameterBuilder parameter) { - if (type is null) + if (parameter is null) return null; - if (UnderlyingMember == type) - return (IReflectionTypeSymbol)this; + if (parameter.GetModuleBuilder() == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(method, parameter); - if (_resolvingType != null && type == _resolvingType.UnderlyingType) - return _resolvingType; + return base.ResolveParameterSymbol(method, parameter); + } - if (type.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateTypeSymbol(type); + /// + [return: NotNullIfNotNull(nameof(parameter))] + public override IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionPropertySymbolBuilder property, ParameterBuilder parameter) + { + if (parameter is null) + return null; - return base.ResolveTypeSymbol(type); + if (parameter.GetMethodBuilder().Module == _resolvingModule.UnderlyingModule) + return _resolvingModule.GetOrCreateParameterSymbol(property, parameter); + + return base.ResolveParameterSymbol(property, parameter); } + #endregion + + #region IReflectionSymbol + /// - [return: NotNullIfNotNull("type")] - public override IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) + [return: NotNullIfNotNull(nameof(type))] + public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) { if (type is null) - throw new ArgumentNullException(nameof(type)); + return null; if (UnderlyingMember == type) - return (IReflectionTypeSymbolBuilder)this; + return (IReflectionTypeSymbol)this; if (_resolvingType != null && type == _resolvingType.UnderlyingType) - return (IReflectionTypeSymbolBuilder)_resolvingType; + return _resolvingType; if (type.Module == _resolvingModule.UnderlyingModule) return _resolvingModule.GetOrCreateTypeSymbol(type); @@ -214,22 +207,6 @@ public override IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) return base.ResolveConstructorSymbol(ctor); } - /// - [return: NotNullIfNotNull(nameof(ctor))] - public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) - { - if (ctor is null) - throw new ArgumentNullException(nameof(ctor)); - - if (UnderlyingMember == ctor) - return (IReflectionConstructorSymbolBuilder)this; - - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); - - return base.ResolveConstructorSymbol(ctor); - } - /// [return: NotNullIfNotNull(nameof(method))] public override IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) @@ -246,22 +223,6 @@ public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(Con return base.ResolveMethodSymbol(method); } - /// - [return: NotNullIfNotNull(nameof(method))] - public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - if (UnderlyingMember == method) - return (IReflectionMethodSymbolBuilder)this; - - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); - - return base.ResolveMethodSymbol(method); - } - /// [return: NotNullIfNotNull(nameof(field))] public override IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) @@ -278,22 +239,6 @@ public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder return base.ResolveFieldSymbol(field); } - /// - [return: NotNullIfNotNull(nameof(field))] - public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - if (UnderlyingMember == field) - return (IReflectionFieldSymbolBuilder)this; - - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); - - return base.ResolveFieldSymbol(field); - } - /// [return: NotNullIfNotNull(nameof(property))] public override IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) @@ -310,22 +255,6 @@ public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder fi return base.ResolvePropertySymbol(property); } - /// - [return: NotNullIfNotNull(nameof(property))] - public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - if (UnderlyingMember == property) - return (IReflectionPropertySymbolBuilder)this; - - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); - - return base.ResolvePropertySymbol(property); - } - /// [return: NotNullIfNotNull(nameof(@event))] public override IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) @@ -342,19 +271,6 @@ public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyB return base.ResolveEventSymbol(@event); } - /// - [return: NotNullIfNotNull(nameof(@event))] - public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - if (@event.GetModuleBuilder() == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); - - return base.ResolveEventSymbol(@event); - } - /// [return: NotNullIfNotNull(nameof(parameter))] public override IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) @@ -368,19 +284,53 @@ public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @e return base.ResolveParameterSymbol(parameter); } + #endregion + + #region IMemberSymbol + /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + + /// + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + + /// + public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + + /// + public virtual int MetadataToken => UnderlyingMember.MetadataToken; + + /// + public virtual string Name => UnderlyingMember.Name; + + /// + public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData()); + } - if (parameter.GetModuleBuilder() == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); + /// + public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); + } - return base.ResolveParameterSymbol(parameter); + /// + public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); } + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); + } + + #endregion + /// public virtual void OnComplete() { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs index d9d2833276..03cd589a41 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs @@ -1,4 +1,5 @@ using System.Reflection; +using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -8,16 +9,18 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit abstract class ReflectionMethodBaseSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionMethodBaseSymbolBuilder { + ReflectionParameterTable _parameterTable; + /// /// Initializes a new instance. /// /// /// /// - public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : + public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType) : base(context, resolvingModule, resolvingType) { - + _parameterTable = new ReflectionParameterTable(context, resolvingModule, this); } /// @@ -26,6 +29,16 @@ public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IRefle /// public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + #region IReflectionMethodBaseSymbol + + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + #region IMethodBaseSymbolBuilder /// @@ -46,15 +59,21 @@ public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IRefle /// public abstract void SetCustomAttribute(ICustomAttributeBuilder customBuilder); + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + #endregion #region IMethodBaseSymbol /// - public MethodAttributes Attributes => UnderlyingMethodBase.Attributes; + public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; /// - public CallingConventions CallingConvention => UnderlyingMethodBase.CallingConvention; + public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; /// public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; @@ -105,7 +124,7 @@ public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IRefle public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; /// - public MethodImplAttributes MethodImplementationFlags => UnderlyingMethodBase.MethodImplementationFlags; + public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; /// public ITypeSymbol[] GetGenericArguments() @@ -114,7 +133,7 @@ public ITypeSymbol[] GetGenericArguments() } /// - public MethodImplAttributes GetMethodImplementationFlags() + public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() { return UnderlyingMethodBase.GetMethodImplementationFlags(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index 9336237402..43ab72c527 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -13,6 +13,9 @@ class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflec MethodBuilder? _builder; MethodInfo _method; + ReflectionGenericTypeParameterTable _genericTypeParameterTable; + ReflectionMethodSpecTable _specTable; + ReflectionILGenerator? _il; /// @@ -23,11 +26,13 @@ class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflec /// /// /// - public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, MethodBuilder builder) : + public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType, MethodBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _method = _builder; + _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, resolvingModule, this); + _specTable = new ReflectionMethodSpecTable(context, resolvingModule, resolvingType, this); } /// @@ -39,18 +44,52 @@ public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectio /// public MethodBuilder UnderlyingMethodBuilder => _builder ?? throw new InvalidOperationException(); + #region IReflectionMethodSymbolBuilder + + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + #endregion + + #region IReflectionMethodSymbol + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + /// + public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) + { + return _specTable.GetOrCreateGenericMethodSymbol(method.GetGenericArguments()); + } + + #endregion + + #region IReflectionMethodBaseSymbol + + #endregion + + #region IReflectionMethodBaseSymbolBuilder + + #endregion + #region IMethodBaseSymbolBuilder /// - public override void SetImplementationFlags(MethodImplAttributes attributes) + public override void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) { - UnderlyingMethodBuilder.SetImplementationFlags(attributes); + UnderlyingMethodBuilder.SetImplementationFlags((MethodImplAttributes)attributes); } /// - public override IParameterSymbolBuilder DefineParameter(int position, ParameterAttributes attributes, string? strParamName) + public override IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) { - return ResolveParameterSymbol(UnderlyingMethodBuilder.DefineParameter(position, attributes, strParamName)); + return ResolveParameterSymbol(this, UnderlyingMethodBuilder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); } /// @@ -104,7 +143,7 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin var l = UnderlyingMethodBuilder.DefineGenericParameters(names); var a = new IGenericTypeParameterSymbolBuilder[l.Length]; for (int i = 0; i < l.Length; i++) - a[i] = (IGenericTypeParameterSymbolBuilder)ResolveTypeSymbol(l[i]); + a[i] = ResolveGenericTypeParameterSymbol(l[i]); return a; } @@ -152,7 +191,6 @@ public override void OnComplete() _builder = null; base.OnComplete(); } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index 42fdb989d9..b671cc5e6e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -4,9 +4,9 @@ using System.Linq; using System.Reflection; using System.Reflection.Emit; -using System.Reflection.PortableExecutable; using System.Resources; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit @@ -16,9 +16,12 @@ class ReflectionModuleSymbolBuilder : ReflectionSymbolBuilder, IReflectionModule { readonly IReflectionAssemblySymbol _resolvingAssembly; + Module _module; + ModuleBuilder? _builder; - readonly ModuleBuilder _builder; - ReflectionModuleMetadata _metadata; + ReflectionTypeTable _typeTable; + ReflectionMethodTable _methodTable; + ReflectionFieldTable _fieldTable; /// /// Initializes a new instance. @@ -32,18 +35,167 @@ public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, IReflectio { _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _metadata = new ReflectionModuleMetadata(this); + _module = _builder; + + _typeTable = new ReflectionTypeTable(context, this, null); + _methodTable = new ReflectionMethodTable(context, this, null); + _fieldTable = new ReflectionFieldTable(context, this, null); } /// - public Module UnderlyingModule => UnderlyingModuleBuilder; + public Module UnderlyingModule => _module; /// - public ModuleBuilder UnderlyingModuleBuilder => _builder; + public ModuleBuilder UnderlyingModuleBuilder => _builder ?? throw new InvalidOperationException(); /// public IReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; + #region IReflectionModuleSymbol + + /// + public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type.IsTypeDefinition()) + return _typeTable.GetOrCreateTypeSymbol(type); + else if (type.IsGenericType) + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + else if (type.IsSZArray()) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateSZArrayTypeSymbol(); + else if (type.IsArray) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateArrayTypeSymbol(type.GetArrayRank()); + else if (type.IsPointer) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreatePointerTypeSymbol(); + else if (type.IsByRef) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateByRefTypeSymbol(); + else if (type.IsGenericParameter && type.DeclaringMethod is MethodInfo dm) + return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(type); + else if (type.IsGenericParameter) + return ResolveTypeSymbol(type.DeclaringType!).GetOrCreateGenericTypeParameterSymbol(type); + else + throw new InvalidOperationException(); + } + + /// + public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + return (IReflectionTypeSymbolBuilder)_typeTable.GetOrCreateTypeSymbol((Type)type); + } + + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodBaseSymbol(method); + else + return _methodTable.GetOrCreateMethodBaseSymbol(method); + } + + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return ResolveTypeSymbol(ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return ResolveTypeSymbol((TypeBuilder)ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodSymbol(method); + else + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateMethodSymbol(method); + else + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateFieldSymbol(field); + else + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + if (field.DeclaringType is { } dt) + return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateFieldSymbol(field); + else + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return ResolveTypeSymbol(property.DeclaringType!).GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return ResolveTypeSymbol(property.GetTypeBuilder()).GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return ResolveTypeSymbol(@event.DeclaringType!).GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return ResolveTypeSymbol(@event.GetTypeBuilder()).GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return ResolveMemberSymbol(parameter.Member) switch + { + IReflectionMethodBaseSymbol method => method.GetOrCreateParameterSymbol(parameter), + IReflectionPropertySymbol property => property.GetOrCreateParameterSymbol(parameter), + _ => throw new InvalidOperationException(), + }; + } + + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter) + { + return member switch + { + IReflectionMethodBaseSymbolBuilder method => method.GetOrCreateParameterSymbol(parameter), + IReflectionPropertySymbolBuilder property => property.GetOrCreateParameterSymbol(parameter), + _ => throw new InvalidOperationException(), + }; + } + + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) + { + if (genericParameterType.DeclaringMethod is MethodBuilder dm) + return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + else + return ResolveTypeSymbol((TypeBuilder)genericParameterType.DeclaringType!).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + } + + #endregion + #region IModuleSymbolBuilder /// @@ -57,10 +209,10 @@ public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, IReflectio } /// - public void DefineManifestResource(string name, Stream stream, ResourceAttributes attribute) + public void DefineManifestResource(string name, Stream stream, System.Reflection.ResourceAttributes attribute) { #if NETFRAMEWORK - UnderlyingModuleBuilder.DefineManifestResource(name, stream, attribute); + UnderlyingModuleBuilder.DefineManifestResource(name, stream, attribute); #else throw new NotSupportedException(); #endif @@ -70,80 +222,80 @@ public void DefineManifestResource(string name, Stream stream, ResourceAttribute public IResourceWriter DefineResource(string name, string description) { #if NETFRAMEWORK - return UnderlyingModuleBuilder.DefineResource(name, description); + return UnderlyingModuleBuilder.DefineResource(name, description); #else throw new NotImplementedException(); #endif } /// - public IResourceWriter DefineResource(string name, string description, ResourceAttributes attribute) + public IResourceWriter DefineResource(string name, string description, System.Reflection.ResourceAttributes attribute) { #if NETFRAMEWORK - return UnderlyingModuleBuilder.DefineResource(name, description, attribute); + return UnderlyingModuleBuilder.DefineResource(name, description, attribute); #else throw new NotImplementedException(); #endif } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? requiredReturnTypeCustomModifiers, ITypeSymbol[]? optionalReturnTypeCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredParameterTypeCustomModifiers, ITypeSymbol[][]? optionalParameterTypeCustomModifiers) + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? requiredReturnTypeCustomModifiers, ITypeSymbol[]? optionalReturnTypeCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredParameterTypeCustomModifiers, ITypeSymbol[][]? optionalParameterTypeCustomModifiers) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, callingConvention, returnType?.Unpack(), requiredReturnTypeCustomModifiers?.Unpack(), optionalReturnTypeCustomModifiers?.Unpack(), parameterTypes?.Unpack(), requiredParameterTypeCustomModifiers?.Unpack(), optionalParameterTypeCustomModifiers?.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), requiredReturnTypeCustomModifiers?.Unpack(), optionalReturnTypeCustomModifiers?.Unpack(), parameterTypes?.Unpack(), requiredParameterTypeCustomModifiers?.Unpack(), optionalParameterTypeCustomModifiers?.Unpack())); } /// - public IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + public IMethodSymbolBuilder DefineGlobalMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + return ResolveMethodSymbol(UnderlyingModuleBuilder.DefineGlobalMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); } /// public ITypeSymbolBuilder DefineType(string name) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name)); + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name)); } /// - public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, int typesize) + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typesize) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), typesize)); + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), typesize)); } /// - public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent) + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack())); + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack())); } /// - public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr) + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr)); + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr)); } /// - public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packsize) + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packsize) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), packsize)); + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packsize)); } /// - public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packingSize, int typesize) + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packingSize, int typesize) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), packingSize, typesize)); + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packingSize, typesize)); } /// - public ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) + public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, attr, parent?.Unpack(), interfaces?.Unpack())); + return ResolveTypeSymbol(UnderlyingModuleBuilder.DefineType(name, (TypeAttributes)attr, parent?.Unpack(), interfaces?.Unpack())); } /// @@ -158,6 +310,36 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) UnderlyingModuleBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); } + /// + public void AddReference(IAssemblySymbol assembly) + { +#if NETFRAMEWORK + var t = ((IReflectionAssemblySymbol)assembly).GetExportedTypes(); + if (t.Length > 0) + UnderlyingModuleBuilder.GetTypeToken(t[0].Unpack()); +#else + throw new NotSupportedException(); +#endif + } + + /// + public void Complete() + { + UnderlyingModuleBuilder.CreateGlobalFunctions(); + + foreach (var type in GetTypes()) + if (type is IReflectionTypeSymbolBuilder t) + t.Complete(); + + _builder = null; + } + + /// + public void Save(System.Reflection.PortableExecutableKinds portableExecutableKind, IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine) + { + throw new NotSupportedException(); + } + #endregion #region IModuleSymbol @@ -195,7 +377,7 @@ public uint FileAlignment } /// - public DllCharacteristics DllCharacteristics + public System.Reflection.PortableExecutable.DllCharacteristics DllCharacteristics { get => throw new NotSupportedException(); set => throw new NotSupportedException(); @@ -211,15 +393,15 @@ public DllCharacteristics DllCharacteristics } /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return ResolveFieldSymbol(UnderlyingModule.GetField(name, bindingAttr)); + return ResolveFieldSymbol(UnderlyingModule.GetField(name, (BindingFlags)bindingAttr)); } /// - public IFieldSymbol[] GetFields(BindingFlags bindingFlags) + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingFlags) { - return ResolveFieldSymbols(UnderlyingModule.GetFields(bindingFlags))!; + return ResolveFieldSymbols(UnderlyingModule.GetFields((BindingFlags)bindingFlags))!; } /// @@ -241,9 +423,9 @@ public IFieldSymbol[] GetFields() } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers)); + return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// @@ -253,9 +435,9 @@ public IMethodSymbol[] GetMethods() } /// - public IMethodSymbol[] GetMethods(BindingFlags bindingFlags) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingFlags) { - return ResolveMethodSymbols(UnderlyingModule.GetMethods(bindingFlags))!; + return ResolveMethodSymbols(UnderlyingModule.GetMethods((BindingFlags)bindingFlags))!; } /// @@ -355,16 +537,17 @@ public CustomAttribute[] GetCustomAttributes(bool inherit = false) } /// - public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { var _attributeType = attributeType.Unpack(); return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); } /// - public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); } /// @@ -373,122 +556,8 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) return UnderlyingModule.IsDefined(attributeType.Unpack(), false); } - /// - public void AddReference(IAssemblySymbol assembly) - { -#if NETFRAMEWORK - var t = ((IReflectionAssemblySymbol)assembly).GetExportedTypes(); - if (t.Length > 0) - UnderlyingModuleBuilder.GetTypeToken(t[0].Unpack()); -#else - throw new NotSupportedException(); -#endif - } - - /// - public void AddTypeForwarder(ITypeSymbol type) - { - throw new NotImplementedException(); - } - - /// - public void Complete() - { - UnderlyingModuleBuilder.CreateGlobalFunctions(); - } - - /// - public void Save(PortableExecutableKinds pekind, ImageFileMachine imageFileMachine) - { - throw new NotSupportedException(); - } - #endregion - /// - public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - return _metadata.GetOrCreateTypeSymbol(type); - } - - /// - public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - return _metadata.GetOrCreateTypeSymbol(type); - } - - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return _metadata.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return _metadata.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return _metadata.GetOrCreateMethodSymbol(method); - } - - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return _metadata.GetOrCreateMethodSymbol(method); - } - - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - return _metadata.GetOrCreateFieldSymbol(field); - } - - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - return _metadata.GetOrCreateFieldSymbol(field); - } - - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return _metadata.GetOrCreatePropertySymbol(property); - } - - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return _metadata.GetOrCreatePropertySymbol(property); - } - - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return _metadata.GetOrCreateEventSymbol(@event); - } - - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return _metadata.GetOrCreateEventSymbol(@event); - } - - /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - return _metadata.GetOrCreateParameterSymbol(parameter); - } - - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return _metadata.GetOrCreateParameterSymbol(parameter); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs index 816de787d3..a3dc816268 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs @@ -1,6 +1,7 @@ using System; using System.Reflection; using System.Reflection.Emit; + using IKVM.CoreLib.Reflection; namespace IKVM.CoreLib.Symbols.Reflection.Emit @@ -37,7 +38,7 @@ public ReflectionParameterBuilderInfo(ParameterBuilder builder, Func ge public override string? Name => _builder.Name; /// - public override int Position => _builder.Position; + public override int Position => _builder.Position - 1; /// public override int MetadataToken => _builder.GetMetadataToken(); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs index 879a74a62a..d5bd36f67e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs @@ -11,8 +11,8 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder, IReflectionParameterSymbolBuilder { - readonly IReflectionModuleSymbol _resolvingModule; - readonly IReflectionMethodBaseSymbol _resolvingMethod; + readonly IReflectionModuleSymbol _module; + readonly IReflectionMemberSymbol _member; ParameterBuilder? _builder; ParameterInfo _parameter; @@ -23,23 +23,23 @@ class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder, IReflectionPar /// Initializes a new instance. /// /// - /// - /// + /// + /// /// - public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMethodBaseSymbol resolvingMethod, ParameterBuilder builder) : + public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionMemberSymbol member, ParameterBuilder builder) : base(context) { - _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _member = member ?? throw new ArgumentNullException(nameof(member)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _parameter = new ReflectionParameterBuilderInfo(_builder, () => _constant); + _parameter = new ReflectionParameterBuilderInfo(builder, () => _constant); } /// - public IReflectionModuleSymbol ResolvingModule => _resolvingMethod.ResolvingModule; + public IReflectionModuleSymbol ResolvingModule => _module; /// - public IReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; + public IReflectionMemberSymbol ResolvingMember => _member; /// public ParameterInfo UnderlyingParameter => _parameter; @@ -72,10 +72,10 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) #region IParameterSymbol /// - public ParameterAttributes Attributes => UnderlyingParameter.Attributes; + public System.Reflection.ParameterAttributes Attributes => (System.Reflection.ParameterAttributes)UnderlyingParameter.Attributes; /// - public object? DefaultValue => UnderlyingParameter.DefaultValue; + public object? DefaultValue => UnderlyingParameter.RawDefaultValue; /// public bool HasDefaultValue => UnderlyingParameter.HasDefaultValue; @@ -128,7 +128,8 @@ public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveCustomAttribute(UnderlyingParameter.GetCustomAttributesData().Where(i => attributeType.IsAssignableFrom(attributeType)).FirstOrDefault()); + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingParameter.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); } /// @@ -154,8 +155,12 @@ public ITypeSymbol[] GetRequiredCustomModifiers() /// public void OnComplete() { - var p = ResolvingMethod.UnderlyingMethodBase.GetParameters(); - _parameter = p[Position]; + if (ResolvingMember is IReflectionMethodBaseSymbolBuilder b) + _parameter = b.UnderlyingMethodBase.GetParameters()[Position]; + + if (ResolvingMember is IReflectionPropertySymbolBuilder p) + _parameter = p.UnderlyingPropertyBuilder.GetIndexParameters()[Position]; + _builder = null; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs index de0c8ac1c4..99859af76d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs @@ -13,6 +13,8 @@ class ReflectionPropertySymbolBuilder : ReflectionMemberSymbolBuilder, IReflecti PropertyBuilder? _builder; PropertyInfo _property; + ReflectionParameterTable _parameterTable; + /// /// Initializes a new instance. /// @@ -21,11 +23,12 @@ class ReflectionPropertySymbolBuilder : ReflectionMemberSymbolBuilder, IReflecti /// /// /// - public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, PropertyBuilder builder) : + public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder resolvingType, PropertyBuilder builder) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _property = _builder; + _parameterTable = new ReflectionParameterTable(context, resolvingModule, this); } /// @@ -37,7 +40,27 @@ public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, IReflect /// public override MemberInfo UnderlyingMember => UnderlyingProperty; - #region IPropertySymbol + #region IReflectionPropertySymbolBuilder + + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + + #region IReflectionPropertySymbol + + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + + #region IPropertySymbolBuilder /// public void SetConstant(object? defaultValue) @@ -80,7 +103,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) #region IPropertySymbol /// - public PropertyAttributes Attributes => UnderlyingProperty.Attributes; + public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)UnderlyingProperty.Attributes; /// public bool CanRead => UnderlyingProperty.CanRead; @@ -169,7 +192,7 @@ public ITypeSymbol[] GetRequiredCustomModifiers() return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); } -#endregion + #endregion /// public override void OnComplete() diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs index aff7f03006..9023177499 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs @@ -1,4 +1,7 @@ -using IKVM.CoreLib.Symbols.Emit; +using System.Diagnostics.CodeAnalysis; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -19,6 +22,13 @@ protected ReflectionSymbolBuilder(ReflectionSymbolContext context) : } + /// + [return: NotNullIfNotNull("genericTypeParameter")] + public IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return Context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 8c64b611ed..92a173aad3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -3,6 +3,7 @@ using System.Reflection.Emit; using System.Runtime.InteropServices; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit @@ -13,20 +14,31 @@ class ReflectionTypeSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionTy TypeBuilder? _builder; Type _type; - ReflectionTypeImpl _impl; + + ReflectionMethodTable _methodTable; + ReflectionFieldTable _fieldTable; + ReflectionPropertyTable _propertyTable; + ReflectionEventTable _eventTable; + ReflectionGenericTypeParameterTable _genericTypeParameterTable; + ReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. /// /// - /// + /// /// - public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, TypeBuilder builder) : - base(context, resolvingModule, null) + public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder module, TypeBuilder builder) : + base(context, module, null) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _type = _builder; - _impl = new ReflectionTypeImpl(this); + _methodTable = new ReflectionMethodTable(context, module, this); + _fieldTable = new ReflectionFieldTable(context, module, this); + _propertyTable = new ReflectionPropertyTable(context, module, this); + _eventTable = new ReflectionEventTable(context, module, this); + _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, module, this); + _specTable = new ReflectionTypeSpecTable(context, module, this); } /// @@ -38,6 +50,122 @@ public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionM /// public TypeBuilder UnderlyingTypeBuilder => _builder ?? throw new InvalidOperationException(); + #region ReflectionTypeSymbol + + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + return _methodTable.GetOrCreateMethodBaseSymbol(method); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + /// + public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion + + #region IReflectionTypeSymbolBuilder + + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return _methodTable.GetOrCreateMethodSymbol(method); + } + + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + + #endregion + #region ITypeSymbolBuilder /// @@ -52,7 +180,7 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin var l = UnderlyingTypeBuilder.DefineGenericParameters(names); var a = new IGenericTypeParameterSymbolBuilder[l.Length]; for (int i = 0; i < l.Length; i++) - a[i] = new ReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModule, this, null, l[i]); + a[i] = ResolveGenericTypeParameterSymbol(l[i]); return a; } @@ -64,75 +192,75 @@ public void AddInterfaceImplementation(ITypeSymbol interfaceType) } /// - public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, ITypeSymbol[]? parameterTypes) + public IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, ITypeSymbol[]? parameterTypes) { - return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor(attributes, CallingConventions.Standard, parameterTypes?.Unpack())); + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor((MethodAttributes)attributes, CallingConventions.Standard, parameterTypes?.Unpack())); } /// - public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes) + public IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol[]? parameterTypes) { - return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack())); + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor((MethodAttributes)attributes, (CallingConventions)callingConvention, parameterTypes?.Unpack())); } /// - public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredCustomModifiers, ITypeSymbol[][]? optionalCustomModifiers) + public IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredCustomModifiers, ITypeSymbol[][]? optionalCustomModifiers) { - return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor(attributes, callingConvention, parameterTypes?.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack())); + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineConstructor((MethodAttributes)attributes, (CallingConventions)callingConvention, parameterTypes?.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack())); } /// - public IConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes) + public IConstructorSymbolBuilder DefineDefaultConstructor(System.Reflection.MethodAttributes attributes) { - return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineDefaultConstructor(attributes)); + return ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineDefaultConstructor((MethodAttributes)attributes)); } /// - public IEventSymbolBuilder DefineEvent(string name, EventAttributes attributes, ITypeSymbol eventtype) + public IEventSymbolBuilder DefineEvent(string name, System.Reflection.EventAttributes attributes, ITypeSymbol eventtype) { - return (IEventSymbolBuilder)ResolveEventSymbol(UnderlyingTypeBuilder.DefineEvent(name, attributes, eventtype.Unpack())); + return ResolveEventSymbol(UnderlyingTypeBuilder.DefineEvent(name, (EventAttributes)attributes, eventtype.Unpack())); } /// - public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, FieldAttributes attributes) + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, System.Reflection.FieldAttributes attributes) { - return (IFieldSymbolBuilder)ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), attributes)); + return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), (FieldAttributes)attributes)); } /// - public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, FieldAttributes attributes) + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, System.Reflection.FieldAttributes attributes) { - return (IFieldSymbolBuilder)ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), attributes)); + return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), (FieldAttributes)attributes)); } /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); } /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); } /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention) + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, callingConvention)); + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention)); } /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes) + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes)); + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes)); } /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) + public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); } /// @@ -142,21 +270,21 @@ public void DefineMethodOverride(IMethodSymbol methodInfoBody, IMethodSymbol met } /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), interfaces?.Unpack())); + return ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), interfaces?.Unpack())); } /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize) + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize, int typeSize) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), packSize, typeSize)); + return ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packSize, typeSize)); } /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize) + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), packSize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), (PackingSize)packSize)); } /// @@ -166,63 +294,63 @@ public ITypeSymbolBuilder DefineNestedType(string name) } /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent) + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack())); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack())); } /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr) + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr)); } /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize) + public ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typeSize) { - return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, attr, parent?.Unpack(), typeSize)); + return (ITypeSymbolBuilder)ResolveTypeSymbol(UnderlyingTypeBuilder.DefineNestedType(name, (TypeAttributes)attr, parent?.Unpack(), typeSize)); } /// - public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); } /// - public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack(), nativeCallConv, nativeCharSet)); } /// - public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) { - return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, attributes, callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack(), nativeCallConv, nativeCharSet)); + return (IMethodSymbolBuilder)ResolveMethodSymbol(UnderlyingTypeBuilder.DefinePInvokeMethod(name, dllName, entryName, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack(), nativeCallConv, nativeCharSet)); } /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) { - return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, returnType.Unpack(), parameterTypes?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, returnType.Unpack(), parameterTypes?.Unpack())); } /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes) { - return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), parameterTypes?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), parameterTypes?.Unpack())); } /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); } /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + public IPropertySymbolBuilder DefineProperty(string name, System.Reflection.PropertyAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, attributes, callingConvention, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + return (IPropertySymbolBuilder)ResolvePropertySymbol(UnderlyingTypeBuilder.DefineProperty(name, (PropertyAttributes)attributes, (CallingConventions)callingConvention, returnType.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); } /// @@ -247,506 +375,525 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) #region ITypeSymbol /// - public TypeAttributes Attributes => _impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public IAssemblySymbol Assembly => _impl.Assembly; + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? FullName => _impl.FullName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? Namespace => _impl.Namespace; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public TypeCode TypeCode => _impl.TypeCode; + public string? FullName => UnderlyingType.FullName; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public string? Namespace => UnderlyingType.Namespace; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public bool HasElementType => UnderlyingType.HasElementType; /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsSZArray => UnderlyingType.IsSZArray(); /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool HasElementType => _impl.HasElementType; + public bool IsClass => UnderlyingType.IsClass; /// - public bool IsClass => _impl.IsClass; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsValueType => _impl.IsValueType; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsInterface => _impl.IsInterface; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsArray => _impl.IsArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsEnum => _impl.IsEnum; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsNotPublic => UnderlyingType.IsNotPublic; + + /// + public bool IsPointer => UnderlyingType.IsPointer; + +#if NET8_0_OR_GREATER /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNested => _impl.IsNested; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; + +#else /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsFunctionPointer => throw new NotImplementedException(); /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSignatureType => throw new NotImplementedException(); /// - public IConstructorSymbol? TypeInitializer => _impl.TypeInitializer; + public bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public override bool IsComplete => _builder == null; + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// public int GetArrayRank() { - return _impl.GetArrayRank(); + return UnderlyingType.GetArrayRank(); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetElementType(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors() { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string[] GetEnumNames() + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumNames(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public ITypeSymbol GetEnumUnderlyingType() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumUnderlyingType(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol[] GetGenericArguments() + public ITypeSymbol? GetElementType() { - return _impl.GetGenericArguments(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string? GetEnumName(object value) { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol GetGenericTypeDefinition() + public string[] GetEnumNames() { - return _impl.GetGenericTypeDefinition(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol? GetInterface(string name) + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetInterface(name); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public Array GetEnumValues() { - return _impl.GetInterface(name, ignoreCase); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents() { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, bindingAttr); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetConstructor(types); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructors(); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name, bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol[] GetFields() + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return _impl.GetFields(); + throw new NotImplementedException(); } /// - public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(bindingAttr); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, types); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name, bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties() { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public bool IsAssignableFrom(ITypeSymbol? c) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.IsAssignableFrom(c); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// public bool IsEnumDefined(object value) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsEnumDefined(value); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(_type.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(_type.MakeArrayType(rank)); } /// public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(_type.MakeGenericType(typeArguments.Unpack())); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(_type.MakePointerType()); } /// public ITypeSymbol MakeByRefType() { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(_type.MakeByRefType()); } #endregion @@ -758,7 +905,10 @@ public void Complete() { // complete type if (_builder.IsCreated() == false) - _builder.CreateType(); + { + _type = _builder.CreateType()!; + _builder = null; + } // force module to reresolve Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); @@ -771,9 +921,6 @@ public override void OnComplete() { const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static; - _type = ResolvingModule.UnderlyingModule.ResolveType(MetadataToken); - _builder = null; - foreach (var i in GetGenericArguments()) if (i is IReflectionGenericTypeParameterSymbolBuilder b) b.OnComplete(); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs index c16db0d745..b858654043 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs @@ -1,7 +1,4 @@ using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -21,13 +18,6 @@ interface IReflectionAssemblySymbol : IReflectionSymbol, IAssemblySymbol /// IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs index 33eca5d428..09a99ae06c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs @@ -1,9 +1,15 @@ -namespace IKVM.CoreLib.Symbols.Reflection +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection { interface IReflectionEventSymbol : IReflectionMemberSymbol, IEventSymbol { + /// + /// Gets the underlying . + /// + EventInfo UnderlyingEvent { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs index 13ccd1ef96..9e0105610a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs @@ -11,6 +11,13 @@ interface IReflectionMethodBaseSymbol : IReflectionMemberSymbol, IMethodBaseSymb /// MethodBase UnderlyingMethodBase { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs index a806c91951..6d17a00c4d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs @@ -1,4 +1,5 @@ -using System.Reflection; +using System; +using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { @@ -11,6 +12,20 @@ interface IReflectionMethodSymbol : IReflectionMethodBaseSymbol, IMethodSymbol /// MethodInfo UnderlyingMethod { get; } + /// + /// Gets or creates a for the given generic type parameter. + /// + /// + /// + IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); + + /// + /// Gets or creates a for the given generic version of this method definition. + /// + /// + /// + IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs index c4b9361297..d91499c770 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs @@ -1,8 +1,5 @@ using System; using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -28,11 +25,11 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type); /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); + IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method); /// /// Gets or creates a for the specified . @@ -41,13 +38,6 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); - /// /// Gets or creates a for the specified . /// @@ -55,13 +45,6 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); - /// /// Gets or creates a for the specified . /// @@ -69,13 +52,6 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); - /// /// Gets or creates a for the specified . /// @@ -83,13 +59,6 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); - /// /// Gets or creates a for the specified . /// @@ -97,13 +66,6 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); - /// /// Gets or creates a for the specified . /// @@ -111,13 +73,6 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs index 20e1cb494c..60632e80cc 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs @@ -12,9 +12,9 @@ interface IReflectionParameterSymbol : IReflectionSymbol, IParameterSymbol IReflectionModuleSymbol ResolvingModule { get; } /// - /// Gets the method that resolved the parameter. + /// Gets the member that resolved the parameter. /// - IReflectionMethodBaseSymbol ResolvingMethod { get; } + IReflectionMemberSymbol ResolvingMember { get; } /// /// Gets the underlying . diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs index 9309bf3ea5..2b7aa24012 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs @@ -11,6 +11,13 @@ interface IReflectionPropertySymbol : IReflectionMemberSymbol, IPropertySymbol /// PropertyInfo UnderlyingProperty { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs index 1ee1657d8b..c2a970c280 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs @@ -3,9 +3,6 @@ using System.Collections.Immutable; using System.Diagnostics.CodeAnalysis; using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -26,14 +23,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(assembly))] IReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly); - /// - /// Resolves the symbol for the specified assembly builder. - /// - /// - /// - [return: NotNullIfNotNull(nameof(assembly))] - IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); - /// /// Resolves the symbols for the specified assemblies. /// @@ -50,14 +39,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(module))] IReflectionModuleSymbol? ResolveModuleSymbol(Module? module); - /// - /// Resolves the symbol for the specified module. - /// - /// - /// - [return: NotNullIfNotNull(nameof(module))] - IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); - /// /// Resolves the symbols for the specified modules. /// @@ -97,14 +78,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(type))] IReflectionTypeSymbol? ResolveTypeSymbol(Type? type); - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - [return: NotNullIfNotNull(nameof(type))] - IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); - /// /// Resolves the symbols for the specified types. /// @@ -136,14 +109,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(ctor))] IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor); - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - [return: NotNullIfNotNull(nameof(ctor))] - IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); - /// /// Resolves the symbols for the specified constructors. /// @@ -160,14 +125,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(method))] IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method); - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - [return: NotNullIfNotNull(nameof(method))] - IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); - /// /// Resolves the symbols for the specified methods. /// @@ -184,14 +141,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(field))] IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field); - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - [return: NotNullIfNotNull(nameof(field))] - IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); - /// /// Resolves the symbols for the specified fields. /// @@ -208,14 +157,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(property))] IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property); - /// - /// Resolves the symbol for the specified property. - /// - /// - /// - [return: NotNullIfNotNull(nameof(property))] - IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); - /// /// Resolves the symbols for the specified properties. /// @@ -232,14 +173,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(@event))] IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event); - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - [return: NotNullIfNotNull(nameof(@event))] - IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); - /// /// Resolves the symbols for the specified events. /// @@ -256,14 +189,6 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(parameter))] IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter); - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - [return: NotNullIfNotNull(nameof(parameter))] - IReflectionParameterSymbolBuilder? ResolveParameterSymbol(ParameterBuilder parameter); - /// /// Resolves the symbols for the specified parameters. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs index fa7dc4bbaf..464cc4a3d5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs @@ -1,4 +1,5 @@ using System; +using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { @@ -11,6 +12,87 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// Type UnderlyingType { get; } + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); + + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); + + /// + /// Gets or creates a for the given generic type parameter type. + /// + /// + /// + IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); + + /// + /// Gets or creates a for the given element type. + /// + /// + IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol(); + + /// + /// Gets or creates a for the given element type. + /// + /// + /// + IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank); + + /// + /// Gets or creates a for the given element type. + /// + /// + IReflectionTypeSymbol GetOrCreatePointerTypeSymbol(); + + /// + /// Gets or creates a for the given element type. + /// + /// + IReflectionTypeSymbol GetOrCreateByRefTypeSymbol(); + + /// + /// Gets or creates a for the given element type. + /// + /// + /// + IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index df2d48527c..c922a5b4d3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -1,12 +1,8 @@ using System; using System.Collections.Generic; -using System.Collections.Immutable; using System.IO; using System.Linq; using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -15,7 +11,8 @@ class ReflectionAssemblySymbol : ReflectionSymbol, IReflectionAssemblySymbol { readonly Assembly _assembly; - ReflectionAssemblyMetadata _impl; + + ReflectionModuleTable _moduleTable; /// /// Initializes a new instance. @@ -26,7 +23,7 @@ public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly assemb base(context) { _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); - _impl = new ReflectionAssemblyMetadata(this); + _moduleTable = new ReflectionModuleTable(context, this); } /// @@ -37,123 +34,127 @@ public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly assemb #region IAssemblySymbol /// - public IEnumerable DefinedTypes => ResolveTypeSymbols(_assembly.DefinedTypes); + public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + { + return _moduleTable.GetOrCreateModuleSymbol(module); + } + + #endregion + + #region IAssemblySymbol + + /// + public IEnumerable DefinedTypes => ResolveTypeSymbols(UnderlyingAssembly.DefinedTypes); /// - public IMethodSymbol? EntryPoint => ResolveMethodSymbol(_assembly.EntryPoint); + public IMethodSymbol? EntryPoint => ResolveMethodSymbol(UnderlyingAssembly.EntryPoint); /// - public IEnumerable ExportedTypes => ResolveTypeSymbols(_assembly.ExportedTypes); + public IEnumerable ExportedTypes => ResolveTypeSymbols(UnderlyingAssembly.ExportedTypes); /// - public string? FullName => _assembly.FullName; + public string? FullName => UnderlyingAssembly.FullName; /// - public string ImageRuntimeVersion => _assembly.ImageRuntimeVersion; + public string ImageRuntimeVersion => UnderlyingAssembly.ImageRuntimeVersion; /// - public string Location => _assembly.Location; + public string Location => UnderlyingAssembly.Location; /// - public IModuleSymbol ManifestModule => ResolveModuleSymbol(_assembly.ManifestModule); + public IModuleSymbol ManifestModule => ResolveModuleSymbol(UnderlyingAssembly.ManifestModule); /// - public IEnumerable Modules => ResolveModuleSymbols(_assembly.Modules); + public IEnumerable Modules => ResolveModuleSymbols(UnderlyingAssembly.Modules); /// public ITypeSymbol[] GetExportedTypes() { - return ResolveTypeSymbols(_assembly.GetExportedTypes()); + return ResolveTypeSymbols(UnderlyingAssembly.GetExportedTypes()); } /// public IModuleSymbol? GetModule(string name) { - return ResolveModuleSymbol(_assembly.GetModule(name)); + return ResolveModuleSymbol(UnderlyingAssembly.GetModule(name)); } /// public IModuleSymbol[] GetModules() { - return ResolveModuleSymbols(_assembly.GetModules()); + return ResolveModuleSymbols(UnderlyingAssembly.GetModules()); } /// public IModuleSymbol[] GetModules(bool getResourceModules) { - return ResolveModuleSymbols(_assembly.GetModules(getResourceModules)); + return ResolveModuleSymbols(UnderlyingAssembly.GetModules(getResourceModules)); } /// public AssemblyNameInfo GetName() { - return ToAssemblyNameInfo(_assembly.GetName()); + return UnderlyingAssembly.GetName().Pack(); } /// public AssemblyNameInfo[] GetReferencedAssemblies() { - return _assembly.GetReferencedAssemblies().Select(i => ToAssemblyNameInfo(i)).ToArray(); - } - - /// - /// Transforms the to a . - /// - /// - /// - /// - AssemblyNameInfo ToAssemblyNameInfo(AssemblyName n) - { - return new AssemblyNameInfo(n.Name ?? throw new InvalidOperationException(), n.Version, n.CultureName, n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? []); + return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } /// public ITypeSymbol? GetType(string name, bool throwOnError) { - return ResolveTypeSymbol(_assembly.GetType(name, throwOnError)); + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError)); } /// public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) { - return ResolveTypeSymbol(_assembly.GetType(name, throwOnError, ignoreCase)); + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError, ignoreCase)); } /// public ITypeSymbol? GetType(string name) { - return ResolveTypeSymbol(_assembly.GetType(name)); + return ResolveTypeSymbol(UnderlyingAssembly.GetType(name)); } /// public ITypeSymbol[] GetTypes() { - return ResolveTypeSymbols(_assembly.GetTypes()); + return ResolveTypeSymbols(UnderlyingAssembly.GetTypes()); } /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return ResolveCustomAttributes(_assembly.GetCustomAttributesData()); + return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData()); } /// public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { var _attributeType = attributeType.Unpack(); - return ResolveCustomAttributes(_assembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); + return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); } /// public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + var _attributeType = attributeType.Unpack(); + var a = UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToList(); + if (a.Count > 0) + return ResolveCustomAttribute(a[0]); + + return null; } /// public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) { - return _assembly.IsDefined(attributeType.Unpack(), inherit); + return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); } /// @@ -176,16 +177,6 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion - public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - return _impl.GetOrCreateModuleSymbol(module); - } - - public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) - { - return (IReflectionModuleSymbolBuilder)_impl.GetOrCreateModuleSymbol(module); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs index 6b30a2fc89..0d7c95667a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs @@ -17,7 +17,7 @@ class ReflectionConstructorSymbol : ReflectionMethodBaseSymbol, IReflectionConst /// /// public ReflectionConstructorSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, ConstructorInfo ctor) : - base(context, resolvingModule, resolvingType, ctor) + base(context, resolvingModule, resolvingType) { _ctor = ctor ?? throw new ArgumentNullException(nameof(ctor)); } @@ -25,6 +25,9 @@ public ReflectionConstructorSymbol(ReflectionSymbolContext context, IReflectionM /// public ConstructorInfo UnderlyingConstructor => _ctor; + /// + public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs index dc1b0c8ee3..1b8abba999 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs @@ -17,20 +17,21 @@ class ReflectionEventSymbol : ReflectionMemberSymbol, IReflectionEventSymbol /// /// public ReflectionEventSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, EventInfo @event) : - base(context, resolvingModule, resolvingType, @event) + base(context, resolvingModule, resolvingType) { _event = @event ?? throw new ArgumentNullException(nameof(@event)); } - /// - /// Gets the underlying wrapped by this symbol. - /// + /// public EventInfo UnderlyingEvent => _event; + /// + public override MemberInfo UnderlyingMember => UnderlyingEvent; + #region IEventSymbol /// - public EventAttributes Attributes => UnderlyingEvent.Attributes; + public System.Reflection.EventAttributes Attributes => (System.Reflection.EventAttributes)UnderlyingEvent.Attributes; /// public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs new file mode 100644 index 0000000000..dcd4f11ebe --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs @@ -0,0 +1,95 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionEventTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionEventTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type ?? throw new ArgumentNullException(nameof(type)); + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = @event.GetMetadataTokenRowNumberSafe(); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + return _table[row] ??= new ReflectionEventSymbol(_context, _module, _type, @event); + + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by event. + /// + /// + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + if (@event is null) + throw new ArgumentNullException(nameof(@event)); + if (@event.GetModuleBuilder() != _module.UnderlyingModule) + throw new ArgumentException(nameof(@event)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = @event.GetMetadataTokenRowNumberSafe(); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + return (IReflectionEventSymbolBuilder)(_table[row] ??= new ReflectionEventSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder)_type, @event)); + + return (IReflectionEventSymbolBuilder?)_table[row] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index 8e476d98e2..c82d80e202 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -17,7 +17,7 @@ class ReflectionFieldSymbol : ReflectionMemberSymbol, IReflectionFieldSymbol /// /// public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, FieldInfo field) : - base(context, resolvingModule, resolvingType, field) + base(context, resolvingModule, resolvingType) { _field = field ?? throw new ArgumentNullException(nameof(field)); } @@ -25,10 +25,13 @@ public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleS /// public FieldInfo UnderlyingField => _field; + /// + public override MemberInfo UnderlyingMember => UnderlyingField; + #region IFieldSymbol /// - public FieldAttributes Attributes => UnderlyingField.Attributes; + public System.Reflection.FieldAttributes Attributes => (System.Reflection.FieldAttributes)UnderlyingField.Attributes; /// public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); @@ -54,10 +57,8 @@ public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleS /// public bool IsLiteral => UnderlyingField.IsLiteral; -#pragma warning disable SYSLIB0050 // Type or member is obsolete /// public bool IsNotSerialized => UnderlyingField.IsNotSerialized; -#pragma warning restore SYSLIB0050 // Type or member is obsolete /// public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs new file mode 100644 index 0000000000..c2e1b3afda --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs @@ -0,0 +1,81 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionFieldTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol? _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionFieldTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + if (field is null) + throw new ArgumentNullException(nameof(field)); + if (field.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(field)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = field.GetMetadataTokenRowNumberSafe(); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + if (field is FieldBuilder builder) + return _table[row] ??= new ReflectionFieldSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder?)_type, builder); + else + return _table[row] ??= new ReflectionFieldSymbol(_context, _module, _type, field); + + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by field. + /// + /// + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return (IReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs index a851d2cf9a..3fdc602d87 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs @@ -2,38 +2,49 @@ using System.Diagnostics.CodeAnalysis; using System.Reflection; +using IKVM.CoreLib.Reflection; + namespace IKVM.CoreLib.Symbols.Reflection { class ReflectionGenericTypeParameterSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol { - readonly IReflectionMethodSymbol? _resolvingMethod; + readonly IReflectionMemberSymbol _resolvingMember; readonly Type _type; - ReflectionTypeImpl _impl; + + ReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. /// /// /// - /// - /// + /// /// /// - public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, IReflectionMethodSymbol? resolvingMethod, Type type) : - base(context, resolvingModule, resolvingType, type) + public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMemberSymbol resolvingMember, Type type) : + base(context, resolvingModule, resolvingMember as IReflectionTypeSymbol) { - _resolvingMethod = resolvingMethod; + _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _type = type ?? throw new ArgumentNullException(nameof(type)); - _impl = new ReflectionTypeImpl(this); + _specTable = new ReflectionTypeSpecTable(); } + /// + public Type UnderlyingType => _type; + + /// + public override MemberInfo UnderlyingMember => UnderlyingType; + /// - /// Resolves the symbol for the specified type. + /// Gets the method base that declares this type parameter. /// - /// - /// + public IReflectionMemberSymbol? ResolvingMemberSymbol => _resolvingMember; + + #region IReflectionSymbol + + /// [return: NotNullIfNotNull(nameof(type))] public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) { @@ -43,519 +54,609 @@ public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IRe return base.ResolveTypeSymbol(type); } - /// - /// Gets the underlying . - /// - public Type UnderlyingType => _type; + #endregion - /// - /// Gets the method base that declares this type parameter. - /// - public IReflectionMethodBaseSymbol? ResolvingMethodBase => _resolvingMethod; + #region IReflectionTypeSymbol + + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + throw new NotSupportedException(); + } + + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + throw new NotSupportedException(); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + throw new NotSupportedException(); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + throw new NotSupportedException(); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + throw new NotSupportedException(); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + throw new NotSupportedException(); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type type) + { + throw new NotSupportedException(); + } + + /// + public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion #region ITypeSymbol /// - public TypeAttributes Attributes => _impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public IAssemblySymbol Assembly => _impl.Assembly; + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? FullName => _impl.FullName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? Namespace => _impl.Namespace; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public TypeCode TypeCode => _impl.TypeCode; + public string? FullName => UnderlyingType.FullName; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public string? Namespace => UnderlyingType.Namespace; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public bool HasElementType => UnderlyingType.HasElementType; /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsSZArray => UnderlyingType.IsSZArray(); /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool HasElementType => _impl.HasElementType; + public bool IsClass => UnderlyingType.IsClass; /// - public bool IsClass => _impl.IsClass; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsValueType => _impl.IsValueType; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsInterface => _impl.IsInterface; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsArray => _impl.IsArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsEnum => _impl.IsEnum; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsPointer => UnderlyingType.IsPointer; + +#if NET8_0_OR_GREATER /// - public bool IsNested => _impl.IsNested; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; + +#else + + /// + public bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsSignatureType => throw new NotImplementedException(); /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// public int GetArrayRank() { - return _impl.GetArrayRank(); + return UnderlyingType.GetArrayRank(); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetElementType(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors() { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string[] GetEnumNames() + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumNames(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public ITypeSymbol GetEnumUnderlyingType() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumUnderlyingType(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol[] GetGenericArguments() + public ITypeSymbol? GetElementType() { - return _impl.GetGenericArguments(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string? GetEnumName(object value) { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol GetGenericTypeDefinition() + public string[] GetEnumNames() { - return _impl.GetGenericTypeDefinition(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol? GetInterface(string name) + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetInterface(name); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public Array GetEnumValues() { - return _impl.GetInterface(name, ignoreCase); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents() { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, bindingAttr); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetConstructor(types); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructors(); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name, bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol[] GetFields() + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { - return _impl.GetFields(); + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); } /// - public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(bindingAttr); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, types); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name, bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties() { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public bool IsAssignableFrom(ITypeSymbol? c) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.IsAssignableFrom(c); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// public bool IsEnumDefined(object value) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsEnumDefined(value); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); } /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + public ITypeSymbol MakeByRefType() { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); } /// - public ITypeSymbol MakeByRefType() + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } - #endregion +#endregion } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs new file mode 100644 index 0000000000..6045831608 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs @@ -0,0 +1,78 @@ +using System; +using System.Reflection.Emit; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionGenericTypeParameterTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionMemberSymbol _member; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionGenericTypeParameterTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionMemberSymbol member) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _member = member; + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + if (genericTypeParameter is null) + throw new ArgumentNullException(nameof(genericTypeParameter)); + if (genericTypeParameter.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(genericTypeParameter)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var pos = genericTypeParameter.GenericParameterPosition; + if (_table[pos] == null) + using (_lock.CreateWriteLock()) + if (genericTypeParameter is GenericTypeParameterBuilder builder) + return _table[pos] ??= new ReflectionGenericTypeParameterSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionMemberSymbolBuilder)_member, builder); + else + return _table[pos] ??= new ReflectionGenericTypeParameterSymbol(_context, _module, _member, genericTypeParameter); + + return _table[pos] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the module. + /// + /// + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return (IReflectionGenericTypeParameterSymbolBuilder)GetOrCreateGenericTypeParameterSymbol((Type)genericTypeParameter); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 496e7b58e0..3baf997db5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -1,12 +1,7 @@ using System; -using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Linq; using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -17,40 +12,8 @@ namespace IKVM.CoreLib.Symbols.Reflection abstract class ReflectionMemberSymbol : ReflectionSymbol, IReflectionMemberSymbol { - /// - /// Concatinates the list of arrays. - /// - /// - /// - static T[] Concat(List? list) - { - if (list == null) - return []; - - var c = 0; - foreach (var i in list) - c += i.Length; - - if (c == 0) - return []; - - var t = 0; - var a = new T[c]; - foreach (var i in list) - { - Array.Copy(i, 0, a, t, i.Length); - t += i.Length; - } - - return a; - } - - readonly IReflectionModuleSymbol _resolvingModule; - readonly IReflectionTypeSymbol? _resolvingType; - readonly MemberInfo _member; - - CustomAttribute[]? _customAttributes; - CustomAttribute[]? _inheritedCustomAttributes; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol? _type; /// /// Initializes a new instance. @@ -59,117 +22,25 @@ static T[] Concat(List? list) /// /// /// - public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, MemberInfo member) : + public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : base(context) { - _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingType = resolvingType; - _member = member ?? throw new ArgumentNullException(nameof(member)); + _module = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); + _type = resolvingType; } /// - public MemberInfo UnderlyingMember => _member; + public abstract MemberInfo UnderlyingMember { get; } /// /// Gets the which contains the metadata of this member. /// - public IReflectionModuleSymbol ResolvingModule => _resolvingModule; + public IReflectionModuleSymbol ResolvingModule => _module; /// /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. /// - public IReflectionTypeSymbol? ResolvingType => _resolvingType; - - #region IMemberSymbol - - /// - public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; - - /// - public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; - - /// - public virtual MemberTypes MemberType => UnderlyingMember.MemberType; - - /// - public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); - - /// - public virtual string Name => UnderlyingMember.Name; - - /// - public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - if (inherit) - { - // check that we've already processed this - if (_inheritedCustomAttributes != null) - return _inheritedCustomAttributes; - - var self = _member; - var list = default(List?); - for (; ; ) - { - if (self == null) - throw new InvalidOperationException(); - - // get attribute for current member and append to list - var attr = ResolveMemberSymbol(self)!.GetCustomAttributes(false); - if (attr.Length > 0) - { - list ??= []; - list.Add(attr); - } - - var type = self as Type; - if (type != null) - { - type = type.BaseType; - if (type == null) - return _inheritedCustomAttributes ??= Concat(list); - - self = type; - continue; - } - - var method = self as MethodInfo; - if (method != null) - { - var prev = self; - method = method.GetBaseDefinition(); - if (method == null || method == prev) - return _inheritedCustomAttributes ??= Concat(list); - - self = method; - continue; - } - - return _inheritedCustomAttributes ??= Concat(list); - } - } - - return _customAttributes ??= ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData())!; - } - - /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); - } - - /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); - } - - /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); - } - - #endregion + public IReflectionTypeSymbol? ResolvingType => _type; /// [return: NotNullIfNotNull(nameof(type))] @@ -178,14 +49,14 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) if (type is null) return null; - if (_member == type) + if (type == UnderlyingMember) return (IReflectionTypeSymbol)this; - if (_resolvingType != null && type == _resolvingType.UnderlyingType) - return _resolvingType; + if (_type != null && type == _type.UnderlyingType) + return _type; - if (type.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateTypeSymbol(type); + if (type.Module == _module.UnderlyingModule) + return _module.GetOrCreateTypeSymbol(type); return base.ResolveTypeSymbol(type); } @@ -197,24 +68,11 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) if (ctor is null) return null; - if (_member == ctor) + if (ctor == UnderlyingMember) return (IReflectionConstructorSymbol)this; - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); - - return base.ResolveConstructorSymbol(ctor); - } - - /// - [return: NotNullIfNotNull(nameof(ctor))] - public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) - { - if (ctor is null) - throw new ArgumentNullException(nameof(ctor)); - - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); + if (ctor.Module == _module.UnderlyingModule) + return _module.GetOrCreateConstructorSymbol(ctor); return base.ResolveConstructorSymbol(ctor); } @@ -226,24 +84,11 @@ public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(Con if (method is null) return null; - if (_member == method) + if (method == UnderlyingMember) return (IReflectionMethodSymbol)this; - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); - - return base.ResolveMethodSymbol(method); - } - - /// - [return: NotNullIfNotNull(nameof(method))] - public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); + if (method.Module == _module.UnderlyingModule) + return _module.GetOrCreateMethodSymbol(method); return base.ResolveMethodSymbol(method); } @@ -255,24 +100,11 @@ public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder if (field is null) return null; - if (_member == field) + if (field == UnderlyingMember) return (IReflectionFieldSymbol)this; - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); - - return base.ResolveFieldSymbol(field); - } - - /// - [return: NotNullIfNotNull(nameof(field))] - public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); + if (field.Module == _module.UnderlyingModule) + return _module.GetOrCreateFieldSymbol(field); return base.ResolveFieldSymbol(field); } @@ -284,24 +116,11 @@ public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder fi if (property is null) return null; - if (_member == property) + if (property == UnderlyingMember) return (IReflectionPropertySymbol)this; - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); - - return base.ResolvePropertySymbol(property); - } - - /// - [return: NotNullIfNotNull(nameof(property))] - public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); + if (property.Module == _module.UnderlyingModule) + return _module.GetOrCreatePropertySymbol(property); return base.ResolvePropertySymbol(property); } @@ -313,54 +132,82 @@ public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyB if (@event is null) return null; - if (_member == @event) + if (@event == UnderlyingMember) return (IReflectionEventSymbol)this; - if (@event.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); + if (@event.Module == _module.UnderlyingModule) + return _module.GetOrCreateEventSymbol(@event); return base.ResolveEventSymbol(@event); } /// - [return: NotNullIfNotNull(nameof(@event))] - public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + [return: NotNullIfNotNull(nameof(parameter))] + public override IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); - if (@event.GetModuleBuilder() == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); + if (parameter.Member.Module == _module.UnderlyingModule) + return _module.GetOrCreateParameterSymbol(parameter); - return base.ResolveEventSymbol(@event); + return base.ResolveParameterSymbol(parameter); } + #region IMemberSymbol + /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) + public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; + + /// + public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; + + /// + public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + + /// + public virtual int MetadataToken => UnderlyingMember.MetadataToken; + + /// + public virtual string Name => UnderlyingMember.Name; + + /// + public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + if (inherit == true) + throw new NotSupportedException(); - if (parameter.Member.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); + return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData()); + } - return base.ResolveParameterSymbol(parameter); + /// + public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + if (inherit == true) + throw new NotSupportedException(); + + var _attribyteType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attribyteType).ToArray()); } /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + if (inherit == true) + throw new NotSupportedException(); - if (parameter.GetModuleBuilder() == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); + } - return base.ResolveParameterSymbol(parameter); + /// + public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); } + #endregion + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs index 76ae425fcf..a4ef99e3f1 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs @@ -1,6 +1,4 @@ -using System; -using System.Diagnostics.CodeAnalysis; -using System.Reflection; +using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { @@ -8,7 +6,7 @@ namespace IKVM.CoreLib.Symbols.Reflection abstract class ReflectionMethodBaseSymbol : ReflectionMemberSymbol, IReflectionMethodBaseSymbol { - readonly MethodBase _method; + ReflectionParameterTable _parameterTable; /// /// Initializes a new instance. @@ -16,25 +14,35 @@ abstract class ReflectionMethodBaseSymbol : ReflectionMemberSymbol, IReflectionM /// /// /// - /// - public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, MethodBase method) : - base(context, resolvingModule, resolvingType, method) + public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : + base(context, resolvingModule, resolvingType) { - _method = method ?? throw new ArgumentNullException(nameof(method)); + _parameterTable = new ReflectionParameterTable(context, resolvingModule, this); } + #region IReflectionMethodBaseSymbol + + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + #region IMethodBaseSymbol - /// - /// Gets the underlying wrapped by this symbol. - /// - public MethodBase UnderlyingMethodBase => _method; + /// + public abstract MethodBase UnderlyingMethodBase { get; } + + /// + public override MemberInfo UnderlyingMember => UnderlyingMethodBase; /// - public MethodAttributes Attributes => UnderlyingMethodBase.Attributes; + public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; /// - public CallingConventions CallingConvention => UnderlyingMethodBase.CallingConvention; + public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; /// public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; @@ -85,7 +93,7 @@ public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, IReflectionMo public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; /// - public MethodImplAttributes MethodImplementationFlags => UnderlyingMethodBase.MethodImplementationFlags; + public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; /// public ITypeSymbol[] GetGenericArguments() @@ -94,9 +102,9 @@ public ITypeSymbol[] GetGenericArguments() } /// - public MethodImplAttributes GetMethodImplementationFlags() + public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() { - return UnderlyingMethodBase.GetMethodImplementationFlags(); + return (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.GetMethodImplementationFlags(); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs new file mode 100644 index 0000000000..a01078ab08 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs @@ -0,0 +1,64 @@ +using System; +using System.Collections.Concurrent; +using System.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionMethodSpecTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol? _type; + readonly IReflectionMethodSymbol _method; + + ConcurrentDictionary? _genericMethodSymbols; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public ReflectionMethodSpecTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type, IReflectionMethodSymbol method) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + _method = method ?? throw new ArgumentNullException(nameof(method)); + } + + /// + /// Gets or creates a representing a specialized generic of this method. + /// + /// + /// + public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(Type[] genericTypeArguments) + { + if (genericTypeArguments is null) + throw new ArgumentNullException(nameof(genericTypeArguments)); + + if (_method.IsGenericMethodDefinition == false) + throw new InvalidOperationException(); + + if (_genericMethodSymbols == null) + Interlocked.CompareExchange(ref _genericMethodSymbols, new(TypeListEqualityComparer.Instance), null); + + return _genericMethodSymbols.GetOrAdd(genericTypeArguments, CreateGenericMethodSymbol); + } + + /// + /// Creates a new representing a specialized generic of this type. + /// + /// + /// + readonly IReflectionMethodSymbol CreateGenericMethodSymbol(Type[] genericTypeArguments) + { + return new ReflectionMethodSymbol(_context, _module, _type, _method.UnderlyingMethod.MakeGenericMethod(genericTypeArguments)); + } + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index 4ee162e53c..0b50048566 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -9,6 +9,9 @@ class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IReflectionMethodSymb readonly MethodInfo _method; + ReflectionGenericTypeParameterTable _genericTypeParameterTable; + ReflectionMethodSpecTable _specTable; + /// /// Initializes a new instance. /// @@ -17,16 +20,35 @@ class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IReflectionMethodSymb /// /// public ReflectionMethodSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type, MethodInfo method) : - base(context, module, type, method) + base(context, module, type) { _method = method ?? throw new ArgumentNullException(nameof(method)); + _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, module, this); + _specTable = new ReflectionMethodSpecTable(context, module, type, this); } - /// - /// Gets the underlying wrapped by this symbol. - /// + /// public MethodInfo UnderlyingMethod => _method; + /// + public override MethodBase UnderlyingMethodBase => UnderlyingMethod; + + #region IReflectionMethodSymbol + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + /// + public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) + { + return _specTable.GetOrCreateGenericMethodSymbol(method.GetGenericArguments()); + } + + #endregion + #region IMethodSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs new file mode 100644 index 0000000000..6e58bb23bd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs @@ -0,0 +1,143 @@ +using System; +using System.Collections.Concurrent; +using System.Collections.Generic; +using System.Reflection; +using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionMethodTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol? _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionMethodTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + if (method.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(method)); + if (method is MethodInfo m_ && m_.IsMethodDefinition() == false) + throw new ArgumentException(nameof(method)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = method.GetMetadataTokenRowNumberSafe(); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + return _table[row] ??= CreateMethodBaseSymbol(_context, _module, _type, method); + + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Creates a new symbol. + /// + /// + /// + /// + static IReflectionMethodBaseSymbol CreateMethodBaseSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type, MethodBase method) + { + if (method is ConstructorInfo c) + { + if (type == null) + throw new InvalidOperationException(); + + if (method is ConstructorBuilder builder) + return new ReflectionConstructorSymbolBuilder(context, (IReflectionModuleSymbolBuilder)module, (IReflectionTypeSymbolBuilder)type, builder); + else + return new ReflectionConstructorSymbol(context, module, type, c); + } + else if (method is MethodInfo m) + { + if (method is MethodBuilder builder) + return new ReflectionMethodSymbolBuilder(context, (IReflectionModuleSymbolBuilder)module, (IReflectionTypeSymbolBuilder?)type, builder); + else + return new ReflectionMethodSymbol(context, module, type, m); + } + else + { + throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return (IReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return (IReflectionConstructorSymbolBuilder)GetOrCreateMethodBaseSymbol(ctor); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + return (IReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return (IReflectionMethodSymbolBuilder)GetOrCreateMethodBaseSymbol(method); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs deleted file mode 100644 index f517096799..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleMetadata.cs +++ /dev/null @@ -1,488 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Emit; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - /// - /// Provides the metadata resolution implementation for a module. - /// - struct ReflectionModuleMetadata - { - - /// - /// Returns true if the given is a TypeDef. That is, not a modified or substituted or generic parameter type. - /// - /// - /// - static bool IsTypeDefinition(Type type) - { -#if NET - return type.IsTypeDefinition; -#else - return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; -#endif - } - - const int MAX_CAPACITY = 65536 * 2; - - readonly IReflectionModuleSymbol _symbol; - - IndexRangeDictionary _typeSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _typeLock; - - IndexRangeDictionary _methodSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _methodLock; - - IndexRangeDictionary _fieldSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _fieldLock; - - IndexRangeDictionary _propertySymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _propertyLock; - - IndexRangeDictionary _eventSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _eventLock; - - IndexRangeDictionary _parameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _parameterLock; - - IndexRangeDictionary _genericParameterSymbols = new(maxCapacity: MAX_CAPACITY); - ReaderWriterLockSlim? _genericParameterLock; - - /// - /// Initializes a new instance. - /// - /// - /// - public ReflectionModuleMetadata(IReflectionModuleSymbol symbol) - { - _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - if (type.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(type)); - - // type is a generic parameter (GenericParam) - if (type.IsGenericParameter) - return GetOrCreateGenericTypeParameterSymbol(type); - - // type is not a type definition (TypeDef) - if (IsTypeDefinition(type) == false) - return GetOrCreateTypeSymbolForSpecification(type); - - // create lock on demand - if (_typeLock == null) - Interlocked.CompareExchange(ref _typeLock, new ReaderWriterLockSlim(), null); - - using (_typeLock.CreateUpgradeableReadLock()) - { - var row = type.GetMetadataTokenRowNumberSafe(); - if (_typeSymbols[row] == null) - using (_typeLock.CreateWriteLock()) - if (type is TypeBuilder builder) - return _typeSymbols[row] ??= new ReflectionTypeSymbolBuilder(_symbol.Context, _symbol, builder); - else - return _typeSymbols[row] ??= new ReflectionTypeSymbol(_symbol.Context, _symbol, type); - else - return _typeSymbols[row] ?? throw new InvalidOperationException(); - } - } - - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - return (IReflectionTypeSymbolBuilder)GetOrCreateTypeSymbol((Type)type); - } - - /// - /// Gets or creates a for the specification type: array, pointer, generic, etc. - /// - /// - /// - /// - /// - IReflectionTypeSymbol GetOrCreateTypeSymbolForSpecification(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - if (type.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(type)); - - if (type.GetElementType() is { } elementType) - { - var elementTypeSymbol = _symbol.ResolveTypeSymbol(elementType)!; - - // handles both SZ arrays and normal arrays - if (type.IsArray) - return (IReflectionTypeSymbol)elementTypeSymbol.MakeArrayType(type.GetArrayRank()); - - if (type.IsPointer) - return (IReflectionTypeSymbol)elementTypeSymbol.MakePointerType(); - - if (type.IsByRef) - return (IReflectionTypeSymbol)elementTypeSymbol.MakeByRefType(); - - throw new InvalidOperationException(); - } - - if (type.IsGenericType) - { - var definitionTypeSymbol = _symbol.GetOrCreateTypeSymbol(type.GetGenericTypeDefinition()); - return (IReflectionTypeSymbol)definitionTypeSymbol.MakeGenericType(definitionTypeSymbol.ResolveTypeSymbols(type.GetGenericArguments())!); - } - - throw new InvalidOperationException(); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - if (method.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(method)); - - // they are methods, but they are associated differently - if (method is DynamicMethod) - throw new ArgumentException("Dynamic methods cannot be attached to context."); - - // create lock on demand - if (_methodLock == null) - Interlocked.CompareExchange(ref _methodLock, new ReaderWriterLockSlim(), null); - - using (_methodLock.CreateUpgradeableReadLock()) - { - var row = method.GetMetadataTokenRowNumberSafe(); - if (_methodSymbols[row] == null) - { - using (_methodLock.CreateWriteLock()) - { - if (method is ConstructorInfo c) - { - if (method is ConstructorBuilder builder) - return _methodSymbols[row] ??= new ReflectionConstructorSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), builder); - else - return _methodSymbols[row] ??= new ReflectionConstructorSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(c.DeclaringType!), c); - } - else if (method is MethodInfo m) - { - if (method is MethodBuilder builder) - return _methodSymbols[row] ??= new ReflectionMethodSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), builder); - else - return _methodSymbols[row] ??= new ReflectionMethodSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(method.DeclaringType), m); - } - else - { - throw new InvalidOperationException(); - } - } - } - else - { - return _methodSymbols[row] ?? throw new InvalidOperationException(); - } - } - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return (IReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by ctor. - /// - /// - /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return (IReflectionConstructorSymbolBuilder)GetOrCreateConstructorSymbol((ConstructorInfo)ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return (IReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return (IReflectionMethodSymbolBuilder)GetOrCreateMethodBaseSymbol((MethodInfo)method); - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - if (field.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(field)); - - // create lock on demand - if (_fieldLock == null) - Interlocked.CompareExchange(ref _fieldLock, new ReaderWriterLockSlim(), null); - - using (_fieldLock.CreateUpgradeableReadLock()) - { - var row = field.GetMetadataTokenRowNumberSafe(); - if (_fieldSymbols[row] == null) - using (_fieldLock.CreateWriteLock()) - if (field is FieldBuilder builder) - return _fieldSymbols[row] ??= new ReflectionFieldSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), builder); - else - return _fieldSymbols[row] ??= new ReflectionFieldSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(field.DeclaringType), field); - else - return _fieldSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - return (IReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field); - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - if (property.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(property)); - - // create lock on demand - if (_propertyLock == null) - Interlocked.CompareExchange(ref _propertyLock, new ReaderWriterLockSlim(), null); - - using (_propertyLock.CreateUpgradeableReadLock()) - { - var row = property.GetMetadataTokenRowNumberSafe(); - if (_propertySymbols[row] == null) - using (_propertyLock.CreateWriteLock()) - if (property is PropertyBuilder builder) - return _propertySymbols[row] ??= new ReflectionPropertySymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), builder); - else - return _propertySymbols[row] ??= new ReflectionPropertySymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(property.DeclaringType!), property); - else - return _propertySymbols[row] ?? throw new InvalidOperationException(); - } - } - - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return (IReflectionPropertySymbolBuilder)GetOrCreatePropertySymbol((PropertyInfo)property); - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - if (@event.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(@event)); - - // create lock on demand - if (_eventLock == null) - Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); - - using (_eventLock.CreateUpgradeableReadLock()) - { - var row = @event.GetMetadataTokenRowNumberSafe(); - if (_eventSymbols[row] == null) - using (_eventLock.CreateWriteLock()) - return _eventSymbols[row] ??= new ReflectionEventSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.DeclaringType!), @event); - else - return _eventSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - if (@event.GetModuleBuilder().GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(@event)); - - // create lock on demand - if (_eventLock == null) - Interlocked.CompareExchange(ref _eventLock, new ReaderWriterLockSlim(), null); - - using (_eventLock.CreateUpgradeableReadLock()) - { - var row = @event.GetMetadataTokenRowNumberSafe(); - if (_eventSymbols[row] == null) - using (_eventLock.CreateWriteLock()) - return (IReflectionEventSymbolBuilder)(_eventSymbols[row] ??= new ReflectionEventSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(@event.GetTypeBuilder()), @event)); - else - return (IReflectionEventSymbolBuilder?)_eventSymbols[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - if (parameter.Member.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(parameter)); - - // create lock on demand - if (_parameterLock == null) - Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); - - using (_parameterLock.CreateUpgradeableReadLock()) - { - var position = parameter.Position; - if (_parameterSymbols[position] == null) - using (_parameterLock.CreateWriteLock()) - return _parameterSymbols[position] ??= new ReflectionParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveMethodBaseSymbol((MethodBase)parameter.Member), parameter); - else - return _parameterSymbols[position] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - if (parameter.GetModuleBuilder().GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(parameter)); - - // create lock on demand - if (_parameterLock == null) - Interlocked.CompareExchange(ref _parameterLock, new ReaderWriterLockSlim(), null); - - using (_parameterLock.CreateUpgradeableReadLock()) - { - var position = parameter.Position; - if (_parameterSymbols[position] == null) - using (_parameterLock.CreateWriteLock()) - return (IReflectionParameterSymbolBuilder)(_parameterSymbols[position] ??= new ReflectionParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveMethodSymbol(parameter.GetMethodBuilder()), parameter)); - else - return (IReflectionParameterSymbolBuilder?)_parameterSymbols[position] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericParameterType) - { - if (genericParameterType is null) - throw new ArgumentNullException(nameof(genericParameterType)); - if (genericParameterType.Module.GetMetadataTokenSafe() != _symbol.MetadataToken) - throw new ArgumentException(nameof(genericParameterType)); - - // create lock on demand - if (_genericParameterLock == null) - Interlocked.CompareExchange(ref _genericParameterLock, new ReaderWriterLockSlim(), null); - - using (_genericParameterLock.CreateUpgradeableReadLock()) - { - var hnd = MetadataTokens.GenericParameterHandle(genericParameterType.GetMetadataTokenSafe()); - var row = MetadataTokens.GetRowNumber(hnd); - if (_genericParameterSymbols[row] == null) - using (_genericParameterLock.CreateWriteLock()) - if (genericParameterType is GenericTypeParameterBuilder builder) - return _genericParameterSymbols[row] ??= new ReflectionGenericTypeParameterSymbolBuilder(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), builder); - else - return _genericParameterSymbols[row] ??= new ReflectionGenericTypeParameterSymbol(_symbol.Context, _symbol, _symbol.ResolveTypeSymbol(genericParameterType.DeclaringType), _symbol.ResolveMethodSymbol((MethodInfo?)genericParameterType.DeclaringMethod), genericParameterType); - else - { - return _genericParameterSymbols[row] ?? throw new InvalidOperationException(); - } - } - } - - /// - /// Gets or creates the cached for the module. - /// - /// - /// - IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) - { - return (IReflectionGenericTypeParameterSymbolBuilder)GetOrCreateGenericTypeParameterSymbol((Type)genericParameterType); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 60a8b9f32e..c596f370e2 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -1,9 +1,8 @@ using System; using System.Linq; using System.Reflection; -using System.Reflection.Emit; -using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { @@ -16,7 +15,10 @@ class ReflectionModuleSymbol : ReflectionSymbol, IReflectionModuleSymbol readonly IReflectionAssemblySymbol _resolvingAssembly; readonly Module _module; - ReflectionModuleMetadata _impl; + + ReflectionTypeTable _typeTable; + ReflectionMethodTable _methodTable; + ReflectionFieldTable _fieldTable; /// /// Initializes a new instance. @@ -30,7 +32,10 @@ public ReflectionModuleSymbol(ReflectionSymbolContext context, IReflectionAssemb { _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); _module = module ?? throw new ArgumentNullException(nameof(module)); - _impl = new ReflectionModuleMetadata(this); + + _typeTable = new ReflectionTypeTable(context, this, null); + _methodTable = new ReflectionMethodTable(context, this, null); + _fieldTable = new ReflectionFieldTable(context, this, null); } /// @@ -219,7 +224,8 @@ public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inh /// public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); } /// @@ -230,89 +236,88 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + #region IReflectionModuleSymbol + /// public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) { - return _impl.GetOrCreateTypeSymbol(type); - } + if (type.IsTypeDefinition()) + return _typeTable.GetOrCreateTypeSymbol(type); + else if (type.IsGenericType) + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + else if (type.IsSZArray()) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateSZArrayTypeSymbol(); + else if (type.IsArray) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateArrayTypeSymbol(type.GetArrayRank()); + else if (type.IsPointer) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreatePointerTypeSymbol(); + else if (type.IsByRef) + return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateByRefTypeSymbol(); + else if (type.IsGenericParameter && type.DeclaringMethod is MethodInfo dm) + return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(type); + else if (type.IsGenericParameter && type.DeclaringType is Type t) + return ResolveTypeSymbol(t).GetOrCreateGenericTypeParameterSymbol(type); - /// - public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - return _impl.GetOrCreateTypeSymbol(type); + throw new InvalidOperationException(); } /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) { - return _impl.GetOrCreateConstructorSymbol(ctor); + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodBaseSymbol(method); + else + return _methodTable.GetOrCreateMethodBaseSymbol(method); } /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { - return _impl.GetOrCreateConstructorSymbol(ctor); + return ResolveTypeSymbol(ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); } /// public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { - return _impl.GetOrCreateMethodSymbol(method); - } - - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return _impl.GetOrCreateMethodSymbol(method); + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateMethodSymbol(method); + else + return _methodTable.GetOrCreateMethodSymbol(method); } /// public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - return _impl.GetOrCreateFieldSymbol(field); - } - - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - return _impl.GetOrCreateFieldSymbol(field); + if (field.DeclaringType is { } dt) + return ResolveTypeSymbol(dt).GetOrCreateFieldSymbol(field); + else + return _fieldTable.GetOrCreateFieldSymbol(field); } /// public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { - return _impl.GetOrCreatePropertySymbol(property); - } - - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return _impl.GetOrCreatePropertySymbol(property); + return ResolveTypeSymbol(property.DeclaringType!).GetOrCreatePropertySymbol(property); } /// public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { - return _impl.GetOrCreateEventSymbol(@event); - } - - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return _impl.GetOrCreateEventSymbol(@event); + return ResolveTypeSymbol(@event.DeclaringType!).GetOrCreateEventSymbol(@event); } /// public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { - return _impl.GetOrCreateParameterSymbol(parameter); + return ResolveMemberSymbol(parameter.Member) switch + { + IReflectionMethodBaseSymbol method => method.GetOrCreateParameterSymbol(parameter), + IReflectionPropertySymbol property => property.GetOrCreateParameterSymbol(parameter), + _ => throw new InvalidOperationException(), + }; } - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return _impl.GetOrCreateParameterSymbol(parameter); - } + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs similarity index 55% rename from src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs rename to src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs index c63ae51455..38f8172721 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblyMetadata.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs @@ -1,7 +1,7 @@ using System; -using System.Diagnostics; using System.Reflection; using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; using System.Threading; using IKVM.CoreLib.Collections; @@ -12,37 +12,36 @@ namespace IKVM.CoreLib.Symbols.Reflection { - struct ReflectionAssemblyMetadata + struct ReflectionModuleTable { - readonly IReflectionAssemblySymbol _symbol; + readonly ReflectionSymbolContext _context; + readonly IReflectionAssemblySymbol _assembly; - IndexRangeDictionary _moduleSymbols = new(maxCapacity: 32); + IndexRangeDictionary _moduleSymbols = new(); ReaderWriterLockSlim? _moduleLock; /// /// Initializes a new instance. /// - /// + /// /// - public ReflectionAssemblyMetadata(IReflectionAssemblySymbol symbol) + public ReflectionModuleTable(ReflectionSymbolContext context, IReflectionAssemblySymbol assembly) { - _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); + _context = context ?? throw new ArgumentNullException(nameof(context)); + _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); } /// - /// Gets or creates the cached for the module. + /// Gets or creates the cached for the module. /// /// /// - /// public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) { if (module is null) throw new ArgumentNullException(nameof(module)); - Debug.Assert(AssemblyNameEqualityComparer.Instance.Equals(module.Assembly.GetName(), _symbol.UnderlyingAssembly.GetName())); - // create lock on demand if (_moduleLock == null) Interlocked.CompareExchange(ref _moduleLock, new ReaderWriterLockSlim(), null); @@ -53,14 +52,24 @@ public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) if (_moduleSymbols[row] == null) using (_moduleLock.CreateWriteLock()) if (module is ModuleBuilder builder) - return _moduleSymbols[row] = new ReflectionModuleSymbolBuilder(_symbol.Context, _symbol, builder); + return _moduleSymbols[row] = new ReflectionModuleSymbolBuilder(_context, _assembly, builder); else - return _moduleSymbols[row] = new ReflectionModuleSymbol(_symbol.Context, _symbol, module); - else - return _moduleSymbols[row] ?? throw new InvalidOperationException(); + return _moduleSymbols[row] = new ReflectionModuleSymbol(_context, _assembly, module); + + return _moduleSymbols[row] ?? throw new InvalidOperationException(); } } + /// + /// Gets or creates the cached for the module. + /// + /// + /// + public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + { + return (IReflectionModuleSymbolBuilder)GetOrCreateModuleSymbol((Module)module); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index 22628fd9dc..cffe5c8ecb 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -9,23 +9,21 @@ class ReflectionParameterSymbol : ReflectionSymbol, IReflectionParameterSymbol { readonly IReflectionModuleSymbol _resolvingModule; - readonly IReflectionMethodBaseSymbol _resolvingMethod; + readonly IReflectionMemberSymbol _resolvingMember; readonly ParameterInfo _parameter; - CustomAttribute[]? _customAttributes; - /// /// Initializes a new instance. /// /// /// - /// + /// /// - public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMethodBaseSymbol resolvingMethod, ParameterInfo parameter) : + public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMemberSymbol? resolvingMember, ParameterInfo parameter) : base(context) { _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingMethod = resolvingMethod ?? throw new ArgumentNullException(nameof(resolvingMethod)); + _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); } @@ -33,7 +31,7 @@ public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionMod public IReflectionModuleSymbol ResolvingModule => _resolvingModule; /// - public IReflectionMethodBaseSymbol ResolvingMethod => _resolvingMethod; + public IReflectionMemberSymbol ResolvingMember => _resolvingMember; /// public ParameterInfo UnderlyingParameter => _parameter; @@ -41,10 +39,10 @@ public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionMod #region IParameterSymbol /// - public ParameterAttributes Attributes => UnderlyingParameter.Attributes; + public System.Reflection.ParameterAttributes Attributes => (System.Reflection.ParameterAttributes)UnderlyingParameter.Attributes; /// - public object? DefaultValue => UnderlyingParameter.DefaultValue; + public object? DefaultValue => UnderlyingParameter.RawDefaultValue; /// public bool HasDefaultValue => UnderlyingParameter.HasDefaultValue; @@ -80,21 +78,32 @@ public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionMod public int Position => UnderlyingParameter.Position; /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) + public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return _customAttributes ??= ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData()); + if (inherit == true) + throw new NotSupportedException(); + + return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData()); } /// public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + if (inherit == true) + throw new NotSupportedException(); + + var _attribyteType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData().Where(i => i.AttributeType == _attribyteType).ToArray()); } /// public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return GetCustomAttributes(attributeType, inherit).FirstOrDefault(); + if (inherit == true) + throw new NotSupportedException(); + + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingParameter.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs new file mode 100644 index 0000000000..8d1faa6b16 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs @@ -0,0 +1,102 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionParameterTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionMemberSymbol _member; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + IReflectionParameterSymbol? _returnParameter; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public ReflectionParameterTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionMemberSymbol member) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _member = member ?? throw new ArgumentNullException(nameof(member)); + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.Member.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var position = parameter.Position; + if (position == -1) + return _returnParameter ??= new ReflectionParameterSymbol(_context, _module, _member, parameter); + + if (_table[position] == null) + using (_lock.CreateWriteLock()) + return _table[position] ??= new ReflectionParameterSymbol(_context, _module, _member, parameter); + + return _table[position] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by method. + /// + /// + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + if (parameter.GetMethodBuilder().Module != _module.UnderlyingModule) + throw new ArgumentException(nameof(parameter)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var position = parameter.Position - 1; + if (position == -1) + return (IReflectionParameterSymbolBuilder)(_returnParameter ??= new ReflectionParameterSymbolBuilder(_context, _module, (IReflectionMethodBaseSymbol)_member, parameter)); + + if (_table[position] == null) + using (_lock.CreateWriteLock()) + return (IReflectionParameterSymbolBuilder)(_table[position] ??= new ReflectionParameterSymbolBuilder(_context, _module, (IReflectionMethodBaseSymbol)_member, parameter)); + + return (IReflectionParameterSymbolBuilder?)_table[position] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs index e0f0036743..4a06567d91 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs @@ -9,6 +9,8 @@ class ReflectionPropertySymbol : ReflectionMemberSymbol, IReflectionPropertySymb readonly PropertyInfo _property; + ReflectionParameterTable _parameterTable; + /// /// Initializes a new instance. /// @@ -17,16 +19,32 @@ class ReflectionPropertySymbol : ReflectionMemberSymbol, IReflectionPropertySymb /// /// public ReflectionPropertySymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol type, PropertyInfo property) : - base(context, module, type, property) + base(context, module, type) { _property = property ?? throw new ArgumentNullException(nameof(property)); + _parameterTable = new ReflectionParameterTable(context, module, this); } /// public PropertyInfo UnderlyingProperty => _property; /// - public PropertyAttributes Attributes => UnderlyingProperty.Attributes; + public override MemberInfo UnderlyingMember => UnderlyingProperty; + + #region IReflectionPropertySymbol + + /// + public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + + #endregion + + #region IPropertySymbol + + /// + public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)UnderlyingProperty.Attributes; /// public bool CanRead => UnderlyingProperty.CanRead; @@ -112,6 +130,8 @@ public ITypeSymbol[] GetRequiredCustomModifiers() return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); } + #endregion + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs new file mode 100644 index 0000000000..c8a96fceb5 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs @@ -0,0 +1,81 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionPropertyTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionPropertyTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type ?? throw new ArgumentNullException(nameof(type)); + } + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + if (property.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(property)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = property.GetMetadataTokenRowNumberSafe(); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + if (property is PropertyBuilder builder) + return _table[row] ??= new ReflectionPropertySymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder)_type, builder); + else + return _table[row] ??= new ReflectionPropertySymbol(_context, _module, _type, property); + + return _table[row] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return (IReflectionPropertySymbolBuilder)GetOrCreatePropertySymbol((PropertyInfo)property); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index 822ba085c0..ae1c1f3171 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -60,7 +60,7 @@ public virtual IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBu /// [return: NotNullIfNotNull(nameof(assemblies))] - public virtual IReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies) + public IReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies) { if (assemblies == null) return null; @@ -94,7 +94,7 @@ public virtual IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder /// [return: NotNullIfNotNull(nameof(modules))] - public virtual IReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules) + public IReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules) { if (modules == null) return null; @@ -110,7 +110,7 @@ public virtual IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder } /// - public virtual IEnumerable ResolveModuleSymbols(IEnumerable modules) + public IEnumerable ResolveModuleSymbols(IEnumerable modules) { foreach (var module in modules) if (ResolveModuleSymbol(module) is { } symbol) @@ -138,7 +138,7 @@ public virtual IEnumerable ResolveModuleSymbols(IEnumer /// [return: NotNullIfNotNull(nameof(members))] - public virtual IReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? members) + public IReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? members) { if (members == null) return null; @@ -172,7 +172,7 @@ public virtual IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) /// [return: NotNullIfNotNull(nameof(types))] - public virtual IReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types) + public IReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types) { if (types == null) return null; @@ -188,7 +188,7 @@ public virtual IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) } /// - public virtual IEnumerable ResolveTypeSymbols(IEnumerable types) + public IEnumerable ResolveTypeSymbols(IEnumerable types) { foreach (var type in types) if (ResolveTypeSymbol(type) is { } symbol) @@ -226,7 +226,7 @@ public virtual IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(Cons /// [return: NotNullIfNotNull(nameof(ctors))] - public virtual IReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors) + public IReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors) { if (ctors == null) return null; @@ -260,7 +260,7 @@ public virtual IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder /// [return: NotNullIfNotNull(nameof(methods))] - public virtual IReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods) + public IReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods) { if (methods == null) return null; @@ -294,7 +294,7 @@ public virtual IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder fie /// [return: NotNullIfNotNull(nameof(fields))] - public virtual IReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields) + public IReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields) { if (fields == null) return null; @@ -328,7 +328,7 @@ public virtual IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBu /// [return: NotNullIfNotNull(nameof(properties))] - public virtual IReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties) + public IReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties) { if (properties == null) return null; @@ -347,12 +347,15 @@ public virtual IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBu [return: NotNullIfNotNull(nameof(@event))] public virtual IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) { - return @event == null ? null : _context.GetOrCreateEventSymbol(@event); + if (@event is null) + return null; + + return _context.GetOrCreateEventSymbol(@event); } /// [return: NotNullIfNotNull(nameof(@event))] - public virtual IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) + public virtual IReflectionEventSymbolBuilder? ResolveEventSymbol(EventBuilder @event) { if (@event is null) throw new ArgumentNullException(nameof(@event)); @@ -362,7 +365,7 @@ public virtual IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @ev /// [return: NotNullIfNotNull(nameof(events))] - public virtual IReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events) + public IReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events) { if (@events == null) return null; @@ -381,22 +384,41 @@ public virtual IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @ev [return: NotNullIfNotNull(nameof(parameter))] public virtual IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) { - return parameter == null ? null : _context.GetOrCreateParameterSymbol(parameter); + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + return _context.GetOrCreateParameterSymbol(parameter); } /// [return: NotNullIfNotNull(nameof(parameter))] - public virtual IReflectionParameterSymbolBuilder ResolveParameterSymbol(ParameterBuilder parameter) + public virtual IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionMethodBaseSymbolBuilder method, ParameterBuilder parameter) { + if (method is null) + throw new ArgumentNullException(nameof(method)); + if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); + return null; - return _context.GetOrCreateParameterSymbol(parameter); + return method.GetOrCreateParameterSymbol(parameter); + } + + /// + [return: NotNullIfNotNull(nameof(parameter))] + public virtual IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionPropertySymbolBuilder property, ParameterBuilder parameter) + { + if (property is null) + throw new ArgumentNullException(nameof(property)); + + if (parameter is null) + return null; + + return property.GetOrCreateParameterSymbol(parameter); } /// [return: NotNullIfNotNull(nameof(parameters))] - public virtual IReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters) + public IReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters) { if (parameters == null) return null; @@ -413,7 +435,7 @@ public virtual IReflectionParameterSymbolBuilder ResolveParameterSymbol(Paramete /// [return: NotNullIfNotNull(nameof(attributes))] - public virtual CustomAttribute[]? ResolveCustomAttributes(IList? attributes) + public CustomAttribute[]? ResolveCustomAttributes(IList? attributes) { if (attributes == null) return null; @@ -429,7 +451,7 @@ public virtual IReflectionParameterSymbolBuilder ResolveParameterSymbol(Paramete } /// - public virtual IEnumerable ResolveCustomAttributes(IEnumerable attributes) + public IEnumerable ResolveCustomAttributes(IEnumerable attributes) { if (attributes is null) throw new ArgumentNullException(nameof(attributes)); @@ -444,7 +466,7 @@ public virtual IEnumerable ResolveCustomAttributes(IEnumerable< /// [return: NotNullIfNotNull(nameof(customAttributeData))] - public virtual CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) + public CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) { if (customAttributeData == null) return null; @@ -484,6 +506,7 @@ public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.R { return value switch { + IList aa => ResolveCustomAttributeTypedArguments(aa), Type v => ResolveTypeSymbol(v), _ => value }; @@ -527,9 +550,9 @@ public InterfaceMapping ResolveInterfaceMapping(System.Reflection.InterfaceMappi /// public ManifestResourceInfo? ResolveManifestResourceInfo(System.Reflection.ManifestResourceInfo? info) { - return info != null ? new ManifestResourceInfo(info.ResourceLocation, info.FileName, ResolveAssemblySymbol(info.ReferencedAssembly)) : null; + return info != null ? new ManifestResourceInfo((System.Reflection.ResourceLocation)info.ResourceLocation, info.FileName, ResolveAssemblySymbol(info.ReferencedAssembly)) : null; } } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index 8b57fc2b6e..1b876eb337 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -17,7 +17,7 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionSymbolContext : ISymbolContext { - readonly ConcurrentDictionary> _symbolByName = new(AssemblyNameEqualityComparer.Instance); + readonly ConcurrentDictionary> _symbolByName = new(); readonly ConditionalWeakTable _symbolByAssembly = new(); /// @@ -28,32 +28,30 @@ public ReflectionSymbolContext() } - /// - /// Defines a dynamic assembly that has the specified name and access rights. - /// - /// - /// - /// + /// public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name) { if (name is null) throw new ArgumentNullException(nameof(name)); +#if NET return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect)); +#else + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave)); +#endif } - /// - /// Defines a dynamic assembly that has the specified name and access rights. - /// - /// - /// - /// + /// public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttributeBuilder[]? assemblyAttributes) { if (name is null) throw new ArgumentNullException(nameof(name)); +#if NET return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); +#else + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave,assemblyAttributes?.Unpack())); +#endif } /// @@ -63,7 +61,7 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttri /// IReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) { - var r = _symbolByName.GetOrAdd(assembly.GetName(), _ => new(null)); + var r = _symbolByName.GetOrAdd(assembly.FullName ?? throw new InvalidOperationException(), _ => new(null)); lock (r) { @@ -73,7 +71,6 @@ IReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) if (assembly is AssemblyBuilder builder) { // we were passed in a builder, so generate a symbol builder and set it as the builder and symbol. - var a = builder.GetRuntimeAssembly(); r.SetTarget(s = new ReflectionAssemblySymbolBuilder(this, builder)); } else @@ -138,7 +135,7 @@ public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) /// public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) { - return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); + return GetOrCreateAssemblySymbol((AssemblyBuilder)module.Assembly).GetOrCreateModuleSymbol(module); } /// @@ -161,7 +158,38 @@ public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) /// public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) { - return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); + return GetOrCreateModuleSymbol((ModuleBuilder)type.Module).GetOrCreateTypeSymbol(type); + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionMemberSymbol GetOrCreateMemberSymbol(MemberInfo member) + { + return member switch + { + MethodBase method => GetOrCreateMethodBaseSymbol(method), + FieldInfo field => GetOrCreateFieldSymbol(field), + PropertyInfo property => GetOrCreatePropertySymbol(property), + EventInfo @event => GetOrCreateEventSymbol(@event), + _ => throw new InvalidOperationException(), + }; + } + + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + return method switch + { + ConstructorInfo ctor => GetOrCreateConstructorSymbol(ctor), + _ => GetOrCreateMethodSymbol((MethodInfo)method) + }; } /// @@ -171,10 +199,11 @@ public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) /// public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { - if (ctor is ConstructorBuilder builder) - return GetOrCreateConstructorSymbol(builder); - else - return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); + return ctor switch + { + ConstructorBuilder builder => GetOrCreateConstructorSymbol(builder), + _ => GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor) + }; } /// @@ -184,7 +213,7 @@ public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo /// public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) { - return GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor); + return GetOrCreateModuleSymbol((ModuleBuilder)ctor.Module).GetOrCreateConstructorSymbol(ctor); } /// @@ -194,10 +223,11 @@ public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(Construc /// public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { - if (method is MethodBuilder builder) - return GetOrCreateMethodSymbol(builder); - else - return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); + return method switch + { + MethodBuilder builder => GetOrCreateMethodSymbol(builder), + _ => GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method) + }; } /// @@ -207,7 +237,7 @@ public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) /// public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) { - return GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method); + return GetOrCreateModuleSymbol((ModuleBuilder)method.Module).GetOrCreateMethodSymbol(method); } /// @@ -220,16 +250,6 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param return GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateParameterSymbol(parameter); } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return GetOrCreateModuleSymbol(parameter.GetModuleBuilder()).GetOrCreateParameterSymbol(parameter); - } - /// /// Gets or creates a for the specified . /// @@ -237,10 +257,7 @@ public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBui /// public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - if (field is FieldBuilder builder) - return GetOrCreateFieldSymbol(builder); - else - return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); } /// @@ -250,7 +267,7 @@ public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) /// public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) { - return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + return GetOrCreateModuleSymbol((ModuleBuilder)field.Module).GetOrCreateFieldSymbol(field); } /// @@ -260,10 +277,11 @@ public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) /// public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { - if (property is PropertyBuilder builder) - return GetOrCreatePropertySymbol(builder); - else - return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); + return property switch + { + PropertyBuilder builder => GetOrCreatePropertySymbol(builder), + _ => GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property) + }; } /// @@ -273,7 +291,7 @@ public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property /// public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) { - return GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property); + return GetOrCreateModuleSymbol((ModuleBuilder)property.Module).GetOrCreatePropertySymbol(property); } /// @@ -296,28 +314,65 @@ public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) return GetOrCreateModuleSymbol(@event.GetModuleBuilder()).GetOrCreateEventSymbol(@event); } + /// + /// Gets or creates a for the specified . + /// + /// + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return GetOrCreateModuleSymbol((ModuleBuilder)genericTypeParameter.Module).GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs) { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs)); + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs))); } /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedFields.Unpack(), fieldValues)); + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedFields.Unpack(), UnpackArguments(fieldValues))); } /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues)); + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues))); } /// public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), constructorArgs, namedProperties.Unpack(), propertyValues, namedFields.Unpack(), fieldValues)); + return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues), namedFields.Unpack(), UnpackArguments(fieldValues))); + } + + /// + /// Unpacks a single constructor argument. + /// + /// + /// + object? UnpackArgument(object? constructorArg) + { + if (constructorArg is ITypeSymbol type) + return type.Unpack(); + + return constructorArg; + } + + /// + /// Unpacks a set of constructor arguments. + /// + /// + /// + object?[] UnpackArguments(object?[] constructorArgs) + { + var l = new object?[constructorArgs.Length]; + for (int i = 0; i < constructorArgs.Length; i++) + l[i] = UnpackArgument(constructorArgs[i]); + + return l; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs deleted file mode 100644 index c7821414cf..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeImpl.cs +++ /dev/null @@ -1,633 +0,0 @@ -using System; -using System.Collections.Concurrent; -using System.Reflection; -using System.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - /// - /// Provides common operations against a . - /// - struct ReflectionTypeImpl - { - - readonly IReflectionTypeSymbol _symbol; - - ReflectionTypeSymbol?[]? _asArray; - ReflectionTypeSymbol? _asSZArray; - ReflectionTypeSymbol? _asPointer; - ReflectionTypeSymbol? _asByRef; - ConcurrentDictionary? _genericTypeSymbols; - - /// - /// Initializes a new instance. - /// - /// - /// - public ReflectionTypeImpl(IReflectionTypeSymbol symbol) - { - _symbol = symbol ?? throw new ArgumentNullException(nameof(symbol)); - } - - /// - /// Gets or creates the cached for the generic parameter type. - /// - /// - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(ITypeSymbol[] genericTypeArguments) - { - if (genericTypeArguments is null) - throw new ArgumentNullException(nameof(genericTypeArguments)); - - if (_symbol.UnderlyingType.IsGenericTypeDefinition == false) - throw new InvalidOperationException(); - - if (_genericTypeSymbols == null) - Interlocked.CompareExchange(ref _genericTypeSymbols, new ConcurrentDictionary(TypeSymbolListEqualityComparer.Instance), null); - - var __symbol = _symbol; - return _genericTypeSymbols.GetOrAdd(genericTypeArguments, _ => new ReflectionTypeSymbol(__symbol.Context, __symbol.ResolvingModule, __symbol.UnderlyingType.MakeGenericType(genericTypeArguments.Unpack()))); - } - - /// - public readonly IAssemblySymbol Assembly => _symbol.ResolveAssemblySymbol(_symbol.UnderlyingType.Assembly); - - /// - public readonly string? AssemblyQualifiedName => _symbol.UnderlyingType.AssemblyQualifiedName; - - /// - public readonly TypeAttributes Attributes => _symbol.UnderlyingType.Attributes; - - /// - public readonly ITypeSymbol? BaseType => _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.BaseType); - - /// - public readonly bool ContainsGenericParameters => _symbol.UnderlyingType.ContainsGenericParameters; - - /// - public readonly IMethodBaseSymbol? DeclaringMethod => _symbol.ResolveMethodBaseSymbol(_symbol.UnderlyingType.DeclaringMethod); - - /// - public readonly string? FullName => _symbol.UnderlyingType.FullName; - - /// - public readonly string? Namespace => _symbol.UnderlyingType.Namespace; - - /// - public readonly GenericParameterAttributes GenericParameterAttributes => _symbol.UnderlyingType.GenericParameterAttributes; - - /// - public readonly int GenericParameterPosition => _symbol.UnderlyingType.GenericParameterPosition; - - /// - public readonly ITypeSymbol[] GenericTypeArguments => _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GenericTypeArguments); - - /// - public readonly bool HasElementType => _symbol.UnderlyingType.HasElementType; - - /// - public readonly TypeCode TypeCode => Type.GetTypeCode(_symbol.UnderlyingType); - - /// - public readonly bool IsAbstract => _symbol.UnderlyingType.IsAbstract; - -#if NETFRAMEWORK - - /// - /// - /// There's no API to distinguish an array of rank 1 from a vector, - /// so we check if the type name ends in [], which indicates it's a vector - /// (non-vectors will have [*] or [,]). - /// - public readonly bool IsSZArray => _symbol.UnderlyingType.IsArray && _symbol.UnderlyingType.Name.EndsWith("[]"); - -#else - - /// - public readonly bool IsSZArray => _symbol.UnderlyingType.IsSZArray; - -#endif - - /// - public readonly bool IsArray => _symbol.UnderlyingType.IsArray; - - /// - public readonly bool IsAutoLayout => _symbol.UnderlyingType.IsAutoLayout; - - /// - public readonly bool IsExplicitLayout => _symbol.UnderlyingType.IsExplicitLayout; - - /// - public readonly bool IsByRef => _symbol.UnderlyingType.IsByRef; - - /// - public readonly bool IsClass => _symbol.UnderlyingType.IsClass; - - /// - public readonly bool IsEnum => _symbol.UnderlyingType.IsEnum; - - /// - public readonly bool IsInterface => _symbol.UnderlyingType.IsInterface; - - /// - public readonly bool IsConstructedGenericType => _symbol.UnderlyingType.IsConstructedGenericType; - - /// - public readonly bool IsGenericParameter => _symbol.UnderlyingType.IsGenericParameter; - - /// - public readonly bool IsGenericType => _symbol.UnderlyingType.IsGenericType; - - /// - public readonly bool IsGenericTypeDefinition => _symbol.UnderlyingType.IsGenericTypeDefinition; - - /// - public readonly bool IsLayoutSequential => _symbol.UnderlyingType.IsLayoutSequential; - - /// - public readonly bool IsNested => _symbol.UnderlyingType.IsNested; - - /// - public readonly bool IsNestedAssembly => _symbol.UnderlyingType.IsNestedAssembly; - - /// - public readonly bool IsNestedFamANDAssem => _symbol.UnderlyingType.IsNestedFamANDAssem; - - /// - public readonly bool IsNestedFamORAssem => _symbol.UnderlyingType.IsNestedFamORAssem; - - /// - public readonly bool IsNestedFamily => _symbol.UnderlyingType.IsNestedFamily; - - /// - public readonly bool IsNestedPrivate => _symbol.UnderlyingType.IsNestedPrivate; - - /// - public readonly bool IsNestedPublic => _symbol.UnderlyingType.IsNestedPublic; - - /// - public readonly bool IsNotPublic => _symbol.UnderlyingType.IsNotPublic; - - /// - public readonly bool IsPointer => _symbol.UnderlyingType.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public readonly bool IsFunctionPointer => _symbol.UnderlyingType.IsFunctionPointer; - - /// - public readonly bool IsUnmanagedFunctionPointer => _symbol.UnderlyingType.IsUnmanagedFunctionPointer; - -#else - - /// - public readonly bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public readonly bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public readonly bool IsPrimitive => _symbol.UnderlyingType.IsPrimitive; - - /// - public readonly bool IsPublic => _symbol.UnderlyingType.IsPublic; - - /// - public readonly bool IsSealed => _symbol.UnderlyingType.IsSealed; - -#pragma warning disable SYSLIB0050 // Type or member is obsolete - /// - public readonly bool IsSerializable => _symbol.UnderlyingType.IsSerializable; -#pragma warning restore SYSLIB0050 // Type or member is obsolete - - /// - public readonly bool IsValueType => _symbol.UnderlyingType.IsValueType; - - /// - public readonly bool IsVisible => _symbol.UnderlyingType.IsVisible; - -#if NET6_0_OR_GREATER - - /// - public readonly bool IsSignatureType => _symbol.UnderlyingType.IsSignatureType; - -#else - - /// - public readonly bool IsSignatureType => throw new NotImplementedException(); - -#endif - - /// - public readonly bool IsSpecialName => _symbol.UnderlyingType.IsSpecialName; - - /// - public readonly IConstructorSymbol? TypeInitializer => _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.TypeInitializer); - - /// - public readonly int GetArrayRank() - { - return _symbol.UnderlyingType.GetArrayRank(); - } - - /// - public readonly IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) - { - return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public readonly IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return _symbol.ResolveConstructorSymbol(_symbol.UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public readonly IConstructorSymbol[] GetConstructors() - { - return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors()); - } - - /// - public readonly IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) - { - return _symbol.ResolveConstructorSymbols(_symbol.UnderlyingType.GetConstructors(bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetDefaultMembers() - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetDefaultMembers()); - } - - /// - public readonly ITypeSymbol? GetElementType() - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetElementType()); - } - - /// - public readonly string? GetEnumName(object value) - { - return _symbol.UnderlyingType.GetEnumName(value); - } - - /// - public readonly string[] GetEnumNames() - { - return _symbol.UnderlyingType.GetEnumNames(); - } - - /// - public readonly ITypeSymbol GetEnumUnderlyingType() - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public readonly Array GetEnumValues() - { - return _symbol.UnderlyingType.GetEnumValues(); - } - - /// - public readonly IEventSymbol? GetEvent(string name) - { - return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name)); - } - - /// - public readonly IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) - { - return _symbol.ResolveEventSymbol(_symbol.UnderlyingType.GetEvent(name, bindingAttr)); - } - - /// - public readonly IEventSymbol[] GetEvents() - { - return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents()); - } - - /// - public readonly IEventSymbol[] GetEvents(BindingFlags bindingAttr) - { - return _symbol.ResolveEventSymbols(_symbol.UnderlyingType.GetEvents(bindingAttr)); - } - - /// - public readonly IFieldSymbol? GetField(string name) - { - return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name)); - } - - /// - public readonly IFieldSymbol? GetField(string name, BindingFlags bindingAttr) - { - return _symbol.ResolveFieldSymbol(_symbol.UnderlyingType.GetField(name, bindingAttr)); - } - - /// - public readonly IFieldSymbol[] GetFields() - { - return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields()); - } - - /// - public readonly IFieldSymbol[] GetFields(BindingFlags bindingAttr) - { - return _symbol.ResolveFieldSymbols(_symbol.UnderlyingType.GetFields(bindingAttr)); - } - - /// - public readonly ITypeSymbol[] GetGenericArguments() - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericArguments()); - } - - /// - public readonly ITypeSymbol[] GetGenericParameterConstraints() - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public readonly ITypeSymbol GetGenericTypeDefinition() - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public readonly ITypeSymbol? GetInterface(string name) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name)); - } - - /// - public readonly ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public readonly InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - return _symbol.ResolveInterfaceMapping(_symbol.UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); - } - - /// - public readonly ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public readonly IMemberSymbol[] GetMember(string name) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name)); - } - - /// - public readonly IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMember(name, type, bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetMembers(BindingFlags bindingAttr) - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers(bindingAttr)); - } - - /// - public readonly IMemberSymbol[] GetMembers() - { - return _symbol.ResolveMemberSymbols(_symbol.UnderlyingType.GetMembers()); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, types.Unpack())); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { -#if NETFRAMEWORK - throw new NotImplementedException(); -#else - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers)); -#endif - } - - /// - public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { -#if NETFRAMEWORK - throw new NotImplementedException(); -#else - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers)); -#endif - } - - /// - public readonly IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers)); - } - - /// - public readonly IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { -#if NETFRAMEWORK - throw new NotImplementedException(); -#else - return _symbol.ResolveMethodSymbol(_symbol.UnderlyingType.GetMethod(name, genericParameterCount, types.Unpack(), modifiers)); -#endif - } - - /// - public readonly IMethodSymbol[] GetMethods(BindingFlags bindingAttr) - { - return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods(bindingAttr)); - } - - /// - public readonly IMethodSymbol[] GetMethods() - { - return _symbol.ResolveMethodSymbols(_symbol.UnderlyingType.GetMethods()); - } - - /// - public readonly ITypeSymbol? GetNestedType(string name) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name)); - } - - /// - public readonly ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) - { - return _symbol.ResolveTypeSymbol(_symbol.UnderlyingType.GetNestedType(name, bindingAttr)); - } - - /// - public readonly ITypeSymbol[] GetNestedTypes() - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes()); - } - - /// - public readonly ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) - { - return _symbol.ResolveTypeSymbols(_symbol.UnderlyingType.GetNestedTypes(bindingAttr)); - } - - /// - public readonly IPropertySymbol[] GetProperties() - { - return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties()); - } - - /// - public readonly IPropertySymbol[] GetProperties(BindingFlags bindingAttr) - { - return _symbol.ResolvePropertySymbols(_symbol.UnderlyingType.GetProperties(bindingAttr)); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, bindingAttr)); - } - - /// - public readonly IPropertySymbol? GetProperty(string name) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name)); - } - - /// - public readonly IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return _symbol.ResolvePropertySymbol(_symbol.UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public readonly bool IsAssignableFrom(ITypeSymbol? c) - { - return _symbol.UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public readonly bool IsEnumDefined(object value) - { - return _symbol.UnderlyingType.IsEnumDefined(value); - } - - /// - public readonly bool IsSubclassOf(ITypeSymbol c) - { - return _symbol.UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public IReflectionTypeSymbol MakeArrayType() - { - if (_asSZArray == null) - Interlocked.CompareExchange(ref _asSZArray, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType()), null); - - return _asSZArray; - } - - /// - public IReflectionTypeSymbol MakeArrayType(int rank) - { - if (rank == 1) - return MakeArrayType(); - - if (_asArray == null) - Interlocked.CompareExchange(ref _asArray, new ReflectionTypeSymbol?[32], null); - - ref var asArray = ref _asArray[rank]; - if (asArray == null) - Interlocked.CompareExchange(ref asArray, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeArrayType(rank)), null); - - return asArray; - } - - /// - public IReflectionTypeSymbol MakeByRefType() - { - if (_asByRef == null) - Interlocked.CompareExchange(ref _asByRef, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakeByRefType()), null); - - return _asByRef; - } - - /// - public IReflectionTypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return GetOrCreateGenericTypeSymbol(typeArguments); - } - - /// - public IReflectionTypeSymbol MakePointerType() - { - if (_asPointer == null) - Interlocked.CompareExchange(ref _asPointer, new ReflectionTypeSymbol(_symbol.Context, _symbol.ResolvingModule, _symbol.UnderlyingType.MakePointerType()), null); - - return _asPointer; - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs new file mode 100644 index 0000000000..0f98f8180b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs @@ -0,0 +1,127 @@ +using System; +using System.Collections.Concurrent; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionTypeSpecTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol _elementType; + + IndexRangeDictionary _asArray; + ReaderWriterLockSlim? _asArrayLock; + IReflectionTypeSymbol? _asSZArray; + IReflectionTypeSymbol? _asPointer; + IReflectionTypeSymbol? _asByRef; + ConcurrentDictionary? _genericTypeSymbols; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionTypeSpecTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol elementType) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); + _asArray = new IndexRangeDictionary(); + } + + /// + /// Gets or creates a representing an Array of this type. + /// + /// + /// + /// + public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + if (_asArrayLock == null) + Interlocked.CompareExchange(ref _asArrayLock, new(), null); + + using (_asArrayLock.CreateUpgradeableReadLock()) + { + if (_asArray[rank] == null) + using (_asArrayLock.CreateWriteLock()) + _asArray[rank] = new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeArrayType(rank)); + + return _asArray[rank] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates a representing a SZArray of this type. + /// + /// + public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + if (_asSZArray == null) + Interlocked.CompareExchange(ref _asSZArray, new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeArrayType()), null); + + return _asSZArray; + } + + /// + /// Gets or creates a representing a pointer of this type. + /// + /// + public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + if (_asPointer == null) + Interlocked.CompareExchange(ref _asPointer, new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakePointerType()), null); + + return _asPointer; + } + + /// + /// Gets or creates a representing a by-ref of this type. + /// + /// + public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + if (_asByRef == null) + Interlocked.CompareExchange(ref _asByRef, new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeByRefType()), null); + + return _asByRef; + } + + /// + /// Gets or creates a representing a specialized generic of this type. + /// + /// + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArguments) + { + if (genericTypeArguments is null) + throw new ArgumentNullException(nameof(genericTypeArguments)); + + if (_elementType.IsGenericTypeDefinition == false) + throw new InvalidOperationException(); + + if (_genericTypeSymbols == null) + Interlocked.CompareExchange(ref _genericTypeSymbols, new(TypeSymbolListEqualityComparer.Instance), null); + + return _genericTypeSymbols.GetOrAdd(_module.ResolveTypeSymbols(genericTypeArguments), CreateGenericTypeSymbol); + } + + /// + /// Creates a new representing a specialized generic of this type. + /// + /// + /// + readonly IReflectionTypeSymbol CreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) + { + return new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeGenericType(genericTypeArguments.Unpack())); + } + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index 1ff52d6809..6e33a98679 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -2,6 +2,8 @@ using System.Diagnostics.CodeAnalysis; using System.Reflection; +using IKVM.CoreLib.Reflection; + namespace IKVM.CoreLib.Symbols.Reflection { @@ -9,7 +11,13 @@ class ReflectionTypeSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol { readonly Type _type; - ReflectionTypeImpl _impl; + + ReflectionMethodTable _methodTable; + ReflectionFieldTable _fieldTable; + ReflectionPropertyTable _propertyTable; + ReflectionEventTable _eventTable; + ReflectionGenericTypeParameterTable _genericTypeParameterTable; + ReflectionTypeSpecTable _specTable; /// /// Initializes a new instance. @@ -18,20 +26,108 @@ class ReflectionTypeSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol /// /// public ReflectionTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, Type type) : - base(context, resolvingModule, null, type) + base(context, resolvingModule, null) { _type = type ?? throw new ArgumentNullException(nameof(type)); - _impl = new ReflectionTypeImpl(this); + _methodTable = new ReflectionMethodTable(context, resolvingModule, this); + _fieldTable = new ReflectionFieldTable(context, resolvingModule, this); + _propertyTable = new ReflectionPropertyTable(context, resolvingModule, this); + _eventTable = new ReflectionEventTable(context, resolvingModule, this); + _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, resolvingModule, this); + _specTable = new ReflectionTypeSpecTable(context, resolvingModule, this); } /// public Type UnderlyingType => _type; - /// - /// Resolves the symbol for the specified type. - /// - /// - /// + /// + public override MemberInfo UnderlyingMember => UnderlyingType; + + #region IReflectionTypeSymbol + + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is ConstructorInfo ctor) + return GetOrCreateConstructorSymbol(ctor); + else + return GetOrCreateMethodSymbol((MethodInfo)method); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + if (method.IsMethodDefinition()) + return _methodTable.GetOrCreateMethodSymbol(method); + else + return ResolveMethodSymbol(method.GetGenericMethodDefinition()).GetOrCreateGenericMethodSymbol(method); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericType) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericType); + } + + /// + public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion + + #region IReflectionSymbol + + /// [return: NotNullIfNotNull(nameof(type))] public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) { @@ -41,506 +137,530 @@ public ReflectionTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSy return base.ResolveTypeSymbol(type); } + #endregion + #region ITypeSymbol /// - public TypeAttributes Attributes => _impl.Attributes; + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public IAssemblySymbol Assembly => _impl.Assembly; + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public IMethodBaseSymbol? DeclaringMethod => _impl.DeclaringMethod; + public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; /// - public string? AssemblyQualifiedName => _impl.AssemblyQualifiedName; + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public string? FullName => _impl.FullName; + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public string? Namespace => _impl.Namespace; + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public TypeCode TypeCode => _impl.TypeCode; + public string? FullName => UnderlyingType.FullName; /// - public ITypeSymbol? BaseType => _impl.BaseType; + public string? Namespace => UnderlyingType.Namespace; /// - public bool ContainsGenericParameters => _impl.ContainsGenericParameters; + public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; /// - public GenericParameterAttributes GenericParameterAttributes => _impl.GenericParameterAttributes; + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public int GenericParameterPosition => _impl.GenericParameterPosition; + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public ITypeSymbol[] GenericTypeArguments => _impl.GenericTypeArguments; + public bool HasElementType => UnderlyingType.HasElementType; /// - public bool IsConstructedGenericType => _impl.IsConstructedGenericType; + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsGenericType => _impl.IsGenericType; + public bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsGenericTypeDefinition => _impl.IsGenericTypeDefinition; + public bool IsSZArray => UnderlyingType.IsSZArray(); /// - public bool IsGenericParameter => _impl.IsGenericParameter; + public bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => _impl.IsAutoLayout; + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => _impl.IsExplicitLayout; + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsLayoutSequential => _impl.IsLayoutSequential; + public bool IsByRef => UnderlyingType.IsByRef; /// - public bool HasElementType => _impl.HasElementType; + public bool IsClass => UnderlyingType.IsClass; /// - public bool IsClass => _impl.IsClass; + public bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsValueType => _impl.IsValueType; + public bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsInterface => _impl.IsInterface; + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsPrimitive => _impl.IsPrimitive; + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsSZArray => _impl.IsSZArray; + public bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsArray => _impl.IsArray; + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsEnum => _impl.IsEnum; + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsPointer => _impl.IsPointer; + public bool IsNested => UnderlyingType.IsNested; /// - public bool IsFunctionPointer => _impl.IsFunctionPointer; + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsUnmanagedFunctionPointer => _impl.IsUnmanagedFunctionPointer; + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsByRef => _impl.IsByRef; + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsAbstract => _impl.IsAbstract; + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsSealed => _impl.IsSealed; + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsVisible => _impl.IsVisible; + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsPublic => _impl.IsPublic; + public bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsNotPublic => _impl.IsNotPublic; + public bool IsPointer => UnderlyingType.IsPointer; + +#if NET8_0_OR_GREATER /// - public bool IsNested => _impl.IsNested; + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsNestedAssembly => _impl.IsNestedAssembly; + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; + +#else /// - public bool IsNestedFamANDAssem => _impl.IsNestedFamANDAssem; + public bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif /// - public bool IsNestedFamily => _impl.IsNestedFamily; + public bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsNestedFamORAssem => _impl.IsNestedFamORAssem; + public bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsNestedPrivate => _impl.IsNestedPrivate; + public bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsNestedPublic => _impl.IsNestedPublic; + public bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsSerializable => _impl.IsSerializable; + public bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsSignatureType => _impl.IsSignatureType; + public bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSpecialName => _impl.IsSpecialName; + public bool IsSignatureType => throw new NotImplementedException(); /// - public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + public bool IsSpecialName => UnderlyingType.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// public int GetArrayRank() { - return _impl.GetArrayRank(); + return UnderlyingType.GetArrayRank(); } /// - public IMemberSymbol[] GetDefaultMembers() + public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetDefaultMembers(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public ITypeSymbol? GetElementType() + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { - return _impl.GetElementType(); + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public string? GetEnumName(object value) + public IConstructorSymbol[] GetConstructors() { - return _impl.GetEnumName(value); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public string[] GetEnumNames() + public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEnumNames(); + return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } /// - public ITypeSymbol GetEnumUnderlyingType() + public IMemberSymbol[] GetDefaultMembers() { - return _impl.GetEnumUnderlyingType(); + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol[] GetGenericArguments() + public ITypeSymbol? GetElementType() { - return _impl.GetGenericArguments(); + return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public string? GetEnumName(object value) { - return _impl.GetGenericParameterConstraints(); + return UnderlyingType.GetEnumName(value); } /// - public ITypeSymbol GetGenericTypeDefinition() + public string[] GetEnumNames() { - return _impl.GetGenericTypeDefinition(); + return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol? GetInterface(string name) + public ITypeSymbol GetEnumUnderlyingType() { - return _impl.GetInterface(name); + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public Array GetEnumValues() { - return _impl.GetInterface(name, ignoreCase); + return UnderlyingType.GetEnumValues(); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public IEventSymbol? GetEvent(string name) { - return _impl.GetInterfaces(inherit); + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetInterfaceMap(interfaceType); + return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name) + public IEventSymbol[] GetEvents() { - return _impl.GetMember(name); + return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMember(name, bindingAttr); + return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name) { - return _impl.GetMember(name, type, bindingAttr); + return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IMemberSymbol[] GetMembers() + public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMembers(); + return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + public IFieldSymbol[] GetFields() { - return _impl.GetMembers(bindingAttr); + return ResolveFieldSymbols(UnderlyingType.GetFields()); } - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + /// + public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetConstructor(types); + return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + public ITypeSymbol[] GetGenericArguments() { - return _impl.GetConstructor(bindingAttr, types); + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public IConstructorSymbol[] GetConstructors() + public ITypeSymbol[] GetGenericParameterConstraints() { - return _impl.GetConstructors(); + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + public ITypeSymbol GetGenericTypeDefinition() { - return _impl.GetConstructors(bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public IFieldSymbol? GetField(string name) + public ITypeSymbol? GetInterface(string name) { - return _impl.GetField(name); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + public ITypeSymbol? GetInterface(string name, bool ignoreCase) { - return _impl.GetField(name, bindingAttr); + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public IFieldSymbol[] GetFields() + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) { - return _impl.GetFields(); + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); } /// - public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name) { - return _impl.GetFields(bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMethodSymbol? GetMethod(string name) + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, types); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr); + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + public IMemberSymbol[] GetMembers() { - return _impl.GetMethod(name, bindingAttr, types); + return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetMethod(name, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return _impl.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name) { - return _impl.GetMethod(name, bindingAttr, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethod(name, genericParameterCount, types, modifiers); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol[] GetMethods() + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(); + throw new NotImplementedException(); } /// - public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetMethods(bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name) + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return _impl.GetProperty(name, bindingAttr); + throw new NotImplementedException(); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperty(name, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public IMethodSymbol[] GetMethods() { - return _impl.GetProperty(name, returnType, types); + return ResolveMethodSymbols(UnderlyingType.GetMethods()); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public ITypeSymbol? GetNestedType(string name) { - return _impl.GetProperty(name, returnType); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public IPropertySymbol[] GetProperties() + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetProperties(); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes() { - return _impl.GetProperties(bindingAttr); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public IEventSymbol? GetEvent(string name) + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvent(name); + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties() { - return _impl.GetEvent(name, bindingAttr); + return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IEventSymbol[] GetEvents() + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { - return _impl.GetEvents(); + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { - return _impl.GetEvents(bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { - return _impl.GetNestedType(name); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { - return _impl.GetNestedType(name, bindingAttr); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes() + public IPropertySymbol? GetProperty(string name) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { - return _impl.GetNestedTypes(); + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// public bool IsAssignableFrom(ITypeSymbol? c) { - return _impl.IsAssignableFrom(c); + return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// - public bool IsSubclassOf(ITypeSymbol c) + public bool IsEnumDefined(object value) { - return _impl.IsSubclassOf(c); + return UnderlyingType.IsEnumDefined(value); } /// - public bool IsEnumDefined(object value) + public bool IsSubclassOf(ITypeSymbol c) { - return _impl.IsEnumDefined(value); + return UnderlyingType.IsSubclassOf(c.Unpack()); } /// public ITypeSymbol MakeArrayType() { - return _impl.MakeArrayType(); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); } /// public ITypeSymbol MakeArrayType(int rank) { - return _impl.MakeArrayType(rank); + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); } /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + public ITypeSymbol MakeByRefType() { - return _impl.MakeGenericType(typeArguments); + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); } /// public ITypeSymbol MakePointerType() { - return _impl.MakePointerType(); + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); } /// - public ITypeSymbol MakeByRefType() + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { - return _impl.MakeByRefType(); + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs new file mode 100644 index 0000000000..37cb46aecb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs @@ -0,0 +1,75 @@ +using System; +using System.Reflection.Emit; +using System.Reflection.Metadata.Ecma335; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + struct ReflectionTypeTable + { + + readonly ReflectionSymbolContext _context; + readonly IReflectionModuleSymbol _module; + readonly IReflectionTypeSymbol? _type; + + IndexRangeDictionary _table = new(); + ReaderWriterLockSlim? _lock; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionTypeTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + } + + /// + /// Gets or creates the cached for the module by type. + /// + /// + /// + public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + if (type.Module.MetadataToken != _module.MetadataToken) + throw new ArgumentException(nameof(type)); + if (type.IsGenericParameter) + throw new ArgumentException(nameof(type)); + if (type.IsTypeDefinition() == false) + throw new ArgumentException(nameof(type)); + + // create lock on demand + if (_lock == null) + Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + + using (_lock.CreateUpgradeableReadLock()) + { + var row = type.GetMetadataTokenRowNumberSafe(); + if (_table[row] == null) + using (_lock.CreateWriteLock()) + if (_table[row] == null) + if (type is TypeBuilder builder) + return _table[row] = new ReflectionTypeSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, builder); + else + return _table[row] = new ReflectionTypeSymbol(_context, _module, type); + + return _table[row] ?? throw new InvalidOperationException(); + } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index 26c53e8989..2a8426e22a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -51,10 +51,40 @@ public static AssemblyName Unpack(this AssemblyNameInfo n) Name = n.Name, Version = n.Version, CultureName = n.CultureName, - Flags = n.Flags, + Flags = (AssemblyNameFlags)n.Flags, }; } + /// + /// Converts a set of to a set of . + /// + /// + /// + public static AssemblyName[] Unpack(this AssemblyNameInfo[] n) + { + if (n.Length == 0) + return []; + + var a = new AssemblyName[n.Length]; + for (int i = 0; i < n.Length; i++) + a[i] = n[i].Unpack(); + + return a; + } + + /// + /// Unpacks the symbol into their original assembly. + /// + /// + /// + public static Assembly Unpack(this IAssemblySymbol type) + { + if (type is IReflectionAssemblySymbol symbol) + return symbol.UnderlyingAssembly; + + throw new InvalidOperationException(); + } + /// /// Unpacks the symbol into their original type. /// @@ -282,6 +312,35 @@ public static PropertyInfo[] Unpack(this IPropertySymbol[] properties) return a; } + /// + /// Unpacks the parameter modifier. + /// + /// + /// + /// + public static ParameterModifier Unpack(this System.Reflection.ParameterModifier modifier) + { + throw new NotSupportedException(); + } + + /// + /// Unpacks the parameter modifier. + /// + /// + /// + /// + public static ParameterModifier[] Unpack(this System.Reflection.ParameterModifier[] modifiers) + { + if (modifiers.Length == 0) + return []; + + var a = new ParameterModifier[modifiers.Length]; + for (int i = 0; i < modifiers.Length; i++) + a[i] = modifiers[i].Unpack(); + + return a; + } + /// /// Unpacks the . /// @@ -343,6 +402,36 @@ public static CustomAttributeBuilder[] Unpack(this ICustomAttributeBuilder[] cus return a; } + /// + /// Returns true if the given type represents a type definition. + /// + /// + /// + public static bool IsTypeDefinition(this Type type) + { + if (type is null) + throw new ArgumentNullException(nameof(type)); + +#if NET + return type.IsTypeDefinition; +#else + return type.HasElementType == false && type.IsConstructedGenericType == false && type.IsGenericParameter == false; +#endif + } + + /// + /// Returns true if the given method represents a method definition. + /// + /// + /// + public static bool IsMethodDefinition(this MethodBase method) + { + if (method is null) + throw new ArgumentNullException(nameof(method)); + + return method.IsGenericMethod == false || method.IsGenericMethodDefinition; + } + } } diff --git a/src/IKVM.Reflection/Emit/MethodBuilder.cs b/src/IKVM.Reflection/Emit/MethodBuilder.cs index f0757a90d1..c8d40f75f7 100644 --- a/src/IKVM.Reflection/Emit/MethodBuilder.cs +++ b/src/IKVM.Reflection/Emit/MethodBuilder.cs @@ -47,7 +47,7 @@ public sealed class MethodBuilder : MethodInfo // user configurable values Type returnType; - Type[] parameterTypes; + Type[] parameterTypes = Array.Empty(); PackedCustomModifiers customModifiers; MethodAttributes attributes; MethodImplAttributes implFlags; @@ -87,6 +87,7 @@ internal MethodBuilder(TypeBuilder typeBuilder, string name, MethodAttributes at if ((attributes & MethodAttributes.Static) == 0) callingConvention |= CallingConventions.HasThis; this.callingConvention = callingConvention; + this.returnType = Module.Universe.System_Void; } public ILGenerator GetILGenerator() diff --git a/src/IKVM.Runtime/RuntimeArrayJavaType.cs b/src/IKVM.Runtime/RuntimeArrayJavaType.cs index 4ee9687a92..96e6eeff39 100644 --- a/src/IKVM.Runtime/RuntimeArrayJavaType.cs +++ b/src/IKVM.Runtime/RuntimeArrayJavaType.cs @@ -119,7 +119,7 @@ internal override ITypeSymbol TypeAsTBD while (arrayType == null) { bool prevFinished = finished; - var type = ArrayRank == 1 ? ultimateElementTypeWrapper.TypeAsArrayType.MakeArrayType() : ultimateElementTypeWrapper.TypeAsArrayType.MakeArrayType(ArrayRank); + var type = MakeArrayType(ultimateElementTypeWrapper.TypeAsArrayType, this.ArrayRank); if (prevFinished) { // We were already finished prior to the call to MakeArrayType, so we can safely diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index d064ee8dfd..d14dc4fef8 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -1173,7 +1173,7 @@ Type GetCustomClassLoaderType() } var attribs = assembly.GetCustomAttribute(Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName), false); - if (attribs is not null) + if (attribs.HasValue) return ((ITypeSymbol)attribs.Value.ConstructorArguments[0].Value).AsReflection(); return null; diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 197ad18ce1..f09830f6c9 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -920,7 +920,7 @@ internal ITypeSymbol TypeAsSignatureType return ((RuntimeUnloadableJavaType)this).MissingType ?? context.Types.Object; if (IsGhostArray) - return ArrayRank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(ArrayRank); + return RuntimeArrayJavaType.MakeArrayType(context.Types.Object, ArrayRank); return TypeAsTBD; } @@ -944,7 +944,7 @@ internal ITypeSymbol TypeAsLocalOrStackType } if (IsGhostArray) - return ArrayRank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(ArrayRank); + return RuntimeArrayJavaType.MakeArrayType(context.Types.Object, ArrayRank); return TypeAsTBD; } @@ -959,7 +959,7 @@ internal ITypeSymbol TypeAsArrayType return context.Types.Object; if (IsGhostArray) - return ArrayRank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(ArrayRank); + return RuntimeArrayJavaType.MakeArrayType(context.Types.Object, ArrayRank); return TypeAsTBD; } @@ -1311,8 +1311,8 @@ internal virtual void EmitCheckcast(CodeEmitter ilgen) } ilgen.EmitLdc_I4(rank); - ilgen.Emit(System.Reflection.Emit.OpCodes.Call, tw.TypeAsTBD.GetMethod("CastArray")); - ilgen.Emit(System.Reflection.Emit.OpCodes.Castclass, rank == 1 ? context.Types.Object.MakeArrayType() : context.Types.Object.MakeArrayType(rank)); + ilgen.Emit(OpCodes.Call, tw.TypeAsTBD.GetMethod("CastArray")); + ilgen.Emit(OpCodes.Castclass, RuntimeArrayJavaType.MakeArrayType(context.Types.Object, rank)); } else { diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index b789061404..0b5a93a43a 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -1255,7 +1255,7 @@ internal override ITypeSymbol EnumType internal override string GetSourceFileName() { var attr = type.GetCustomAttribute(Context.Resolver.GetSymbol(typeof(SourceFileAttribute))); - if (attr != null && attr.Value.ConstructorArguments.Length > 0) + if (attr.HasValue && attr.Value.ConstructorArguments.Length > 0) return (string)attr.Value.ConstructorArguments[0].Value; if (DeclaringTypeWrapper != null) @@ -1273,11 +1273,12 @@ internal override string GetSourceFileName() internal override int GetSourceLineNumber(IMethodBaseSymbol mb, int ilOffset) { var attr = type.GetCustomAttribute(Context.Resolver.GetSymbol(typeof(LineNumberTableAttribute))); - if (attr != null && attr.Value.Constructor != null) + if (attr.HasValue && attr.Value.Constructor != null) return ((LineNumberTableAttribute)attr.Value.Constructor.AsReflection().Invoke(attr.Value.ConstructorArguments.Cast().ToArray())).GetLineNumber(ilOffset); return -1; } + #endif internal override bool IsFastClassLiteralSafe diff --git a/src/IKVM.Runtime/StubGen/StubGenerator.cs b/src/IKVM.Runtime/StubGen/StubGenerator.cs index 2706d4c187..9b6aa01982 100644 --- a/src/IKVM.Runtime/StubGen/StubGenerator.cs +++ b/src/IKVM.Runtime/StubGen/StubGenerator.cs @@ -951,7 +951,7 @@ object[] GetAnnotation(CustomAttribute cad) string GetAnnotationInterface(CustomAttribute cad) { var attr = cad.Constructor.DeclaringType.GetCustomAttribute(context.Resolver.ResolveRuntimeType(typeof(ImplementsAttribute).FullName), false); - if (attr != null) + if (attr.HasValue) { var interfaces = (string[])attr.Value.ConstructorArguments[0].Value; if (interfaces.Length == 1) diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index f7894b03ca..72ccbb4a81 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -599,8 +599,6 @@ void Save() mb.AddReference(referencedAssemblies[i].MainAssembly); } - mb.Complete(); - AddJavaModuleAttribute(mb); // add a package list and export map @@ -621,6 +619,9 @@ void Save() } } + // complete the module and all types + mb.Complete(); + if (targetIsModule) { Diagnostics.GenericCompilerInfo($"CompilerClassLoader saving {assemblyFile} in {assemblyDir}"); diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json index 7b5a3610e7..42c5223ee6 100644 --- a/src/ikvmstub/Properties/launchSettings.json +++ b/src/ikvmstub/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmstub": { "commandName": "Project", - "commandLineArgs": "--bootstrap --nostdlib --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Numerics.Vectors.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.Intrinsics.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"System.Runtime.Intrinsics.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.Intrinsics.dll\"" + "commandLineArgs": "--bootstrap --nostdlib --non-public-types --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\Microsoft.Win32.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Collections.Concurrent.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Collections.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Collections.NonGeneric.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Diagnostics.StackTrace.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Diagnostics.Tracing.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.IO.Compression.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.IO.MemoryMappedFiles.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Linq.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Memory.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Net.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Numerics.Vectors.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Emit.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Emit.ILGeneration.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Emit.Lightweight.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Resources.Writer.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.CompilerServices.Unsafe.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.InteropServices.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.Intrinsics.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.Loader.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.Algorithms.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.Encoding.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.X509Certificates.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Text.Encoding.Extensions.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Threading.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Threading.Overlapped.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Threading.ThreadPool.dll\" --reference:\"D:\\ikvm\\src\\IKVM.CoreLib\\obj\\Debug\\net6.0\\ref\\IKVM.CoreLib.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net6.0\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Reflection\\obj\\Debug\\net6.0\\ref\\IKVM.Reflection.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net6.0\\ref\\IKVM.Runtime.dll\" --reference:\"D:\\packages\\NuGet\\cache\\ikvm.bytecode\\9.1.3\\lib\\net6.0\\IKVM.ByteCode.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.collections.immutable\\8.0.0\\lib\\net6.0\\System.Collections.Immutable.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.io.pipelines\\8.0.0\\lib\\net6.0\\System.IO.Pipelines.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.reflection.metadata\\8.0.0\\lib\\net6.0\\System.Reflection.Metadata.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.encodings.web\\8.0.0\\lib\\net6.0\\System.Text.Encodings.Web.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.json\\8.0.4\\lib\\net6.0\\System.Text.Json.dll\" --out:\"IKVM.Runtime.jar\" \"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net6.0\\ref\\IKVM.Runtime.dll\"" } } } \ No newline at end of file diff --git a/src/ikvmstub/ikvmstub.csproj b/src/ikvmstub/ikvmstub.csproj index e66f94dc41..f3f5a41919 100644 --- a/src/ikvmstub/ikvmstub.csproj +++ b/src/ikvmstub/ikvmstub.csproj @@ -1,7 +1,7 @@  Exe - net8.0;net6.0;net472; + net6.0;net8.0;net472; $(_SupportedToolRuntimes) true true From 0c0660dde401797e16d3bcd41460c953b74034b6 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 2 Oct 2024 18:41:14 -0500 Subject: [PATCH 21/59] Almost..... --- ...ectionGenericTypeParameterSymbolBuilder.cs | 2 +- .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 4 +- .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 2 +- .../IIkvmReflectionTypeSymbol.cs | 2 +- .../IkvmReflectionEventTable.cs | 66 +++++++----- .../IkvmReflectionFieldTable.cs | 44 ++++++-- ...kvmReflectionGenericTypeParameterSymbol.cs | 2 +- ...IkvmReflectionGenericTypeParameterTable.cs | 4 +- .../IkvmReflectionMethodTable.cs | 7 +- .../IkvmReflectionModuleSymbol.cs | 4 +- .../IkvmReflectionModuleTable.cs | 8 +- .../IkvmReflectionParameterTable.cs | 2 +- .../IkvmReflectionPropertyTable.cs | 44 ++++++-- .../IkvmReflection/IkvmReflectionSymbol.cs | 3 +- .../IkvmReflectionTypeSpecTable.cs | 6 +- .../IkvmReflectionTypeSymbol.cs | 2 +- .../IkvmReflection/IkvmReflectionTypeTable.cs | 56 ++++++++-- .../ReflectionConstructorSymbolBuilder.cs | 11 ++ ...ectionGenericTypeParameterSymbolBuilder.cs | 2 +- .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 4 +- .../Emit/ReflectionMethodSymbolBuilder.cs | 2 +- .../Emit/ReflectionModuleSymbolBuilder.cs | 8 +- .../Emit/ReflectionTypeSymbolBuilder.cs | 2 +- .../Reflection/IReflectionTypeSymbol.cs | 2 +- .../ReflectionGenericTypeParameterSymbol.cs | 2 +- .../Reflection/ReflectionMethodSpecTable.cs | 10 +- .../Reflection/ReflectionMethodSymbol.cs | 2 +- .../Reflection/ReflectionModuleSymbol.cs | 2 +- .../Reflection/ReflectionTypeSpecTable.cs | 4 +- .../Reflection/ReflectionTypeSymbol.cs | 2 +- src/IKVM.Reflection/Universe.cs | 6 +- src/IKVM.Runtime/AttributeHelper.cs | 31 ++++-- src/IKVM.Runtime/IRuntimeSymbolResolver.cs | 8 ++ src/IKVM.Runtime/JVM.Resolver.cs | 42 +++++--- .../RuntimeByteCodeJavaType.FinishContext.cs | 3 +- .../ExportRuntimeSymbolResolver.cs | 14 +++ .../ImportAssemblyResolver.cs | 100 ++++++------------ .../ImportDiagnosticHandler.cs | 10 +- .../ImportRuntimeSymbolResolver.cs | 55 ++++++++-- src/IKVM.Tools.Importer/ImportTool.cs | 4 +- src/ikvmc/Properties/launchSettings.json | 12 +-- src/ikvmc/ikvmc.csproj | 2 +- 42 files changed, 388 insertions(+), 210 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs index 5e318922e5..3e455d9d83 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -153,7 +153,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IIkvmReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs index 339bb88c21..a1ee9f91d2 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -38,7 +38,7 @@ public IkvmReflectionModuleSymbolBuilder(IkvmReflectionSymbolContext context, II _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _module = _builder; - _typeTable = new IkvmReflectionTypeTable(context, this, null); + _typeTable = new IkvmReflectionTypeTable(context, this); _methodTable = new IkvmReflectionMethodTable(context, this, null); _fieldTable = new IkvmReflectionFieldTable(context, this, null); } @@ -60,7 +60,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) if (type.IsTypeDefinition()) return _typeTable.GetOrCreateTypeSymbol(type); else if (type.IsGenericType) - return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); else if (type.IsSZArray) return ResolveTypeSymbol(type.GetElementType()).GetOrCreateSZArrayTypeSymbol(); else if (type.IsArray) diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index 3ec41457e8..6c899d7fef 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -126,7 +126,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IIkvmReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs index b2dac0f006..9c3e762dc4 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs @@ -92,7 +92,7 @@ interface IIkvmReflectionTypeSymbol : IIkvmReflectionMemberSymbol, ITypeSymbol /// /// /// - IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition); + IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IIkvmReflectionTypeSymbol[] genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs index c131d4927c..1574b0f658 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Concurrent; using System.Reflection.Metadata.Ecma335; using System.Threading; @@ -21,6 +22,8 @@ struct IkvmReflectionEventTable IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; + ConcurrentDictionary? _byToken; + /// /// Initializes a new instance. /// @@ -47,46 +50,61 @@ public IIkvmReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) if (@event.Module.MetadataToken != _module.MetadataToken) throw new ArgumentException(nameof(@event)); + var token = @event is EventBuilder b ? b.GetEventToken().Token : @event.MetadataToken; + if (token == 0) + throw new InvalidOperationException(); + + // pseudo tokens: since IKVM.Reflection does not remove pseudo tokens after creation, we can keep using these + // but they are non-sequential per-type, so we need to use a real dictionary + if (token < 0) + { + // we fall back to lookup by name if there is no valid metadata token + if (_byToken == null) + Interlocked.CompareExchange(ref _byToken, new(), null); + + var value = (_context, _module, _type, @event); + return _byToken.GetOrAdd(token, _ => CreateEventSymbol(value._context, value._module, value._type, value.@event)); + } + // create lock on demand if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + Interlocked.CompareExchange(ref _lock, new(), null); using (_lock.CreateUpgradeableReadLock()) { - var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.MetadataToken)); + var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(token)); if (_table[row] == null) using (_lock.CreateWriteLock()) - return _table[row] ??= new IkvmReflectionEventSymbol(_context, _module, _type, @event); - else - return _table[row] ?? throw new InvalidOperationException(); + _table[row] ??= CreateEventSymbol(_context, _module, _type, @event); + + return _table[row] ?? throw new InvalidOperationException(); } } /// - /// Gets or creates the cached for the type by event. + /// Creates a new symbol. /// + /// + /// + /// /// /// - public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + static IIkvmReflectionEventSymbol CreateEventSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol type, EventInfo @event) { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - if (@event.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(@event)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); + if (@event is EventBuilder builder) + return new IkvmReflectionEventSymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, (IIkvmReflectionTypeSymbolBuilder)type, builder); + else + return new IkvmReflectionEventSymbol(context, module, type, @event); + } - using (_lock.CreateUpgradeableReadLock()) - { - var row = MetadataTokens.GetRowNumber(MetadataTokens.EventDefinitionHandle(@event.GetEventToken().Token)); - if (_table[row] == null) - using (_lock.CreateWriteLock()) - return (IIkvmReflectionEventSymbolBuilder)(_table[row] ??= new IkvmReflectionEventSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionTypeSymbolBuilder)_type, @event)); - else - return (IIkvmReflectionEventSymbolBuilder?)_table[row] ?? throw new InvalidOperationException(); - } + /// + /// Gets or creates the cached for the type by property. + /// + /// + /// + public IIkvmReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder property) + { + return (IIkvmReflectionEventSymbolBuilder)GetOrCreateEventSymbol((EventInfo)property); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs index 9158d9d19a..d493f35fae 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Concurrent; using System.Reflection.Metadata.Ecma335; using System.Threading; @@ -21,6 +22,8 @@ struct IkvmReflectionFieldTable IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; + ConcurrentDictionary? _byToken; + /// /// Initializes a new instance. /// @@ -47,24 +50,51 @@ public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) if (field.Module.MetadataToken != _module.MetadataToken) throw new ArgumentException(nameof(field)); + var token = field.MetadataToken; + if (token == 0) + throw new InvalidOperationException(); + + // pseudo tokens: since IKVM.Reflection does not remove pseudo tokens after creation, we can keep using these + // but they are non-sequential per-type, so we need to use a real dictionary + if (token < 0) + { + // we fall back to lookup by name if there is no valid metadata token + if (_byToken == null) + Interlocked.CompareExchange(ref _byToken, new(), null); + + var value = (_context, _module, _type, field); + return _byToken.GetOrAdd(token, _ => CreateFieldSymbol(value._context, value._module, value._type, value.field)); + } + // create lock on demand if (_lock == null) Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); using (_lock.CreateUpgradeableReadLock()) { - var row = MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(field.MetadataToken)); + var row = MetadataTokens.GetRowNumber(MetadataTokens.FieldDefinitionHandle(token)); if (_table[row] == null) using (_lock.CreateWriteLock()) - if (field is FieldBuilder builder) - return _table[row] ??= new IkvmReflectionFieldSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionTypeSymbolBuilder?)_type, builder); - else - return _table[row] ??= new IkvmReflectionFieldSymbol(_context, _module, _type, field); - else - return _table[row] ?? throw new InvalidOperationException(); + _table[row] ??= CreateFieldSymbol(_context, _module, _type, field); + + return _table[row] ?? throw new InvalidOperationException(); } } + /// + /// Creates a new symbol. + /// + /// + /// + /// + static IIkvmReflectionFieldSymbol CreateFieldSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type, FieldInfo field) + { + if (field is FieldBuilder builder) + return new IkvmReflectionFieldSymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, (IIkvmReflectionTypeSymbolBuilder?)type, builder); + else + return new IkvmReflectionFieldSymbol(context, module, type, field); + } + /// /// Gets or creates the cached for the type by field. /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs index ec027dd931..1b92b0131b 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs @@ -126,7 +126,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IIkvmReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs index 9bff410a3d..78633cd9f0 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs @@ -57,9 +57,9 @@ public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type gene if (_table[pos] == null) using (_lock.CreateWriteLock()) if (genericTypeParameter is GenericTypeParameterBuilder builder) - return _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionMemberSymbolBuilder)_member, builder); + _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionMemberSymbolBuilder)_member, builder); else - return _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbol(_context, _module, _member, genericTypeParameter); + _table[pos] ??= new IkvmReflectionGenericTypeParameterSymbol(_context, _module, _member, genericTypeParameter); return _table[pos] ?? throw new InvalidOperationException(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs index ec6a020171..bab5adf60d 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs @@ -75,11 +75,12 @@ public IIkvmReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase me using (_lock.CreateUpgradeableReadLock()) { - if (_table[token] == null) + var row = MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(token)); + if (_table[row] == null) using (_lock.CreateWriteLock()) - return _table[token] ??= CreateMethodBaseSymbol(_context, _module, _type, method); + _table[row] ??= CreateMethodBaseSymbol(_context, _module, _type, method); - return _table[token] ?? throw new InvalidOperationException(); + return _table[row] ?? throw new InvalidOperationException(); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index 806f0cb7c7..7c6fddcae0 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -34,7 +34,7 @@ public IkvmReflectionModuleSymbol(IkvmReflectionSymbolContext context, IIkvmRefl _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); _module = module ?? throw new ArgumentNullException(nameof(module)); - _typeTable = new IkvmReflectionTypeTable(context, this, null); + _typeTable = new IkvmReflectionTypeTable(context, this); _methodTable = new IkvmReflectionMethodTable(context, this, null); _fieldTable = new IkvmReflectionFieldTable(context, this, null); } @@ -251,7 +251,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) if (type.IsTypeDefinition()) return _typeTable.GetOrCreateTypeSymbol(type); else if (type.IsGenericType) - return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); else if (type.IsSZArray) return ResolveTypeSymbol(type.GetElementType()).GetOrCreateSZArrayTypeSymbol(); else if (type.IsArray) diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs index bb04071744..393695e15f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs @@ -51,11 +51,11 @@ public IIkvmReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) if (_moduleSymbols[row] == null) using (_moduleLock.CreateWriteLock()) if (module is ModuleBuilder builder) - return _moduleSymbols[row] = new IkvmReflectionModuleSymbolBuilder(_context, _assembly, builder); + _moduleSymbols[row] = new IkvmReflectionModuleSymbolBuilder(_context, _assembly, builder); else - return _moduleSymbols[row] = new IkvmReflectionModuleSymbol(_context, _assembly, module); - else - return _moduleSymbols[row] ?? throw new InvalidOperationException(); + _moduleSymbols[row] = new IkvmReflectionModuleSymbol(_context, _assembly, module); + + return _moduleSymbols[row] ?? throw new InvalidOperationException(); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs index 9f4452ec4f..87094d0dfe 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs @@ -60,7 +60,7 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p if (_table[position] == null) using (_lock.CreateWriteLock()) - return _table[position] ??= new IkvmReflectionParameterSymbol(_context, _module, _member, parameter); + _table[position] ??= new IkvmReflectionParameterSymbol(_context, _module, _member, parameter); return _table[position] ?? throw new InvalidOperationException(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs index 6718e08988..6e2c77442e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Concurrent; using System.Reflection.Metadata.Ecma335; using System.Threading; @@ -21,6 +22,8 @@ struct IkvmReflectionPropertyTable IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; + ConcurrentDictionary? _byToken; + /// /// Initializes a new instance. /// @@ -47,24 +50,51 @@ public IIkvmReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo prop if (property.Module.MetadataToken != _module.MetadataToken) throw new ArgumentException(nameof(property)); + var token = property.MetadataToken; + if (token == 0) + throw new InvalidOperationException(); + + // pseudo tokens: since IKVM.Reflection does not remove pseudo tokens after creation, we can keep using these + // but they are non-sequential per-type, so we need to use a real dictionary + if (token < 0) + { + // we fall back to lookup by name if there is no valid metadata token + if (_byToken == null) + Interlocked.CompareExchange(ref _byToken, new(), null); + + var value = (_context, _module, _type, property); + return _byToken.GetOrAdd(token, _ => CreatePropertySymbol(value._context, value._module, value._type, value.property)); + } + // create lock on demand if (_lock == null) Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); using (_lock.CreateUpgradeableReadLock()) { - var row = MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(property.MetadataToken)); + var row = MetadataTokens.GetRowNumber(MetadataTokens.PropertyDefinitionHandle(token)); if (_table[row] == null) using (_lock.CreateWriteLock()) - if (property is PropertyBuilder builder) - return _table[row] ??= new IkvmReflectionPropertySymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, (IIkvmReflectionTypeSymbolBuilder)_type, builder); - else - return _table[row] ??= new IkvmReflectionPropertySymbol(_context, _module, _type, property); - else - return _table[row] ?? throw new InvalidOperationException(); + _table[row] ??= CreatePropertySymbol(_context, _module, _type, property); + + return _table[row] ?? throw new InvalidOperationException(); } } + /// + /// Creates a new symbol. + /// + /// + /// + /// + static IIkvmReflectionPropertySymbol CreatePropertySymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol type, PropertyInfo property) + { + if (property is PropertyBuilder builder) + return new IkvmReflectionPropertySymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, (IIkvmReflectionTypeSymbolBuilder)type, builder); + else + return new IkvmReflectionPropertySymbol(context, module, type, property); + } + /// /// Gets or creates the cached for the type by property. /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs index fb4f446f2d..4d7ca6c37a 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs @@ -446,8 +446,7 @@ public virtual IIkvmReflectionPropertySymbolBuilder ResolvePropertySymbol(Proper var a = new CustomAttribute[attributes.Count]; for (int i = 0; i < attributes.Count; i++) - if (ResolveCustomAttribute(attributes[i]) is { } v) - a[i] = v; + a[i] = ResolveCustomAttribute(attributes[i]) ?? throw new InvalidOperationException(); return a; } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs index f52e96eb45..2f69be22f4 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs @@ -5,8 +5,6 @@ using IKVM.CoreLib.Collections; using IKVM.CoreLib.Threading; -using Type = IKVM.Reflection.Type; - namespace IKVM.CoreLib.Symbols.IkvmReflection { @@ -101,7 +99,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() /// /// /// - public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArguments) + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IIkvmReflectionTypeSymbol[] genericTypeArguments) { if (genericTypeArguments is null) throw new ArgumentNullException(nameof(genericTypeArguments)); @@ -112,7 +110,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericType if (_genericTypeSymbols == null) Interlocked.CompareExchange(ref _genericTypeSymbols, new(TypeSymbolListEqualityComparer.Instance), null); - return _genericTypeSymbols.GetOrAdd(_module.ResolveTypeSymbols(genericTypeArguments), CreateGenericTypeSymbol); + return _genericTypeSymbols.GetOrAdd(genericTypeArguments, CreateGenericTypeSymbol); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index 7a984642fc..f9ab22f98b 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -119,7 +119,7 @@ public IIkvmReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IIkvmReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IIkvmReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs index d089438c75..706ffe0124 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs @@ -1,10 +1,12 @@ using System; +using System.Collections.Concurrent; using System.Reflection.Metadata.Ecma335; using System.Threading; using IKVM.CoreLib.Collections; using IKVM.CoreLib.Symbols.IkvmReflection.Emit; using IKVM.CoreLib.Threading; +using IKVM.Reflection; using IKVM.Reflection.Emit; using Type = IKVM.Reflection.Type; @@ -17,23 +19,23 @@ struct IkvmReflectionTypeTable readonly IkvmReflectionSymbolContext _context; readonly IIkvmReflectionModuleSymbol _module; - readonly IIkvmReflectionTypeSymbol? _type; IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; + ConcurrentDictionary _byName; + ConcurrentDictionary? _byToken; + /// /// Initializes a new instance. /// /// /// - /// /// - public IkvmReflectionTypeTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type) + public IkvmReflectionTypeTable(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module) { _context = context ?? throw new ArgumentNullException(nameof(context)); _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type; } /// @@ -52,6 +54,32 @@ public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) if (type.IsTypeDefinition() == false) throw new ArgumentException(nameof(type)); + // IKVM.Reflection may deliver a missing type, without a token, so we are forced to index this by name + if (type.__IsMissing) + { + if (_byName == null) + Interlocked.CompareExchange(ref _byName, new(), null); + + var value = (_context, _module, type); + return _byName.GetOrAdd(type.FullName, _ => CreateTypeSymbol(value._context, value._module, value.type)); + } + + var token = type.MetadataToken; + if (token == 0) + throw new InvalidOperationException(); + + // pseudo tokens: since IKVM.Reflection does not remove pseudo tokens after creation, we can keep using these + // but they are non-sequential per-type, so we need to use a real dictionary + if (token < 0) + { + // we fall back to lookup by name if there is no valid metadata token + if (_byToken == null) + Interlocked.CompareExchange(ref _byToken, new(), null); + + var value = (_context, _module, type); + return _byToken.GetOrAdd(token, _ => CreateTypeSymbol(value._context, value._module, value.type)); + } + // create lock on demand if (_lock == null) Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); @@ -61,16 +89,26 @@ public IIkvmReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) var row = MetadataTokens.GetRowNumber(MetadataTokens.TypeDefinitionHandle(type.MetadataToken)); if (_table[row] == null) using (_lock.CreateWriteLock()) - if (_table[row] == null) - if (type is TypeBuilder builder) - return _table[row] = new IkvmReflectionTypeSymbolBuilder(_context, (IIkvmReflectionModuleSymbolBuilder)_module, builder); - else - return _table[row] = new IkvmReflectionTypeSymbol(_context, _module, type); + _table[row] ??= CreateTypeSymbol(_context, _module, type); return _table[row] ?? throw new InvalidOperationException(); } } + /// + /// Creates a new symbol. + /// + /// + /// + /// + static IIkvmReflectionTypeSymbol CreateTypeSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, Type type) + { + if (type is TypeBuilder builder) + return new IkvmReflectionTypeSymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, builder); + else + return new IkvmReflectionTypeSymbol(context, module, type); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index ba6d7c8b83..414a329efa 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -89,6 +89,17 @@ public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAtt #endregion + #region IMethodBaseSymbol + + /// + public override ITypeSymbol[] GetGenericArguments() + { + // constructor never has generic arguments + return []; + } + + #endregion + /// public override void OnComplete() { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs index 17651ec77a..6bced14f44 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs @@ -152,7 +152,7 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs index 03cd589a41..ac5e723377 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs @@ -124,10 +124,10 @@ public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBui public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; /// - public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; + public MethodImplAttributes MethodImplementationFlags => UnderlyingMethodBase.MethodImplementationFlags; /// - public ITypeSymbol[] GetGenericArguments() + public virtual ITypeSymbol[] GetGenericArguments() { return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index 43ab72c527..dc5b528dda 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -65,7 +65,7 @@ public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericT /// public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) { - return _specTable.GetOrCreateGenericMethodSymbol(method.GetGenericArguments()); + return _specTable.GetOrCreateGenericMethodSymbol(ResolveTypeSymbols(method.GetGenericArguments())); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index b671cc5e6e..9882c333a6 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -59,7 +59,7 @@ public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) if (type.IsTypeDefinition()) return _typeTable.GetOrCreateTypeSymbol(type); else if (type.IsGenericType) - return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); else if (type.IsSZArray()) return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateSZArrayTypeSymbol(); else if (type.IsArray) @@ -212,7 +212,7 @@ public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParame public void DefineManifestResource(string name, Stream stream, System.Reflection.ResourceAttributes attribute) { #if NETFRAMEWORK - UnderlyingModuleBuilder.DefineManifestResource(name, stream, attribute); + UnderlyingModuleBuilder.DefineManifestResource(name, stream, attribute); #else throw new NotSupportedException(); #endif @@ -222,7 +222,7 @@ public void DefineManifestResource(string name, Stream stream, System.Reflection public IResourceWriter DefineResource(string name, string description) { #if NETFRAMEWORK - return UnderlyingModuleBuilder.DefineResource(name, description); + return UnderlyingModuleBuilder.DefineResource(name, description); #else throw new NotImplementedException(); #endif @@ -232,7 +232,7 @@ public IResourceWriter DefineResource(string name, string description) public IResourceWriter DefineResource(string name, string description, System.Reflection.ResourceAttributes attribute) { #if NETFRAMEWORK - return UnderlyingModuleBuilder.DefineResource(name, description, attribute); + return UnderlyingModuleBuilder.DefineResource(name, description, attribute); #else throw new NotImplementedException(); #endif diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 92a173aad3..176f7d60c0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -125,7 +125,7 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs index 464cc4a3d5..edc48697a6 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs @@ -91,7 +91,7 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// /// /// - IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition); + IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs index 3fdc602d87..853b5e4f90 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs @@ -125,7 +125,7 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs index a01078ab08..63c4da0ece 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs @@ -13,7 +13,7 @@ struct ReflectionMethodSpecTable readonly IReflectionTypeSymbol? _type; readonly IReflectionMethodSymbol _method; - ConcurrentDictionary? _genericMethodSymbols; + ConcurrentDictionary? _genericMethodSymbols; /// /// Initializes a new instance. @@ -36,7 +36,7 @@ public ReflectionMethodSpecTable(ReflectionSymbolContext context, IReflectionMod /// /// /// - public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(Type[] genericTypeArguments) + public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(IReflectionTypeSymbol[] genericTypeArguments) { if (genericTypeArguments is null) throw new ArgumentNullException(nameof(genericTypeArguments)); @@ -45,7 +45,7 @@ public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(Type[] genericType throw new InvalidOperationException(); if (_genericMethodSymbols == null) - Interlocked.CompareExchange(ref _genericMethodSymbols, new(TypeListEqualityComparer.Instance), null); + Interlocked.CompareExchange(ref _genericMethodSymbols, new(TypeSymbolListEqualityComparer.Instance), null); return _genericMethodSymbols.GetOrAdd(genericTypeArguments, CreateGenericMethodSymbol); } @@ -55,9 +55,9 @@ public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(Type[] genericType /// /// /// - readonly IReflectionMethodSymbol CreateGenericMethodSymbol(Type[] genericTypeArguments) + readonly IReflectionMethodSymbol CreateGenericMethodSymbol(IReflectionTypeSymbol[] genericTypeArguments) { - return new ReflectionMethodSymbol(_context, _module, _type, _method.UnderlyingMethod.MakeGenericMethod(genericTypeArguments)); + return new ReflectionMethodSymbol(_context, _module, _type, _method.UnderlyingMethod.MakeGenericMethod(genericTypeArguments.Unpack())); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index 0b50048566..ada2a5653c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -44,7 +44,7 @@ public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericT /// public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) { - return _specTable.GetOrCreateGenericMethodSymbol(method.GetGenericArguments()); + return _specTable.GetOrCreateGenericMethodSymbol(ResolveTypeSymbols(method.GetGenericArguments())); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index c596f370e2..9bb62cf7c2 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -244,7 +244,7 @@ public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) if (type.IsTypeDefinition()) return _typeTable.GetOrCreateTypeSymbol(type); else if (type.IsGenericType) - return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(type.GetGenericArguments()); + return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); else if (type.IsSZArray()) return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateSZArrayTypeSymbol(); else if (type.IsArray) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs index 0f98f8180b..b83bdff39d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs @@ -99,7 +99,7 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() /// /// /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArguments) + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) { if (genericTypeArguments is null) throw new ArgumentNullException(nameof(genericTypeArguments)); @@ -110,7 +110,7 @@ public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeArgu if (_genericTypeSymbols == null) Interlocked.CompareExchange(ref _genericTypeSymbols, new(TypeSymbolListEqualityComparer.Instance), null); - return _genericTypeSymbols.GetOrAdd(_module.ResolveTypeSymbols(genericTypeArguments), CreateGenericTypeSymbol); + return _genericTypeSymbols.GetOrAdd(genericTypeArguments, CreateGenericTypeSymbol); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index 6e33a98679..1880246baa 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -118,7 +118,7 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() } /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(Type[] genericTypeDefinition) + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) { return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); } diff --git a/src/IKVM.Reflection/Universe.cs b/src/IKVM.Reflection/Universe.cs index 2c71d09935..bddb9da495 100644 --- a/src/IKVM.Reflection/Universe.cs +++ b/src/IKVM.Reflection/Universe.cs @@ -584,10 +584,10 @@ internal Assembly Load(string refname, Module requestingModule, bool throwOnErro if (asm != null) { + // cache assembly by both the lookup name and the resolved name var defname = asm.FullName; - if (refname != defname) - assembliesByName.Add(refname, asm); - + assembliesByName[refname] = asm; + assembliesByName[defname] = asm; return asm; } diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index ebdec4ceb6..46f8e86aa6 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -38,10 +38,6 @@ Jeroen Frijters using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols.Reflection; -#if IMPORTER -using IKVM.Tools.Importer; -#endif - namespace IKVM.Runtime { @@ -1048,18 +1044,33 @@ internal bool IsJavaModule(IModuleSymbol mod) internal object[] GetJavaModuleAttributes(IModuleSymbol mod) { - var attrs = new List(); + var l = mod.GetCustomAttributes(TypeOfJavaModuleAttribute); + var a = new object[l.Length]; - foreach (var cad in mod.GetCustomAttributes(TypeOfJavaModuleAttribute)) + for (int i = 0; i < l.Length; i++) { - var args = cad.ConstructorArguments; + JavaModuleAttribute attr; + + var args = l[i].ConstructorArguments; if (args.Length == 0) - attrs.Add(new JavaModuleAttribute()); + attr = new JavaModuleAttribute(); else - attrs.Add(new JavaModuleAttribute(DecodeArray(args[0]))); + attr = new JavaModuleAttribute(DecodeArray(args[0])); + + foreach (var arg in l[i].NamedArguments) + { + switch (arg.MemberName) + { + case nameof(JavaModuleAttribute.Jars): + attr.Jars = DecodeArray(arg.TypedValue); + break; + } + } + + a[i] = attr; } - return attrs.ToArray(); + return a; } internal bool IsNoPackagePrefix(ITypeSymbol type) diff --git a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs index 3d89c7c9a6..335c601179 100644 --- a/src/IKVM.Runtime/IRuntimeSymbolResolver.cs +++ b/src/IKVM.Runtime/IRuntimeSymbolResolver.cs @@ -49,6 +49,14 @@ interface IRuntimeSymbolResolver : ISymbolResolver /// ITypeSymbol ResolveRuntimeType(string typeName); + /// + /// Attempts to resolve the named type from the IKVM runtime assembly. + /// + /// + /// + /// + bool TryResolveRuntimeType(string typeName, out ITypeSymbol? type); + /// /// Resolves the known Java base assembly. /// diff --git a/src/IKVM.Runtime/JVM.Resolver.cs b/src/IKVM.Runtime/JVM.Resolver.cs index 83d23d67b8..d1603aa510 100644 --- a/src/IKVM.Runtime/JVM.Resolver.cs +++ b/src/IKVM.Runtime/JVM.Resolver.cs @@ -1,4 +1,6 @@ -using System; +#nullable enable + +using System; using System.Collections.Concurrent; using System.Collections.Generic; using System.ComponentModel; @@ -44,16 +46,16 @@ static IEnumerable GetSystemAssemblies() readonly ReflectionSymbolContext _symbols = new(); IAssemblySymbol _coreAssembly; - readonly ConcurrentDictionary _coreTypeCache = new(); + readonly ConcurrentDictionary _coreTypeCache = new(); IAssemblySymbol[] _systemAssemblies; - readonly ConcurrentDictionary _systemTypeCache = new(); + readonly ConcurrentDictionary _systemTypeCache = new(); IAssemblySymbol _runtimeAssembly; - readonly ConcurrentDictionary _runtimeTypeCache = new(); + readonly ConcurrentDictionary _runtimeTypeCache = new(); IAssemblySymbol _baseAssembly; - readonly ConcurrentDictionary _baseTypeCache = new(); + readonly ConcurrentDictionary _baseTypeCache = new(); /// /// Initializes a new instance. @@ -84,7 +86,7 @@ public IAssemblySymbol GetCoreAssembly() /// public ITypeSymbol ResolveCoreType(string typeName) { - return _coreTypeCache.GetOrAdd(typeName, ResolveCoreTypeImpl); + return _coreTypeCache.GetOrAdd(typeName, ResolveCoreTypeImpl) ?? throw new InvalidOperationException(); } /// @@ -92,7 +94,7 @@ public ITypeSymbol ResolveCoreType(string typeName) /// /// /// - ITypeSymbol ResolveCoreTypeImpl(string typeName) + ITypeSymbol? ResolveCoreTypeImpl(string typeName) { return _coreAssembly.GetType(typeName); } @@ -100,7 +102,7 @@ ITypeSymbol ResolveCoreTypeImpl(string typeName) /// public ITypeSymbol ResolveSystemType(string typeName) { - return _systemTypeCache.GetOrAdd(typeName, ResolveSystemTypeImpl); + return _systemTypeCache.GetOrAdd(typeName, FindSystemType) ?? throw new InvalidOperationException(); } /// @@ -108,7 +110,7 @@ public ITypeSymbol ResolveSystemType(string typeName) /// /// /// - ITypeSymbol ResolveSystemTypeImpl(string typeName) + ITypeSymbol? FindSystemType(string typeName) { foreach (var assembly in _systemAssemblies) if (assembly.GetType(typeName) is ITypeSymbol t) @@ -126,7 +128,21 @@ public IAssemblySymbol GetRuntimeAssembly() /// public ITypeSymbol ResolveRuntimeType(string typeName) { - return _runtimeTypeCache.GetOrAdd(typeName, ResolveRuntimeTypeImpl); + return _runtimeTypeCache.GetOrAdd(typeName, FindRuntimeType) ?? throw new InvalidOperationException(); + } + + /// + public bool TryResolveRuntimeType(string typeName, out ITypeSymbol? type) + { + var t = _runtimeTypeCache.GetOrAdd(typeName, FindRuntimeType); + if (t != null) + { + type = t; + return true; + } + + type = null; + return false; } /// @@ -134,7 +150,7 @@ public ITypeSymbol ResolveRuntimeType(string typeName) /// /// /// - ITypeSymbol ResolveRuntimeTypeImpl(string typeName) + ITypeSymbol? FindRuntimeType(string typeName) { return _runtimeAssembly.GetType(typeName); } @@ -148,11 +164,11 @@ public IAssemblySymbol GetBaseAssembly() /// public ITypeSymbol ResolveBaseType(string typeName) { - return _baseAssembly.GetType(typeName); + return _baseAssembly.GetType(typeName) ?? throw new InvalidOperationException(); } /// - public ITypeSymbol ResolveType(string typeName) + public ITypeSymbol? ResolveType(string typeName) { foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies()) if (assembly.GetType(typeName) is Type t) diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index a300dae6ed..06f473f1f3 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -388,8 +388,7 @@ internal ITypeSymbol FinishImpl() #if IMPORTER // see if there exists a "managed JNI" class for this type - var nativeCodeType = context.Resolver.ResolveRuntimeType("IKVM.Java.Externs." + classFile.Name.Replace("$", "+")); - if (nativeCodeType != null) + if (context.Resolver.TryResolveRuntimeType("IKVM.Java.Externs." + classFile.Name.Replace("$", "+"), out var nativeCodeType)) { if (!m.IsStatic) nargs = ArrayUtil.Concat(wrapper, args); diff --git a/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs index d994169864..ebbcf5ed5b 100644 --- a/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs +++ b/src/IKVM.Tools.Exporter/ExportRuntimeSymbolResolver.cs @@ -172,6 +172,20 @@ public ITypeSymbol ResolveRuntimeType(string typeName) return _runtimeTypeCache.GetOrAdd(typeName, FindRuntimeType) ?? throw new DiagnosticEventException(DiagnosticEvent.CriticalClassNotFound(typeName)); } + /// + public bool TryResolveRuntimeType(string typeName, out ITypeSymbol? type) + { + var t = _runtimeTypeCache.GetOrAdd(typeName, FindRuntimeType); + if (t != null) + { + type = t; + return true; + } + + type = null; + return false; + } + /// /// Attempts to load the specified runtime type. /// diff --git a/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs b/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs index b51a8be78b..89c9df5c29 100644 --- a/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs +++ b/src/IKVM.Tools.Importer/ImportAssemblyResolver.cs @@ -1,27 +1,4 @@ -/* - Copyright (C) 2010-2013 Jeroen Frijters - - This software is provided 'as-is', without any express or implied - warranty. In no event will the authors be held liable for any damages - arising from the use of this software. - - Permission is granted to anyone to use this software for any purpose, - including commercial applications, and to alter it and redistribute it - freely, subject to the following restrictions: - - 1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - 2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - 3. This notice may not be removed or altered from any source distribution. - - Jeroen Frijters - jeroen@frijters.net - -*/ -using System; +using System; using System.Collections.Generic; using System.IO; @@ -32,7 +9,7 @@ namespace IKVM.Tools.Importer { /// - /// Resolves assemblies from the universe of types. + /// Resolves assemblies for the universe of types. /// class ImportAssemblyResolver { @@ -41,7 +18,6 @@ class ImportAssemblyResolver readonly ImportOptions options; readonly IDiagnosticHandler diagnostics; readonly List libpaths = new List(); - readonly Version coreLibVersion; /// /// Initializes a new instance. @@ -69,12 +45,6 @@ public ImportAssemblyResolver(Universe universe, ImportOptions options, IDiagnos // add LIB environmental variable AddLibraryPaths(Environment.GetEnvironmentVariable("LIB") ?? "", false); - - // either load the corelib from the references, or from what already exists - if (options.NoStdLib) - coreLibVersion = LoadCoreLib(options.References).GetName().Version; - else - coreLibVersion = universe.Load(universe.CoreLibName).GetName().Version; } /// @@ -88,45 +58,30 @@ public ImportAssemblyResolver(Universe universe, ImportOptions options, IDiagnos /// /// /// - internal Assembly LoadFile(string path) + Assembly LoadFile(string path) { - string ex = null; - try { - using (var module = universe.OpenRawModule(path)) - { - if (coreLibVersion != null) - { - // to avoid problems (i.e. weird exceptions), we don't allow assemblies to load that reference a newer version of the corelib - foreach (var asmref in module.GetReferencedAssemblies()) - if (asmref.Name == universe.CoreLibName && asmref.Version > coreLibVersion) - throw new DiagnosticEventException(DiagnosticEvent.CoreAssemblyVersionMismatch(asmref.Name, universe.CoreLibName)); - } - - var asm = universe.LoadAssembly(module); - if (asm.Location != module.Location && CanonicalizePath(asm.Location) != CanonicalizePath(module.Location)) - diagnostics.AssemblyLocationIgnored(path, asm.Location, asm.FullName); + using var module = universe.OpenRawModule(path); + var asm = universe.LoadAssembly(module); + if (asm.Location != module.Location && CanonicalizePath(asm.Location) != CanonicalizePath(module.Location)) + diagnostics.AssemblyLocationIgnored(path, asm.Location, asm.FullName); - return asm; - } + return asm; } - catch (IOException x) + catch (IOException e) { - ex = x.Message; + diagnostics.ErrorReadingFile(path, e.Message); } - catch (UnauthorizedAccessException x) + catch (UnauthorizedAccessException e) { - ex = x.Message; + diagnostics.ErrorReadingFile(path, e.Message); } - catch (IKVM.Reflection.BadImageFormatException x) + catch (IKVM.Reflection.BadImageFormatException e) { - ex = x.Message; + diagnostics.ErrorReadingFile(path, e.Message); } - // TODO - Console.Error.WriteLine("Error: unable to load assembly '{0}'" + Environment.NewLine + " ({1})", path, ex); - Environment.Exit(1); return null; } @@ -177,14 +132,6 @@ static string CanonicalizePath(string path) return path; } - internal Assembly LoadWithPartialName(string name) - { - foreach (string path in FindAssemblyPath(name + ".dll")) - return LoadFile(path); - - return null; - } - internal bool ResolveReference(Dictionary cache, List references, string reference) { var files = Array.Empty(); @@ -250,6 +197,10 @@ public Assembly AssemblyResolve(object sender, IKVM.Reflection.ResolveEventArgs if (Match(asm.GetName(), name)) return asm; + // try to locate from library paths + foreach (var lib in FindAssemblyPath(name.Name + ".dll")) + return LoadFile(lib); + if (args.RequestingAssembly != null) return universe.CreateMissingAssembly(args.Name); @@ -318,8 +269,6 @@ Assembly LoadCoreLib(IList references) foreach (var coreLib in FindAssemblyPath(universe.CoreLibName + ".dll")) return LoadFile(coreLib); - Console.Error.WriteLine($"Error: unable to find '{universe.CoreLibName}.dll'."); - Environment.Exit(1); return null; } @@ -337,6 +286,19 @@ IEnumerable FindAssemblyPath(string path) } else { + // check that named assembly exists in references + foreach (var reference in options.References) + { + if (File.Exists(reference) && Path.GetFileName(reference) == path) + yield return reference; + + // for legacy compat, we try again after appending .dll + var p = path + ".dll"; + if (File.Exists(reference) && Path.GetFileName(reference) == p) + yield return reference; + } + + // check for files in libpaths foreach (var libpath in libpaths) { var p = Path.Combine(libpath, path); diff --git a/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs b/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs index 53d32a8a19..474603051b 100644 --- a/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs +++ b/src/IKVM.Tools.Importer/ImportDiagnosticHandler.cs @@ -30,12 +30,14 @@ public ImportDiagnosticHandler(ImportOptions options, string spec, DiagnosticFor /// public override bool IsEnabled(Diagnostic diagnostic) { - //if (diagnostic.Level is DiagnosticLevel.Trace or DiagnosticLevel.Info) - // return false; - - if (diagnostic.Level == DiagnosticLevel.Warning && _options.NoWarn.Any(i => i.Id == diagnostic.Id)) + // trace messages aren't useful for the command line + if (diagnostic.Level is DiagnosticLevel.Trace) return false; + // nowarn empty means all + if (diagnostic.Level == DiagnosticLevel.Warning && _options.NoWarn != null) + return _options.NoWarn.Length == 0 || _options.NoWarn.Any(i => i == diagnostic) == false; + return true; } diff --git a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs index eed6535111..c0e42bdb28 100644 --- a/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs +++ b/src/IKVM.Tools.Importer/ImportRuntimeSymbolResolver.cs @@ -3,6 +3,7 @@ using System; using System.Collections.Concurrent; using System.Collections.Generic; +using System.IO; using System.Linq; using IKVM.CoreLib.Diagnostics; @@ -40,7 +41,7 @@ static IEnumerable GetSystemTypeNames() readonly IDiagnosticHandler _diagnostics; readonly Universe _universe; readonly IkvmReflectionSymbolContext _symbols; - readonly bool _bootstrap; + readonly ImportOptions _options; IAssemblySymbol? _coreAssembly; readonly ConcurrentDictionary _coreTypeCache = new(); @@ -67,7 +68,7 @@ public ImportRuntimeSymbolResolver(IDiagnosticHandler diagnostics, Universe univ _diagnostics = diagnostics ?? throw new ArgumentNullException(nameof(diagnostics)); _universe = universe ?? throw new ArgumentNullException(nameof(universe)); _symbols = symbols ?? throw new ArgumentNullException(nameof(symbols)); - _bootstrap = options.Bootstrap; + _options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -90,10 +91,26 @@ public IAssemblySymbol GetRuntimeAssembly() /// IAssemblySymbol? FindRuntimeAssembly() { + // search for already loaded runtime foreach (var assembly in _universe.GetAssemblies()) if (assembly.GetType("IKVM.Runtime.JVM") is Type) return GetSymbol(assembly); + // user explicitly specified path to runtime + if (_options.Runtime != null) + if (_options.Runtime.Exists) + return GetSymbol(_universe.LoadFile(_options.Runtime.FullName)); + + // fallback to resolution against universe + try + { + return GetSymbol(_universe.Load("IKVM.Runtime")); + } + catch (FileNotFoundException) + { + // ignore, we tried + } + return null; } @@ -101,7 +118,7 @@ public IAssemblySymbol GetRuntimeAssembly() public IAssemblySymbol? GetBaseAssembly() { // bootstrap mode is used for builing the main assembly, and thus should not return the existing base assembly - if (_bootstrap) + if (_options.Bootstrap) return null; return (_baseAssembly ??= FindBaseAssembly()) ?? throw new DiagnosticEventException(DiagnosticEvent.BootstrapClassesMissing()); @@ -116,6 +133,16 @@ public IAssemblySymbol GetRuntimeAssembly() if (assembly.GetType("java.lang.Object") is Type) return GetSymbol(assembly); + // fallback to resolution against universe + try + { + return GetSymbol(_universe.Load("IKVM.Java")); + } + catch (FileNotFoundException) + { + // ignore, we tried + } + return null; } @@ -167,15 +194,29 @@ public ITypeSymbol ResolveSystemType(string typeName) } /// - public ITypeSymbol? ResolveRuntimeType(string typeName) + public ITypeSymbol ResolveRuntimeType(string typeName) + { + return GetRuntimeAssembly().GetType(typeName) ?? throw new TypeLoadException(); + } + + /// + public bool TryResolveRuntimeType(string typeName, out ITypeSymbol? type) { - return GetRuntimeAssembly().GetType(typeName); + var t = GetRuntimeAssembly().GetType(typeName); + if (t != null) + { + type = t; + return true; + } + + type = null; + return false; } /// - public ITypeSymbol? ResolveBaseType(string typeName) + public ITypeSymbol ResolveBaseType(string typeName) { - return GetBaseAssembly().GetType(typeName); + return GetBaseAssembly()?.GetType(typeName) ?? throw new TypeLoadException(); } /// diff --git a/src/IKVM.Tools.Importer/ImportTool.cs b/src/IKVM.Tools.Importer/ImportTool.cs index 6dd53d2323..c853fdd929 100644 --- a/src/IKVM.Tools.Importer/ImportTool.cs +++ b/src/IKVM.Tools.Importer/ImportTool.cs @@ -152,8 +152,8 @@ ImportAssemblyResolver CreateResolver(IDiagnosticHandler diagnostics, ImportOpti // warn when unable to resolve a member universe.ResolvedMissingMember += (Module requestingModule, MemberInfo member) => { - if (requestingModule != null && member is IKVM.Reflection.Type) - diagnostics.UnableToResolveType(requestingModule.Name, ((IKVM.Reflection.Type)member).FullName, member.Module.FullyQualifiedName); + if (requestingModule != null && member is IKVM.Reflection.Type type) + diagnostics.UnableToResolveType(requestingModule.Name, type.FullName, member.Module.FullyQualifiedName); }; // enable embedded symbol writer diff --git a/src/ikvmc/Properties/launchSettings.json b/src/ikvmc/Properties/launchSettings.json index 02b8e637e6..65eabd5773 100644 --- a/src/ikvmc/Properties/launchSettings.json +++ b/src/ikvmc/Properties/launchSettings.json @@ -1,8 +1,8 @@ { - "profiles": { - "ikvmc": { - "commandName": "Project", - "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java.runtime.win\\obj\\Debug\\net8.0\\IKVM.Java.runtime.win.ikvmc.rsp" - } + "profiles": { + "ikvmc": { + "commandName": "Project", + "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net472\\IKVM.Java.ikvmc.rsp" } -} + } +} \ No newline at end of file diff --git a/src/ikvmc/ikvmc.csproj b/src/ikvmc/ikvmc.csproj index 939ff4bbc3..89cfd5c007 100644 --- a/src/ikvmc/ikvmc.csproj +++ b/src/ikvmc/ikvmc.csproj @@ -1,7 +1,7 @@  Exe - net8.0;net472;net6.0 + net472;net8.0;net6.0 $(_SupportedToolRuntimes) true true From 5b464a51c18555d0a079e6922009d28e473be940 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 2 Oct 2024 21:09:56 -0500 Subject: [PATCH 22/59] Formatting. --- src/IKVM.Runtime/JVM.Properties.cs | 691 ++++++++++++++--------------- 1 file changed, 345 insertions(+), 346 deletions(-) diff --git a/src/IKVM.Runtime/JVM.Properties.cs b/src/IKVM.Runtime/JVM.Properties.cs index 589833449a..f97f9f49ea 100644 --- a/src/IKVM.Runtime/JVM.Properties.cs +++ b/src/IKVM.Runtime/JVM.Properties.cs @@ -11,122 +11,122 @@ namespace IKVM.Runtime { - static partial class JVM - { - - /// - /// Property values loaded into the JVM from various sources. - /// - public static class Properties - { - - /// - /// Represents an entry in the IKVM properties. - /// - internal record struct IkvmPropEntry(string BasePath, string Value); - - static readonly IDictionary user = new Dictionary(); - static readonly Lazy> ikvm = new Lazy>(GetIkvmProperties); - static readonly Lazy> init = new Lazy>(GetInitProperties); - static readonly Lazy homePath = new Lazy(GetHomePath); - - /// - /// Gets the set of properties that are set by the user before initialization. Modification of values in this - /// dictionary must happen early in the program's initialization before any Java code has been accessed or - /// run. - /// - public static IDictionary User => user; - - /// - /// Gets the set of properties that are set in the 'ikvm.properties' file before initialization. - /// - internal static IReadOnlyDictionary Ikvm => ikvm.Value; - - /// - /// Gets the set of properties that are initialized with the JVM and provided to the JDK. - /// - internal static IReadOnlyDictionary Init => init.Value; - - /// - /// Gets the home path. - /// - internal static string HomePath => homePath.Value; - - /// - /// Gets the raw search paths to examine for ikvm.properties. - /// - /// - static IEnumerable GetIkvmPropertiesSearchPathsIter() - { - if (AppContext.BaseDirectory is string basePath && !string.IsNullOrEmpty(basePath)) - yield return basePath; - - if (AppDomain.CurrentDomain.BaseDirectory is string appBasePath && !string.IsNullOrEmpty(appBasePath)) - yield return appBasePath; - - // search upwards from the location of IKVM.Runtime - // we do this because IKVM.Runtime may be in runtimes/{rid}/lib - if (typeof(Properties).Assembly.Location is string runtimeAssemblyPath && !string.IsNullOrEmpty(runtimeAssemblyPath)) - foreach (var parent in GetParentDirs(runtimeAssemblyPath)) - yield return parent; - } - - /// - /// Returns an iteration of each parent path of the given path until the root. - /// - /// - /// - static IEnumerable GetParentDirs(string path) - { - while (string.IsNullOrWhiteSpace(path = Path.GetDirectoryName(path)) == false) - yield return path; - } - - /// - /// Gets the unique search paths to examine for ikvm.properties. - /// - /// - static IEnumerable GetIkvmPropertiesSearchPaths() - { - return GetIkvmPropertiesSearchPathsIter().Distinct(); - } - - /// - /// Gets the set of properties loaded from any companion 'ikvm.properties' file. - /// - /// - static Dictionary GetIkvmProperties() - { - var props = new Dictionary(); - - foreach (var basePath in GetIkvmPropertiesSearchPaths()) - { - var ikvmPropertiesPath = Path.Combine(basePath, "ikvm.properties"); - if (File.Exists(ikvmPropertiesPath)) - { - LoadProperties(basePath, File.ReadAllLines(ikvmPropertiesPath), props); - break; - } - } - - return props; - } - - /// - /// Gets the home path for IKVM. - /// - /// - static string GetHomePath() - { - // user value takes priority - if (User.TryGetValue("ikvm.home", out var userHomePath) && !string.IsNullOrWhiteSpace(userHomePath)) - if (Directory.Exists(Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, userHomePath)))) - return Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, userHomePath)); - - // ikvm properties value comes next - if (Ikvm.TryGetValue("ikvm.home", out var ikvmHomeEntry) && !string.IsNullOrWhiteSpace(ikvmHomeEntry.Value)) - if (Directory.Exists(Path.GetFullPath(Path.Combine(ikvmHomeEntry.BasePath, ikvmHomeEntry.Value)))) - return Path.GetFullPath(Path.Combine(ikvmHomeEntry.BasePath, ikvmHomeEntry.Value)); + static partial class JVM + { + + /// + /// Property values loaded into the JVM from various sources. + /// + public static class Properties + { + + /// + /// Represents an entry in the IKVM properties. + /// + internal record struct IkvmPropEntry(string BasePath, string Value); + + static readonly IDictionary user = new Dictionary(); + static readonly Lazy> ikvm = new Lazy>(GetIkvmProperties); + static readonly Lazy> init = new Lazy>(GetInitProperties); + static readonly Lazy homePath = new Lazy(GetHomePath); + + /// + /// Gets the set of properties that are set by the user before initialization. Modification of values in this + /// dictionary must happen early in the program's initialization before any Java code has been accessed or + /// run. + /// + public static IDictionary User => user; + + /// + /// Gets the set of properties that are set in the 'ikvm.properties' file before initialization. + /// + internal static IReadOnlyDictionary Ikvm => ikvm.Value; + + /// + /// Gets the set of properties that are initialized with the JVM and provided to the JDK. + /// + internal static IReadOnlyDictionary Init => init.Value; + + /// + /// Gets the home path. + /// + internal static string HomePath => homePath.Value; + + /// + /// Gets the raw search paths to examine for ikvm.properties. + /// + /// + static IEnumerable GetIkvmPropertiesSearchPathsIter() + { + if (AppContext.BaseDirectory is string basePath && !string.IsNullOrEmpty(basePath)) + yield return basePath; + + if (AppDomain.CurrentDomain.BaseDirectory is string appBasePath && !string.IsNullOrEmpty(appBasePath)) + yield return appBasePath; + + // search upwards from the location of IKVM.Runtime + // we do this because IKVM.Runtime may be in runtimes/{rid}/lib + if (typeof(Properties).Assembly.Location is string runtimeAssemblyPath && !string.IsNullOrEmpty(runtimeAssemblyPath)) + foreach (var parent in GetParentDirs(runtimeAssemblyPath)) + yield return parent; + } + + /// + /// Returns an iteration of each parent path of the given path until the root. + /// + /// + /// + static IEnumerable GetParentDirs(string path) + { + while (string.IsNullOrWhiteSpace(path = Path.GetDirectoryName(path)) == false) + yield return path; + } + + /// + /// Gets the unique search paths to examine for ikvm.properties. + /// + /// + static IEnumerable GetIkvmPropertiesSearchPaths() + { + return GetIkvmPropertiesSearchPathsIter().Distinct(); + } + + /// + /// Gets the set of properties loaded from any companion 'ikvm.properties' file. + /// + /// + static Dictionary GetIkvmProperties() + { + var props = new Dictionary(); + + foreach (var basePath in GetIkvmPropertiesSearchPaths()) + { + var ikvmPropertiesPath = Path.Combine(basePath, "ikvm.properties"); + if (File.Exists(ikvmPropertiesPath)) + { + LoadProperties(basePath, File.ReadAllLines(ikvmPropertiesPath), props); + break; + } + } + + return props; + } + + /// + /// Gets the home path for IKVM. + /// + /// + static string GetHomePath() + { + // user value takes priority + if (User.TryGetValue("ikvm.home", out var userHomePath) && !string.IsNullOrWhiteSpace(userHomePath)) + if (Directory.Exists(Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, userHomePath)))) + return Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, userHomePath)); + + // ikvm properties value comes next + if (Ikvm.TryGetValue("ikvm.home", out var ikvmHomeEntry) && !string.IsNullOrWhiteSpace(ikvmHomeEntry.Value)) + if (Directory.Exists(Path.GetFullPath(Path.Combine(ikvmHomeEntry.BasePath, ikvmHomeEntry.Value)))) + return Path.GetFullPath(Path.Combine(ikvmHomeEntry.BasePath, ikvmHomeEntry.Value)); #if NET // specified home directory in runtime.json, where path is relative to application @@ -150,15 +150,15 @@ static string GetHomePath() } #endif - // find first occurance of home root - if (User.TryGetValue("ikvm.home.root", out var userHomeRoot) && !string.IsNullOrWhiteSpace(userHomeRoot)) - if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, userHomeRoot))) is string userHomeRootPath) - return userHomeRootPath; + // find first occurance of home root + if (User.TryGetValue("ikvm.home.root", out var userHomeRoot) && !string.IsNullOrWhiteSpace(userHomeRoot)) + if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, userHomeRoot))) is string userHomeRootPath) + return userHomeRootPath; - // ikvm properties value comes next - if (Ikvm.TryGetValue("ikvm.home.root", out var ikvmHomeRootEntry) && !string.IsNullOrWhiteSpace(ikvmHomeRootEntry.Value)) - if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(ikvmHomeRootEntry.BasePath, ikvmHomeRootEntry.Value))) is string ikvmHomeRootPath) - return ikvmHomeRootPath; + // ikvm properties value comes next + if (Ikvm.TryGetValue("ikvm.home.root", out var ikvmHomeRootEntry) && !string.IsNullOrWhiteSpace(ikvmHomeRootEntry.Value)) + if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(ikvmHomeRootEntry.BasePath, ikvmHomeRootEntry.Value))) is string ikvmHomeRootPath) + return ikvmHomeRootPath; #if NET // specified home root directory in runtime.json, where path is relative to application @@ -182,106 +182,105 @@ static string GetHomePath() } #endif - // fallback to directory in base dir - if (string.IsNullOrWhiteSpace(AppContext.BaseDirectory) == false) - if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, "ikvm"))) is string appHomeRootPath) - return appHomeRootPath; - - // fallback to directory in base dir - if (string.IsNullOrWhiteSpace(AppDomain.CurrentDomain.BaseDirectory) == false) - if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "ikvm"))) is string domainHomeRootPath) - return domainHomeRootPath; - - throw new InternalException("Could not locate ikvm home path."); - } - - /// - /// Scans the given root path for the home for the currently executing runtime. - /// - /// - /// - static string ResolveHomePathFromRoot(string homePathRoot) - { - // calculate ikvm.home from ikvm.home.root - if (Directory.Exists(homePathRoot)) - { - foreach (var rid in RuntimeUtil.SupportedRuntimeIdentifiers) - { - var ikvmHomePath = Path.GetFullPath(Path.Combine(homePathRoot, rid)); - if (Directory.Exists(ikvmHomePath)) - return ikvmHomePath; - } - } - - return null; - } - - /// - /// Reads the property lines from the specified file into the dictionary. - /// - /// - /// - static void LoadProperties(string basePath, IEnumerable lines, Dictionary props) - { - foreach (var l in lines) - { - var a = l.Split(new[] { '=' }, 2, StringSplitOptions.RemoveEmptyEntries); - if (a.Length >= 2) - props[a[0].Trim()] = new IkvmPropEntry(basePath, a[1]?.Trim() ?? ""); - } - } - - /// - /// Gets the set of init properties. - /// - /// - static Dictionary GetInitProperties() - { + // fallback to directory in base dir + if (string.IsNullOrWhiteSpace(AppContext.BaseDirectory) == false) + if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(AppContext.BaseDirectory, "ikvm"))) is string appHomeRootPath) + return appHomeRootPath; + + // fallback to directory in base dir + if (string.IsNullOrWhiteSpace(AppDomain.CurrentDomain.BaseDirectory) == false) + if (ResolveHomePathFromRoot(Path.GetFullPath(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "ikvm"))) is string domainHomeRootPath) + return domainHomeRootPath; + + throw new InternalException("Could not locate ikvm home path."); + } + + /// + /// Scans the given root path for the home for the currently executing runtime. + /// + /// + /// + static string ResolveHomePathFromRoot(string homePathRoot) + { + // calculate ikvm.home from ikvm.home.root + if (Directory.Exists(homePathRoot)) + { + foreach (var rid in RuntimeUtil.SupportedRuntimeIdentifiers) + { + var ikvmHomePath = Path.GetFullPath(Path.Combine(homePathRoot, rid)); + if (Directory.Exists(ikvmHomePath)) + return ikvmHomePath; + } + } + + return null; + } + + /// + /// Reads the property lines from the specified file into the dictionary. + /// + /// + /// + static void LoadProperties(string basePath, IEnumerable lines, Dictionary props) + { + foreach (var l in lines) + { + var a = l.Split(new[] { '=' }, 2, StringSplitOptions.RemoveEmptyEntries); + if (a.Length >= 2) + props[a[0].Trim()] = new IkvmPropEntry(basePath, a[1]?.Trim() ?? ""); + } + } + + /// + /// Gets the set of init properties. + /// + /// + static Dictionary GetInitProperties() + { #if FIRST_PASS || IMPORTER || EXPORTER throw new NotImplementedException(); #else - var p = new Dictionary(); - InitSystemProperties(p); - return p; + var p = new Dictionary(); + InitSystemProperties(p); + return p; #endif - } - - /// - /// Initialize system properties key and value. - /// - /// - static void InitSystemProperties(Dictionary p) - { + } + + /// + /// Initialize system properties key and value. + /// + /// + static void InitSystemProperties(Dictionary p) + { #if FIRST_PASS || IMPORTER || EXPORTER - throw new NotImplementedException(); + throw new NotImplementedException(); #else - p["openjdk.version"] = Constants.openjdk_version; - p["java.vm.name"] = Constants.java_vm_name; - p["java.vm.version"] = Constants.java_vm_version; - p["java.vm.vendor"] = Constants.java_vm_vendor; - p["java.vm.specification.name"] = "Java Virtual Machine Specification"; - p["java.vm.specification.version"] = Constants.java_vm_specification_version; - p["java.vm.specification.vendor"] = Constants.java_vm_specification_vendor; - p["java.vm.info"] = "compiled mode"; - p["java.runtime.name"] = Constants.java_runtime_name; - p["java.runtime.version"] = Constants.java_runtime_version; - - // various directory paths - p["ikvm.home"] = HomePath; - p["java.home"] = HomePath; - p["java.library.path"] = GetLibraryPath(); - p["java.ext.dirs"] = Path.Combine(HomePath, "lib", "ext"); - p["java.endorsed.dirs"] = Path.Combine(HomePath, "lib", "endorsed"); - p["sun.boot.library.path"] = GetBootLibraryPath(); - p["sun.boot.class.path"] = VfsTable.GetAssemblyClassesPath(Vfs.Context, Context.Resolver.ResolveBaseAssembly().AsReflection(), HomePath); - p["sun.cds.enableSharedLookupCache"] = "false"; - - // unlimited direct memory - p["sun.nio.MaxDirectMemorySize"] = "-1"; - - // default to FORK on OSX, instead of posix_spawn with jspawnhelper - if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX)) - p["jdk.lang.Process.launchMechanism"] = "FORK"; + p["openjdk.version"] = Constants.openjdk_version; + p["java.vm.name"] = Constants.java_vm_name; + p["java.vm.version"] = Constants.java_vm_version; + p["java.vm.vendor"] = Constants.java_vm_vendor; + p["java.vm.specification.name"] = "Java Virtual Machine Specification"; + p["java.vm.specification.version"] = Constants.java_vm_specification_version; + p["java.vm.specification.vendor"] = Constants.java_vm_specification_vendor; + p["java.vm.info"] = "compiled mode"; + p["java.runtime.name"] = Constants.java_runtime_name; + p["java.runtime.version"] = Constants.java_runtime_version; + + // various directory paths + p["java.home"] = HomePath; + p["java.library.path"] = GetLibraryPath(); + p["java.ext.dirs"] = Path.Combine(HomePath, "lib", "ext"); + p["java.endorsed.dirs"] = Path.Combine(HomePath, "lib", "endorsed"); + p["sun.boot.library.path"] = GetBootLibraryPath(); + p["sun.boot.class.path"] = VfsTable.GetAssemblyClassesPath(Vfs.Context, Context.Resolver.GetBaseAssembly().AsReflection(), HomePath); + p["sun.cds.enableSharedLookupCache"] = "false"; + + // unlimited direct memory + p["sun.nio.MaxDirectMemorySize"] = "-1"; + + // default to FORK on OSX, instead of posix_spawn with jspawnhelper + if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX)) + p["jdk.lang.Process.launchMechanism"] = "FORK"; #if NETFRAMEWORK // read properties from app.config @@ -310,138 +309,138 @@ static void InitSystemProperties(Dictionary p) } #endif - // set the properties that were specfied - if (user != null) - foreach (var kvp in user) - p[kvp.Key] = kvp.Value; + // set the properties that were specfied + if (user != null) + foreach (var kvp in user) + p[kvp.Key] = kvp.Value; #endif - } - - /// - /// Gets the path string for loading native libraries. - /// - /// - static string GetLibraryPath() - { + } + + /// + /// Gets the path string for loading native libraries. + /// + /// + static string GetLibraryPath() + { #if FIRST_PASS || IMPORTER || EXPORTER throw new NotImplementedException(); #else - var libraryPath = new List(); - - if (RuntimeUtil.IsWindows) - { - // see /hotspot/src/os/windows/vm/os_windows.cpp for the comment that describes how we build the path - var windir = SafeGetEnvironmentVariable("SystemRoot"); - if (windir != null) - libraryPath.Add(Path.Combine(windir, "Sun", "Java", "bin")); - - try - { - libraryPath.Add(Environment.SystemDirectory); - } - catch (SecurityException) - { - - } - - if (windir != null) - libraryPath.Add(windir); - - var path = SafeGetEnvironmentVariable("PATH"); - if (path != null) - foreach (var i in path.Split(Path.PathSeparator)) - libraryPath.Add(i); - } - - if (RuntimeUtil.IsLinux) - { - // on Linux we have some hardcoded paths (from /hotspot/src/os/linux/vm/os_linux.cpp) - // and we can only guess the cpu arch based on bitness (that means only x86 and x64) - libraryPath.Add(Path.Combine("/usr/java/packages/lib/", IntPtr.Size == 4 ? "i386" : "amd64")); - libraryPath.Add("/lib"); - libraryPath.Add("/usr/lib"); - - // prefix with LD_LIBRARY_PATH - var ld_library_path = SafeGetEnvironmentVariable("LD_LIBRARY_PATH"); - if (ld_library_path != null) - foreach (var i in ld_library_path.Split(Path.PathSeparator).Reverse()) - libraryPath.Insert(0, i); - } - - if (RuntimeUtil.IsOSX) - { - var home = SafeGetEnvironmentVariable("HOME"); - if (home != null) - libraryPath.Add(Path.Combine(home, "Library/Java/Extensions")); - - libraryPath.Add("/Library/Java/Extensions"); - libraryPath.Add("/Network/Library/Java/Extensions"); - libraryPath.Add("/System/Library/Java/Extensions"); - libraryPath.Add("/usr/lib/java"); - - // prefix with JAVA_LIBRARY_PATH - var javaLibraryPath = SafeGetEnvironmentVariable("JAVA_LIBRARY_PATH"); - if (javaLibraryPath != null) - foreach (var i in javaLibraryPath.Split(Path.PathSeparator)) - libraryPath.Add(i); - - // prefix with DYLD_LIBRARY_PATH - var dyldLibraryPath = SafeGetEnvironmentVariable("DYLD_LIBRARY_PATH"); - if (dyldLibraryPath != null) - foreach (var i in dyldLibraryPath.Split(Path.PathSeparator)) - libraryPath.Add(i); - - if (home != null) - libraryPath.Add(home); - - libraryPath.Add("."); - } - - try - { - var l = new List(); - - foreach (var d in GetIkvmPropertiesSearchPaths()) - { - l.Add(d); - foreach (var rid in RuntimeUtil.SupportedRuntimeIdentifiers) - l.Add(Path.Combine(d, "runtimes", rid, "native")); - } - - libraryPath.InsertRange(0, l); - } - catch (Exception) - { - // ignore - } - - if (RuntimeUtil.IsWindows) - libraryPath.Add("."); - - return string.Join(Path.PathSeparator.ToString(), libraryPath.Distinct()); + var libraryPath = new List(); + + if (RuntimeUtil.IsWindows) + { + // see /hotspot/src/os/windows/vm/os_windows.cpp for the comment that describes how we build the path + var windir = SafeGetEnvironmentVariable("SystemRoot"); + if (windir != null) + libraryPath.Add(Path.Combine(windir, "Sun", "Java", "bin")); + + try + { + libraryPath.Add(Environment.SystemDirectory); + } + catch (SecurityException) + { + + } + + if (windir != null) + libraryPath.Add(windir); + + var path = SafeGetEnvironmentVariable("PATH"); + if (path != null) + foreach (var i in path.Split(Path.PathSeparator)) + libraryPath.Add(i); + } + + if (RuntimeUtil.IsLinux) + { + // on Linux we have some hardcoded paths (from /hotspot/src/os/linux/vm/os_linux.cpp) + // and we can only guess the cpu arch based on bitness (that means only x86 and x64) + libraryPath.Add(Path.Combine("/usr/java/packages/lib/", IntPtr.Size == 4 ? "i386" : "amd64")); + libraryPath.Add("/lib"); + libraryPath.Add("/usr/lib"); + + // prefix with LD_LIBRARY_PATH + var ld_library_path = SafeGetEnvironmentVariable("LD_LIBRARY_PATH"); + if (ld_library_path != null) + foreach (var i in ld_library_path.Split(Path.PathSeparator).Reverse()) + libraryPath.Insert(0, i); + } + + if (RuntimeUtil.IsOSX) + { + var home = SafeGetEnvironmentVariable("HOME"); + if (home != null) + libraryPath.Add(Path.Combine(home, "Library/Java/Extensions")); + + libraryPath.Add("/Library/Java/Extensions"); + libraryPath.Add("/Network/Library/Java/Extensions"); + libraryPath.Add("/System/Library/Java/Extensions"); + libraryPath.Add("/usr/lib/java"); + + // prefix with JAVA_LIBRARY_PATH + var javaLibraryPath = SafeGetEnvironmentVariable("JAVA_LIBRARY_PATH"); + if (javaLibraryPath != null) + foreach (var i in javaLibraryPath.Split(Path.PathSeparator)) + libraryPath.Add(i); + + // prefix with DYLD_LIBRARY_PATH + var dyldLibraryPath = SafeGetEnvironmentVariable("DYLD_LIBRARY_PATH"); + if (dyldLibraryPath != null) + foreach (var i in dyldLibraryPath.Split(Path.PathSeparator)) + libraryPath.Add(i); + + if (home != null) + libraryPath.Add(home); + + libraryPath.Add("."); + } + + try + { + var l = new List(); + + foreach (var d in GetIkvmPropertiesSearchPaths()) + { + l.Add(d); + foreach (var rid in RuntimeUtil.SupportedRuntimeIdentifiers) + l.Add(Path.Combine(d, "runtimes", rid, "native")); + } + + libraryPath.InsertRange(0, l); + } + catch (Exception) + { + // ignore + } + + if (RuntimeUtil.IsWindows) + libraryPath.Add("."); + + return string.Join(Path.PathSeparator.ToString(), libraryPath.Distinct()); #endif - } - - /// - /// Gets the boot library paths. - /// - /// - static IEnumerable GetBootLibraryPathsIter() - { - yield return Path.Combine(HomePath, "bin"); - } - - /// - /// Gets the boot library paths - /// - /// - static string GetBootLibraryPath() - { - return string.Join(Path.PathSeparator.ToString(), GetBootLibraryPathsIter()); - } - - } - - } + } + + /// + /// Gets the boot library paths. + /// + /// + static IEnumerable GetBootLibraryPathsIter() + { + yield return Path.Combine(HomePath, "bin"); + } + + /// + /// Gets the boot library paths + /// + /// + static string GetBootLibraryPath() + { + return string.Join(Path.PathSeparator.ToString(), GetBootLibraryPathsIter()); + } + + } + + } } From c6f5b095cea6450ac01a9fa6bb99afb26175787c Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Thu, 3 Oct 2024 00:12:52 -0500 Subject: [PATCH 23/59] Remove debug stuff. --- Directory.Build.props | 4 ---- src/ikvmc/Properties/launchSettings.json | 8 -------- src/ikvmstub/Properties/launchSettings.json | 8 -------- 3 files changed, 20 deletions(-) delete mode 100644 src/ikvmc/Properties/launchSettings.json delete mode 100644 src/ikvmstub/Properties/launchSettings.json diff --git a/Directory.Build.props b/Directory.Build.props index bc21f1c585..bde86f5e56 100644 --- a/Directory.Build.props +++ b/Directory.Build.props @@ -7,10 +7,6 @@ win-x64;win-x86;win-arm64;linux-x64;linux-arm;linux-arm64;linux-musl-x64;linux-musl-arm;linux-musl-arm64;osx-x64;osx-arm64 $(SupportedImageRuntimes) - win-x64;win-x86 - win-x64;win-x86 - win-x64;win-x86 - <_SupportedRuntimes>;$(SupportedRuntimes); <_EnabledRuntimes>;$(EnabledRuntimes); <_SupportedToolRuntimes>;$(SupportedToolRuntimes); diff --git a/src/ikvmc/Properties/launchSettings.json b/src/ikvmc/Properties/launchSettings.json deleted file mode 100644 index 65eabd5773..0000000000 --- a/src/ikvmc/Properties/launchSettings.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "profiles": { - "ikvmc": { - "commandName": "Project", - "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net472\\IKVM.Java.ikvmc.rsp" - } - } -} \ No newline at end of file diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json deleted file mode 100644 index 42c5223ee6..0000000000 --- a/src/ikvmstub/Properties/launchSettings.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "profiles": { - "ikvmstub": { - "commandName": "Project", - "commandLineArgs": "--bootstrap --nostdlib --non-public-types --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\Microsoft.Win32.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Collections.Concurrent.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Collections.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Collections.NonGeneric.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Diagnostics.StackTrace.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Diagnostics.Tracing.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.IO.Compression.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.IO.MemoryMappedFiles.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Linq.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Memory.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Net.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Numerics.Vectors.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Emit.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Emit.ILGeneration.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Emit.Lightweight.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Reflection.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Resources.Writer.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.CompilerServices.Unsafe.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.InteropServices.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.Intrinsics.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Runtime.Loader.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.Algorithms.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.Encoding.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Security.Cryptography.X509Certificates.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Text.Encoding.Extensions.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Threading.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Threading.Overlapped.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\6.0.33\\ref\\net6.0\\System.Threading.ThreadPool.dll\" --reference:\"D:\\ikvm\\src\\IKVM.CoreLib\\obj\\Debug\\net6.0\\ref\\IKVM.CoreLib.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net6.0\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Reflection\\obj\\Debug\\net6.0\\ref\\IKVM.Reflection.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net6.0\\ref\\IKVM.Runtime.dll\" --reference:\"D:\\packages\\NuGet\\cache\\ikvm.bytecode\\9.1.3\\lib\\net6.0\\IKVM.ByteCode.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.collections.immutable\\8.0.0\\lib\\net6.0\\System.Collections.Immutable.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.io.pipelines\\8.0.0\\lib\\net6.0\\System.IO.Pipelines.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.reflection.metadata\\8.0.0\\lib\\net6.0\\System.Reflection.Metadata.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.encodings.web\\8.0.0\\lib\\net6.0\\System.Text.Encodings.Web.dll\" --reference:\"D:\\packages\\NuGet\\cache\\system.text.json\\8.0.4\\lib\\net6.0\\System.Text.Json.dll\" --out:\"IKVM.Runtime.jar\" \"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net6.0\\ref\\IKVM.Runtime.dll\"" - } - } -} \ No newline at end of file From 672d456782ab5d9d21d1a9b8a3c6de445b782fb3 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 4 Oct 2024 16:21:16 -0500 Subject: [PATCH 24/59] Allow GetMethods when incomplete. --- .../IkvmReflectionSymbolTests.cs | 61 ++++++++---- .../Reflection/ReflectionSymbolTests.cs | 28 ++++++ src/IKVM.CoreLib/Symbols/IMethodSymbol.cs | 4 +- .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 70 ++++++++++++-- .../IkvmReflectionAssemblySymbol.cs | 2 +- .../IkvmReflectionMemberSymbol.cs | 2 +- .../IkvmReflectionModuleSymbol.cs | 2 +- .../IkvmReflectionParameterSymbol.cs | 2 +- .../Emit/ReflectionMemberSymbolBuilder.cs | 2 +- .../Emit/ReflectionMethodSymbolBuilder.cs | 1 + .../Emit/ReflectionTypeSymbolBuilder.cs | 69 ++++++++++++-- .../Reflection/ReflectionAssemblySymbol.cs | 3 + .../Reflection/ReflectionMemberSymbol.cs | 2 + .../Reflection/ReflectionModuleSymbol.cs | 3 + .../Reflection/ReflectionParameterSymbol.cs | 3 + src/IKVM.CoreLib/Symbols/SymbolUtil.cs | 94 +++++++++++++++++++ .../java/lang/invoke/MethodHandleTests.java | 84 +++++------------ src/IKVM.Runtime/ByteCodeHelper.cs | 1 + src/IKVM.Runtime/ReflectUtil.cs | 4 +- .../java/lang/invoke/MethodHandleTests.cs | 25 ++++- src/ikvmc/Properties/launchSettings.json | 8 ++ src/ikvmc/ikvmc.csproj | 2 +- 22 files changed, 364 insertions(+), 108 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/SymbolUtil.cs create mode 100644 src/ikvmc/Properties/launchSettings.json diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index ab284d995b..721eefcd68 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -4,6 +4,7 @@ using FluentAssertions; +using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.IkvmReflection; using IKVM.CoreLib.Symbols.IkvmReflection.Emit; using IKVM.Reflection; @@ -251,7 +252,7 @@ class ClassWithAttributeWithType [TestMethod] public void CanReadCustomAttributes() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); var v = a.Value.ConstructorArguments[0].Value; @@ -261,7 +262,7 @@ public void CanReadCustomAttributes() [TestMethod] public void CanResolveAssemblyBuilder() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var assemblySymbol = c.GetOrCreateAssemblySymbol(a); assemblySymbol.Should().BeOfType(); @@ -271,7 +272,7 @@ public void CanResolveAssemblyBuilder() [TestMethod] public void CanResolveModuleBuilder() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var moduleSymbol = c.GetOrCreateModuleSymbol(m); @@ -282,7 +283,7 @@ public void CanResolveModuleBuilder() [TestMethod] public void CanResolveTypeBuilder() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); @@ -295,7 +296,7 @@ public void CanResolveTypeBuilder() [TestMethod] public void CanResolveMultipleTypeBuilders() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); @@ -314,7 +315,7 @@ public void CanResolveMultipleTypeBuilders() [TestMethod] public void CanResolveMethodBuilder() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -328,7 +329,7 @@ public void CanResolveMethodBuilder() [TestMethod] public void CanResolveMultipleMethodBuilders() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -347,7 +348,7 @@ public void CanResolveMultipleMethodBuilders() [TestMethod] public void CanResolveFieldBuilder() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -361,7 +362,7 @@ public void CanResolveFieldBuilder() [TestMethod] public void CanResolveMultipleFieldBuilders() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -380,7 +381,7 @@ public void CanResolveMultipleFieldBuilders() [TestMethod] public void CanResolvePropertyBuilder() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); @@ -394,12 +395,12 @@ public void CanResolvePropertyBuilder() [TestMethod] public void CanResolveMultiplePropertyBuilders() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); - var property1 = t.DefineProperty("DynamicProperty1", PropertyAttributes.None, coreAssembly.GetType("System.Object"), []); + var property1 = t.DefineProperty("DynamicProperty1", PropertyAttributes.None, coreAssembly!.GetType("System.Object"), []); var property1Symbol = c.GetOrCreatePropertySymbol(property1); property1Symbol.Should().BeOfType(); property1Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property1)); @@ -413,12 +414,12 @@ public void CanResolveMultiplePropertyBuilders() [TestMethod] public void CanResolveEventBuilder() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); - var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly.GetType("System.EventHandler")); + var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly!.GetType("System.EventHandler")); var event1Symbol = c.GetOrCreateEventSymbol(event1); event1Symbol.Should().BeOfType(); event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); @@ -427,12 +428,12 @@ public void CanResolveEventBuilder() [TestMethod] public void CanResolveMultipleEventBuilders() { - var c = new IkvmReflectionSymbolContext(universe); + var c = new IkvmReflectionSymbolContext(universe!); var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); var t = m.DefineType("DynamicType"); - var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly.GetType("System.EventHandler")); + var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly!.GetType("System.EventHandler")); var event1Symbol = c.GetOrCreateEventSymbol(event1); event1Symbol.Should().BeOfType(); event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); @@ -443,6 +444,34 @@ public void CanResolveMultipleEventBuilders() event2Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event2)); } + [TestMethod] + public void CanGetMethodsFromTypeBuilder() + { + var c = new IkvmReflectionSymbolContext(universe!); + var a = c.DefineAssembly(new AssemblyNameInfo("DynamicAssembly")); + var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); + var type = m.DefineType("DynamicType"); + + var method = type.DefineMethod("DynamicMethod1", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); + var il = method.GetILGenerator(); + il.Emit(System.Reflection.Emit.OpCodes.Ret); + + // before complete + type.GetMethods().Should().HaveCount(5); + var incompleteMethod = type.GetMethod("DynamicMethod1"); + + // complete the type + type.Complete(); + + // after complete + type.GetMethods().Should().HaveCount(5); + var completeMethod = type.GetMethod("DynamicMethod1"); + + // all the methods should be the same + incompleteMethod.Should().BeSameAs(completeMethod); + incompleteMethod.Should().BeSameAs(method); + } + } } diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index 5d01df9423..f0219bf6fd 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -421,6 +421,34 @@ public void CanCompleteTypeBuilder() moduleSymbol.GetType("DynamicType1").Should().BeSameAs(type1Symbol); } + [TestMethod] + public void CanGetMethodsFromTypeBuilder() + { + var c = new ReflectionSymbolContext(); + var a = c.DefineAssembly(new AssemblyNameInfo("DynamicAssembly")); + var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); + var type = m.DefineType("DynamicType"); + + var method = type.DefineMethod("DynamicMethod1", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); + var il = method.GetILGenerator(); + il.Emit(OpCodes.Ret); + + // before complete + type.GetMethods().Should().HaveCount(5); + var incompleteMethod = type.GetMethod("DynamicMethod1"); + + // complete the type + type.Complete(); + + // after complete + type.GetMethods().Should().HaveCount(5); + var completeMethod = type.GetMethod("DynamicMethod1"); + + // all the methods should be the same + incompleteMethod.Should().BeSameAs(completeMethod); + incompleteMethod.Should().BeSameAs(method); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs index 06709a3679..c3c8d5c9e0 100644 --- a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs @@ -1,6 +1,4 @@ -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols +namespace IKVM.CoreLib.Symbols { /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index 6c899d7fef..c59ad45077 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -1,4 +1,6 @@ using System; +using System.Collections.Generic; +using System.Linq; using System.Runtime.InteropServices; using IKVM.CoreLib.Symbols.Emit; @@ -23,6 +25,8 @@ class IkvmReflectionTypeSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkvm IkvmReflectionGenericTypeParameterTable _genericTypeParameterTable; IkvmReflectionTypeSpecTable _specTable; + List? _incompleteMethods; + /// /// Initializes a new instance. /// @@ -237,31 +241,46 @@ public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, IType /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention)); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention)); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes)); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes)); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// @@ -516,6 +535,9 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) /// public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); + /// + public override bool IsComplete => _builder == null; + /// public int GetArrayRank() { @@ -726,13 +748,19 @@ public IMemberSymbol[] GetMembers() /// public IMethodSymbol? GetMethod(string name) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); + else + return GetIncompleteMethods().FirstOrDefault(i => i.Name == name); } /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + else + throw new NotImplementedException(); } /// @@ -750,7 +778,10 @@ public IMemberSymbol[] GetMembers() /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + else + throw new NotImplementedException(); } /// @@ -762,13 +793,31 @@ public IMemberSymbol[] GetMembers() /// public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); + if (IsComplete) + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); + else + return GetIncompleteMethods(bindingAttr); } /// public IMethodSymbol[] GetMethods() { - return ResolveMethodSymbols(UnderlyingType.GetMethods()); + if (IsComplete) + return ResolveMethodSymbols(UnderlyingType.GetMethods()); + else + return GetIncompleteMethods(); + } + + /// + /// Gets the set of incomplete methods. + /// + /// + IMethodSymbol[] GetIncompleteMethods(System.Reflection.BindingFlags bindingAttr = System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance) + { + if (_incompleteMethods == null) + return []; + else + return SymbolUtil.FilterMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); } /// @@ -897,6 +946,7 @@ public void Complete() { _type = _builder.CreateType(); _builder = null; + _incompleteMethods = null; } // force module to reresolve diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index b5c1d3dd1e..2feec1bc0b 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -181,7 +181,7 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion /// - public override string ToString() => UnderlyingAssembly.ToString(); + public override string? ToString() => UnderlyingAssembly.ToString(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs index b9d3222320..f491b412a4 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs @@ -209,7 +209,7 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion /// - public override string ToString() => UnderlyingMember.ToString()!; + public override string? ToString() => UnderlyingMember.ToString(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs index 7c6fddcae0..bdd3567c0b 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleSymbol.cs @@ -327,7 +327,7 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p #endregion /// - public override string ToString() => UnderlyingModule.ToString()!; + public override string? ToString() => UnderlyingModule.ToString(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs index 98fb45d390..99e2905812 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterSymbol.cs @@ -122,7 +122,7 @@ public ITypeSymbol[] GetRequiredCustomModifiers() #endregion /// - public override string ToString() => UnderlyingParameter.ToString()!; + public override string? ToString() => UnderlyingParameter.ToString(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs index d3c13c2050..b0ee71636d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs @@ -298,7 +298,7 @@ public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @e public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; /// - public virtual int MetadataToken => UnderlyingMember.MetadataToken; + public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); /// public virtual string Name => UnderlyingMember.Name; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index dc5b528dda..c071e4f5f2 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -2,6 +2,7 @@ using System.Reflection; using System.Reflection.Emit; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 176f7d60c0..7eede6c1d7 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -1,4 +1,6 @@ using System; +using System.Collections.Generic; +using System.Linq; using System.Reflection; using System.Reflection.Emit; using System.Runtime.InteropServices; @@ -22,6 +24,8 @@ class ReflectionTypeSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionTy ReflectionGenericTypeParameterTable _genericTypeParameterTable; ReflectionTypeSpecTable _specTable; + List? _incompleteMethods; + /// /// Initializes a new instance. /// @@ -236,31 +240,46 @@ public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, IType /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention)); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention)); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes)); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes)); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { - return ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); + _incompleteMethods ??= []; + _incompleteMethods.Add(m); + return m; } /// @@ -527,6 +546,9 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) /// public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); + /// + public override bool IsComplete => _builder == null; + /// public int GetArrayRank() { @@ -737,13 +759,19 @@ public IMemberSymbol[] GetMembers() /// public IMethodSymbol? GetMethod(string name) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); + else + return GetIncompleteMethods().FirstOrDefault(i => i.Name == name); } /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + else + throw new NotImplementedException(); } /// @@ -761,7 +789,10 @@ public IMemberSymbol[] GetMembers() /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + else + throw new NotImplementedException(); } /// @@ -773,13 +804,31 @@ public IMemberSymbol[] GetMembers() /// public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { - return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); + if (IsComplete) + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); + else + return GetIncompleteMethods(bindingAttr); } /// public IMethodSymbol[] GetMethods() { - return ResolveMethodSymbols(UnderlyingType.GetMethods()); + if (IsComplete) + return ResolveMethodSymbols(UnderlyingType.GetMethods()); + else + return GetIncompleteMethods(); + } + + /// + /// Gets the set of incomplete methods. + /// + /// + IMethodSymbol[] GetIncompleteMethods(System.Reflection.BindingFlags bindingAttr = System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance) + { + if (_incompleteMethods == null) + return []; + else + return SymbolUtil.FilterMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index c922a5b4d3..f589ea11de 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -177,6 +177,9 @@ public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + /// + public override string? ToString() => UnderlyingAssembly.ToString(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 3baf997db5..b97fa7aa7e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -208,6 +208,8 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + public override string? ToString() => UnderlyingMember.ToString(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 9bb62cf7c2..7f1bd1ed16 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -319,6 +319,9 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param #endregion + /// + public override string? ToString() => UnderlyingModule.ToString(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index cffe5c8ecb..23bfcf04c7 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -126,6 +126,9 @@ public ITypeSymbol[] GetRequiredCustomModifiers() #endregion + /// + public override string? ToString() => UnderlyingParameter.ToString(); + } } diff --git a/src/IKVM.CoreLib/Symbols/SymbolUtil.cs b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs new file mode 100644 index 0000000000..7727345ac2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs @@ -0,0 +1,94 @@ +using System.Collections.Generic; + +namespace IKVM.CoreLib.Symbols +{ + + static class SymbolUtil + { + + /// + /// Returns true if the given binding flags match, combined with the specified state. + /// + /// + /// + /// + /// + /// + static bool BindingFlagsMatch(bool state, System.Reflection.BindingFlags flags, System.Reflection.BindingFlags trueFlag, System.Reflection.BindingFlags falseFlag) + { + return (state && (flags & trueFlag) == trueFlag) || (!state && (flags & falseFlag) == falseFlag); + } + + /// + /// Evaluates whether the specified would match the . + /// + /// + /// + /// + public static bool BindingFlagsMatch(IMethodSymbol member, System.Reflection.BindingFlags flags) + { + return BindingFlagsMatch(member.IsPublic, flags, System.Reflection.BindingFlags.Public, System.Reflection.BindingFlags.NonPublic) + && BindingFlagsMatch(member.IsStatic, flags, System.Reflection.BindingFlags.Static, System.Reflection.BindingFlags.Instance); + } + + /// + /// Evaluates whether the specified would match the . + /// + /// + /// + /// + public static bool BindingFlagsMatchInherited(IMethodSymbol method, System.Reflection.BindingFlags flags) + { + return BindingFlagsMatch(method.IsPublic, flags, System.Reflection.BindingFlags.Public, System.Reflection.BindingFlags.NonPublic) + && BindingFlagsMatch(method.IsStatic, flags, System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.FlattenHierarchy, System.Reflection.BindingFlags.Instance); + } + + /// + /// Filters the set of methods by the binding attributes. + /// + /// + public static IEnumerable FilterMethods(ITypeSymbol type, IEnumerable methods, System.Reflection.BindingFlags bindingAttr = System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance) + { + var list = new HashSet(); + + foreach (var mb in methods) + { + var mi = mb as IMethodSymbol; + if (mi != null && BindingFlagsMatch(mi, bindingAttr)) + if (list.Add(mi)) + yield return mi; + } + + if ((bindingAttr & System.Reflection.BindingFlags.DeclaredOnly) == 0) + { + var baseMethods = new List(); + foreach (var mi in list) + if (mi.IsVirtual) + baseMethods.Add(mi.GetBaseDefinition()); + + for (var baseType = type.BaseType; baseType != null; baseType = baseType.BaseType) + { + foreach (var mi in baseType.GetMethods(System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance)) + { + if (BindingFlagsMatchInherited(mi, bindingAttr)) + { + if (mi.IsVirtual) + { + baseMethods ??= []; + if (baseMethods.Contains(mi.GetBaseDefinition())) + continue; + + baseMethods.Add(mi.GetBaseDefinition()); + } + + if (list.Add(mi)) + yield return mi; + } + } + } + } + } + + } + +} diff --git a/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java b/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java index 1a74e96b27..40b6ae0c45 100644 --- a/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java +++ b/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java @@ -19,75 +19,39 @@ public static String addStringStatic(String a, String b) { } - interface AddItf { - void apply(List st, int idx, Object v) throws Throwable; - } - @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() - public void canInvokeVirtual() throws Throwable { - MethodHandles.Lookup lookup = MethodHandles.lookup(); - MethodType mt = MethodType.methodType(String.class, String.class, String.class); - MethodHandle mh = lookup.findVirtual(TestClass.class, "addString", mt); - String s = (String)mh.invoke(new TestClass(), (Object)"a", (Object)"b"); + public void canInvokeExactVirtual() throws Throwable { + MethodHandles.Lookup lookup = getLookup(); + MethodType mt = getMethodType(); + MethodHandle mh = getMethodHandle(lookup, mt); + String s = invokeIt(mh); if (!s.equals("ab")) { throw new Exception(s); } } - @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() - public void canInvokeStatic() throws Throwable { - MethodHandles.Lookup lookup = MethodHandles.lookup(); - MethodType mt = MethodType.methodType(String.class, String.class, String.class); - MethodHandle mh = lookup.findStatic(TestClass.class, "addStringStatic", mt); - String s = (String)mh.invoke((Object)"a", (Object)"b"); - if (!s.equals("ab")) { - throw new Exception(s); - } + @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) + MethodHandles.Lookup getLookup() throws Throwable + { + return MethodHandles.lookup(); } - - @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() - public void canInvokeExactVirtual() throws Throwable { - MethodHandles.Lookup lookup = MethodHandles.lookup(); - MethodType mt = MethodType.methodType(String.class, String.class, String.class); - MethodHandle mh = lookup.findVirtual(TestClass.class, "addString", mt); - String s = (String)mh.invokeExact(new TestClass(), "a", "b"); - if (!s.equals("ab")) { - throw new Exception(s); - } + + @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) + MethodType getMethodType() throws Throwable + { + return MethodType.methodType(String.class, String.class, String.class); } - - @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() - public void canInvokeExactStatic() throws Throwable { - MethodHandles.Lookup lookup = MethodHandles.lookup(); - MethodType mt = MethodType.methodType(String.class, String.class, String.class); - MethodHandle mh = lookup.findStatic(TestClass.class, "addStringStatic", mt); - String s = (String)mh.invokeExact("a", "b"); - if (!s.equals("ab")) { - throw new Exception(s); - } + + @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) + MethodHandle getMethodHandle(MethodHandles.Lookup lookup, MethodType mt) throws Throwable + { + return lookup.findVirtual(TestClass.class, "addString", mt); } - - @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() - public void canInvokeStaticMethodThatReturnsVoid() throws Throwable { - MethodHandles.Lookup lookup = MethodHandles.lookup(); - MethodType pmt = MethodType.methodType(void.class, int.class, Object.class); - MethodHandle pms = lookup.findVirtual(List.class, "add", pmt); - List list = new ArrayList<>(); - pms.invoke(list, 0, "Hi"); - AddItf pf2 = pms::invoke; - pf2.apply(list, 1, "there"); - AddItf pf3 = pms::invokeExact; - pf3.apply(list, 2, "you"); - - if (!list.get(0).equals("Hi")) { - throw new Exception(list.get(0)); - }; - if (!list.get(1).equals("there")) { - throw new Exception(list.get(1)); - }; - if (!list.get(2).equals("you")) { - throw new Exception(list.get(2)); - }; + + @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) + String invokeIt(MethodHandle mh) throws Throwable + { + return (String)mh.invokeExact(new TestClass(), "a", "b"); } } diff --git a/src/IKVM.Runtime/ByteCodeHelper.cs b/src/IKVM.Runtime/ByteCodeHelper.cs index 942f28550e..5ba3bd6354 100644 --- a/src/IKVM.Runtime/ByteCodeHelper.cs +++ b/src/IKVM.Runtime/ByteCodeHelper.cs @@ -1112,6 +1112,7 @@ public static Exception DynamicMapException(Exception x, MapFlags mode, global:: #endif } + [MethodImpl(MethodImplOptions.NoInlining)] public static T GetDelegateForInvokeExact(object methodHandle) where T : class, Delegate { diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index beca070d4d..a87e8132c4 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -97,13 +97,13 @@ internal static bool ContainsTypeBuilder(ITypeSymbol type) type = type.GetElementType(); if (!type.IsGenericType || type.IsGenericTypeDefinition) - return type.AsReflection() is TypeBuilder; + return type is ITypeSymbolBuilder; foreach (var arg in type.GetGenericArguments()) if (ContainsTypeBuilder(arg)) return true; - return type.GetGenericTypeDefinition().AsReflection() is TypeBuilder; + return type.GetGenericTypeDefinition() is ITypeSymbolBuilder; } internal static bool IsDynamicMethod(IMethodSymbol method) diff --git a/src/IKVM.Tests/Java/java/lang/invoke/MethodHandleTests.cs b/src/IKVM.Tests/Java/java/lang/invoke/MethodHandleTests.cs index e6a594c06d..29ed961075 100644 --- a/src/IKVM.Tests/Java/java/lang/invoke/MethodHandleTests.cs +++ b/src/IKVM.Tests/Java/java/lang/invoke/MethodHandleTests.cs @@ -1,4 +1,9 @@ -using Microsoft.VisualStudio.TestTools.UnitTesting; +using IKVM.Runtime; + +using java.lang; +using java.lang.invoke; + +using Microsoft.VisualStudio.TestTools.UnitTesting; namespace IKVM.Tests.Java.java.lang.invoke { @@ -7,7 +12,25 @@ namespace IKVM.Tests.Java.java.lang.invoke public class MethodHandleTests { + class TestClass + { + + public int Int32Method() + { + return 1; + } + + } + [TestMethod] + public void CanInvokeExactForVirtualWithReturn() + { + var lookup = MethodHandles.lookup(); + var mt = MethodType.methodType(JVM.Context.PrimitiveJavaTypeFactory.INT.ClassObject); + var mh = lookup.findVirtual((Class)ClassLiteral.Value, "Int32Method", mt); + var d = ByteCodeHelper.GetDelegateForInvokeExact>(mh); + var s = d.Invoke(new TestClass()); + } } diff --git a/src/ikvmc/Properties/launchSettings.json b/src/ikvmc/Properties/launchSettings.json new file mode 100644 index 0000000000..1506066246 --- /dev/null +++ b/src/ikvmc/Properties/launchSettings.json @@ -0,0 +1,8 @@ +{ + "profiles": { + "ikvmc": { + "commandName": "Project", + "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java.Tests\\obj\\Debug\\net8.0\\IKVM.Java.Tests.ikvmc.rsp" + } + } +} \ No newline at end of file diff --git a/src/ikvmc/ikvmc.csproj b/src/ikvmc/ikvmc.csproj index 89cfd5c007..939ff4bbc3 100644 --- a/src/ikvmc/ikvmc.csproj +++ b/src/ikvmc/ikvmc.csproj @@ -1,7 +1,7 @@  Exe - net472;net8.0;net6.0 + net8.0;net472;net6.0 $(_SupportedToolRuntimes) true true From 0f1f1be10a60c4fa9236f96ba0fb9df8e0b2edde Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 4 Oct 2024 17:12:26 -0500 Subject: [PATCH 25/59] Remove invoking base generic type definition for delegate invoke method. Instead, we now support GetMethod properly on the delegate type itself using _incompleteMethods. --- .../IkvmReflectionSymbolTests.cs | 24 +++++++++++++++++++ src/IKVM.Runtime/MethodHandleUtil.compiler.cs | 9 +------ 2 files changed, 25 insertions(+), 8 deletions(-) diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index 721eefcd68..0e7d5b5a87 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -472,6 +472,30 @@ public void CanGetMethodsFromTypeBuilder() incompleteMethod.Should().BeSameAs(method); } + [TestMethod] + public void CanGetGenericDelegateInvoke() + { + var c = new IkvmReflectionSymbolContext(universe!); + var a = c.DefineAssembly(new AssemblyNameInfo("DynamicAssembly")); + var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); + + var tb = m.DefineType("DynamicGenericDelegate", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Sealed, c.GetOrCreateTypeSymbol(coreAssembly!.GetType("System.MulticastDelegate"))); + var gtp = tb.DefineGenericParameters("T1"); + var mb = tb.DefineMethod("Invoke", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.NewSlot | System.Reflection.MethodAttributes.Virtual, null, [gtp[0]]); + mb.SetImplementationFlags(System.Reflection.MethodImplAttributes.Runtime); + + var type = m.DefineType("DynamicType2"); + var method = type.DefineMethod("CallDelegate", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); + var il = method.GetILGenerator(); + il.Emit(System.Reflection.Emit.OpCodes.Ldind_I4, 0); + il.Emit(System.Reflection.Emit.OpCodes.Ldnull); + il.Emit(System.Reflection.Emit.OpCodes.Castclass, tb); + il.EmitCall(System.Reflection.Emit.OpCodes.Callvirt, mb, null); + + tb.Complete(); + type.Complete(); + } + } } diff --git a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs index 606793ebff..b4e2f1d716 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs @@ -39,14 +39,7 @@ private void WrapArgs(CodeEmitter ilgen, ITypeSymbol type) internal IMethodSymbol GetDelegateInvokeMethod(ITypeSymbol delegateType) { - if (ReflectUtil.ContainsTypeBuilder(delegateType)) - { - return delegateType.GetGenericTypeDefinition().GetMethod("Invoke"); - } - else - { - return delegateType.GetMethod("Invoke"); - } + return delegateType.GetMethod("Invoke"); } internal IConstructorSymbol GetDelegateConstructor(ITypeSymbol delegateType) From dc36f8cff8eceb25ace9da29b56ea9009046644c Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 4 Oct 2024 17:16:40 -0500 Subject: [PATCH 26/59] Implment few more. --- .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 15 ++++- .../Emit/ReflectionTypeSymbolBuilder.cs | 59 +++++++++++-------- 2 files changed, 46 insertions(+), 28 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index c59ad45077..babaa086ad 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -730,19 +730,28 @@ public IMemberSymbol[] GetMembers() /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); + else + return GetIncompleteMethods(bindingAttr).FirstOrDefault(i => i.Name == name); } /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); + else + throw new NotImplementedException(); } /// public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); + else + throw new NotImplementedException(); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 7eede6c1d7..31c468853d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -556,7 +556,7 @@ public int GetArrayRank() } /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) { return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); } @@ -574,7 +574,7 @@ public IConstructorSymbol[] GetConstructors() } /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) + public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) { return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); } @@ -622,7 +622,7 @@ public Array GetEnumValues() } /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) + public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) { return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); } @@ -634,7 +634,7 @@ public IEventSymbol[] GetEvents() } /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) + public IEventSymbol[] GetEvents(BindingFlags bindingAttr) { return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); } @@ -646,7 +646,7 @@ public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) } /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) { return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); } @@ -658,7 +658,7 @@ public IFieldSymbol[] GetFields() } /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) + public IFieldSymbol[] GetFields(BindingFlags bindingAttr) { return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); } @@ -715,19 +715,19 @@ public IMemberSymbol[] GetMember(string name) } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); } @@ -739,21 +739,30 @@ public IMemberSymbol[] GetMembers() } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr)); + else + return GetIncompleteMethods(bindingAttr).FirstOrDefault(i => i.Name == name); } /// public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); + else + throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); + if (IsComplete) + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); + else + throw new NotImplementedException(); } /// @@ -766,28 +775,28 @@ public IMemberSymbol[] GetMembers() } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { if (IsComplete) - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); else throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { if (IsComplete) return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); @@ -802,7 +811,7 @@ public IMemberSymbol[] GetMembers() } /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) { if (IsComplete) return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); @@ -823,7 +832,7 @@ public IMethodSymbol[] GetMethods() /// Gets the set of incomplete methods. /// /// - IMethodSymbol[] GetIncompleteMethods(System.Reflection.BindingFlags bindingAttr = System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance) + IMethodSymbol[] GetIncompleteMethods(BindingFlags bindingAttr = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance) { if (_incompleteMethods == null) return []; @@ -838,7 +847,7 @@ IMethodSymbol[] GetIncompleteMethods(System.Reflection.BindingFlags bindingAttr } /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) { return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } @@ -850,7 +859,7 @@ public ITypeSymbol[] GetNestedTypes() } /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) { return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } @@ -862,7 +871,7 @@ public IPropertySymbol[] GetProperties() } /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) { return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } @@ -880,7 +889,7 @@ public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAtt } /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) { return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } From 6667f5fd3e0dd12e45368f1b12803f185b4eeda0 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 4 Oct 2024 17:19:34 -0500 Subject: [PATCH 27/59] Revert. --- .../java/lang/invoke/MethodHandleTests.java | 86 +++++++++++++------ 1 file changed, 61 insertions(+), 25 deletions(-) diff --git a/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java b/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java index 40b6ae0c45..422db2bc53 100644 --- a/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java +++ b/src/IKVM.Java.Tests/java/lang/invoke/MethodHandleTests.java @@ -19,39 +19,75 @@ public static String addStringStatic(String a, String b) { } + interface AddItf { + void apply(List st, int idx, Object v) throws Throwable; + } + @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() - public void canInvokeExactVirtual() throws Throwable { - MethodHandles.Lookup lookup = getLookup(); - MethodType mt = getMethodType(); - MethodHandle mh = getMethodHandle(lookup, mt); - String s = invokeIt(mh); + public void canInvokeVirtual() throws Throwable { + MethodHandles.Lookup lookup = MethodHandles.lookup(); + MethodType mt = MethodType.methodType(String.class, String.class, String.class); + MethodHandle mh = lookup.findVirtual(TestClass.class, "addString", mt); + String s = (String)mh.invoke(new TestClass(), (Object)"a", (Object)"b"); if (!s.equals("ab")) { throw new Exception(s); } } - @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) - MethodHandles.Lookup getLookup() throws Throwable - { - return MethodHandles.lookup(); + @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() + public void canInvokeStatic() throws Throwable { + MethodHandles.Lookup lookup = MethodHandles.lookup(); + MethodType mt = MethodType.methodType(String.class, String.class, String.class); + MethodHandle mh = lookup.findStatic(TestClass.class, "addStringStatic", mt); + String s = (String)mh.invoke((Object)"a", (Object)"b"); + if (!s.equals("ab")) { + throw new Exception(s); + } } - - @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) - MethodType getMethodType() throws Throwable - { - return MethodType.methodType(String.class, String.class, String.class); + + @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() + public void canInvokeExactVirtual() throws Throwable { + MethodHandles.Lookup lookup = MethodHandles.lookup(); + MethodType mt = MethodType.methodType(String.class, String.class, String.class); + MethodHandle mh = lookup.findVirtual(TestClass.class, "addString", mt); + String s = (String)mh.invokeExact(new TestClass(), "a", "b"); + if (!s.equals("ab")) { + throw new Exception(s); + } } - - @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) - MethodHandle getMethodHandle(MethodHandles.Lookup lookup, MethodType mt) throws Throwable - { - return lookup.findVirtual(TestClass.class, "addString", mt); + + @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() + public void canInvokeExactStatic() throws Throwable { + MethodHandles.Lookup lookup = MethodHandles.lookup(); + MethodType mt = MethodType.methodType(String.class, String.class, String.class); + MethodHandle mh = lookup.findStatic(TestClass.class, "addStringStatic", mt); + String s = (String)mh.invokeExact("a", "b"); + if (!s.equals("ab")) { + throw new Exception(s); + } } - - @cli.System.Runtime.CompilerServices.MethodImplAttribute.Annotation(value = cli.System.Runtime.CompilerServices.MethodImplOptions.__Enum.NoInlining) - String invokeIt(MethodHandle mh) throws Throwable - { - return (String)mh.invokeExact(new TestClass(), "a", "b"); + + @cli.Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute.Annotation() + public void canInvokeStaticMethodThatReturnsVoid() throws Throwable { + MethodHandles.Lookup lookup = MethodHandles.lookup(); + MethodType pmt = MethodType.methodType(void.class, int.class, Object.class); + MethodHandle pms = lookup.findVirtual(List.class, "add", pmt); + List list = new ArrayList<>(); + pms.invoke(list, 0, "Hi"); + AddItf pf2 = pms::invoke; + pf2.apply(list, 1, "there"); + AddItf pf3 = pms::invokeExact; + pf3.apply(list, 2, "you"); + + if (!list.get(0).equals("Hi")) { + throw new Exception(list.get(0)); + }; + if (!list.get(1).equals("there")) { + throw new Exception(list.get(1)); + }; + if (!list.get(2).equals("you")) { + throw new Exception(list.get(2)); + }; } -} +} \ No newline at end of file From 326cd18322516f0a9705158bd7215d13248ffcc9 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 4 Oct 2024 19:53:14 -0500 Subject: [PATCH 28/59] Assert. Allow fileName to be null. --- .../Reflection/Emit/ReflectionAssemblySymbolBuilder.cs | 10 ++++++++-- src/IKVM.Runtime/RuntimeJavaType.cs | 2 +- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index 1ae5eba59c..5d64699174 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -67,7 +67,10 @@ public IModuleSymbolBuilder DefineModule(string name) public IModuleSymbolBuilder DefineModule(string name, string fileName) { #if NETFRAMEWORK - return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName)); + if (fileName == null) + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name)); + else + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName)); #else return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name)); #endif @@ -77,7 +80,10 @@ public IModuleSymbolBuilder DefineModule(string name, string fileName) public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo) { #if NETFRAMEWORK - return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName, emitSymbolInfo)); + if (fileName == null) + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, emitSymbolInfo)); + else + return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name, fileName, emitSymbolInfo)); #else return GetOrCreateModuleSymbol(UnderlyingAssemblyBuilder.DefineDynamicModule(name)); #endif diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index f09830f6c9..abb8df9745 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -1193,7 +1193,7 @@ internal static void AssertFinished(ITypeSymbol type) while (type.HasElementType) type = type.GetElementType(); - Debug.Assert(!(type.AsReflection() is TypeBuilder)); + Debug.Assert(type.IsComplete); } } From d3e85201ee4ca4c2d1bbeeea1d0680695d02ddf0 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sat, 5 Oct 2024 16:33:34 -0500 Subject: [PATCH 29/59] Rename AssemblyNameInfo to Assemblyidentity. Fix up some equality stuff. Remove DefineTypeInitializer from ReflectionUtil now that symbols do it. --- .../IkvmReflectionSymbolTests.cs | 4 +- .../Reflection/ReflectionSymbolTests.cs | 2 +- src/IKVM.CoreLib/IKVM.CoreLib.csproj | 3 +- src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs | 308 ++++++++++++++++++ .../Symbols/AssemblyIdentityComparer.cs | 23 ++ .../Symbols/AssemblyNameFormatter.cs | 17 +- src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs | 159 --------- src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs | 75 ++++- src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 4 +- .../IkvmReflectionAssemblySymbolBuilder.cs | 4 +- .../IkvmReflectionAssemblySymbol.cs | 4 +- .../IkvmReflectionSymbolContext.cs | 4 +- .../IkvmReflection/IkvmReflectionUtil.cs | 73 +++-- .../Emit/ReflectionAssemblySymbolBuilder.cs | 4 +- .../Reflection/ReflectionAssemblySymbol.cs | 4 +- .../Reflection/ReflectionSymbolContext.cs | 4 +- .../Symbols/Reflection/ReflectionUtil.cs | 63 ++-- src/IKVM.CoreLib/Text/HexConverter.cs | 12 +- src/IKVM.Runtime/AttributeHelper.cs | 4 +- src/IKVM.Runtime/DynamicClassLoader.cs | 33 +- src/IKVM.Runtime/LambdaMetafactory.cs | 2 +- src/IKVM.Runtime/ReflectUtil.cs | 22 +- .../RuntimeAssemblyClassLoader.cs | 8 +- .../RuntimeByteCodeJavaType.FinishContext.cs | 2 +- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 2 +- src/IKVM.Runtime/compiler.cs | 4 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 26 +- .../ImportContextFactory.cs | 2 +- src/IKVM.Tools.Importer/Proxy.cs | 2 +- 29 files changed, 558 insertions(+), 316 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs create mode 100644 src/IKVM.CoreLib/Symbols/AssemblyIdentityComparer.cs delete mode 100644 src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index 0e7d5b5a87..b827019c2f 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -448,7 +448,7 @@ public void CanResolveMultipleEventBuilders() public void CanGetMethodsFromTypeBuilder() { var c = new IkvmReflectionSymbolContext(universe!); - var a = c.DefineAssembly(new AssemblyNameInfo("DynamicAssembly")); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly")); var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); var type = m.DefineType("DynamicType"); @@ -476,7 +476,7 @@ public void CanGetMethodsFromTypeBuilder() public void CanGetGenericDelegateInvoke() { var c = new IkvmReflectionSymbolContext(universe!); - var a = c.DefineAssembly(new AssemblyNameInfo("DynamicAssembly")); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly")); var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); var tb = m.DefineType("DynamicGenericDelegate", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Sealed, c.GetOrCreateTypeSymbol(coreAssembly!.GetType("System.MulticastDelegate"))); diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index f0219bf6fd..5c5bc6d2aa 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -425,7 +425,7 @@ public void CanCompleteTypeBuilder() public void CanGetMethodsFromTypeBuilder() { var c = new ReflectionSymbolContext(); - var a = c.DefineAssembly(new AssemblyNameInfo("DynamicAssembly")); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly")); var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); var type = m.DefineType("DynamicType"); diff --git a/src/IKVM.CoreLib/IKVM.CoreLib.csproj b/src/IKVM.CoreLib/IKVM.CoreLib.csproj index 13d67775f9..d61e8958e6 100644 --- a/src/IKVM.CoreLib/IKVM.CoreLib.csproj +++ b/src/IKVM.CoreLib/IKVM.CoreLib.csproj @@ -24,10 +24,11 @@ all runtime; build; native; contentfiles; analyzers; buildtransitive - + + diff --git a/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs b/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs new file mode 100644 index 0000000000..3551bd310f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs @@ -0,0 +1,308 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics; +using System.Linq; +using System.Reflection; +using System.Security.Cryptography; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Represents an identity of an assembly as defined by CLI metadata specification. + /// + class AssemblyIdentity + { + + /// + /// Determines whether two instances are equal. + /// + /// The operand appearing on the left side of the operator. + /// The operand appearing on the right side of the operator. + public static bool operator ==(AssemblyIdentity? left, AssemblyIdentity? right) + { + return EqualityComparer.Default.Equals(left!, right!); + } + + /// + /// Determines whether two instances are not equal. + /// + /// The operand appearing on the left side of the operator. + /// The operand appearing on the right side of the operator. + public static bool operator !=(AssemblyIdentity? left, AssemblyIdentity? right) + { + return !(left == right); + } + + /// + /// Returns true (false) if specified assembly identities are (not) equal + /// regardless of unification, retargeting or other assembly binding policies. + /// Returns null if these policies must be consulted to determine name equivalence. + /// + public static bool? MemberwiseEqual(AssemblyIdentity x, AssemblyIdentity y) + { + if (ReferenceEquals(x, y)) + return true; + + if (!AssemblyIdentityComparer.SimpleNameComparer.Equals(x._name, y._name)) + return false; + + if (x._version.Equals(y._version) && EqualIgnoringNameAndVersion(x, y)) + return true; + + return null; + } + + /// + /// Returns true if the components of the assembly names, other than name and version, are equal. + /// + /// + /// + /// + public static bool EqualIgnoringNameAndVersion(AssemblyIdentity x, AssemblyIdentity y) + { + return x.ContentType == y.ContentType && AssemblyIdentityComparer.CultureComparer.Equals(x.CultureName, y.CultureName) && KeysEqual(x, y); + } + + /// + /// Returns true if the public keys of both identities are equal. + /// + /// + /// + /// + public static bool KeysEqual(AssemblyIdentity x, AssemblyIdentity y) + { + var xToken = x._publicKeyToken; + var yToken = y._publicKeyToken; + + // weak names or both strong names with initialized PKT - compare tokens: + if (!xToken.IsDefault && !yToken.IsDefault) + return xToken.SequenceEqual(yToken); + + // both are strong names with uninitialized PKT - compare full keys: + if (xToken.IsDefault && yToken.IsDefault) + return x._publicKey.SequenceEqual(y._publicKey); + + // one of the strong names doesn't have PK, other doesn't have PTK initialized. + if (xToken.IsDefault) + return x.PublicKeyToken.SequenceEqual(yToken); + else + return xToken.SequenceEqual(y.PublicKeyToken); + } + + /// + /// Initializes the publickey and publickeytoken values. + /// + /// + /// + /// + /// + static void InitializeKey(ImmutableArray publicKeyOrToken, bool hasPublicKey, out ImmutableArray publicKey, out ImmutableArray publicKeyToken) + { + if (hasPublicKey) + { + publicKey = publicKeyOrToken; + publicKeyToken = default; + } + else + { + publicKey = ImmutableArray.Empty; + publicKeyToken = publicKeyOrToken.IsDefault ? ImmutableArray.Empty : publicKeyOrToken; + } + } + + /// + /// Calculates the public key token from the given public key. + /// + /// + /// + static ImmutableArray CalculatePublicKeyToken(ImmutableArray publicKey) + { + var hash = SHA1.Create().ComputeHash(publicKey.ToArray()); + + // SHA1 hash is always 160 bits: + Debug.Assert(hash.Length == 20); + + // PublicKeyToken is the low 64 bits of the SHA-1 hash of the public key. + int l = hash.Length - 1; + var result = ImmutableArray.CreateBuilder(8); + for (int i = 0; i < 8; i++) + result.Add(hash[l - i]); + + return result.ToImmutable(); + } + + readonly string _name; + readonly Version _version; + readonly string? _cultureName; + readonly AssemblyContentType _contentType; + readonly ProcessorArchitecture _processorArchitecture; + + string? _fullName; + ImmutableArray _publicKey; + ImmutableArray _publicKeyToken; + int _hashCode = 0; + + /// + /// Initializes a new instance of the class. + /// + /// The simple name of the assembly. + /// The version of the assembly. + /// The name of the culture associated with the assembly. + /// The public key or its token. + /// is null. + public AssemblyIdentity(string name, Version? version = null, string? cultureName = null, ImmutableArray publicKeyOrToken = default, bool hasPublicKey = false, AssemblyContentType contentType = default, ProcessorArchitecture processorArchitecture = ProcessorArchitecture.None) + { + _name = name ?? throw new ArgumentNullException(nameof(name)); + _version = version ?? new Version(0, 0, 0, 0); + _cultureName = cultureName; + _contentType = contentType; + _processorArchitecture = processorArchitecture; + InitializeKey(publicKeyOrToken, hasPublicKey, out _publicKey, out _publicKeyToken); + } + + /// + /// Gets the simple name of the assembly. + /// + public string Name => _name; + + /// + /// Gets the version of the assembly. + /// + public Version? Version => _version; + + /// + /// Gets the name of the culture associated with the assembly. + /// + /// + /// Do not create a instance from this string unless + /// you know the string has originated from a trustworthy source. + /// + public string? CultureName => _cultureName; + + /// + /// Returns true if a public key is available. + /// + public bool HasPublicKey => _publicKey.Length > 0; + + /// + /// Gets the public key or the public key token of the assembly. + /// + public ImmutableArray PublicKey => _publicKey; + + /// + /// Low 8 bytes of SHA1 hash of the public key, or empty. + /// + public ImmutableArray PublicKeyToken + { + get + { + if (_publicKeyToken.IsDefault) + ImmutableInterlocked.InterlockedCompareExchange(ref _publicKeyToken, CalculatePublicKeyToken(_publicKey), default); + + return _publicKeyToken; + } + } + + /// + /// Gets the full name of the assembly, also known as the display name. + /// + /// In contrary to it does not validate public key token neither computes it based on the provided public key. + public string FullName => _fullName ??= AssemblyNameFormatter.ComputeDisplayName(Name, Version, CultureName, PublicKeyToken, Flags, ContentType, PublicKey); + + /// + /// Gets the . + /// + public AssemblyNameFlags Flags => HasPublicKey ? AssemblyNameFlags.PublicKey : AssemblyNameFlags.None; + + /// + /// Specifies the binding model for how this object will be treated in comparisons. + /// + public AssemblyContentType ContentType => _contentType; + + /// + /// Gets the processor architecture of the assembly name. + /// + public ProcessorArchitecture ProcessorArchitecture => _processorArchitecture; + + /// + /// True if the assembly identity has a strong name, ie. either a full public key or a token. + /// + public bool IsStrongName => HasPublicKey || _publicKeyToken.Length > 0; + + /// + /// Determines whether the specified instance is equal to the current instance. + /// + /// The object to be compared with the current instance. + public bool Equals(AssemblyIdentity? obj) + { + return !ReferenceEquals(obj, null) && (_hashCode == 0 || obj._hashCode == 0 || _hashCode == obj._hashCode) && MemberwiseEqual(this, obj) == true; + } + + /// + /// Determines whether the specified instance is equal to the current instance. + /// + /// The object to be compared with the current instance. + public override bool Equals(object? obj) + { + return Equals(obj as AssemblyIdentity); + } + + /// + /// Returns the hash code for the current instance. + /// + /// + public override int GetHashCode() + { + if (_hashCode == 0) + { + // Do not include PK/PKT in the hash - collisions on PK/PKT are rare (assembly identities differ only in PKT/PK) + // and we can't calculate hash of PKT if only PK is available + _hashCode = + HashCode.Combine(AssemblyIdentityComparer.SimpleNameComparer.GetHashCode(_name), + HashCode.Combine(_version?.GetHashCode(), GetHashCodeIgnoringNameAndVersion())); + } + + return _hashCode; + } + + /// + /// Gets the hashcode for this instance, without considering the name and version. + /// + /// + int GetHashCodeIgnoringNameAndVersion() + { + return HashCode.Combine((int)_contentType, AssemblyIdentityComparer.CultureComparer.GetHashCode(_cultureName ?? "")); + } + + /// + /// Initializes a new instance of the class based on the stored information. + /// + /// + /// Do not create an instance with string unless + /// you know the string has originated from a trustworthy source. + /// + public AssemblyName ToAssemblyName() + { + AssemblyName assemblyName = new(); + assemblyName.Name = Name; + assemblyName.CultureName = CultureName; + assemblyName.Version = Version; + assemblyName.Flags = Flags; + assemblyName.ContentType = ContentType; +#pragma warning disable SYSLIB0037 // Type or member is obsolete + assemblyName.ProcessorArchitecture = ProcessorArchitecture; +#pragma warning restore SYSLIB0037 // Type or member is obsolete + + if (HasPublicKey) + assemblyName.SetPublicKey(PublicKey.ToArray()); + else if (PublicKeyToken.IsDefaultOrEmpty == false) + assemblyName.SetPublicKeyToken(PublicKeyToken.ToArray()); + + return assemblyName; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/AssemblyIdentityComparer.cs b/src/IKVM.CoreLib/Symbols/AssemblyIdentityComparer.cs new file mode 100644 index 0000000000..a4727d08cf --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/AssemblyIdentityComparer.cs @@ -0,0 +1,23 @@ +using System; + +namespace IKVM.CoreLib.Symbols +{ + + class AssemblyIdentityComparer + { + + public static AssemblyIdentityComparer Default { get; } = new AssemblyIdentityComparer(); + + public static StringComparer SimpleNameComparer + { + get { return StringComparer.OrdinalIgnoreCase; } + } + + public static StringComparer CultureComparer + { + get { return StringComparer.OrdinalIgnoreCase; } + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs b/src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs index 08c41a9c6d..60ff5b9855 100644 --- a/src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs +++ b/src/IKVM.CoreLib/Symbols/AssemblyNameFormatter.cs @@ -1,18 +1,21 @@ using System; +using System.Collections.Immutable; using System.Diagnostics; using System.Reflection; +using System.Security.Cryptography; using IKVM.CoreLib.Text; namespace IKVM.CoreLib.Symbols { - internal static class AssemblyNameFormatter + static class AssemblyNameFormatter { - public static string ComputeDisplayName(string name, Version? version, string? cultureName, byte[]? pkt, AssemblyNameFlags flags = 0, AssemblyContentType contentType = 0, byte[]? pk = null) + public static string ComputeDisplayName(string name, Version? version, string? cultureName, ImmutableArray pkt, AssemblyNameFlags flags, AssemblyContentType contentType, ImmutableArray pk) { const int PUBLIC_KEY_TOKEN_LEN = 8; + Debug.Assert(name.Length != 0); var vsb = new ValueStringBuilder(stackalloc char[256]); @@ -57,7 +60,7 @@ public static string ComputeDisplayName(string name, Version? version, string? c vsb.AppendQuoted(cultureName); } - byte[]? keyOrToken = pkt ?? pk; + var keyOrToken = pkt.IsDefaultOrEmpty == false ? pkt : pk; if (keyOrToken != null) { if (pkt != null) @@ -78,7 +81,7 @@ public static string ComputeDisplayName(string name, Version? version, string? c } else { - HexConverter.EncodeToUtf16(keyOrToken, vsb.AppendSpan(keyOrToken.Length * 2), HexConverter.Casing.Lower); + HexConverter.EncodeToUtf16(keyOrToken.AsSpan(), vsb.AppendSpan(keyOrToken.Length * 2), HexConverter.Casing.Lower); } } @@ -88,12 +91,10 @@ public static string ComputeDisplayName(string name, Version? version, string? c if (contentType == AssemblyContentType.WindowsRuntime) vsb.Append(", ContentType=WindowsRuntime"); - // NOTE: By design (desktop compat) AssemblyName.FullName and ToString() do not include ProcessorArchitecture. - return vsb.ToString(); } - private static void AppendQuoted(this ref ValueStringBuilder vsb, string s) + static void AppendQuoted(this ref ValueStringBuilder vsb, string s) { bool needsQuoting = false; const char quoteChar = '\"'; @@ -136,7 +137,7 @@ private static void AppendQuoted(this ref ValueStringBuilder vsb, string s) vsb.Append(quoteChar); } - private static void AppendSpanFormattable(this ref ValueStringBuilder vsb, ushort value) + static void AppendSpanFormattable(this ref ValueStringBuilder vsb, ushort value) { vsb.Append(value.ToString()); } diff --git a/src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs b/src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs deleted file mode 100644 index b92ecd28f3..0000000000 --- a/src/IKVM.CoreLib/Symbols/AssemblyNameInfo.cs +++ /dev/null @@ -1,159 +0,0 @@ -using System; -using System.Collections.Immutable; -using System.Diagnostics.CodeAnalysis; -using System.Linq; -using System.Reflection; - -namespace IKVM.CoreLib.Symbols -{ - - class AssemblyNameInfo - { - - readonly AssemblyNameFlags _flags; - string? _fullName; - - /// - /// Initializes a new instance of the AssemblyNameInfo class. - /// - /// The simple name of the assembly. - /// The version of the assembly. - /// The name of the culture associated with the assembly. - /// The attributes of the assembly. - /// The public key or its token. Set to when it's public key. - /// is null. - public AssemblyNameInfo(string name, Version? version = null, string? cultureName = null, AssemblyNameFlags flags = AssemblyNameFlags.None, ImmutableArray publicKeyOrToken = default) - { - Name = name ?? throw new ArgumentNullException(nameof(name)); - Version = version; - CultureName = cultureName; - _flags = flags; - PublicKeyOrToken = publicKeyOrToken; - } - - /// - /// Gets the simple name of the assembly. - /// - public string Name { get; } - - /// - /// Gets the version of the assembly. - /// - public Version? Version { get; } - - /// - /// Gets the name of the culture associated with the assembly. - /// - /// - /// Do not create a instance from this string unless - /// you know the string has originated from a trustworthy source. - /// - public string? CultureName { get; } - - /// - /// Gets the attributes of the assembly. - /// - public AssemblyNameFlags Flags => _flags; - - /// - /// Gets the public key or the public key token of the assembly. - /// - /// Check for flag to see whether it's public key or its token. -#if SYSTEM_PRIVATE_CORELIB - public byte[]? PublicKeyOrToken { get; } -#else - public ImmutableArray PublicKeyOrToken { get; } -#endif - - - /// - /// Gets the full name of the assembly, also known as the display name. - /// - /// In contrary to it does not validate public key token neither computes it based on the provided public key. - public string FullName - { - get - { - if (_fullName is null) - { - bool isPublicKey = (Flags & AssemblyNameFlags.PublicKey) != 0; - - byte[]? publicKeyOrToken = -#if SYSTEM_PRIVATE_CORELIB - PublicKeyOrToken; -#elif NET8_0_OR_GREATER - !PublicKeyOrToken.IsDefault ? System.Runtime.InteropServices.ImmutableCollectionsMarshal.AsArray(PublicKeyOrToken) : null; -#else - !PublicKeyOrToken.IsDefault ? PublicKeyOrToken.ToArray() : null; -#endif - _fullName = AssemblyNameFormatter.ComputeDisplayName(Name, Version, CultureName, - pkt: isPublicKey ? null : publicKeyOrToken, - ExtractAssemblyNameFlags(_flags), ExtractAssemblyContentType(_flags), - pk: isPublicKey ? publicKeyOrToken : null); - } - - return _fullName; - } - } - - /// - /// Initializes a new instance of the class based on the stored information. - /// - /// - /// Do not create an instance with string unless - /// you know the string has originated from a trustworthy source. - /// - public AssemblyName ToAssemblyName() - { - AssemblyName assemblyName = new(); - assemblyName.Name = Name; - assemblyName.CultureName = CultureName; - assemblyName.Version = Version; - assemblyName.Flags = Flags; - assemblyName.ContentType = ExtractAssemblyContentType(_flags); -#pragma warning disable SYSLIB0037 // Type or member is obsolete - assemblyName.ProcessorArchitecture = ExtractProcessorArchitecture(_flags); -#pragma warning restore SYSLIB0037 // Type or member is obsolete - -#if SYSTEM_PRIVATE_CORELIB - if (PublicKeyOrToken is not null) - { - if ((Flags & AssemblyNameFlags.PublicKey) != 0) - { - assemblyName.SetPublicKey(PublicKeyOrToken); - } - else - { - assemblyName.SetPublicKeyToken(PublicKeyOrToken); - } - } -#else - if (!PublicKeyOrToken.IsDefault) - { - // A copy of the array needs to be created, as AssemblyName allows for the mutation of provided array. - if ((Flags & AssemblyNameFlags.PublicKey) != 0) - { - assemblyName.SetPublicKey(PublicKeyOrToken.ToArray()); - } - else - { - assemblyName.SetPublicKeyToken(PublicKeyOrToken.ToArray()); - } - } -#endif - - return assemblyName; - } - - internal static AssemblyNameFlags ExtractAssemblyNameFlags(AssemblyNameFlags combinedFlags) - => combinedFlags & unchecked((AssemblyNameFlags)0xFFFFF10F); - - internal static AssemblyContentType ExtractAssemblyContentType(AssemblyNameFlags flags) - => (AssemblyContentType)((((int)flags) >> 9) & 0x7); - - internal static ProcessorArchitecture ExtractProcessorArchitecture(AssemblyNameFlags flags) - => (ProcessorArchitecture)((((int)flags) >> 4) & 0x7); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs index 17fecec182..dbdfb9eef0 100644 --- a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs @@ -4,13 +4,20 @@ namespace IKVM.CoreLib.Symbols { + /// + /// Represents an assembly, which is a reusable, versionable, and self-describing building block of a common language runtime application. + /// interface IAssemblySymbol : ISymbol, ICustomAttributeProvider { + /// + /// Gets a collection of the types defined in this assembly. + /// IEnumerable DefinedTypes { get; } - IMethodSymbol? EntryPoint { get; } - + /// + /// Gets a collection of the public types defined in this assembly that are visible outside the assembly. + /// IEnumerable ExportedTypes { get; } /// @@ -33,6 +40,9 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider /// IModuleSymbol ManifestModule { get; } + /// + /// Gets a collection that contains the modules in this assembly. + /// IEnumerable Modules { get; } /// @@ -57,34 +67,79 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider /// Stream? GetManifestResourceStream(ITypeSymbol type, string name); - ITypeSymbol[] GetExportedTypes(); - + /// + /// Gets the specified module in this assembly. + /// + /// + /// IModuleSymbol? GetModule(string name); + /// + /// Gets all the modules that are part of this assembly. + /// + /// IModuleSymbol[] GetModules(); + /// + /// Gets all the modules that are part of this assembly, specifying whether to include resource modules. + /// + /// + /// IModuleSymbol[] GetModules(bool getResourceModules); /// - /// Gets an for this assembly. + /// Gets an for this assembly. + /// + /// + AssemblyIdentity GetIdentity(); + + /// + /// Gets the objects for all the assemblies referenced by this assembly. /// /// - AssemblyNameInfo GetName(); + AssemblyIdentity[] GetReferencedAssemblies(); /// - /// Gets the objects for all the assemblies referenced by this assembly. + /// Gets the Type object with the specified name in the assembly instance. /// + /// /// - AssemblyNameInfo[] GetReferencedAssemblies(); + ITypeSymbol? GetType(string name); + /// + /// Gets the object with the specified name in the assembly instance and optionally throws an exception if the type is not found. + /// + /// + /// + /// ITypeSymbol? GetType(string name, bool throwOnError); + /// + /// Gets the object with the specified name in the assembly instance, with the options of ignoring the case, and of throwing an exception if the type is not found. + /// + /// + /// + /// + /// ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase); - ITypeSymbol? GetType(string name); - + /// + /// Gets all types defined in this assembly. + /// + /// ITypeSymbol[] GetTypes(); + /// + /// Gets the public types defined in this assembly that are visible outside the assembly. + /// + /// + ITypeSymbol[] GetExportedTypes(); + + /// + /// Gets the entry point of this assembly. + /// + IMethodSymbol? EntryPoint { get; } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index 37440c21b5..32910c1899 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -14,14 +14,14 @@ interface ISymbolContext /// /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name); + IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name); /// /// Defines a dynamic assembly that has the specified name and access rights. /// /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttributeBuilder[]? assemblyAttributes); + IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes); /// /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs index 0d876aa823..8145099b2e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -190,13 +190,13 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public AssemblyNameInfo GetName() + public AssemblyIdentity GetIdentity() { return UnderlyingAssembly.GetName().Pack(); } /// - public AssemblyNameInfo[] GetReferencedAssemblies() + public AssemblyIdentity[] GetReferencedAssemblies() { return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs index 2feec1bc0b..3af8e7726a 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionAssemblySymbol.cs @@ -96,13 +96,13 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public AssemblyNameInfo GetName() + public AssemblyIdentity GetIdentity() { return UnderlyingAssembly.GetName().Pack(); } /// - public AssemblyNameInfo[] GetReferencedAssemblies() + public AssemblyIdentity[] GetReferencedAssemblies() { return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs index 4cc41b20b4..56a5613391 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -32,7 +32,7 @@ public IkvmReflectionSymbolContext(Universe universe) } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name) { if (name is null) throw new ArgumentNullException(nameof(name)); @@ -41,7 +41,7 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name) } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttributeBuilder[]? assemblyAttributes) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes) { if (name is null) throw new ArgumentNullException(nameof(name)); diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs index 5898b55e8f..600292ba80 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Immutable; +using System.Linq; using IKVM.CoreLib.Symbols.Emit; using IKVM.CoreLib.Symbols.IkvmReflection.Emit; @@ -15,61 +16,79 @@ static class IkvmReflectionUtil { /// - /// Converts a to a . + /// Converts a to a . /// /// /// - public static AssemblyNameInfo Pack(this AssemblyName n) + public static AssemblyIdentity Pack(this AssemblyName assemblyName) { - return new AssemblyNameInfo(n.Name, n.Version, n.CultureName, (System.Reflection.AssemblyNameFlags)n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? ImmutableArray.Empty); + var pk = assemblyName.GetPublicKey()?.ToImmutableArray() ?? ImmutableArray.Empty; + var hasPublicKey = pk.Length > 0; + var pkt = assemblyName.GetPublicKeyToken()?.ToImmutableArray() ?? ImmutableArray.Empty; + + return new AssemblyIdentity( + assemblyName.Name ?? throw new InvalidOperationException(), + assemblyName.Version, + assemblyName.CultureName, + hasPublicKey ? pk : pkt, + hasPublicKey, + (System.Reflection.AssemblyContentType)assemblyName.ContentType, + (System.Reflection.ProcessorArchitecture)assemblyName.ProcessorArchitecture); } /// - /// Converts a set of to a set of . + /// Converts a set of to a set of . /// - /// + /// /// - public static AssemblyNameInfo[] Pack(this AssemblyName[] n) + public static AssemblyIdentity[] Pack(this AssemblyName[] assemblyNames) { - if (n.Length == 0) + if (assemblyNames.Length == 0) return []; - var a = new AssemblyNameInfo[n.Length]; - for (int i = 0; i < n.Length; i++) - a[i] = n[i].Pack(); + var a = new AssemblyIdentity[assemblyNames.Length]; + for (int i = 0; i < assemblyNames.Length; i++) + a[i] = assemblyNames[i].Pack(); return a; } /// - /// Converts a to a . + /// Converts a to a . /// - /// + /// /// - public static AssemblyName Unpack(this AssemblyNameInfo n) + public static AssemblyName Unpack(this AssemblyIdentity assemblyNameInfo) { - return new AssemblyName() - { - Name = n.Name, - Version = n.Version, - CultureName = n.CultureName, - Flags = (AssemblyNameFlags)n.Flags, - }; + AssemblyName assemblyName = new(); + assemblyName.Name = assemblyNameInfo.Name; + assemblyName.CultureName = assemblyNameInfo.CultureName; + assemblyName.Version = assemblyNameInfo.Version; + assemblyName.Flags = (AssemblyNameFlags)assemblyNameInfo.Flags; + assemblyName.ContentType = (AssemblyContentType)assemblyNameInfo.ContentType; + assemblyName.ProcessorArchitecture = (ProcessorArchitecture)assemblyNameInfo.ProcessorArchitecture; + + if (assemblyNameInfo.HasPublicKey) + assemblyName.SetPublicKey(assemblyNameInfo.PublicKey.ToArray()); + else if (assemblyNameInfo.PublicKeyToken.IsDefaultOrEmpty == false) + assemblyName.SetPublicKeyToken(assemblyNameInfo.PublicKeyToken.ToArray()); + + return assemblyName; } /// - /// Converts a set of to a set of . + /// Converts a set of to a set of . /// - /// + /// /// - public static AssemblyName[] Unpack(this AssemblyNameInfo[] n) + public static AssemblyName[] Unpack(this AssemblyIdentity[] assemblyNameInfos) { - if (n.Length == 0) + if (assemblyNameInfos.Length == 0) return []; - var a = new AssemblyName[n.Length]; - for (int i = 0; i < n.Length; i++) - a[i] = n[i].Unpack(); + var a = new AssemblyName[assemblyNameInfos.Length]; + for (int i = 0; i < assemblyNameInfos.Length; i++) + a[i] = assemblyNameInfos[i].Unpack(); return a; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index 5d64699174..c5d085a526 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -216,13 +216,13 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public AssemblyNameInfo GetName() + public AssemblyIdentity GetIdentity() { return UnderlyingAssembly.GetName().Pack(); } /// - public AssemblyNameInfo[] GetReferencedAssemblies() + public AssemblyIdentity[] GetReferencedAssemblies() { return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index f589ea11de..7496acfff8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -92,13 +92,13 @@ public IModuleSymbol[] GetModules(bool getResourceModules) } /// - public AssemblyNameInfo GetName() + public AssemblyIdentity GetIdentity() { return UnderlyingAssembly.GetName().Pack(); } /// - public AssemblyNameInfo[] GetReferencedAssemblies() + public AssemblyIdentity[] GetReferencedAssemblies() { return UnderlyingAssembly.GetReferencedAssemblies().Pack(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index 1b876eb337..b435aa9033 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -29,7 +29,7 @@ public ReflectionSymbolContext() } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name) { if (name is null) throw new ArgumentNullException(nameof(name)); @@ -42,7 +42,7 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name) } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyNameInfo name, ICustomAttributeBuilder[]? assemblyAttributes) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes) { if (name is null) throw new ArgumentNullException(nameof(name)); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index 2a8426e22a..5a19f7b9ae 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -13,61 +13,68 @@ static class ReflectionUtil { /// - /// Converts a to a . + /// Converts a to a . /// - /// + /// /// - public static AssemblyNameInfo Pack(this AssemblyName n) + public static AssemblyIdentity Pack(this AssemblyName assemblyName) { - return new AssemblyNameInfo(n.Name ?? throw new InvalidOperationException(), n.Version, n.CultureName, n.Flags, n.GetPublicKeyToken()?.ToImmutableArray() ?? ImmutableArray.Empty); + var pk = assemblyName.GetPublicKey()?.ToImmutableArray() ?? ImmutableArray.Empty; + var hasPublicKey = pk.Length > 0; + var pkt = assemblyName.GetPublicKeyToken()?.ToImmutableArray() ?? ImmutableArray.Empty; + +#pragma warning disable SYSLIB0037 // Type or member is obsolete + return new AssemblyIdentity( + assemblyName.Name ?? throw new InvalidOperationException(), + assemblyName.Version, + assemblyName.CultureName, + hasPublicKey ? pk : pkt, + hasPublicKey, + assemblyName.ContentType, + assemblyName.ProcessorArchitecture); +#pragma warning restore SYSLIB0037 // Type or member is obsolete } /// - /// Converts a set of to a set of . + /// Converts a set of to a set of . /// - /// + /// /// - public static AssemblyNameInfo[] Pack(this AssemblyName[] n) + public static AssemblyIdentity[] Pack(this AssemblyName[] assemblyNames) { - if (n.Length == 0) + if (assemblyNames.Length == 0) return []; - var a = new AssemblyNameInfo[n.Length]; - for (int i = 0; i < n.Length; i++) - a[i] = n[i].Pack(); + var a = new AssemblyIdentity[assemblyNames.Length]; + for (int i = 0; i < assemblyNames.Length; i++) + a[i] = assemblyNames[i].Pack(); return a; } /// - /// Converts a to a . + /// Converts a to a . /// - /// + /// /// - public static AssemblyName Unpack(this AssemblyNameInfo n) + public static AssemblyName Unpack(this AssemblyIdentity assemblyNameInfo) { - return new AssemblyName() - { - Name = n.Name, - Version = n.Version, - CultureName = n.CultureName, - Flags = (AssemblyNameFlags)n.Flags, - }; + return assemblyNameInfo.ToAssemblyName(); } /// - /// Converts a set of to a set of . + /// Converts a set of to a set of . /// - /// + /// /// - public static AssemblyName[] Unpack(this AssemblyNameInfo[] n) + public static AssemblyName[] Unpack(this AssemblyIdentity[] assemblyNameInfos) { - if (n.Length == 0) + if (assemblyNameInfos.Length == 0) return []; - var a = new AssemblyName[n.Length]; - for (int i = 0; i < n.Length; i++) - a[i] = n[i].Unpack(); + var a = new AssemblyName[assemblyNameInfos.Length]; + for (int i = 0; i < assemblyNameInfos.Length; i++) + a[i] = assemblyNameInfos[i].Unpack(); return a; } diff --git a/src/IKVM.CoreLib/Text/HexConverter.cs b/src/IKVM.CoreLib/Text/HexConverter.cs index 504f432382..2b9c0aad0f 100644 --- a/src/IKVM.CoreLib/Text/HexConverter.cs +++ b/src/IKVM.CoreLib/Text/HexConverter.cs @@ -159,13 +159,6 @@ public static void EncodeToUtf16(ReadOnlySpan bytes, Span chars, Cas { Debug.Assert(chars.Length >= bytes.Length * 2); -#if SYSTEM_PRIVATE_CORELIB - if ((AdvSimd.Arm64.IsSupported || Ssse3.IsSupported) && bytes.Length >= 4) - { - EncodeToUtf16_Vector128(bytes, chars, casing); - return; - } -#endif for (int pos = 0; pos < bytes.Length; pos++) { ToCharsBuffer(bytes[pos], chars, pos * 2, casing); @@ -175,9 +168,7 @@ public static void EncodeToUtf16(ReadOnlySpan bytes, Span chars, Cas public static unsafe string ToString(ReadOnlySpan bytes, Casing casing = Casing.Upper) { #if NETFRAMEWORK || NETSTANDARD2_0 - Span result = bytes.Length > 16 ? - new char[bytes.Length * 2].AsSpan() : - stackalloc char[bytes.Length * 2]; + var result = bytes.Length > 16 ? new char[bytes.Length * 2].AsSpan() : stackalloc char[bytes.Length * 2]; int pos = 0; foreach (byte b in bytes) @@ -185,6 +176,7 @@ public static unsafe string ToString(ReadOnlySpan bytes, Casing casing = C ToCharsBuffer(b, result, pos, casing); pos += 2; } + return result.ToString(); #else return string.Create(bytes.Length * 2, (RosPtr: (IntPtr)(&bytes), casing), static (chars, args) => diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index 46f8e86aa6..36bd449d0d 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -1015,9 +1015,9 @@ internal string GetAnnotationAttributeType(ITypeSymbol type) return null; } - internal AssemblyNameInfo[] GetInternalsVisibleToAttributes(IAssemblySymbol assembly) + internal AssemblyIdentity[] GetInternalsVisibleToAttributes(IAssemblySymbol assembly) { - var list = new List(); + var list = new List(); foreach (var cad in assembly.GetCustomAttributes()) { diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index 3feb88869c..9280aba817 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -33,7 +33,8 @@ Jeroen Frijters using static System.Diagnostics.DebuggableAttribute; -using System.Collections.Immutable; +using IKVM.CoreLib.Symbols.Reflection; + #if IMPORTER @@ -135,18 +136,24 @@ public DynamicClassLoader GetOrCreate(RuntimeClassLoader loader) // each assembly class loader gets its own dynamic class loader if (loader is RuntimeAssemblyClassLoader acl) { - var name = acl.MainAssembly.GetName().Name + context.Options.DynamicAssemblySuffixAndPublicKey; - foreach (var attr in acl.MainAssembly.AsReflection().GetCustomAttributes()) + // search for the InternalsVisibleToAttribute on the assembly that specifies the dynamic assembly name + // the name may have a public key suffix for Framework + var internalsVisibleToAttribute = context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName); + var internalsVisibleToName = acl.MainAssembly.GetIdentity().Name + context.Options.DynamicAssemblySuffixAndPublicKey; + + foreach (var attr in acl.MainAssembly.GetCustomAttributes(internalsVisibleToAttribute)) { - if (attr.AssemblyName == name) + var attributeConstructorArgValue = (string)attr.ConstructorArguments[0].Value; + if (attributeConstructorArgValue == internalsVisibleToName) { - byte[] kp = []; + var kp = Array.Empty(); #if NETFRAMEWORK kp = DynamicClassLoader.ForgedKeyPair.Instance.PublicKey; #endif - - var n = new AssemblyNameInfo(name, publicKeyOrToken: kp.ToImmutableArray()); - return new DynamicClassLoader(context, loader.Diagnostics, DynamicClassLoader.CreateModuleBuilder(context, n), true); + // desired assembly name, which may contain token + var assemblyName = new AssemblyName(internalsVisibleToName); + assemblyName.SetPublicKey(kp); + return new DynamicClassLoader(context, loader.Diagnostics, DynamicClassLoader.CreateModuleBuilder(context, assemblyName.Pack()), true); } } } @@ -447,7 +454,7 @@ internal void FinishAll() internal static IModuleSymbolBuilder CreateJniProxyModuleBuilder(RuntimeContext context) { - jniProxyAssemblyBuilder = DefineDynamicAssembly(context, new AssemblyNameInfo("jniproxy"), null); + jniProxyAssemblyBuilder = DefineDynamicAssembly(context, new AssemblyIdentity("jniproxy"), null); return jniProxyAssemblyBuilder.DefineModule("jniproxy.dll"); } @@ -519,13 +526,13 @@ private static SerializationInfo ToInfo(byte[] publicKey) public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context) { - return CreateModuleBuilder(context, new AssemblyNameInfo("ikvm_dynamic_assembly__" + (uint)Environment.TickCount)); + return CreateModuleBuilder(context, new AssemblyIdentity("ikvm_dynamic_assembly__" + (uint)Environment.TickCount)); } - public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, AssemblyNameInfo name) + public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, AssemblyIdentity name) { var now = DateTime.Now; - name = new AssemblyNameInfo(name.Name, new Version(now.Year, (now.Month * 100) + now.Day, (now.Hour * 100) + now.Minute, (now.Second * 1000) + now.Millisecond)); + name = new AssemblyIdentity(name.Name, new Version(now.Year, (now.Month * 100) + now.Day, (now.Hour * 100) + now.Minute, (now.Second * 1000) + now.Millisecond)); var attribs = new List(); #if NETFRAMEWORK @@ -549,7 +556,7 @@ public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, A return moduleBuilder; } - static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyNameInfo name, ICustomAttributeBuilder[] assemblyAttributes) + static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyIdentity name, ICustomAttributeBuilder[] assemblyAttributes) { return context.Resolver.Symbols.DefineAssembly(name, assemblyAttributes); } diff --git a/src/IKVM.Runtime/LambdaMetafactory.cs b/src/IKVM.Runtime/LambdaMetafactory.cs index 6b88472003..e36d89bfda 100644 --- a/src/IKVM.Runtime/LambdaMetafactory.cs +++ b/src/IKVM.Runtime/LambdaMetafactory.cs @@ -441,7 +441,7 @@ private static IMethodSymbolBuilder CreateConstructorAndDispatch(RuntimeByteCode var instField = tb.DefineField("inst", tb, FieldAttributes.Private | FieldAttributes.Static); // static constructor - var cctor = ReflectUtil.DefineTypeInitializer(tb, context.TypeWrapper.ClassLoader); + var cctor = tb.DefineTypeInitializer(); var ilgenCCtor = context.Context.CodeEmitterFactory.Create(cctor); ilgenCCtor.Emit(OpCodes.Newobj, ctor); ilgenCCtor.Emit(OpCodes.Stsfld, instField); diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index a87e8132c4..2259bc0653 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -121,26 +121,18 @@ internal static bool IsDynamicMethod(IMethodSymbol method) } } - internal static IConstructorSymbolBuilder DefineTypeInitializer(ITypeSymbolBuilder typeBuilder, RuntimeClassLoader loader) - { - return typeBuilder.DefineTypeInitializer(); - } - - internal static bool MatchNameAndPublicKeyToken(AssemblyNameInfo name1, AssemblyNameInfo name2) - { - return name1.Name.Equals(name2.Name, StringComparison.OrdinalIgnoreCase) && CompareKeys(name1.PublicKeyOrToken, name2.PublicKeyOrToken); - } - - static bool CompareKeys(ImmutableArray b1, ImmutableArray b2) - { - return b1.AsSpan().SequenceEqual(b2.AsSpan()); - } - internal static bool IsConstructor(IMethodBaseSymbol method) { return method.IsSpecialName && method.Name == ConstructorInfo.ConstructorName; } + /// + /// Defines a constructor. + /// + /// + /// + /// + /// internal static IConstructorSymbolBuilder DefineConstructor(ITypeSymbolBuilder tb, System.Reflection.MethodAttributes attribs, ITypeSymbol[] parameterTypes) { return tb.DefineConstructor(attribs | System.Reflection.MethodAttributes.SpecialName | System.Reflection.MethodAttributes.RTSpecialName, parameterTypes); diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index d14dc4fef8..e8c275675d 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -75,7 +75,7 @@ sealed class AssemblyLoader IModuleSymbol[] modules; Dictionary nameMap; bool hasDotNetModule; - AssemblyNameInfo[] internalsVisibleTo; + AssemblyIdentity[] internalsVisibleTo; string[] jarList; #if !IMPORTER && !EXPORTER && !FIRST_PASS sun.misc.URLClassPath urlClassPath; @@ -384,7 +384,7 @@ internal RuntimeJavaType CreateJavaTypeForAssemblyType(ITypeSymbol type) } } - internal bool InternalsVisibleTo(AssemblyNameInfo otherName) + internal bool InternalsVisibleTo(AssemblyIdentity otherName) { if (internalsVisibleTo == null) Interlocked.CompareExchange(ref internalsVisibleTo, loader.Context.AttributeHelper.GetInternalsVisibleToAttributes(assembly), null); @@ -393,7 +393,7 @@ internal bool InternalsVisibleTo(AssemblyNameInfo otherName) { // we match the simple name and PublicKeyToken (because the AssemblyName constructor used // by GetInternalsVisibleToAttributes() only sets the PublicKeyToken, even if a PublicKey is specified) - if (ReflectUtil.MatchNameAndPublicKeyToken(name, otherName)) + if (AssemblyIdentity.MemberwiseEqual(name, otherName) == true && AssemblyIdentity.KeysEqual(name, otherName)) return true; } @@ -1108,7 +1108,7 @@ internal override bool InternalsVisibleToImpl(RuntimeJavaType wrapper, RuntimeJa if (acl == null) return false; - var otherName = acl.GetAssembly(friend).GetName(); + var otherName = acl.GetAssembly(friend).GetIdentity(); #endif return GetLoader(GetAssembly(wrapper)).InternalsVisibleTo(otherName); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index 06f473f1f3..1cbe1c18ff 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -558,7 +558,7 @@ internal ITypeSymbol FinishImpl() } else { - cb = ReflectUtil.DefineTypeInitializer(typeBuilder, wrapper.classLoader); + cb = typeBuilder.DefineTypeInitializer(); context.AttributeHelper.HideFromJava(cb); } var ilGenerator = context.CodeEmitterFactory.Create(cb); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index ed378f2a18..d166671fe1 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -2481,7 +2481,7 @@ internal override IMethodBaseSymbol LinkMethod(RuntimeJavaMethod mw) } else if (m.IsClassInitializer) { - method = ReflectUtil.DefineTypeInitializer(typeBuilder, wrapper.classLoader); + method = typeBuilder.DefineTypeInitializer(); } else { diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index 4bb8d9c889..3dbfba4b51 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -2744,7 +2744,7 @@ internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDyn var tb = compiler.finish.DefineIndyCallSiteType(); var fb = tb.DefineField("value", typeofIndyCallSite, FieldAttributes.Static | FieldAttributes.Assembly); - var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(ReflectUtil.DefineTypeInitializer(tb, compiler.clazz.ClassLoader)); + var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(tb.DefineTypeInitializer()); ilgen.Emit(System.Reflection.Emit.OpCodes.Ldnull); ilgen.Emit(System.Reflection.Emit.OpCodes.Ldftn, CreateBootstrapStub(compiler, cpi, delegateType, tb, fb, methodGetTarget)); ilgen.Emit(System.Reflection.Emit.OpCodes.Newobj, compiler.finish.Context.MethodHandleUtil.GetDelegateConstructor(delegateType)); @@ -3102,7 +3102,7 @@ static IFieldSymbolBuilder CreateField(Compiler compiler, MethodTypeConstantHand { var tb = compiler.finish.DefineMethodTypeConstantType(handle); var field = tb.DefineField("value", compiler.finish.Context.JavaBase.TypeOfJavaLangInvokeMethodType.TypeAsSignatureType, FieldAttributes.Assembly | FieldAttributes.Static | FieldAttributes.InitOnly); - var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(ReflectUtil.DefineTypeInitializer(tb, compiler.clazz.ClassLoader)); + var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(tb.DefineTypeInitializer()); var delegateType = compiler.finish.Context.MethodHandleUtil.CreateDelegateTypeForLoadConstant(args, ret); ilgen.Emit(System.Reflection.Emit.OpCodes.Call, compiler.finish.Context.ByteCodeHelperMethods.LoadMethodType.MakeGenericMethod(delegateType)); ilgen.Emit(System.Reflection.Emit.OpCodes.Stsfld, field); diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index 72ccbb4a81..7e321787bc 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -135,9 +135,9 @@ internal void AddReference(ImportClassLoader ccl) peerReferences.Add(ccl); } - internal AssemblyNameInfo GetAssemblyName() + internal AssemblyIdentity GetAssemblyName() { - return assemblyBuilder.GetName(); + return assemblyBuilder.GetIdentity(); } private static PermissionSet Combine(PermissionSet p1, PermissionSet p2) @@ -481,18 +481,15 @@ void AddInternalsVisibleToAttribute(ImportClassLoader ccl) { internalsVisibleTo.Add(ccl); var asm = ccl.assemblyBuilder; - var asmName = asm.GetName(); - var name = asmName.Name; - var pubkey = asmName.PublicKeyOrToken; + var asmIdentity = asm.GetIdentity(); - if (pubkey.IsEmpty && asmName.PublicKeyOrToken.IsEmpty == false) - pubkey = asmName.PublicKeyOrToken; - - if (pubkey != null && pubkey.Length != 0) + var name = asmIdentity.Name; + var publicKeyToken = asmIdentity.PublicKeyToken; + if (publicKeyToken.Length > 0) { var sb = new StringBuilder(name); sb.Append(", PublicKey="); - foreach (byte b in pubkey) + foreach (byte b in publicKeyToken) sb.AppendFormat("{0:X2}", b); name = sb.ToString(); @@ -1897,7 +1894,7 @@ internal void Process4thPass(ICollection remappedTypes) if (classDef.Clinit != null) { - var cb = ReflectUtil.DefineTypeInitializer(typeBuilder, classLoader); + var cb = typeBuilder.DefineTypeInitializer(); var ilgen = Context.CodeEmitterFactory.Create(cb); // TODO emit code to make sure super class is initialized classDef.Clinit.Body.Emit(classLoader, ilgen); @@ -2507,7 +2504,7 @@ internal void FinishRemappedTypes() private static bool IsSigned(IAssemblySymbol asm) { - return asm.GetName().PublicKeyOrToken.IsEmpty == false; + return asm.GetIdentity().IsStrongName; } /// @@ -2618,7 +2615,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag // if it's an IKVM compiled assembly, make sure that it was compiled against same version of the runtime foreach (var asmref in reference.GetReferencedAssemblies()) { - if (asmref.Name == runtimeAssembly.GetName().Name) + if (asmref.Name == runtimeAssembly.GetIdentity().Name) { if (IsSigned(runtimeAssembly)) { @@ -2628,8 +2625,7 @@ static int CreateCompiler(RuntimeContext context, StaticCompiler compiler, IDiag } else { - if (asmref.PublicKeyOrToken.IsEmpty == false) - throw new DiagnosticEventException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); + throw new DiagnosticEventException(DiagnosticEvent.RuntimeMismatch(reference.Location, runtimeAssembly.FullName, asmref.FullName)); } } } diff --git a/src/IKVM.Tools.Importer/ImportContextFactory.cs b/src/IKVM.Tools.Importer/ImportContextFactory.cs index 40c8f58d91..5772faabd1 100644 --- a/src/IKVM.Tools.Importer/ImportContextFactory.cs +++ b/src/IKVM.Tools.Importer/ImportContextFactory.cs @@ -494,7 +494,7 @@ void ResolveReferences(List imports) { var forwarder = asm.GetType("__"); if (forwarder != null && forwarder.Assembly != asm) - diagnostics.NonPrimaryAssemblyReference(asm.Location, forwarder.Assembly.GetName().Name); + diagnostics.NonPrimaryAssemblyReference(asm.Location, forwarder.Assembly.GetIdentity().Name); } } } diff --git a/src/IKVM.Tools.Importer/Proxy.cs b/src/IKVM.Tools.Importer/Proxy.cs index 2c1717e7e3..f0d9999e57 100644 --- a/src/IKVM.Tools.Importer/Proxy.cs +++ b/src/IKVM.Tools.Importer/Proxy.cs @@ -360,7 +360,7 @@ void CreateMethod(ImportClassLoader loader, ITypeSymbolBuilder tb, ProxyMethod p void CreateStaticInitializer(ITypeSymbolBuilder tb, List methods, ImportClassLoader loader) { - var ilgen = loader.Context.CodeEmitterFactory.Create(ReflectUtil.DefineTypeInitializer(tb, loader)); + var ilgen = loader.Context.CodeEmitterFactory.Create(tb.DefineTypeInitializer()); var callerID = ilgen.DeclareLocal(loader.Context.JavaBase.TypeOfIkvmInternalCallerID.TypeAsSignatureType); var tbCallerID = RuntimeByteCodeJavaType.FinishContext.EmitCreateCallerID(loader.Context, tb, ilgen); ilgen.Emit(OpCodes.Stloc, callerID); From 9fa2ff9754cfb4ab0e721b3922202c99271c839c Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sat, 5 Oct 2024 20:30:47 -0500 Subject: [PATCH 30/59] Add EmitSymbols to RuntimeContextOptions instead of JVM. Fix ExportTool's bootstrap settings. --- src/IKVM.Runtime/AttributeHelper.cs | 3 + src/IKVM.Runtime/DynamicClassLoader.cs | 61 ++++++++++++------- src/IKVM.Runtime/JVM.Internal.cs | 5 +- src/IKVM.Runtime/JVM.cs | 39 ------------ src/IKVM.Runtime/RuntimeClassLoaderFactory.cs | 8 +-- src/IKVM.Runtime/RuntimeContextOptions.cs | 10 ++- src/IKVM.Tools.Exporter/ExportImpl.cs | 4 +- src/IKVM.Tools.Importer/ImportTool.cs | 3 +- 8 files changed, 61 insertions(+), 72 deletions(-) diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index 36bd449d0d..6bf07f89b6 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -996,6 +996,9 @@ internal RemappedTypeAttribute GetRemappedType(ITypeSymbol type) internal RemappedClassAttribute[] GetRemappedClasses(IAssemblySymbol coreAssembly) { + if (coreAssembly == null) + throw new ArgumentNullException(nameof(coreAssembly)); + var attrs = new List(); foreach (var cad in coreAssembly.GetCustomAttributes(TypeOfRemappedClassAttribute)) diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index 9280aba817..bd93ff2fc0 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -210,9 +210,7 @@ public static string TypeNameMangleImpl(ConcurrentDictionary moduleBuilder; -#if !IMPORTER - -#if NETFRAMEWORK +#if NETFRAMEWORK && !IMPORTER internal sealed class ForgedKeyPair : StrongNameKeyPair { @@ -524,45 +516,68 @@ private static SerializationInfo ToInfo(byte[] publicKey) #endif + /// + /// Creates a new dynamic module. + /// + /// + /// public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context) { return CreateModuleBuilder(context, new AssemblyIdentity("ikvm_dynamic_assembly__" + (uint)Environment.TickCount)); } + /// + /// Creates a new dynamic module. + /// + /// + /// + /// public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, AssemblyIdentity name) { + // set version on assembly var now = DateTime.Now; - name = new AssemblyIdentity(name.Name, new Version(now.Year, (now.Month * 100) + now.Day, (now.Hour * 100) + now.Minute, (now.Second * 1000) + now.Millisecond)); - var attribs = new List(); - -#if NETFRAMEWORK - if (!AppDomain.CurrentDomain.IsFullyTrusted) - attribs.Add(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(System.Security.SecurityTransparentAttribute).FullName).GetConstructor([]), [])); -#endif - - var assemblyBuilder = DefineDynamicAssembly(context, name, attribs.ToArray()); + name = new AssemblyIdentity( + name.Name, + new Version(now.Year, (now.Month * 100) + now.Day, (now.Hour * 100) + now.Minute, (now.Second * 1000) + now.Millisecond), + name.CultureName, + name.HasPublicKey ? name.PublicKey : name.PublicKeyToken, + name.HasPublicKey, + name.ContentType, + name.ProcessorArchitecture); + + var attribs = Array.Empty(); + if (AppDomain.CurrentDomain.IsFullyTrusted == false) + attribs = [context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(System.Security.SecurityTransparentAttribute).FullName).GetConstructor([]), [])]; + + var assemblyBuilder = DefineDynamicAssembly(context, name, attribs); context.AttributeHelper.SetRuntimeCompatibilityAttribute(assemblyBuilder); // determine debugging mode var debugMode = DebuggingModes.Default | DebuggingModes.IgnoreSymbolStoreSequencePoints; - if (JVM.EmitSymbols) + if (context.Options.EmitSymbols) debugMode |= DebuggingModes.DisableOptimizations; + // add debugging mode to assembly context.AttributeHelper.SetDebuggingModes(assemblyBuilder, debugMode); - var moduleBuilder = assemblyBuilder.DefineModule(name.Name, null, JVM.EmitSymbols); - + // create new module + var moduleBuilder = assemblyBuilder.DefineModule(name.Name, null, context.Options.EmitSymbols); moduleBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.JavaModuleAttribute).FullName).GetConstructor([]), [])); return moduleBuilder; } + /// + /// Creates a new dynamic assembly. + /// + /// + /// + /// + /// static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyIdentity name, ICustomAttributeBuilder[] assemblyAttributes) { return context.Resolver.Symbols.DefineAssembly(name, assemblyAttributes); } -#endif - } } diff --git a/src/IKVM.Runtime/JVM.Internal.cs b/src/IKVM.Runtime/JVM.Internal.cs index 543cf847f9..c2c71d6156 100644 --- a/src/IKVM.Runtime/JVM.Internal.cs +++ b/src/IKVM.Runtime/JVM.Internal.cs @@ -1,4 +1,5 @@ using System; +using System.Diagnostics; using IKVM.CoreLib.Diagnostics.Tracing; using IKVM.Runtime.Accessors; @@ -25,9 +26,9 @@ internal static class Internal #if FIRST_PASS == false && IMPORTER == false && EXPORTER == false #if NETFRAMEWORK - internal static readonly RuntimeContextOptions contextOptions = new RuntimeContextOptions(dynamicAssemblySuffixAndPublicKey: RuntimeContextOptions.SignedDefaultDynamicAssemblySuffixAndPublicKey); + internal static readonly RuntimeContextOptions contextOptions = new RuntimeContextOptions(Debugger.IsAttached, dynamicAssemblySuffixAndPublicKey: RuntimeContextOptions.SignedDefaultDynamicAssemblySuffixAndPublicKey); #else - internal static readonly RuntimeContextOptions contextOptions = new RuntimeContextOptions(dynamicAssemblySuffixAndPublicKey: RuntimeContextOptions.UnsignedDefaultDynamicAssemblySuffixAndPublicKey); + internal static readonly RuntimeContextOptions contextOptions = new RuntimeContextOptions(Debugger.IsAttached, dynamicAssemblySuffixAndPublicKey: RuntimeContextOptions.UnsignedDefaultDynamicAssemblySuffixAndPublicKey); #endif internal static readonly RuntimeContext context = new RuntimeContext(contextOptions, DiagnosticEventSource.Instance, new Resolver()); internal static readonly VfsTable vfs = VfsTable.BuildDefaultTable(new VfsRuntimeContext(context), Properties.HomePath); diff --git a/src/IKVM.Runtime/JVM.cs b/src/IKVM.Runtime/JVM.cs index 159f7aadf5..61bc043ed2 100644 --- a/src/IKVM.Runtime/JVM.cs +++ b/src/IKVM.Runtime/JVM.cs @@ -1,10 +1,8 @@ using System; -using System.Diagnostics; using System.Runtime.CompilerServices; using System.Runtime.ExceptionServices; using System.Security; using System.Text; -using System.Threading; using IKVM.Runtime.Vfs; @@ -21,7 +19,6 @@ public static partial class JVM static bool initialized; #if EXPORTER == false - static int emitSymbols; internal static bool RelaxedVerification = true; internal static bool AllowNonVirtualCalls; internal static readonly bool DisableEagerClassLoading = SafeGetEnvironmentVariable("IKVM_DISABLE_EAGER_CLASS_LOADING") != null; @@ -90,42 +87,6 @@ internal static void Init() #endif } -#if !IMPORTER && !EXPORTER - - internal static bool EmitSymbols - { - get - { - if (emitSymbols == 0) - { - var state = 2; - -#if NETFRAMEWORK - // check app.config on Framework - if (string.Equals(System.Configuration.ConfigurationManager.AppSettings["ikvm-emit-symbols"] ?? "", "true", StringComparison.OrdinalIgnoreCase)) - state = 1; -#endif - - // respect the IKVM_EMIT_SYMBOLs environmental variable - if (string.Equals(Environment.GetEnvironmentVariable("IKVM_EMIT_SYMBOLS") ?? "", "true", StringComparison.OrdinalIgnoreCase)) - state = 1; - - // by default enable symbols if a debugger is attached - if (state == 2 && Debugger.IsAttached) - state = 1; - - // make sure we only set the value once, because it isn't allowed to changed as that could cause - // the compiler to try emitting symbols into a ModuleBuilder that doesn't accept them (and would - // throw an InvalidOperationException) - Interlocked.CompareExchange(ref emitSymbols, state, 0); - } - - return emitSymbols == 1; - } - } - -#endif - #if FIRST_PASS == false && IMPORTER == false && EXPORTER == false /// diff --git a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs index 6e564b1660..a8220ffade 100644 --- a/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs +++ b/src/IKVM.Runtime/RuntimeClassLoaderFactory.cs @@ -153,18 +153,18 @@ internal RuntimeClassLoader GetClassLoaderWrapper(java.lang.ClassLoader javaClas if (wrapper == null) { var opt = CodeGenOptions.None; - if (JVM.EmitSymbols) + if (context.Options.EmitSymbols) opt |= CodeGenOptions.DisableOptimizations; -#if NETFRAMEWORK - if (!AppDomain.CurrentDomain.IsFullyTrusted) + if (AppDomain.CurrentDomain.IsFullyTrusted == false) opt |= CodeGenOptions.NoAutomagicSerialization; -#endif + wrapper = new RuntimeClassLoader(context, opt, javaClassLoader); SetWrapperForClassLoader(javaClassLoader, wrapper); } return wrapper; } } + #endif /// diff --git a/src/IKVM.Runtime/RuntimeContextOptions.cs b/src/IKVM.Runtime/RuntimeContextOptions.cs index 20f1f047c6..3fd7743caf 100644 --- a/src/IKVM.Runtime/RuntimeContextOptions.cs +++ b/src/IKVM.Runtime/RuntimeContextOptions.cs @@ -7,20 +7,28 @@ internal class RuntimeContextOptions internal const string SignedDefaultDynamicAssemblySuffixAndPublicKey = "-ikvm-runtime-injected, PublicKey=00240000048000009400000006020000002400005253413100040000010001009D674F3D63B8D7A4C428BD7388341B025C71AA61C6224CD53A12C21330A3159D300051FE2EED154FE30D70673A079E4529D0FD78113DCA771DA8B0C1EF2F77B73651D55645B0A4294F0AF9BF7078432E13D0F46F951D712C2FCF02EB15552C0FE7817FC0AED58E0984F86661BF64D882F29B619899DD264041E7D4992548EB9E"; internal const string UnsignedDefaultDynamicAssemblySuffixAndPublicKey = "-ikvm-runtime-injected"; + readonly bool emitSymbols; readonly bool bootstrap; readonly string dynamicAssemblySuffixAndPublicKey; /// /// Initializes a new instance. /// + /// /// /// - public RuntimeContextOptions(bool bootstrap = false, string dynamicAssemblySuffixAndPublicKey = null) + public RuntimeContextOptions(bool emitSymbols = false, bool bootstrap = false, string dynamicAssemblySuffixAndPublicKey = null) { + this.emitSymbols = emitSymbols; this.bootstrap = bootstrap; this.dynamicAssemblySuffixAndPublicKey = dynamicAssemblySuffixAndPublicKey ?? UnsignedDefaultDynamicAssemblySuffixAndPublicKey; } + /// + /// Gets whether or not symbols should be emitted. + /// + public bool EmitSymbols => emitSymbols; + /// /// Gets whether or not bootstrap mode is enabled. /// diff --git a/src/IKVM.Tools.Exporter/ExportImpl.cs b/src/IKVM.Tools.Exporter/ExportImpl.cs index 1c506da3a9..37622464fc 100644 --- a/src/IKVM.Tools.Exporter/ExportImpl.cs +++ b/src/IKVM.Tools.Exporter/ExportImpl.cs @@ -146,7 +146,7 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(true), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols, options.Bootstrap), compiler); + context = new RuntimeContext(new RuntimeContextOptions(bootstrap: true), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols, true), compiler); context.ClassLoaderFactory.SetBootstrapClassLoader(new RuntimeBootstrapClassLoader(context)); } else @@ -172,7 +172,7 @@ public int Execute() } compiler = new StaticCompiler(universe, assemblyResolver, runtimeAssembly); - context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols, options.Bootstrap), compiler); + context = new RuntimeContext(new RuntimeContextOptions(), diagnostics, new ExportRuntimeSymbolResolver(diagnostics, universe, symbols, false), compiler); } if (context.AttributeHelper.IsJavaModule(context.Resolver.GetSymbol(assembly.ManifestModule))) diff --git a/src/IKVM.Tools.Importer/ImportTool.cs b/src/IKVM.Tools.Importer/ImportTool.cs index c853fdd929..0e4131b3f4 100644 --- a/src/IKVM.Tools.Importer/ImportTool.cs +++ b/src/IKVM.Tools.Importer/ImportTool.cs @@ -285,9 +285,10 @@ static DiagnosticOptions GetDiagnosticOptions(IServiceProvider services, ImportO static RuntimeContextOptions CreateContextOptions(IServiceProvider services) { var u = services.GetRequiredService(); + var o = services.GetRequiredService(); var isNetFX = u.CoreLibName == "mscorlib"; var dynamicSuffix = isNetFX ? RuntimeContextOptions.SignedDefaultDynamicAssemblySuffixAndPublicKey : RuntimeContextOptions.UnsignedDefaultDynamicAssemblySuffixAndPublicKey; - return new RuntimeContextOptions(services.GetRequiredService().Bootstrap, dynamicSuffix); + return new RuntimeContextOptions(o.Debug != ImportDebug.Unspecified, o.Bootstrap, dynamicSuffix); } /// From cfa237ad61498b7a61a8739825e5a74b3e295af0 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 6 Oct 2024 11:02:50 -0500 Subject: [PATCH 31/59] Annotations need actual live attribute types. --- .../Java/Externs/java/lang/Class.cs | 32 +++++++++++++------ src/IKVM.Runtime/RuntimeJavaType.cs | 20 ++++++++++++ .../RuntimeManagedByteCodeJavaType.cs | 12 +++---- src/IKVM.Runtime/SymbolExtensions.cs | 12 +++++++ 4 files changed, 60 insertions(+), 16 deletions(-) diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs index e7c9d49e86..31a66d3d91 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/Class.cs @@ -450,26 +450,38 @@ public static string getGenericSignature0(global::java.lang.Class thisClass) return tw.GetGenericSignature(); } - internal static object AnnotationsToMap(RuntimeClassLoader loader, object[] objAnn) + /// + /// Converts an array of annotation instances to a IMap. + /// + /// + /// + /// + internal static object AnnotationsToMap(RuntimeClassLoader loader, object[] annotations) { #if FIRST_PASS throw new NotImplementedException(); #else var map = new global::java.util.LinkedHashMap(); - if (objAnn != null) + + if (annotations != null) { - foreach (object obj in objAnn) + foreach (var obj in annotations) { - var a = obj as global::java.lang.annotation.Annotation; - if (a != null) + // annotation is an actual annotation instance + if (obj is global::java.lang.annotation.Annotation annotation) { - map.put(a.annotationType(), FreezeOrWrapAttribute(a)); + map.put(annotation.annotationType(), FreezeOrWrapAttribute(annotation)); + continue; } - else if (obj is IKVM.Attributes.DynamicAnnotationAttribute) + + // annotation is a DynamicAnnotationAttribute, which encapsulates an annotation + if (obj is IKVM.Attributes.DynamicAnnotationAttribute dynamicAttribute) { - a = (global::java.lang.annotation.Annotation)JVM.NewAnnotation(loader.GetJavaClassLoader(), ((IKVM.Attributes.DynamicAnnotationAttribute)obj).Definition); - if (a != null) - map.put(a.annotationType(), a); + annotation = (global::java.lang.annotation.Annotation)JVM.NewAnnotation(loader.GetJavaClassLoader(), dynamicAttribute.Definition); + if (annotation != null) + map.put(annotation.annotationType(), annotation); + + continue; } } } diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index abb8df9745..7a5e44cf17 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -1443,26 +1443,46 @@ internal virtual MethodParametersEntry[] GetMethodParameters(RuntimeJavaMethod m } #if !IMPORTER && !EXPORTER + internal virtual string[] GetEnclosingMethod() { return null; } + /// + /// Gets the annotations declared on this type. Expected to return actual runtime instances. + /// + /// internal virtual object[] GetDeclaredAnnotations() { return null; } + /// + /// Gets the annotations declared on the specified method of this type. Expected to return actual runtime instances. + /// + /// + /// internal virtual object[] GetMethodAnnotations(RuntimeJavaMethod mw) { return null; } + /// + /// Gets the annotations declared on the specified parameters of the specified method of this type. Expected to return actual runtime instances. + /// + /// + /// internal virtual object[][] GetParameterAnnotations(RuntimeJavaMethod mw) { return null; } + /// + /// Gets the annotations declared on the specified fieldof this type. Expected to return actual runtime instances. + /// + /// + /// internal virtual object[] GetFieldAnnotations(RuntimeJavaField fw) { return null; diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index 0b5a93a43a..73fa252736 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -1104,7 +1104,7 @@ internal override string[] GetEnclosingMethod() return null; } - object[] CastArray(CustomAttribute[] l) + object[] CastArray(object[] l) { var a = new object[l.Length]; for (int i = 0; i < l.Length; i++) @@ -1115,7 +1115,7 @@ object[] CastArray(CustomAttribute[] l) internal override object[] GetDeclaredAnnotations() { - return CastArray(type.GetCustomAttributes(false)); + return CastArray(type.AsReflection().GetCustomAttributes(false)); } internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) @@ -1127,7 +1127,7 @@ internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) return null; } - return CastArray(mb.GetCustomAttributes(false)); + return CastArray(mb.AsReflection().GetCustomAttributes(false)); } internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) @@ -1150,7 +1150,7 @@ internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) var attribs = new object[parameters.Length - skip - skipEnd][]; for (int i = skip; i < parameters.Length - skipEnd; i++) - attribs[i - skip] = CastArray(parameters[i].GetCustomAttributes(false)); + attribs[i - skip] = CastArray(parameters[i].AsReflection().GetCustomAttributes(false)); return attribs; } @@ -1159,10 +1159,10 @@ internal override object[] GetFieldAnnotations(RuntimeJavaField fw) { var field = fw.GetField(); if (field != null) - return CastArray(field.GetCustomAttributes(false)); + return CastArray(field.AsReflection().GetCustomAttributes(false)); if (fw is RuntimeManagedByteCodePropertyJavaField prop) - return CastArray(prop.GetProperty().GetCustomAttributes(false)); + return CastArray(prop.GetProperty().AsReflection().GetCustomAttributes(false)); return Array.Empty(); } diff --git a/src/IKVM.Runtime/SymbolExtensions.cs b/src/IKVM.Runtime/SymbolExtensions.cs index 52745475af..e98aa76975 100644 --- a/src/IKVM.Runtime/SymbolExtensions.cs +++ b/src/IKVM.Runtime/SymbolExtensions.cs @@ -107,6 +107,18 @@ public static MethodInfo AsReflection(this IMethodSymbol symbol) #endif } + public static ParameterInfo AsReflection(this IParameterSymbol symbol) + { + if (symbol == null) + return null; + +#if IMPORTER || EXPORTER + return ((IIkvmReflectionParameterSymbol)symbol).UnderlyingParameter; +#else + return ((IReflectionParameterSymbol)symbol).UnderlyingParameter; +#endif + } + public static FieldInfo AsReflection(this IFieldSymbol symbol) { if (symbol == null) From 61300493a43ccdf1dfac077ed65760fbb4c1ea3a Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 6 Oct 2024 16:08:23 -0500 Subject: [PATCH 32/59] No need to use open generic, since GetMethod now works against closed builder. --- src/IKVM.Runtime/compiler.cs | 15 ++------------- 1 file changed, 2 insertions(+), 13 deletions(-) diff --git a/src/IKVM.Runtime/compiler.cs b/src/IKVM.Runtime/compiler.cs index 3dbfba4b51..e6692cfa10 100644 --- a/src/IKVM.Runtime/compiler.cs +++ b/src/IKVM.Runtime/compiler.cs @@ -2729,19 +2729,8 @@ internal static void Emit(Compiler compiler, ClassFile.ConstantPoolItemInvokeDyn methodLookup.Link(); var typeofIndyCallSite = typeofOpenIndyCallSite.MakeGenericType(delegateType); - IMethodSymbol methodCreateBootStrap; - IMethodSymbol methodGetTarget; - if (ReflectUtil.ContainsTypeBuilder(typeofIndyCallSite)) - { - methodCreateBootStrap = typeofOpenIndyCallSite.GetMethod("CreateBootstrap"); - methodGetTarget = typeofOpenIndyCallSite.GetMethod("GetTarget"); - } - else - { - methodCreateBootStrap = typeofIndyCallSite.GetMethod("CreateBootstrap"); - methodGetTarget = typeofIndyCallSite.GetMethod("GetTarget"); - } - + var methodCreateBootStrap = typeofIndyCallSite.GetMethod("CreateBootstrap"); + var methodGetTarget = typeofIndyCallSite.GetMethod("GetTarget"); var tb = compiler.finish.DefineIndyCallSiteType(); var fb = tb.DefineField("value", typeofIndyCallSite, FieldAttributes.Static | FieldAttributes.Assembly); var ilgen = compiler.finish.Context.CodeEmitterFactory.Create(tb.DefineTypeInitializer()); From 6ccacea9493b546221fe3dad47cdffebec448391 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 6 Oct 2024 19:27:05 -0500 Subject: [PATCH 33/59] For GetConstructors, same deal, no need to check for TypeBuilders. --- .../Java/Externs/ikvm/runtime/Util.cs | 2 +- src/IKVM.Runtime/MethodHandleUtil.compiler.cs | 9 +-------- src/IKVM.Runtime/ReflectUtil.cs | 20 ------------------- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 1 - 4 files changed, 2 insertions(+), 30 deletions(-) diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs index 5d50f9c5b6..2da52208a7 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs @@ -117,7 +117,7 @@ internal static RuntimeJavaType GetTypeWrapperFromObject(RuntimeContext context, var ts = JVM.Context.Resolver.GetSymbol(type); int rank = 0; - while (ReflectUtil.IsVector(ts)) + while (ts.IsSZArray) { ts = ts.GetElementType(); rank++; diff --git a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs index b4e2f1d716..041845bb12 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs @@ -49,14 +49,7 @@ internal IConstructorSymbol GetDelegateConstructor(ITypeSymbol delegateType) private IConstructorSymbol GetDelegateOrPackedArgsConstructor(ITypeSymbol type) { - if (ReflectUtil.ContainsTypeBuilder(type)) - { - return type.GetGenericTypeDefinition().GetConstructors()[0]; - } - else - { - return type.GetConstructors()[0]; - } + return type.GetConstructors()[0]; } // for delegate types used for "ldc " we don't want ghost arrays to be erased diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index 2259bc0653..69c23a0a99 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -91,21 +91,6 @@ internal static bool IsReflectionOnly(ITypeSymbol type) return false; } - internal static bool ContainsTypeBuilder(ITypeSymbol type) - { - while (type.HasElementType) - type = type.GetElementType(); - - if (!type.IsGenericType || type.IsGenericTypeDefinition) - return type is ITypeSymbolBuilder; - - foreach (var arg in type.GetGenericArguments()) - if (ContainsTypeBuilder(arg)) - return true; - - return type.GetGenericTypeDefinition() is ITypeSymbolBuilder; - } - internal static bool IsDynamicMethod(IMethodSymbol method) { // there's no way to distinguish a baked DynamicMethod from a RuntimeMethodInfo and @@ -179,11 +164,6 @@ private static bool MatchTypes(ITypeSymbol[] t1, ITypeSymbol[] t2) return false; } - internal static bool IsVector(ITypeSymbol type) - { - return type.IsSZArray; - } - #if IMPORTER internal static ITypeSymbol GetMissingType(ITypeSymbol type) diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index d166671fe1..21106db457 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -73,7 +73,6 @@ private sealed partial class JavaTypeImpl : DynamicImpl internal JavaTypeImpl(RuntimeJavaType host, ClassFile f, RuntimeByteCodeJavaType wrapper) { - wrapper.ClassLoader.Diagnostics.GenericCompilerInfo("constructing JavaTypeImpl for " + f.Name); this.host = host; this.classFile = f; this.wrapper = (RuntimeDynamicOrImportJavaType)wrapper; From 14a06b08dfe0e5f5c81a875d3ecc7c2f2d736e35 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Mon, 7 Oct 2024 00:22:11 -0500 Subject: [PATCH 34/59] Complete parameters on first access. Enumeratingn them on type complete causes recursion. --- .../Emit/IReflectionParameterSymbolBuilder.cs | 5 +-- .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 4 --- .../Emit/ReflectionParameterSymbolBuilder.cs | 32 +++++++++++++------ .../Reflection/ReflectionParameterTable.cs | 18 ++++------- 4 files changed, 33 insertions(+), 26 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs index 17f6fb75ea..212f8a24fc 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs @@ -1,4 +1,5 @@ -using System.Reflection.Emit; +using System.Reflection; +using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -16,7 +17,7 @@ interface IReflectionParameterSymbolBuilder : IReflectionSymbolBuilder, IParamet /// /// Invoked when the owning method of this parameter is completed. /// - void OnComplete(); + void OnComplete(ParameterInfo parameter); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs index ac5e723377..990e9379c7 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs @@ -153,10 +153,6 @@ public override void OnComplete() if (i is IReflectionGenericTypeParameterSymbolBuilder b) b.OnComplete(); - foreach (var i in GetParameters()) - if (i is IReflectionParameterSymbolBuilder b) - b.OnComplete(); - base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs index d5bd36f67e..20209ba1db 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs @@ -111,7 +111,14 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) public int Position => UnderlyingParameter.Position; /// - public override bool IsComplete => _builder == null; + public override bool IsComplete + { + get + { + lock (this) + return _builder == null; + } + } /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) @@ -153,15 +160,22 @@ public ITypeSymbol[] GetRequiredCustomModifiers() #endregion /// - public void OnComplete() + public void OnComplete(ParameterInfo parameter) { - if (ResolvingMember is IReflectionMethodBaseSymbolBuilder b) - _parameter = b.UnderlyingMethodBase.GetParameters()[Position]; - - if (ResolvingMember is IReflectionPropertySymbolBuilder p) - _parameter = p.UnderlyingPropertyBuilder.GetIndexParameters()[Position]; - - _builder = null; + if (parameter is null) + throw new ArgumentNullException(nameof(parameter)); + + if (IsComplete == false) + { + lock (this) + { + if (IsComplete == false) + { + _parameter = parameter; + _builder = null; + } + } + } } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs index 8d1faa6b16..b4d03c1d69 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs @@ -20,7 +20,6 @@ struct ReflectionParameterTable IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; - IReflectionParameterSymbol? _returnParameter; /// /// Initializes a new instance. @@ -28,7 +27,6 @@ struct ReflectionParameterTable /// /// /// - /// /// public ReflectionParameterTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionMemberSymbol member) { @@ -56,14 +54,15 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param using (_lock.CreateUpgradeableReadLock()) { var position = parameter.Position; - if (position == -1) - return _returnParameter ??= new ReflectionParameterSymbol(_context, _module, _member, parameter); - if (_table[position] == null) using (_lock.CreateWriteLock()) - return _table[position] ??= new ReflectionParameterSymbol(_context, _module, _member, parameter); + _table[position] ??= new ReflectionParameterSymbol(_context, _module, _member, parameter); + + var item = _table[position] ?? throw new InvalidOperationException(); + if (item.IsComplete == false && item is IReflectionParameterSymbolBuilder builder) + builder.OnComplete(parameter); - return _table[position] ?? throw new InvalidOperationException(); + return item; } } @@ -86,12 +85,9 @@ public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBui using (_lock.CreateUpgradeableReadLock()) { var position = parameter.Position - 1; - if (position == -1) - return (IReflectionParameterSymbolBuilder)(_returnParameter ??= new ReflectionParameterSymbolBuilder(_context, _module, (IReflectionMethodBaseSymbol)_member, parameter)); - if (_table[position] == null) using (_lock.CreateWriteLock()) - return (IReflectionParameterSymbolBuilder)(_table[position] ??= new ReflectionParameterSymbolBuilder(_context, _module, (IReflectionMethodBaseSymbol)_member, parameter)); + _table[position] ??= new ReflectionParameterSymbolBuilder(_context, _module, (IReflectionMethodBaseSymbol)_member, parameter); return (IReflectionParameterSymbolBuilder?)_table[position] ?? throw new InvalidOperationException(); } From 9222bb5448e98f0ab1b1ff4eee25c5e9c0a5d944 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Mon, 7 Oct 2024 15:31:00 -0500 Subject: [PATCH 35/59] Fix. --- .../IkvmReflectionSymbolTests.cs | 4 +- .../Reflection/ReflectionSymbolTests.cs | 4 +- .../Symbols/Emit/IAssemblySymbolBuilder.cs | 10 +-- src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 9 ++- .../IkvmReflectionAssemblySymbolBuilder.cs | 4 +- .../IkvmReflectionSymbolContext.cs | 13 +++- .../Emit/ReflectionAssemblySymbolBuilder.cs | 16 +++-- .../Reflection/ReflectionSymbolContext.cs | 37 ++++++++-- .../ErrorHandlerInterceptor.cs | 43 ++++++------ .../HarnessObserverInterceptor.cs | 68 +++++++++---------- .../IKVM.JTReg.TestAdapter.Core.csproj | 1 + .../JTRegTestDiscoverer.cs | 7 ++ src/IKVM.Runtime/DynamicClassLoader.cs | 2 +- 13 files changed, 138 insertions(+), 80 deletions(-) diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs index b827019c2f..792c054a3c 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs @@ -448,7 +448,7 @@ public void CanResolveMultipleEventBuilders() public void CanGetMethodsFromTypeBuilder() { var c = new IkvmReflectionSymbolContext(universe!); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly")); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, true); var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); var type = m.DefineType("DynamicType"); @@ -476,7 +476,7 @@ public void CanGetMethodsFromTypeBuilder() public void CanGetGenericDelegateInvoke() { var c = new IkvmReflectionSymbolContext(universe!); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly")); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, true); var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); var tb = m.DefineType("DynamicGenericDelegate", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Sealed, c.GetOrCreateTypeSymbol(coreAssembly!.GetType("System.MulticastDelegate"))); diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index 5c5bc6d2aa..edf8cf48e6 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -425,8 +425,8 @@ public void CanCompleteTypeBuilder() public void CanGetMethodsFromTypeBuilder() { var c = new ReflectionSymbolContext(); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly")); - var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); + var m = a.DefineModule("DynamicModule"); var type = m.DefineType("DynamicType"); var method = type.DefineMethod("DynamicMethod1", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs index 5df264c934..8c9ab94eff 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs @@ -63,15 +63,15 @@ interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySym /// /// Sets the entry point for this assembly, assuming that a console application is being built. /// - /// - void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy); + /// + void SetEntryPoint(IMethodSymbol entryMethod); /// /// Sets the entry point for this assembly and defines the type of the portable executable (PE file) being built. /// - /// - /// - void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, PEFileKinds target); + /// + /// + void SetEntryPoint(IMethodSymbol entryMethod, PEFileKinds fileKind); /// /// Adds a forwarded type to this assembly. diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index 32910c1899..f014a0a5bb 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -13,15 +13,20 @@ interface ISymbolContext /// Defines a dynamic assembly that has the specified name and access rights. /// /// + /// + /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name); + IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, bool collectable = true, bool saveable = false); /// /// Defines a dynamic assembly that has the specified name and access rights. /// /// + /// + /// + /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes); + IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes, bool collectable = true, bool saveable = false); /// /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs index 8145099b2e..13cc310439 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -106,13 +106,13 @@ public void DefineVersionInfoResource() } /// - public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy) + public void SetEntryPoint(IMethodSymbol mainMethodProxy) { UnderlyingAssemblyBuilder.SetEntryPoint(mainMethodProxy.Unpack()); } /// - public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, IKVM.CoreLib.Symbols.Emit.PEFileKinds target) + public void SetEntryPoint(IMethodSymbol mainMethodProxy, IKVM.CoreLib.Symbols.Emit.PEFileKinds target) { UnderlyingAssemblyBuilder.SetEntryPoint(mainMethodProxy.Unpack(), (IKVM.Reflection.Emit.PEFileKinds)target); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs index 56a5613391..a3e8d19a56 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -32,19 +32,28 @@ public IkvmReflectionSymbolContext(Universe universe) } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, bool collectable, bool saveable) { if (name is null) throw new ArgumentNullException(nameof(name)); + if (collectable) + throw new NotSupportedException("IKVM Reflection cannot produce collectable assemblies."); + if (saveable == false) + throw new NotSupportedException("IKVM Reflection can only produce saveable assemblies."); + return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Save)); } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes, bool collectable, bool saveable) { if (name is null) throw new ArgumentNullException(nameof(name)); + if (collectable) + throw new NotSupportedException("IKVM Reflection cannot produce collectable assemblies."); + if (saveable == false) + throw new NotSupportedException("IKVM Reflection can only produce saveable assemblies."); return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Save, assemblyAttributes?.Unpack())); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index c5d085a526..eae10821bd 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -124,15 +124,23 @@ public void DefineVersionInfoResource() } /// - public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy) + public void SetEntryPoint(IMethodSymbol mainMethodProxy) { - throw new NotImplementedException(); +#if NETFRAMEWORK + UnderlyingAssemblyBuilder.SetEntryPoint(mainMethodProxy.Unpack()); +#else + throw new NotSupportedException(); +#endif } /// - public void SetEntryPoint(IMethodSymbolBuilder mainMethodProxy, IKVM.CoreLib.Symbols.Emit.PEFileKinds target) + public void SetEntryPoint(IMethodSymbol mainMethodProxy, IKVM.CoreLib.Symbols.Emit.PEFileKinds target) { - throw new NotImplementedException(); +#if NETFRAMEWORK + UnderlyingAssemblyBuilder.SetEntryPoint(mainMethodProxy.Unpack(), (System.Reflection.Emit.PEFileKinds)target); +#else + throw new NotSupportedException(); +#endif } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index b435aa9033..d4f421bb90 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -29,28 +29,53 @@ public ReflectionSymbolContext() } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, bool collectable, bool saveable) { if (name is null) throw new ArgumentNullException(nameof(name)); + if (collectable && saveable) + throw new NotSupportedException("Assembly cannot be both colletable and saveable."); #if NET - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect)); + if (saveable) + throw new NotSupportedException("Assembly cannot be saveable."); + else if (collectable) + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect)); + else + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run)); #else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave)); + if (saveable) + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave)); + else if (collectable) + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect)); + else + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run)); #endif } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes, bool collectable, bool saveable) { if (name is null) throw new ArgumentNullException(nameof(name)); + if (collectable && saveable) + throw new NotSupportedException("Assembly cannot be both colletable and saveable."); + #if NET - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); + if (saveable) + throw new NotSupportedException("Assembly cannot be saveable."); + else if (collectable) + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); + else + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, assemblyAttributes?.Unpack())); #else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave,assemblyAttributes?.Unpack())); + if (saveable) + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave, assemblyAttributes?.Unpack())); + else if (collectable) + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); + else + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, assemblyAttributes?.Unpack())); #endif } diff --git a/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs b/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs index 2c39731e69..611f02bfde 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs +++ b/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs @@ -1,6 +1,6 @@ using System; - -using Castle.DynamicProxy; +using System.Linq; +using System.Reflection; namespace IKVM.JTReg.TestAdapter.Core { @@ -8,54 +8,57 @@ namespace IKVM.JTReg.TestAdapter.Core /// /// Generates an implementation of 'com.sun.javatest.TestFinder$ErrorHandler'. /// - class ErrorHandlerInterceptor : IInterceptor + class ErrorHandlerInterceptor : DispatchProxy { - static readonly ProxyGenerator DefaultProxyGenerator = new ProxyGenerator(); + static readonly MethodInfo CreateMethodInfo = typeof(DispatchProxy).GetMethods() + .Where(i => i.Name == "Create") + .Where(i => i.GetGenericArguments().Length == 2) + .First(); /// /// Creates a new implementation of 'com.sun.javatest.TestFinder$ErrorHandler'. /// /// - public static dynamic Create(IJTRegLoggerContext logger) + public static ErrorHandlerInterceptor Create(IJTRegLoggerContext logger) { - return DefaultProxyGenerator.CreateInterfaceProxyWithoutTarget(JTRegTypes.TestFinder.ErrorHandler.Type, new ErrorHandlerInterceptor(logger)); + var proxy = (ErrorHandlerInterceptor)CreateMethodInfo.MakeGenericMethod(JTRegTypes.TestFinder.ErrorHandler.Type, typeof(ErrorHandlerInterceptor)).Invoke(null, []); + proxy.SetLogger(logger); + return proxy; } - readonly IJTRegLoggerContext logger; + IJTRegLoggerContext logger; /// - /// Initializes a new instance. + /// Sets the logger instance. /// /// - /// - public ErrorHandlerInterceptor(IJTRegLoggerContext logger) + public void SetLogger(IJTRegLoggerContext logger) { this.logger = logger ?? throw new ArgumentNullException(nameof(logger)); } /// - /// + /// Intercepts method calls to the underlying type. /// - /// - public void Intercept(IInvocation invocation) + /// + /// + protected override object Invoke(MethodInfo targetMethod, object[] args) { - switch (invocation.Method.Name) + switch (targetMethod.Name) { case "error": - error(invocation.Proxy, (string)invocation.GetArgumentValue(0)); - break; - default: - invocation.Proceed(); + error((string)args[0]); break; } + + throw new InvalidOperationException(); } - public void error(dynamic proxy, string msg) + void error(string msg) { logger.SendMessage(JTRegTestMessageLevel.Error, msg); } - } } diff --git a/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs b/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs index e37941fb2e..aeb21f7489 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs +++ b/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs @@ -2,8 +2,7 @@ using System.Collections.Concurrent; using System.Collections.Generic; using System.Linq; - -using Castle.DynamicProxy; +using System.Reflection; namespace IKVM.JTReg.TestAdapter.Core { @@ -11,10 +10,13 @@ namespace IKVM.JTReg.TestAdapter.Core /// /// Generates an implementation of 'com.sun.javatest.Harness$Observer'. /// - class HarnessObserverInterceptor : IInterceptor + class HarnessObserverInterceptor : DispatchProxy { - static readonly ProxyGenerator DefaultProxyGenerator = new ProxyGenerator(); + static readonly MethodInfo CreateMethodInfo = typeof(DispatchProxy).GetMethods() + .Where(i => i.Name == "Create") + .Where(i => i.GetGenericArguments().Length == 2) + .First(); /// /// Creates a new implementation of 'com.sun.javatest.Harness$Observer'. @@ -22,23 +24,25 @@ class HarnessObserverInterceptor : IInterceptor /// public static dynamic Create(string source, dynamic testSuite, IJTRegExecutionContext context, IEnumerable tests) { - return DefaultProxyGenerator.CreateInterfaceProxyWithoutTarget(JTRegTypes.Harness.Observer.Type, new HarnessObserverInterceptor(source, testSuite, context, tests)); + var proxy = (HarnessObserverInterceptor)CreateMethodInfo.MakeGenericMethod(JTRegTypes.Harness.Observer.Type, typeof(HarnessObserverInterceptor)).Invoke(null, []); + proxy.Init(source, testSuite, context, tests); + return proxy; } - readonly string source; - readonly dynamic testSuite; - readonly IJTRegExecutionContext context; - readonly ConcurrentDictionary tests; + string source; + dynamic testSuite; + IJTRegExecutionContext context; + ConcurrentDictionary tests; /// - /// Initializes a new instance. + /// Initializes the instance. /// /// /// /// /// /// - public HarnessObserverInterceptor(string source, dynamic testSuite, IJTRegExecutionContext context, IEnumerable tests) + void Init(string source, dynamic testSuite, IJTRegExecutionContext context, IEnumerable tests) { this.source = source ?? throw new ArgumentNullException(nameof(source)); this.testSuite = testSuite ?? throw new ArgumentNullException(nameof(testSuite)); @@ -46,47 +50,43 @@ public HarnessObserverInterceptor(string source, dynamic testSuite, IJTRegExecut this.tests = new ConcurrentDictionary(tests?.Where(i => i.Source == source).ToDictionary(i => i.FullyQualifiedName, i => i) ?? new Dictionary()); } - /// - /// Invoked for any operation on the original type. - /// - /// - public void Intercept(IInvocation invocation) + /// + protected override object Invoke(MethodInfo targetMethod, object[] args) { - switch (invocation.Method.Name) + switch (targetMethod.Name) { case "startingTestRun": - startingTestRun(invocation.Proxy, invocation.GetArgumentValue(0)); + startingTestRun(args[0]); break; case "startingTest": - startingTest(invocation.Proxy, invocation.GetArgumentValue(0)); + startingTest(args[0]); break; case "error": - error(invocation.Proxy, (string)invocation.GetArgumentValue(0)); + error((string)args[0]); break; case "stoppingTestRun": - stoppingTestRun(invocation.Proxy); + stoppingTestRun(); break; case "finishedTest": - finishedTest(invocation.Proxy, invocation.GetArgumentValue(0)); + finishedTest(args[0]); break; case "finishedTesting": - finishedTesting(invocation.Proxy); + finishedTesting(); break; case "finishedTestRun": - finishedTestRun(invocation.Proxy, (bool)invocation.GetArgumentValue(0)); - break; - default: - invocation.Proceed(); + finishedTestRun((bool)args[0]); break; } + + throw new InvalidOperationException(); } - public void startingTestRun(dynamic self, dynamic parameters) + void startingTestRun(dynamic parameters) { context.SendMessage(JTRegTestMessageLevel.Informational, $"JTReg: starting test run"); } - public void startingTest(dynamic self, dynamic testResult) + void startingTest(dynamic testResult) { var desc = testResult.getDescription(); var name = (string)Util.GetFullyQualifiedTestName(source, testSuite, desc); @@ -96,17 +96,17 @@ public void startingTest(dynamic self, dynamic testResult) context.RecordStart(test); } - public void error(dynamic self, string message) + void error(string message) { context.SendMessage(JTRegTestMessageLevel.Error, $"JTReg: error: '{message}'"); } - public void stoppingTestRun(dynamic self) + void stoppingTestRun() { context.SendMessage(JTRegTestMessageLevel.Informational, $"JTReg: stopping test run"); } - public void finishedTest(dynamic self, dynamic testResult) + void finishedTest(dynamic testResult) { var desc = testResult.getDescription(); var name = (string)Util.GetFullyQualifiedTestName(source, testSuite, desc); @@ -118,12 +118,12 @@ public void finishedTest(dynamic self, dynamic testResult) context.RecordResult(rslt); } - public void finishedTesting(dynamic self) + void finishedTesting() { context.SendMessage(JTRegTestMessageLevel.Informational, $"JTReg: finished testing"); } - public void finishedTestRun(dynamic self, bool success) + void finishedTestRun(bool success) { context.SendMessage(success ? JTRegTestMessageLevel.Informational : JTRegTestMessageLevel.Warning, $"JTReg: finished test run with overall result '{success}'"); } diff --git a/src/IKVM.JTReg.TestAdapter.Core/IKVM.JTReg.TestAdapter.Core.csproj b/src/IKVM.JTReg.TestAdapter.Core/IKVM.JTReg.TestAdapter.Core.csproj index 49898215be..83826c1e42 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/IKVM.JTReg.TestAdapter.Core.csproj +++ b/src/IKVM.JTReg.TestAdapter.Core/IKVM.JTReg.TestAdapter.Core.csproj @@ -20,6 +20,7 @@ + diff --git a/src/IKVM.JTReg.TestAdapter/JTRegTestDiscoverer.cs b/src/IKVM.JTReg.TestAdapter/JTRegTestDiscoverer.cs index c4f9a52fdc..4759b6909f 100644 --- a/src/IKVM.JTReg.TestAdapter/JTRegTestDiscoverer.cs +++ b/src/IKVM.JTReg.TestAdapter/JTRegTestDiscoverer.cs @@ -43,6 +43,13 @@ public void DiscoverTests(IEnumerable sources, IDiscoveryContext discove /// public void DiscoverTests(IEnumerable sources, IDiscoveryContext discoveryContext, IMessageLogger logger, ITestCaseDiscoverySink discoverySink, CancellationToken cancellationToken) { + if (discoveryContext is null) + throw new ArgumentNullException(nameof(discoveryContext)); + if (logger is null) + throw new ArgumentNullException(nameof(logger)); + if (discoverySink is null) + throw new ArgumentNullException(nameof(discoverySink)); + foreach (var source in sources) { if (Path.GetExtension(source) is not ".exe" and not ".dll") diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index bd93ff2fc0..ab9860866e 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -575,7 +575,7 @@ public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, A /// static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyIdentity name, ICustomAttributeBuilder[] assemblyAttributes) { - return context.Resolver.Symbols.DefineAssembly(name, assemblyAttributes); + return context.Resolver.Symbols.DefineAssembly(name, assemblyAttributes, false, false); } } From 36f2f2c4876ae04805dded4d4c77436d74e8f0dc Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Mon, 7 Oct 2024 15:31:40 -0500 Subject: [PATCH 36/59] Hmm. --- src/IKVM.ConsoleApp/IKVM.ConsoleApp.csproj | 3 +- src/IKVM.ConsoleApp/Program.cs | 33 ++++++++++++++-------- src/ikvmstub/ikvmstub.csproj | 2 +- src/java/java.csproj | 2 +- src/javac/javac.csproj | 2 +- 5 files changed, 26 insertions(+), 16 deletions(-) diff --git a/src/IKVM.ConsoleApp/IKVM.ConsoleApp.csproj b/src/IKVM.ConsoleApp/IKVM.ConsoleApp.csproj index d8e11e329e..eeb7909130 100644 --- a/src/IKVM.ConsoleApp/IKVM.ConsoleApp.csproj +++ b/src/IKVM.ConsoleApp/IKVM.ConsoleApp.csproj @@ -6,13 +6,14 @@ Exe net481;net6.0;net8.0 - 11 x64 + + diff --git a/src/IKVM.ConsoleApp/Program.cs b/src/IKVM.ConsoleApp/Program.cs index ef839d3604..4772ff69cc 100644 --- a/src/IKVM.ConsoleApp/Program.cs +++ b/src/IKVM.ConsoleApp/Program.cs @@ -1,5 +1,6 @@ -using System; -using System.Diagnostics.Tracing; +using System.Threading; + +using IKVM.JTReg.TestAdapter.Core; namespace IKVM.ConsoleApp { @@ -7,21 +8,29 @@ namespace IKVM.ConsoleApp public class Program { - public static void Main(string[] args) + class MyDiscoverycontext : IJTRegDiscoveryContext { - var l = new Listener(); - var o = new java.lang.Object(); - java.lang.System.loadLibrary("hi"); - } - } + public JTRegTestOptions Options => new JTRegTestOptions() + { - class Listener : EventListener - { + }; + + public void SendMessage(JTRegTestMessageLevel level, string message) + { - protected override void OnEventWritten(EventWrittenEventArgs eventData) + } + + public void SendTestCase(JTRegTestCase testCase) + { + + } + + } + + public static void Main(string[] args) { - Console.WriteLine(eventData); + JTRegTestManager.Instance.DiscoverTests(@"D:\ikvm\src\IKVM.JTReg.TestAdapter.Tests\bin\Debug\net478\IKVM.JTReg.TestAdapter.Tests.dll", new MyDiscoverycontext(), CancellationToken.None); } } diff --git a/src/ikvmstub/ikvmstub.csproj b/src/ikvmstub/ikvmstub.csproj index f3f5a41919..e66f94dc41 100644 --- a/src/ikvmstub/ikvmstub.csproj +++ b/src/ikvmstub/ikvmstub.csproj @@ -1,7 +1,7 @@  Exe - net6.0;net8.0;net472; + net8.0;net6.0;net472; $(_SupportedToolRuntimes) true true diff --git a/src/java/java.csproj b/src/java/java.csproj index 50c47c7c4b..c83f902fdc 100644 --- a/src/java/java.csproj +++ b/src/java/java.csproj @@ -5,7 +5,7 @@ Exe - net472;net6.0;net8.0 + net8.0;net472;net6.0; $(_SupportedImageRuntimes) true ikvm.tools.java diff --git a/src/javac/javac.csproj b/src/javac/javac.csproj index b9c7810863..e539ea8fd2 100644 --- a/src/javac/javac.csproj +++ b/src/javac/javac.csproj @@ -5,7 +5,7 @@ Exe - net472;net6.0;net8.0 + net8.0;net472;net6.0 $(_SupportedImageRuntimes) true com.sun.tools.javac.Main From 8a8fa193da7f04950e2c7579e4841622a59c450a Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Mon, 7 Oct 2024 15:31:46 -0500 Subject: [PATCH 37/59] Hmm --- src/ikvmc/Properties/launchSettings.json | 2 +- src/ikvmstub/Properties/launchSettings.json | 8 ++++++++ src/java/Properties/launchSettings.json | 10 +++++----- src/javac/Properties/launchSettings.json | 14 +++++++------- 4 files changed, 21 insertions(+), 13 deletions(-) create mode 100644 src/ikvmstub/Properties/launchSettings.json diff --git a/src/ikvmc/Properties/launchSettings.json b/src/ikvmc/Properties/launchSettings.json index 1506066246..d7c47f0f8d 100644 --- a/src/ikvmc/Properties/launchSettings.json +++ b/src/ikvmc/Properties/launchSettings.json @@ -2,7 +2,7 @@ "profiles": { "ikvmc": { "commandName": "Project", - "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java.Tests\\obj\\Debug\\net8.0\\IKVM.Java.Tests.ikvmc.rsp" + "commandLineArgs": "@D:\\ikvm\\src\\IKVM.Java\\obj\\Debug\\net8.0\\IKVM.Java.ikvmc.rsp" } } } \ No newline at end of file diff --git a/src/ikvmstub/Properties/launchSettings.json b/src/ikvmstub/Properties/launchSettings.json new file mode 100644 index 0000000000..27995bdb57 --- /dev/null +++ b/src/ikvmstub/Properties/launchSettings.json @@ -0,0 +1,8 @@ +{ + "profiles": { + "ikvmstub": { + "commandName": "Project", + "commandLineArgs": "--bootstrap --nostdlib --parameters --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\Microsoft.Win32.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Collections.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Collections.NonGeneric.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Collections.Specialized.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.ComponentModel.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.ComponentModel.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Formats.Asn1.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Memory.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.HttpListener.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Primitives.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.Security.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.WebHeaderCollection.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.WebSockets.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.ObjectModel.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.InteropServices.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Runtime.Numerics.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Security.Claims.dll\" --reference:\"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Security.Cryptography.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Java\\bin\\Debug\\net8.0\\IKVM.Java.dll\" --reference:\"D:\\ikvm\\src\\IKVM.Runtime-ref\\obj\\Debug\\net8.0\\ref\\IKVM.Runtime.dll\" --out:\"System.Net.HttpListener.jar\" \"C:\\Program Files\\dotnet\\packs\\Microsoft.NETCore.App.Ref\\8.0.8\\ref\\net8.0\\System.Net.HttpListener.dll\"" + } + } +} \ No newline at end of file diff --git a/src/java/Properties/launchSettings.json b/src/java/Properties/launchSettings.json index 00ad1de133..3c1b0f9929 100644 --- a/src/java/Properties/launchSettings.json +++ b/src/java/Properties/launchSettings.json @@ -1,11 +1,11 @@ { "profiles": { "java": { - "commandName": "Project", - "commandLineArgs": "-version", - "environmentVariables": { - "IKVM_HOME_ROOT": "C:\\dev\\ikvm2\\src\\IKVM.Tests\\bin\\Debug\\net6.0\\ikvm\\" - } + "commandName": "Project", + "commandLineArgs": "-cp C:\\Users\\jhaltom\\Downloads Test", + "environmentVariables": { + "IKVM_HOME_ROOT": "D:\\ikvm\\src\\IKVM.Tests\\bin\\Debug\\net8.0\\ikvm\\" + } } } } \ No newline at end of file diff --git a/src/javac/Properties/launchSettings.json b/src/javac/Properties/launchSettings.json index b796f7ffde..daa0a7491b 100644 --- a/src/javac/Properties/launchSettings.json +++ b/src/javac/Properties/launchSettings.json @@ -1,10 +1,10 @@ { - "profiles": { - "javac": { - "commandName": "Project", - "environmentVariables": { - "IKVM_HOME_ROOT": "C:\\dev\\ikvm2\\src\\IKVM.Tests\\bin\\Debug\\net6.0\\ikvm\\" - } - } + "profiles": { + "javac": { + "commandName": "Project", + "environmentVariables": { + "IKVM_HOME_ROOT": "D:\\ikvm\\src\\IKVM.Tests\\bin\\Debug\\net8.0\\ikvm\\" + } } + } } \ No newline at end of file From c597e1c32cf1c34e1a8fedc62dac41242776f548 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Tue, 8 Oct 2024 18:57:46 -0500 Subject: [PATCH 38/59] Emit properties. The idea here is that a given symbol might need to be emitted as a different underlying type depending on the target. DynamicMethod requires RuntimeTypeHandles, and so cannot accept builders. But, building types on the fly to be used by DynamicMethods is a thing. Think this just worked out on accident previously. But now it's explicit. --- .../ReflectionConstructorSymbolBuilder.cs | 21 +- .../Emit/ReflectionEventSymbolBuilder.cs | 15 +- .../Emit/ReflectionFieldSymbolBuilder.cs | 18 +- ...ectionGenericTypeParameterSymbolBuilder.cs | 14 +- .../Reflection/Emit/ReflectionILGenerator.cs | 113 ++- .../Emit/ReflectionMemberSymbolBuilder.cs | 6 + .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 6 + .../Emit/ReflectionMethodSymbolBuilder.cs | 22 +- .../Emit/ReflectionParameterSymbolBuilder.cs | 33 +- .../Emit/ReflectionPropertySymbolBuilder.cs | 16 +- .../Emit/ReflectionSymbolBuilder.cs | 2 +- .../Emit/ReflectionTypeSymbolBuilder.cs | 680 +----------------- .../IReflectionConstructorSymbol.cs | 10 + .../Reflection/IReflectionEventSymbol.cs | 5 + .../Reflection/IReflectionFieldSymbol.cs | 10 + .../Reflection/IReflectionMemberSymbol.cs | 5 + .../Reflection/IReflectionMethodBaseSymbol.cs | 7 +- .../Reflection/IReflectionMethodSymbol.cs | 10 + .../Reflection/IReflectionParameterSymbol.cs | 5 + .../Reflection/IReflectionPropertySymbol.cs | 5 + .../Reflection/IReflectionTypeSymbol.cs | 10 + .../Reflection/ReflectionArrayTypeSymbol.cs | 34 + .../Reflection/ReflectionByRefTypeSymbol.cs | 32 + .../Reflection/ReflectionConstructorSymbol.cs | 6 + .../Reflection/ReflectionEventSymbol.cs | 3 + .../Reflection/ReflectionFieldSymbol.cs | 6 + .../ReflectionGenericSpecTypeSymbol.cs | 35 + .../ReflectionGenericTypeParameterSymbol.cs | 6 + .../Reflection/ReflectionMemberSymbol.cs | 4 + .../Reflection/ReflectionMethodBaseSymbol.cs | 3 + .../Reflection/ReflectionMethodSymbol.cs | 6 + .../Reflection/ReflectionParameterSymbol.cs | 3 + .../Reflection/ReflectionPointerTypeSymbol.cs | 32 + .../Reflection/ReflectionPropertySymbol.cs | 3 + .../Reflection/ReflectionSZArrayTypeSymbol.cs | 32 + .../Reflection/ReflectionTypeSpecSymbol.cs | 37 + .../Reflection/ReflectionTypeSpecTable.cs | 25 +- .../Reflection/ReflectionTypeSymbol.cs | 633 +--------------- .../Reflection/ReflectionTypeSymbolBase.cs | 669 +++++++++++++++++ 39 files changed, 1185 insertions(+), 1397 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index 414a329efa..ab93503cd6 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -10,8 +10,8 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflectionConstructorSymbolBuilder { - ConstructorBuilder? _builder; - ConstructorInfo _ctor; + readonly ConstructorBuilder _builder; + ConstructorInfo? _ctor; ReflectionILGenerator? _il; @@ -27,17 +27,25 @@ public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, IRefl base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _ctor = _builder; } /// - public ConstructorInfo UnderlyingConstructor => _ctor; + public ConstructorInfo UnderlyingConstructor => _ctor ?? _builder; + + /// + public ConstructorInfo UnderlyingEmitConstructor => _builder; + + /// + public ConstructorInfo UnderlyingDynamicEmitConstructor => _ctor ?? throw new InvalidOperationException(); /// public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; /// - public ConstructorBuilder UnderlyingConstructorBuilder => _builder ?? throw new InvalidOperationException(); + public override MethodBase UnderlyingEmitMethodBase => UnderlyingEmitConstructor; + + /// + public ConstructorBuilder UnderlyingConstructorBuilder => _builder; #region IConstructorSymbolBuilder @@ -85,7 +93,7 @@ public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAtt #region IConstructorSymbol /// - public override bool IsComplete => _builder == null; + public override bool IsComplete => _ctor != null; #endregion @@ -104,7 +112,6 @@ public override ITypeSymbol[] GetGenericArguments() public override void OnComplete() { _ctor = (ConstructorInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); - _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs index 0241418019..9525d00455 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs @@ -10,8 +10,9 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit class ReflectionEventSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionEventSymbolBuilder { - EventBuilder? _builder; - EventInfo _event; + readonly EventBuilder _builder; + readonly ReflectionEventBuilderInfo _builderInfo; + EventInfo? _event; /// /// Initializes a new instance. @@ -25,11 +26,14 @@ public ReflectionEventSymbolBuilder(ReflectionSymbolContext context, IReflection base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _event = new ReflectionEventBuilderInfo(_builder); + _builderInfo = new ReflectionEventBuilderInfo(_builder); } /// - public EventInfo UnderlyingEvent => _event; + public EventInfo UnderlyingEvent => _event ?? _builderInfo; + + /// + public EventInfo UnderlyingEmitEvent => UnderlyingEvent; /// public EventBuilder UnderlyingEventBuilder => _builder ?? throw new NotImplementedException(); @@ -98,7 +102,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) public IMethodSymbol? RaiseMethod => ResolveMethodSymbol(UnderlyingEvent.RaiseMethod); /// - public override bool IsComplete => _builder == null; + public override bool IsComplete => _event != null; /// public IMethodSymbol? GetAddMethod() @@ -154,7 +158,6 @@ public IMethodSymbol[] GetOtherMethods(bool nonPublic) public override void OnComplete() { _event = (EventInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); - _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs index 1c96e8bd8b..91186b5ad4 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs @@ -10,8 +10,8 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit class ReflectionFieldSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionFieldSymbolBuilder { - FieldBuilder? _builder; - FieldInfo _field; + readonly FieldBuilder _builder; + FieldInfo? _field; /// /// Initializes a new instance. @@ -25,17 +25,22 @@ public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflection base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _field = _builder; } /// - public FieldInfo UnderlyingField => _field; + public FieldInfo UnderlyingField => _field ?? _builder; + + /// + public FieldInfo UnderlyingEmitField => _builder; + + /// + public FieldInfo UnderlyingDynamicEmitField => _field ?? throw new InvalidOperationException(); /// public override MemberInfo UnderlyingMember => UnderlyingField; /// - public FieldBuilder UnderlyingFieldBuilder => _builder ?? throw new InvalidOperationException(); + public FieldBuilder UnderlyingFieldBuilder => _builder; #region IFieldSymbolBuilder @@ -110,7 +115,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) public bool IsStatic => UnderlyingField.IsStatic; /// - public override bool IsComplete => _builder == null; + public override bool IsComplete => _field != null; /// public ITypeSymbol[] GetOptionalCustomModifiers() @@ -136,7 +141,6 @@ public ITypeSymbol[] GetRequiredCustomModifiers() public override void OnComplete() { _field = ResolvingModule.UnderlyingModule.ResolveField(MetadataToken) ?? throw new InvalidOperationException(); - _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs index 6bced14f44..37c8c2b5c8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs @@ -11,9 +11,8 @@ class ReflectionGenericTypeParameterSymbolBuilder : ReflectionMemberSymbolBuilde { readonly IReflectionMemberSymbol? _resolvingMember; - - GenericTypeParameterBuilder? _builder; - Type _type; + readonly GenericTypeParameterBuilder _builder; + Type? _type; ReflectionTypeSpecTable _specTable; @@ -30,12 +29,17 @@ public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext conte { _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _type = _builder; _specTable = new ReflectionTypeSpecTable(); } /// - public Type UnderlyingType => _type; + public Type UnderlyingType => _type ?? _builder; + + /// + public Type UnderlyingEmitType => UnderlyingType; + + /// + public Type UnderlyingDynamicEmitType => _type ?? throw new InvalidOperationException(); /// public override MemberInfo UnderlyingMember => UnderlyingType; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs index ee009451eb..4cbac54c0b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs @@ -1,4 +1,5 @@ using System; +using System.Diagnostics.CodeAnalysis; using System.Diagnostics.SymbolStore; using System.Reflection; using System.Reflection.Emit; @@ -14,25 +15,86 @@ class ReflectionILGenerator : IILGenerator readonly ReflectionSymbolContext _context; readonly ILGenerator _il; + readonly bool _dynamic = false; /// /// Initializes a new instance. /// + /// /// - public ReflectionILGenerator(ReflectionSymbolContext context, ILGenerator il) + /// + /// + public ReflectionILGenerator(ReflectionSymbolContext context, ILGenerator il, bool dynamic = false) { _context = context ?? throw new ArgumentNullException(nameof(context)); _il = il ?? throw new ArgumentNullException(nameof(il)); + _dynamic = dynamic; } /// public int ILOffset => _il.ILOffset; + /// + /// Gets the underlying emit type for the given . + /// + /// + /// + [return: NotNullIfNotNull(nameof(symbol))] + Type? GetEmitType(ITypeSymbol? symbol) + { + var n = symbol.Name; + if (_dynamic) + return ((IReflectionTypeSymbol?)symbol)?.UnderlyingDynamicEmitType; + else + return ((IReflectionTypeSymbol?)symbol)?.UnderlyingEmitType; + } + + /// + /// Gets the underlying emit type for the given . + /// + /// + /// + [return: NotNullIfNotNull(nameof(symbol))] + FieldInfo? GetEmitField(IFieldSymbol? symbol) + { + if (_dynamic) + return ((IReflectionFieldSymbol?)symbol)?.UnderlyingDynamicEmitField; + else + return ((IReflectionFieldSymbol?)symbol)?.UnderlyingEmitField; + } + + /// + /// Gets the underlying emit type for the given . + /// + /// + /// + [return: NotNullIfNotNull(nameof(symbol))] + ConstructorInfo? GetEmitConstructor(IConstructorSymbol? symbol) + { + if (_dynamic) + return ((IReflectionConstructorSymbol?)symbol)?.UnderlyingDynamicEmitConstructor; + else + return ((IReflectionConstructorSymbol?)symbol)?.UnderlyingEmitConstructor; + } + + /// + /// Gets the underlying emit type for the given . + /// + /// + /// + [return: NotNullIfNotNull(nameof(symbol))] + MethodInfo? GetEmitMethod(IMethodSymbol? symbol) + { + if (_dynamic) + return ((IReflectionMethodSymbol?)symbol)?.UnderlyingDynamicEmitMethod; + else + return ((IReflectionMethodSymbol?)symbol)?.UnderlyingEmitMethod; + } + /// public void BeginCatchBlock(ITypeSymbol? exceptionType) { - _il.BeginCatchBlock(exceptionType?.Unpack()!); - + _il.BeginCatchBlock(GetEmitType(exceptionType)!); } /// @@ -68,13 +130,13 @@ public void BeginScope() /// public ILocalBuilder DeclareLocal(ITypeSymbol localType, bool pinned) { - return new ReflectionLocalBuilder(_context, _il.DeclareLocal(localType.Unpack(), pinned)); + return new ReflectionLocalBuilder(_context, _il.DeclareLocal(GetEmitType(localType), pinned)); } /// public ILocalBuilder DeclareLocal(ITypeSymbol localType) { - return new ReflectionLocalBuilder(_context, _il.DeclareLocal(localType.Unpack())); + return new ReflectionLocalBuilder(_context, _il.DeclareLocal(GetEmitType(localType))); } /// @@ -84,64 +146,63 @@ public ILabel DefineLabel() } /// - public void Emit(OpCode opcode, ILocalBuilder local) + public void Emit(OpCode opcode, ITypeSymbol cls) { - _il.Emit(opcode, local.Unpack()); + _il.Emit(opcode, GetEmitType(cls)); } /// - public void Emit(OpCode opcode, ITypeSymbol cls) + public void Emit(OpCode opcode, IFieldSymbol field) { - _il.Emit(opcode, cls.Unpack()); + _il.Emit(opcode, GetEmitField(field)); } /// - public void Emit(OpCode opcode, string str) + public void Emit(OpCode opcode, IConstructorSymbol con) { - _il.Emit(opcode, str); + _il.Emit(opcode, GetEmitConstructor(con)); } /// - public void Emit(OpCode opcode, float arg) + public void Emit(OpCode opcode, IMethodSymbol method) { - _il.Emit(opcode, arg); + _il.Emit(opcode, GetEmitMethod(method)); } /// - public void Emit(OpCode opcode, sbyte arg) + public void Emit(OpCode opcode, ISignatureHelper signature) { - _il.Emit(opcode, arg); + throw new NotImplementedException(); } /// - public void Emit(OpCode opcode, IMethodSymbol meth) + public void Emit(OpCode opcode, ILabel[] labels) { - _il.Emit(opcode, meth.Unpack()); + _il.Emit(opcode, labels.Unpack()); } /// - public void Emit(OpCode opcode, ISignatureHelper signature) + public void Emit(OpCode opcode, ILocalBuilder local) { - throw new NotImplementedException(); - //_il.Emit(opcode, signature.Unpack()); + _il.Emit(opcode, local.Unpack()); } /// - public void Emit(OpCode opcode, ILabel[] labels) + public void Emit(OpCode opcode, string str) { - _il.Emit(opcode, labels.Unpack()); + _il.Emit(opcode, str); } /// - public void Emit(OpCode opcode, IFieldSymbol field) + public void Emit(OpCode opcode, float arg) { - _il.Emit(opcode, field.Unpack()); + _il.Emit(opcode, arg); } /// - public void Emit(OpCode opcode, IConstructorSymbol con) + public void Emit(OpCode opcode, sbyte arg) { - _il.Emit(opcode, con.Unpack()); + _il.Emit(opcode, arg); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs index b0ee71636d..b093a18e12 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs @@ -33,6 +33,9 @@ public ReflectionMemberSymbolBuilder(ReflectionSymbolContext context, IReflectio /// public abstract MemberInfo UnderlyingMember { get; } + /// + public virtual MemberInfo UnderlyingEmitMember => UnderlyingMember; + /// public IReflectionModuleSymbol ResolvingModule => _resolvingModule; @@ -337,6 +340,9 @@ public virtual void OnComplete() } + /// + public override string? ToString() => UnderlyingMember.ToString(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs index 990e9379c7..eabf450d17 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs @@ -26,9 +26,15 @@ public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IRefle /// public abstract MethodBase UnderlyingMethodBase { get; } + /// + public virtual MethodBase UnderlyingEmitMethodBase => UnderlyingMethodBase; + /// public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + /// + public override MemberInfo UnderlyingEmitMember => UnderlyingEmitMethodBase; + #region IReflectionMethodBaseSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index c071e4f5f2..c43c266183 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -2,7 +2,6 @@ using System.Reflection; using System.Reflection.Emit; -using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit @@ -11,8 +10,8 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflectionMethodSymbolBuilder { - MethodBuilder? _builder; - MethodInfo _method; + readonly MethodBuilder _builder; + MethodInfo? _method; ReflectionGenericTypeParameterTable _genericTypeParameterTable; ReflectionMethodSpecTable _specTable; @@ -31,19 +30,27 @@ public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectio base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _method = _builder; _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, resolvingModule, this); _specTable = new ReflectionMethodSpecTable(context, resolvingModule, resolvingType, this); } /// - public MethodInfo UnderlyingMethod => _method; + public MethodInfo UnderlyingMethod => _method ?? _builder; + + /// + public MethodInfo UnderlyingEmitMethod => _builder; + + /// + public MethodInfo UnderlyingDynamicEmitMethod => _method ?? throw new InvalidOperationException(); /// public override MethodBase UnderlyingMethodBase => UnderlyingMethod; /// - public MethodBuilder UnderlyingMethodBuilder => _builder ?? throw new InvalidOperationException(); + public override MethodBase UnderlyingEmitMethodBase => UnderlyingEmitMethod; + + /// + public MethodBuilder UnderlyingMethodBuilder => _builder; #region IReflectionMethodSymbolBuilder @@ -163,7 +170,7 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); /// - public override bool IsComplete => _builder == null; + public override bool IsComplete => _method != null; /// public IMethodSymbol GetBaseDefinition() @@ -189,7 +196,6 @@ public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) public override void OnComplete() { _method = (MethodInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); - _builder = null; base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs index 20209ba1db..760ce9921a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs @@ -14,7 +14,8 @@ class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder, IReflectionPar readonly IReflectionModuleSymbol _module; readonly IReflectionMemberSymbol _member; - ParameterBuilder? _builder; + readonly ParameterBuilder _builder; + readonly ReflectionParameterBuilderInfo _builderInfo; ParameterInfo _parameter; object? _constant; @@ -32,7 +33,7 @@ public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, IReflec _module = module ?? throw new ArgumentNullException(nameof(module)); _member = member ?? throw new ArgumentNullException(nameof(member)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _parameter = new ReflectionParameterBuilderInfo(builder, () => _constant); + _builderInfo = new ReflectionParameterBuilderInfo(builder, () => _constant); } /// @@ -42,10 +43,13 @@ public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, IReflec public IReflectionMemberSymbol ResolvingMember => _member; /// - public ParameterInfo UnderlyingParameter => _parameter; + public ParameterInfo UnderlyingParameter => _parameter ?? _builderInfo; /// - public ParameterBuilder UnderlyingParameterBuilder => _builder ?? throw new InvalidOperationException(); + public ParameterInfo UnderlyingEmitParameter => _parameter ?? throw new InvalidOperationException(); + + /// + public ParameterBuilder UnderlyingParameterBuilder => _builder; #region IParameterSymbolBuilder @@ -111,14 +115,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) public int Position => UnderlyingParameter.Position; /// - public override bool IsComplete - { - get - { - lock (this) - return _builder == null; - } - } + public override bool IsComplete => _parameter != null; /// public CustomAttribute[] GetCustomAttributes(bool inherit = false) @@ -165,17 +162,7 @@ public void OnComplete(ParameterInfo parameter) if (parameter is null) throw new ArgumentNullException(nameof(parameter)); - if (IsComplete == false) - { - lock (this) - { - if (IsComplete == false) - { - _parameter = parameter; - _builder = null; - } - } - } + _parameter = parameter; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs index 99859af76d..d25067236e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs @@ -10,8 +10,8 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit class ReflectionPropertySymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionPropertySymbolBuilder { - PropertyBuilder? _builder; - PropertyInfo _property; + PropertyBuilder _builder; + PropertyInfo? _property; ReflectionParameterTable _parameterTable; @@ -27,12 +27,14 @@ public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, IReflect base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _property = _builder; _parameterTable = new ReflectionParameterTable(context, resolvingModule, this); } /// - public PropertyInfo UnderlyingProperty => _property; + public PropertyInfo UnderlyingProperty => _property ?? _builder; + + /// + public PropertyInfo UnderlyingEmitProperty => UnderlyingProperty; /// public PropertyBuilder UnderlyingPropertyBuilder => _builder ?? throw new InvalidOperationException(); @@ -40,6 +42,9 @@ public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, IReflect /// public override MemberInfo UnderlyingMember => UnderlyingProperty; + /// + public override MemberInfo UnderlyingEmitMember => UnderlyingEmitProperty; + #region IReflectionPropertySymbolBuilder /// @@ -124,7 +129,7 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) public IMethodSymbol? SetMethod => ResolveMethodSymbol(UnderlyingProperty.SetMethod); /// - public override bool IsComplete => _builder == null; + public override bool IsComplete => _property != null; /// public object? GetRawConstantValue() @@ -198,7 +203,6 @@ public ITypeSymbol[] GetRequiredCustomModifiers() public override void OnComplete() { _property = (PropertyInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); - _builder = null; base.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs index 9023177499..a21ac89444 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs @@ -23,7 +23,7 @@ protected ReflectionSymbolBuilder(ReflectionSymbolContext context) : } /// - [return: NotNullIfNotNull("genericTypeParameter")] + [return: NotNullIfNotNull(nameof(genericTypeParameter))] public IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) { return Context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 31c468853d..5ce8a95be5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -1,28 +1,20 @@ using System; using System.Collections.Generic; -using System.Linq; +using System.Diagnostics.CodeAnalysis; using System.Reflection; using System.Reflection.Emit; using System.Runtime.InteropServices; -using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionTypeSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionTypeSymbolBuilder + class ReflectionTypeSymbolBuilder : ReflectionTypeSymbolBase, IReflectionTypeSymbolBuilder { - TypeBuilder? _builder; - Type _type; - - ReflectionMethodTable _methodTable; - ReflectionFieldTable _fieldTable; - ReflectionPropertyTable _propertyTable; - ReflectionEventTable _eventTable; - ReflectionGenericTypeParameterTable _genericTypeParameterTable; - ReflectionTypeSpecTable _specTable; + readonly TypeBuilder _builder; + Type? _type; List? _incompleteMethods; @@ -33,105 +25,33 @@ class ReflectionTypeSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionTy /// /// public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder module, TypeBuilder builder) : - base(context, module, null) + base(context, module) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _type = _builder; - _methodTable = new ReflectionMethodTable(context, module, this); - _fieldTable = new ReflectionFieldTable(context, module, this); - _propertyTable = new ReflectionPropertyTable(context, module, this); - _eventTable = new ReflectionEventTable(context, module, this); - _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, module, this); - _specTable = new ReflectionTypeSpecTable(context, module, this); } /// - public Type UnderlyingType => _type; - - /// - public override MemberInfo UnderlyingMember => UnderlyingType; + public override Type UnderlyingType => _type ?? _builder; /// - public TypeBuilder UnderlyingTypeBuilder => _builder ?? throw new InvalidOperationException(); - - #region ReflectionTypeSymbol - - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return _methodTable.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - return _methodTable.GetOrCreateMethodBaseSymbol(method); - } + public override Type UnderlyingEmitType => _builder; /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return _methodTable.GetOrCreateMethodSymbol(method); - } + public override Type UnderlyingDynamicEmitType => _type ?? throw new InvalidOperationException(); /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - return _fieldTable.GetOrCreateFieldSymbol(field); - } + public TypeBuilder UnderlyingTypeBuilder => _builder; /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return _propertyTable.GetOrCreatePropertySymbol(property); - } + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => (IReflectionModuleSymbolBuilder)ResolvingModule; - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return _eventTable.GetOrCreateEventSymbol(@event); - } + #region IReflectionSymbolBuilder /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) + [return: NotNullIfNotNull("genericTypeParameter")] + public IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - - /// - public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() - { - return _specTable.GetOrCreateSZArrayTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) - { - return _specTable.GetOrCreateArrayTypeSymbol(rank); - } - - /// - public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() - { - return _specTable.GetOrCreatePointerTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() - { - return _specTable.GetOrCreateByRefTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) - { - return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + return Context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); } #endregion @@ -391,571 +311,6 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) #endregion - #region ITypeSymbol - - /// - public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); - - /// - public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; - - /// - public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; - - /// - public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); - - /// - public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; - - /// - public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); - - /// - public string? FullName => UnderlyingType.FullName; - - /// - public string? Namespace => UnderlyingType.Namespace; - - /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; - - /// - public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; - - /// - public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); - - /// - public bool HasElementType => UnderlyingType.HasElementType; - - /// - public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); - - /// - public bool IsAbstract => UnderlyingType.IsAbstract; - - /// - public bool IsSZArray => UnderlyingType.IsSZArray(); - - /// - public bool IsArray => UnderlyingType.IsArray; - - /// - public bool IsAutoLayout => UnderlyingType.IsAutoLayout; - - /// - public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; - - /// - public bool IsByRef => UnderlyingType.IsByRef; - - /// - public bool IsClass => UnderlyingType.IsClass; - - /// - public bool IsEnum => UnderlyingType.IsEnum; - - /// - public bool IsInterface => UnderlyingType.IsInterface; - - /// - public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; - - /// - public bool IsGenericParameter => UnderlyingType.IsGenericParameter; - - /// - public bool IsGenericType => UnderlyingType.IsGenericType; - - /// - public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; - - /// - public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; - - /// - public bool IsNested => UnderlyingType.IsNested; - - /// - public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; - - /// - public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; - - /// - public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; - - /// - public bool IsNestedFamily => UnderlyingType.IsNestedFamily; - - /// - public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; - - /// - public bool IsNestedPublic => UnderlyingType.IsNestedPublic; - - /// - public bool IsNotPublic => UnderlyingType.IsNotPublic; - - /// - public bool IsPointer => UnderlyingType.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; - - /// - public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; - -#else - - /// - public bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public bool IsPrimitive => UnderlyingType.IsPrimitive; - - /// - public bool IsPublic => UnderlyingType.IsPublic; - - /// - public bool IsSealed => UnderlyingType.IsSealed; - - /// - public bool IsSerializable => UnderlyingType.IsSerializable; - - /// - public bool IsValueType => UnderlyingType.IsValueType; - - /// - public bool IsVisible => UnderlyingType.IsVisible; - - /// - public bool IsSignatureType => throw new NotImplementedException(); - - /// - public bool IsSpecialName => UnderlyingType.IsSpecialName; - - /// - public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); - - /// - public override bool IsComplete => _builder == null; - - /// - public int GetArrayRank() - { - return UnderlyingType.GetArrayRank(); - } - - /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); - } - - /// - public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetDefaultMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); - } - - /// - public ITypeSymbol? GetElementType() - { - return ResolveTypeSymbol(UnderlyingType.GetElementType()); - } - - /// - public string? GetEnumName(object value) - { - return UnderlyingType.GetEnumName(value); - } - - /// - public string[] GetEnumNames() - { - return UnderlyingType.GetEnumNames(); - } - - /// - public ITypeSymbol GetEnumUnderlyingType() - { - return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public Array GetEnumValues() - { - return UnderlyingType.GetEnumValues(); - } - - /// - public IEventSymbol? GetEvent(string name) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name)); - } - - /// - public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); - } - - /// - public IEventSymbol[] GetEvents() - { - return ResolveEventSymbols(UnderlyingType.GetEvents()); - } - - /// - public IEventSymbol[] GetEvents(BindingFlags bindingAttr) - { - return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name)); - } - - /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingType.GetFields()); - } - - /// - public IFieldSymbol[] GetFields(BindingFlags bindingAttr) - { - return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); - } - - /// - public ITypeSymbol[] GetGenericParameterConstraints() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public ITypeSymbol GetGenericTypeDefinition() - { - return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public ITypeSymbol? GetInterface(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); - } - - /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public IMemberSymbol[] GetMember(string name) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name)); - } - - /// - public IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers(BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetMembers()); - } - - /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) - { - if (IsComplete) - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr)); - else - return GetIncompleteMethods(bindingAttr).FirstOrDefault(i => i.Name == name); - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - if (IsComplete) - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); - else - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) - { - if (IsComplete) - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); - else - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name) - { - if (IsComplete) - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); - else - return GetIncompleteMethods().FirstOrDefault(i => i.Name == name); - } - - /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - if (IsComplete) - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); - else - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - if (IsComplete) - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); - else - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol[] GetMethods(BindingFlags bindingAttr) - { - if (IsComplete) - return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); - else - return GetIncompleteMethods(bindingAttr); - } - - /// - public IMethodSymbol[] GetMethods() - { - if (IsComplete) - return ResolveMethodSymbols(UnderlyingType.GetMethods()); - else - return GetIncompleteMethods(); - } - - /// - /// Gets the set of incomplete methods. - /// - /// - IMethodSymbol[] GetIncompleteMethods(BindingFlags bindingAttr = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance) - { - if (_incompleteMethods == null) - return []; - else - return SymbolUtil.FilterMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); - } - - /// - public ITypeSymbol? GetNestedType(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); - } - - /// - public ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetNestedTypes() - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); - } - - /// - public ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr) - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol[] GetProperties() - { - return ResolvePropertySymbols(UnderlyingType.GetProperties()); - } - - /// - public IPropertySymbol[] GetProperties(BindingFlags bindingAttr) - { - return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public bool IsAssignableFrom(ITypeSymbol? c) - { - return UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public bool IsEnumDefined(object value) - { - return UnderlyingType.IsEnumDefined(value); - } - - /// - public bool IsSubclassOf(ITypeSymbol c) - { - return UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public ITypeSymbol MakeArrayType() - { - return ResolveTypeSymbol(_type.MakeArrayType()); - } - - /// - public ITypeSymbol MakeArrayType(int rank) - { - return ResolveTypeSymbol(_type.MakeArrayType(rank)); - } - - /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return ResolveTypeSymbol(_type.MakeGenericType(typeArguments.Unpack())); - } - - /// - public ITypeSymbol MakePointerType() - { - return ResolveTypeSymbol(_type.MakePointerType()); - } - - /// - public ITypeSymbol MakeByRefType() - { - return ResolveTypeSymbol(_type.MakeByRefType()); - } - - #endregion - /// public void Complete() { @@ -963,10 +318,7 @@ public void Complete() { // complete type if (_builder.IsCreated() == false) - { _type = _builder.CreateType()!; - _builder = null; - } // force module to reresolve Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); @@ -975,7 +327,7 @@ public void Complete() } /// - public override void OnComplete() + public void OnComplete() { const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static; @@ -1002,8 +354,6 @@ public override void OnComplete() foreach (var m in GetEvents(DefaultBindingFlags)) if (m is IReflectionPropertySymbolBuilder b) b.OnComplete(); - - base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs index 6da5dafb04..43d1160302 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs @@ -11,6 +11,16 @@ interface IReflectionConstructorSymbol : IReflectionMethodBaseSymbol, IConstruct /// ConstructorInfo UnderlyingConstructor { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + ConstructorInfo UnderlyingEmitConstructor { get; } + + /// + /// Gets the underlying used for IL emit operations against dynamic methods. + /// + ConstructorInfo UnderlyingDynamicEmitConstructor { get; } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs index 09a99ae06c..f2c411fc95 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs @@ -11,6 +11,11 @@ interface IReflectionEventSymbol : IReflectionMemberSymbol, IEventSymbol /// EventInfo UnderlyingEvent { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + EventInfo UnderlyingEmitEvent { get; } + } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs index 0ceb9e07cd..86094cd8da 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs @@ -11,6 +11,16 @@ interface IReflectionFieldSymbol : IReflectionMemberSymbol, IFieldSymbol /// FieldInfo UnderlyingField { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + FieldInfo UnderlyingEmitField { get; } + + /// + /// Gets the underlying used for IL emit operations against dynamic methods. + /// + FieldInfo UnderlyingDynamicEmitField { get; } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs index a839713036..b62765637e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs @@ -21,6 +21,11 @@ interface IReflectionMemberSymbol : IReflectionSymbol, IMemberSymbol /// MemberInfo UnderlyingMember { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + MemberInfo UnderlyingEmitMember { get; } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs index 9e0105610a..b46e914f7c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs @@ -7,10 +7,15 @@ interface IReflectionMethodBaseSymbol : IReflectionMemberSymbol, IMethodBaseSymb { /// - /// Gets the underlying . + /// Gets the underlying . /// MethodBase UnderlyingMethodBase { get; } + /// + /// Gets the underlying . + /// + MethodBase UnderlyingEmitMethodBase { get; } + /// /// Gets or creates a for the given . /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs index 6d17a00c4d..07cc3b2531 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs @@ -12,6 +12,16 @@ interface IReflectionMethodSymbol : IReflectionMethodBaseSymbol, IMethodSymbol /// MethodInfo UnderlyingMethod { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + MethodInfo UnderlyingEmitMethod { get; } + + /// + /// Gets the underlying used for IL emit operations against dynamic methods. + /// + MethodInfo UnderlyingDynamicEmitMethod { get; } + /// /// Gets or creates a for the given generic type parameter. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs index 60632e80cc..55d9de63c2 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs @@ -21,6 +21,11 @@ interface IReflectionParameterSymbol : IReflectionSymbol, IParameterSymbol /// ParameterInfo UnderlyingParameter { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + ParameterInfo UnderlyingEmitParameter { get; } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs index 2b7aa24012..c1f545f79c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs @@ -11,6 +11,11 @@ interface IReflectionPropertySymbol : IReflectionMemberSymbol, IPropertySymbol /// PropertyInfo UnderlyingProperty { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + PropertyInfo UnderlyingEmitProperty { get; } + /// /// Gets or creates a for the given . /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs index edc48697a6..a36c6f0a47 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs @@ -12,6 +12,16 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// Type UnderlyingType { get; } + /// + /// Gets the underlying used for IL emit operations. + /// + Type UnderlyingEmitType { get; } + + /// + /// Gets the underlying used for IL emit operations for dynamic methods. + /// + Type UnderlyingDynamicEmitType { get; } + /// /// Gets or creates a for the given . /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs new file mode 100644 index 0000000000..99a1f0236e --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs @@ -0,0 +1,34 @@ +using System; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionArrayTypeSymbol : ReflectionTypeSpecSymbol + { + + readonly int rank; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionArrayTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, int rank) : + base(context, resolvingModule, elementType) + { + this.rank = rank; + } + + /// + public override Type UnderlyingType => ElementType.UnderlyingType.MakeArrayType(rank); + + /// + public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeArrayType(rank); + + /// + public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeArrayType(rank); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs new file mode 100644 index 0000000000..70320ff0b9 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs @@ -0,0 +1,32 @@ +using System; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionByRefTypeSymbol : ReflectionTypeSpecSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionByRefTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : + base(context, resolvingModule, elementType) + { + + } + + /// + public override Type UnderlyingType => ElementType.UnderlyingType.MakeByRefType(); + + /// + public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeByRefType(); + + /// + public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeByRefType(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs index 0d7c95667a..ce5d37ac29 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs @@ -25,6 +25,12 @@ public ReflectionConstructorSymbol(ReflectionSymbolContext context, IReflectionM /// public ConstructorInfo UnderlyingConstructor => _ctor; + /// + public ConstructorInfo UnderlyingEmitConstructor => UnderlyingConstructor; + + /// + public ConstructorInfo UnderlyingDynamicEmitConstructor => UnderlyingEmitConstructor; + /// public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs index 1b8abba999..33a0c5721f 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs @@ -25,6 +25,9 @@ public ReflectionEventSymbol(ReflectionSymbolContext context, IReflectionModuleS /// public EventInfo UnderlyingEvent => _event; + /// + public EventInfo UnderlyingEmitEvent => _event; + /// public override MemberInfo UnderlyingMember => UnderlyingEvent; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index c82d80e202..39b5c32736 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -25,6 +25,12 @@ public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleS /// public FieldInfo UnderlyingField => _field; + /// + public FieldInfo UnderlyingEmitField => UnderlyingField; + + /// + public FieldInfo UnderlyingDynamicEmitField => UnderlyingEmitField; + /// public override MemberInfo UnderlyingMember => UnderlyingField; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs new file mode 100644 index 0000000000..bba26a6ad4 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs @@ -0,0 +1,35 @@ +using System; +using System.Linq; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionGenericSpecTypeSymbol : ReflectionTypeSpecSymbol + { + + readonly IReflectionTypeSymbol[] genericTypeArguments; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionGenericSpecTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, IReflectionTypeSymbol[] genericTypeArguments) : + base(context, resolvingModule, elementType) + { + this.genericTypeArguments = genericTypeArguments ?? throw new ArgumentNullException(nameof(genericTypeArguments)); + } + + /// + public override Type UnderlyingType => ElementType.UnderlyingType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingType).ToArray()); + + /// + public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingEmitType).ToArray()); + + /// + public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingDynamicEmitType).ToArray()); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs index 853b5e4f90..5000896e34 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs @@ -34,6 +34,12 @@ public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IRe /// public Type UnderlyingType => _type; + /// + public Type UnderlyingEmitType => UnderlyingType; + + /// + public Type UnderlyingDynamicEmitType => _type; + /// public override MemberInfo UnderlyingMember => UnderlyingType; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index b97fa7aa7e..2292781123 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -32,6 +32,9 @@ public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModule /// public abstract MemberInfo UnderlyingMember { get; } + /// + public virtual MemberInfo UnderlyingEmitMember => UnderlyingMember; + /// /// Gets the which contains the metadata of this member. /// @@ -208,6 +211,7 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + /// public override string? ToString() => UnderlyingMember.ToString(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs index a4ef99e3f1..c16020d4c8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs @@ -35,6 +35,9 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param /// public abstract MethodBase UnderlyingMethodBase { get; } + /// + public virtual MethodBase UnderlyingEmitMethodBase => UnderlyingMethodBase; + /// public override MemberInfo UnderlyingMember => UnderlyingMethodBase; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index ada2a5653c..35b421e48b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -30,6 +30,12 @@ public ReflectionMethodSymbol(ReflectionSymbolContext context, IReflectionModule /// public MethodInfo UnderlyingMethod => _method; + /// + public MethodInfo UnderlyingEmitMethod => UnderlyingMethod; + + /// + public MethodInfo UnderlyingDynamicEmitMethod => UnderlyingEmitMethod; + /// public override MethodBase UnderlyingMethodBase => UnderlyingMethod; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index 23bfcf04c7..5d9c954461 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -36,6 +36,9 @@ public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionMod /// public ParameterInfo UnderlyingParameter => _parameter; + /// + public ParameterInfo UnderlyingEmitParameter => UnderlyingParameter; + #region IParameterSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs new file mode 100644 index 0000000000..0ac8787703 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs @@ -0,0 +1,32 @@ +using System; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionPointerTypeSymbol : ReflectionTypeSpecSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionPointerTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : + base(context, resolvingModule, elementType) + { + + } + + /// + public override Type UnderlyingType => ElementType.UnderlyingType.MakePointerType(); + + /// + public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakePointerType(); + + /// + public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakePointerType(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs index 4a06567d91..ca77f5d845 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs @@ -28,6 +28,9 @@ public ReflectionPropertySymbol(ReflectionSymbolContext context, IReflectionModu /// public PropertyInfo UnderlyingProperty => _property; + /// + public PropertyInfo UnderlyingEmitProperty => UnderlyingProperty; + /// public override MemberInfo UnderlyingMember => UnderlyingProperty; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs new file mode 100644 index 0000000000..63845863fe --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs @@ -0,0 +1,32 @@ +using System; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionSZArrayTypeSymbol : ReflectionTypeSpecSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionSZArrayTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : + base(context, resolvingModule, elementType) + { + + } + + /// + public override Type UnderlyingType => ElementType.UnderlyingType.MakeArrayType(); + + /// + public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeArrayType(); + + /// + public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeArrayType(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs new file mode 100644 index 0000000000..bc68441c57 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs @@ -0,0 +1,37 @@ +using System; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + abstract class ReflectionTypeSpecSymbol : ReflectionTypeSymbolBase + { + + readonly IReflectionTypeSymbol _elementType; + + ReflectionMethodTable _methodTable; + ReflectionFieldTable _fieldTable; + ReflectionPropertyTable _propertyTable; + ReflectionEventTable _eventTable; + ReflectionGenericTypeParameterTable _genericTypeParameterTable; + ReflectionTypeSpecTable _specTable; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionTypeSpecSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : + base(context, resolvingModule) + { + _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); + } + + /// + /// Gets the element type. + /// + protected IReflectionTypeSymbol ElementType => _elementType; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs index b83bdff39d..b115fb485b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs @@ -15,12 +15,12 @@ struct ReflectionTypeSpecTable readonly IReflectionModuleSymbol _module; readonly IReflectionTypeSymbol _elementType; - IndexRangeDictionary _asArray; + IndexRangeDictionary _asArray; ReaderWriterLockSlim? _asArrayLock; - IReflectionTypeSymbol? _asSZArray; - IReflectionTypeSymbol? _asPointer; - IReflectionTypeSymbol? _asByRef; - ConcurrentDictionary? _genericTypeSymbols; + ReflectionSZArrayTypeSymbol? _asSZArray; + ReflectionPointerTypeSymbol? _asPointer; + ReflectionByRefTypeSymbol? _asByRef; + ConcurrentDictionary? _genericTypeSymbols; /// /// Initializes a new instance. @@ -34,7 +34,7 @@ public ReflectionTypeSpecTable(ReflectionSymbolContext context, IReflectionModul _context = context ?? throw new ArgumentNullException(nameof(context)); _module = module ?? throw new ArgumentNullException(nameof(module)); _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); - _asArray = new IndexRangeDictionary(); + _asArray = new IndexRangeDictionary(); } /// @@ -52,7 +52,7 @@ public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) { if (_asArray[rank] == null) using (_asArrayLock.CreateWriteLock()) - _asArray[rank] = new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeArrayType(rank)); + _asArray[rank] = new ReflectionArrayTypeSymbol(_context, _module, _elementType, rank); return _asArray[rank] ?? throw new InvalidOperationException(); } @@ -65,7 +65,7 @@ public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() { if (_asSZArray == null) - Interlocked.CompareExchange(ref _asSZArray, new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeArrayType()), null); + Interlocked.CompareExchange(ref _asSZArray, new ReflectionSZArrayTypeSymbol(_context, _module, _elementType), null); return _asSZArray; } @@ -77,7 +77,7 @@ public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() { if (_asPointer == null) - Interlocked.CompareExchange(ref _asPointer, new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakePointerType()), null); + Interlocked.CompareExchange(ref _asPointer, new ReflectionPointerTypeSymbol(_context, _module, _elementType), null); return _asPointer; } @@ -89,7 +89,7 @@ public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() { if (_asByRef == null) - Interlocked.CompareExchange(ref _asByRef, new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeByRefType()), null); + Interlocked.CompareExchange(ref _asByRef, new ReflectionByRefTypeSymbol(_context, _module, _elementType), null); return _asByRef; } @@ -118,10 +118,11 @@ public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[ /// /// /// - readonly IReflectionTypeSymbol CreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) + readonly ReflectionGenericSpecTypeSymbol CreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) { - return new ReflectionTypeSymbol(_context, _module, _elementType.UnderlyingType.MakeGenericType(genericTypeArguments.Unpack())); + return new ReflectionGenericSpecTypeSymbol(_context, _module, _elementType, genericTypeArguments); } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index 1880246baa..f8476934b8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -1,24 +1,14 @@ using System; using System.Diagnostics.CodeAnalysis; -using System.Reflection; - -using IKVM.CoreLib.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionTypeSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol + class ReflectionTypeSymbol : ReflectionTypeSymbolBase { readonly Type _type; - ReflectionMethodTable _methodTable; - ReflectionFieldTable _fieldTable; - ReflectionPropertyTable _propertyTable; - ReflectionEventTable _eventTable; - ReflectionGenericTypeParameterTable _genericTypeParameterTable; - ReflectionTypeSpecTable _specTable; - /// /// Initializes a new instance. /// @@ -26,104 +16,13 @@ class ReflectionTypeSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol /// /// public ReflectionTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, Type type) : - base(context, resolvingModule, null) + base(context, resolvingModule) { _type = type ?? throw new ArgumentNullException(nameof(type)); - _methodTable = new ReflectionMethodTable(context, resolvingModule, this); - _fieldTable = new ReflectionFieldTable(context, resolvingModule, this); - _propertyTable = new ReflectionPropertyTable(context, resolvingModule, this); - _eventTable = new ReflectionEventTable(context, resolvingModule, this); - _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, resolvingModule, this); - _specTable = new ReflectionTypeSpecTable(context, resolvingModule, this); - } - - /// - public Type UnderlyingType => _type; - - /// - public override MemberInfo UnderlyingMember => UnderlyingType; - - #region IReflectionTypeSymbol - - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return _methodTable.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is ConstructorInfo ctor) - return GetOrCreateConstructorSymbol(ctor); - else - return GetOrCreateMethodSymbol((MethodInfo)method); - } - - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - if (method.IsMethodDefinition()) - return _methodTable.GetOrCreateMethodSymbol(method); - else - return ResolveMethodSymbol(method.GetGenericMethodDefinition()).GetOrCreateGenericMethodSymbol(method); - } - - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - return _fieldTable.GetOrCreateFieldSymbol(field); - } - - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return _propertyTable.GetOrCreatePropertySymbol(property); - } - - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return _eventTable.GetOrCreateEventSymbol(@event); - } - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericType) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericType); - } - - /// - public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() - { - return _specTable.GetOrCreateSZArrayTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) - { - return _specTable.GetOrCreateArrayTypeSymbol(rank); - } - - /// - public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() - { - return _specTable.GetOrCreatePointerTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() - { - return _specTable.GetOrCreateByRefTypeSymbol(); } /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) - { - return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); - } - - #endregion + public override Type UnderlyingType => _type; #region IReflectionSymbol @@ -139,532 +38,6 @@ public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[ #endregion - #region ITypeSymbol - - /// - public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); - - /// - public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; - - /// - public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; - - /// - public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); - - /// - public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; - - /// - public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); - - /// - public string? FullName => UnderlyingType.FullName; - - /// - public string? Namespace => UnderlyingType.Namespace; - - /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; - - /// - public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; - - /// - public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); - - /// - public bool HasElementType => UnderlyingType.HasElementType; - - /// - public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); - - /// - public bool IsAbstract => UnderlyingType.IsAbstract; - - /// - public bool IsSZArray => UnderlyingType.IsSZArray(); - - /// - public bool IsArray => UnderlyingType.IsArray; - - /// - public bool IsAutoLayout => UnderlyingType.IsAutoLayout; - - /// - public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; - - /// - public bool IsByRef => UnderlyingType.IsByRef; - - /// - public bool IsClass => UnderlyingType.IsClass; - - /// - public bool IsEnum => UnderlyingType.IsEnum; - - /// - public bool IsInterface => UnderlyingType.IsInterface; - - /// - public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; - - /// - public bool IsGenericParameter => UnderlyingType.IsGenericParameter; - - /// - public bool IsGenericType => UnderlyingType.IsGenericType; - - /// - public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; - - /// - public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; - - /// - public bool IsNested => UnderlyingType.IsNested; - - /// - public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; - - /// - public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; - - /// - public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; - - /// - public bool IsNestedFamily => UnderlyingType.IsNestedFamily; - - /// - public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; - - /// - public bool IsNestedPublic => UnderlyingType.IsNestedPublic; - - /// - public bool IsNotPublic => UnderlyingType.IsNotPublic; - - /// - public bool IsPointer => UnderlyingType.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; - - /// - public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; - -#else - - /// - public bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public bool IsPrimitive => UnderlyingType.IsPrimitive; - - /// - public bool IsPublic => UnderlyingType.IsPublic; - - /// - public bool IsSealed => UnderlyingType.IsSealed; - - /// - public bool IsSerializable => UnderlyingType.IsSerializable; - - /// - public bool IsValueType => UnderlyingType.IsValueType; - - /// - public bool IsVisible => UnderlyingType.IsVisible; - - /// - public bool IsSignatureType => throw new NotImplementedException(); - - /// - public bool IsSpecialName => UnderlyingType.IsSpecialName; - - /// - public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); - - /// - public int GetArrayRank() - { - return UnderlyingType.GetArrayRank(); - } - - /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); - } - - /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetDefaultMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); - } - - /// - public ITypeSymbol? GetElementType() - { - return ResolveTypeSymbol(UnderlyingType.GetElementType()); - } - - /// - public string? GetEnumName(object value) - { - return UnderlyingType.GetEnumName(value); - } - - /// - public string[] GetEnumNames() - { - return UnderlyingType.GetEnumNames(); - } - - /// - public ITypeSymbol GetEnumUnderlyingType() - { - return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public Array GetEnumValues() - { - return UnderlyingType.GetEnumValues(); - } - - /// - public IEventSymbol? GetEvent(string name) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name)); - } - - /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); - } - - /// - public IEventSymbol[] GetEvents() - { - return ResolveEventSymbols(UnderlyingType.GetEvents()); - } - - /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) - { - return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name)); - } - - /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingType.GetFields()); - } - - /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); - } - - /// - public ITypeSymbol[] GetGenericParameterConstraints() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public ITypeSymbol GetGenericTypeDefinition() - { - return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public ITypeSymbol? GetInterface(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); - } - - /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); - } - - /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public IMemberSymbol[] GetMember(string name) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name)); - } - - /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetMembers()); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); - } - - /// - public IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(UnderlyingType.GetMethods()); - } - - /// - public ITypeSymbol? GetNestedType(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); - } - - /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetNestedTypes() - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); - } - - /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol[] GetProperties() - { - return ResolvePropertySymbols(UnderlyingType.GetProperties()); - } - - /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public bool IsAssignableFrom(ITypeSymbol? c) - { - return UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public bool IsEnumDefined(object value) - { - return UnderlyingType.IsEnumDefined(value); - } - - /// - public bool IsSubclassOf(ITypeSymbol c) - { - return UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public ITypeSymbol MakeArrayType() - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); - } - - /// - public ITypeSymbol MakeArrayType(int rank) - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); - } - - /// - public ITypeSymbol MakeByRefType() - { - return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); - } - - /// - public ITypeSymbol MakePointerType() - { - return ResolveTypeSymbol(UnderlyingType.MakePointerType()); - } - - /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); - } - - #endregion - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs new file mode 100644 index 0000000000..33c07a976c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs @@ -0,0 +1,669 @@ +using System; +using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + abstract class ReflectionTypeSymbolBase : ReflectionMemberSymbol, IReflectionTypeSymbol + { + + protected ReflectionMethodTable _methodTable; + protected ReflectionFieldTable _fieldTable; + protected ReflectionPropertyTable _propertyTable; + protected ReflectionEventTable _eventTable; + protected ReflectionGenericTypeParameterTable _genericTypeParameterTable; + protected ReflectionTypeSpecTable _specTable; + + /// + /// Initializes a new instance. + /// + /// + /// + public ReflectionTypeSymbolBase(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule) : + base(context, resolvingModule, null) + { + _methodTable = new ReflectionMethodTable(context, resolvingModule, this); + _fieldTable = new ReflectionFieldTable(context, resolvingModule, this); + _propertyTable = new ReflectionPropertyTable(context, resolvingModule, this); + _eventTable = new ReflectionEventTable(context, resolvingModule, this); + _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, resolvingModule, this); + _specTable = new ReflectionTypeSpecTable(context, resolvingModule, this); + } + + /// + public abstract Type UnderlyingType { get; } + + /// + public virtual Type UnderlyingEmitType => UnderlyingType; + + /// + public virtual Type UnderlyingDynamicEmitType => UnderlyingEmitType; + + /// + public override MemberInfo UnderlyingMember => UnderlyingType; + + #region IReflectionTypeSymbol + + /// + public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + + /// + public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + { + if (method is ConstructorInfo ctor) + return GetOrCreateConstructorSymbol(ctor); + else + return GetOrCreateMethodSymbol((MethodInfo)method); + } + + /// + public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + { + if (method.IsMethodDefinition()) + return _methodTable.GetOrCreateMethodSymbol(method); + else + return ResolveMethodSymbol(method.GetGenericMethodDefinition()).GetOrCreateGenericMethodSymbol(method); + } + + /// + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + + /// + public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + + /// + public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericType) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericType); + } + + /// + public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + return _specTable.GetOrCreateSZArrayTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + return _specTable.GetOrCreateArrayTypeSymbol(rank); + } + + /// + public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() + { + return _specTable.GetOrCreatePointerTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() + { + return _specTable.GetOrCreateByRefTypeSymbol(); + } + + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + + #endregion + + #region IReflectionTypeSymbolBuilder + + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + #endregion + + #region ITypeSymbol + + /// + public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); + + /// + public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; + + /// + public TypeAttributes Attributes => UnderlyingType.Attributes; + + /// + public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); + + /// + public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; + + /// + public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); + + /// + public string? FullName => UnderlyingType.FullName; + + /// + public string? Namespace => UnderlyingType.Namespace; + + /// + public GenericParameterAttributes GenericParameterAttributes => UnderlyingType.GenericParameterAttributes; + + /// + public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; + + /// + public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); + + /// + public bool HasElementType => UnderlyingType.HasElementType; + + /// + public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); + + /// + public bool IsAbstract => UnderlyingType.IsAbstract; + + /// + public bool IsSZArray => UnderlyingType.IsSZArray(); + + /// + public bool IsArray => UnderlyingType.IsArray; + + /// + public bool IsAutoLayout => UnderlyingType.IsAutoLayout; + + /// + public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; + + /// + public bool IsByRef => UnderlyingType.IsByRef; + + /// + public bool IsClass => UnderlyingType.IsClass; + + /// + public bool IsEnum => UnderlyingType.IsEnum; + + /// + public bool IsInterface => UnderlyingType.IsInterface; + + /// + public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; + + /// + public bool IsGenericParameter => UnderlyingType.IsGenericParameter; + + /// + public bool IsGenericType => UnderlyingType.IsGenericType; + + /// + public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; + + /// + public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; + + /// + public bool IsNested => UnderlyingType.IsNested; + + /// + public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; + + /// + public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; + + /// + public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; + + /// + public bool IsNestedFamily => UnderlyingType.IsNestedFamily; + + /// + public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; + + /// + public bool IsNestedPublic => UnderlyingType.IsNestedPublic; + + /// + public bool IsNotPublic => UnderlyingType.IsNotPublic; + + /// + public bool IsPointer => UnderlyingType.IsPointer; + +#if NET8_0_OR_GREATER + + /// + public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; + + /// + public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; + +#else + + /// + public bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif + + /// + public bool IsPrimitive => UnderlyingType.IsPrimitive; + + /// + public bool IsPublic => UnderlyingType.IsPublic; + + /// + public bool IsSealed => UnderlyingType.IsSealed; + + /// + public bool IsSerializable => UnderlyingType.IsSerializable; + + /// + public bool IsValueType => UnderlyingType.IsValueType; + + /// + public bool IsVisible => UnderlyingType.IsVisible; + + /// + public bool IsSignatureType => throw new NotImplementedException(); + + /// + public bool IsSpecialName => UnderlyingType.IsSpecialName; + + /// + public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); + + /// + public int GetArrayRank() + { + return UnderlyingType.GetArrayRank(); + } + + /// + public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + { + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null)); + } + + /// + public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); + } + + /// + public IConstructorSymbol[] GetConstructors() + { + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); + } + + /// + public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + { + return ResolveConstructorSymbols(UnderlyingType.GetConstructors(bindingAttr)); + } + + /// + public IMemberSymbol[] GetDefaultMembers() + { + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); + } + + /// + public ITypeSymbol? GetElementType() + { + return ResolveTypeSymbol(UnderlyingType.GetElementType()); + } + + /// + public string? GetEnumName(object value) + { + return UnderlyingType.GetEnumName(value); + } + + /// + public string[] GetEnumNames() + { + return UnderlyingType.GetEnumNames(); + } + + /// + public ITypeSymbol GetEnumUnderlyingType() + { + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); + } + + /// + public Array GetEnumValues() + { + return UnderlyingType.GetEnumValues(); + } + + /// + public IEventSymbol? GetEvent(string name) + { + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); + } + + /// + public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + { + return ResolveEventSymbol(UnderlyingType.GetEvent(name, bindingAttr)); + } + + /// + public IEventSymbol[] GetEvents() + { + return ResolveEventSymbols(UnderlyingType.GetEvents()); + } + + /// + public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + { + return ResolveEventSymbols(UnderlyingType.GetEvents(bindingAttr)); + } + + /// + public IFieldSymbol? GetField(string name) + { + return ResolveFieldSymbol(UnderlyingType.GetField(name)); + } + + /// + public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + return ResolveFieldSymbol(UnderlyingType.GetField(name, bindingAttr)); + } + + /// + public IFieldSymbol[] GetFields() + { + return ResolveFieldSymbols(UnderlyingType.GetFields()); + } + + /// + public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + { + return ResolveFieldSymbols(UnderlyingType.GetFields(bindingAttr)); + } + + /// + public ITypeSymbol[] GetGenericArguments() + { + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); + } + + /// + public ITypeSymbol[] GetGenericParameterConstraints() + { + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); + } + + /// + public ITypeSymbol GetGenericTypeDefinition() + { + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); + } + + /// + public ITypeSymbol? GetInterface(string name) + { + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); + } + + /// + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); + } + + /// + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); + } + + /// + public ITypeSymbol[] GetInterfaces(bool inherit = true) + { + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); + } + + /// + public IMemberSymbol[] GetMember(string name) + { + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); + } + + /// + public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + { + return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); + } + + /// + public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + { + return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); + } + + /// + public IMemberSymbol[] GetMembers() + { + return ResolveMemberSymbols(UnderlyingType.GetMembers()); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); + } + + /// + public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + } + + /// + public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + { + return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); + } + + /// + public IMethodSymbol[] GetMethods() + { + return ResolveMethodSymbols(UnderlyingType.GetMethods()); + } + + /// + public ITypeSymbol? GetNestedType(string name) + { + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); + } + + /// + public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); + } + + /// + public ITypeSymbol[] GetNestedTypes() + { + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); + } + + /// + public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + { + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); + } + + /// + public IPropertySymbol[] GetProperties() + { + return ResolvePropertySymbols(UnderlyingType.GetProperties()); + } + + /// + public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + { + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); + } + + /// + public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); + } + + /// + public IPropertySymbol? GetProperty(string name) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); + } + + /// + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); + } + + /// + public bool IsAssignableFrom(ITypeSymbol? c) + { + return UnderlyingType.IsAssignableFrom(c?.Unpack()); + } + + /// + public bool IsEnumDefined(object value) + { + return UnderlyingType.IsEnumDefined(value); + } + + /// + public bool IsSubclassOf(ITypeSymbol c) + { + return UnderlyingType.IsSubclassOf(c.Unpack()); + } + + /// + public ITypeSymbol MakeArrayType() + { + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); + } + + /// + public ITypeSymbol MakeArrayType(int rank) + { + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); + } + + /// + public ITypeSymbol MakeByRefType() + { + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); + } + + /// + public ITypeSymbol MakePointerType() + { + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); + } + + /// + public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); + } + + #endregion + + } + +} From d715c0ed52c1e187f78a02d43c949013ce8c3cfb Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Tue, 8 Oct 2024 18:57:58 -0500 Subject: [PATCH 39/59] Pick proper emit type. --- src/IKVM.Runtime/CodeEmitter.cs | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/src/IKVM.Runtime/CodeEmitter.cs b/src/IKVM.Runtime/CodeEmitter.cs index a74869d2ce..f873048aa6 100644 --- a/src/IKVM.Runtime/CodeEmitter.cs +++ b/src/IKVM.Runtime/CodeEmitter.cs @@ -79,8 +79,6 @@ public CodeEmitter Create(IMethodBaseSymbolBuilder method) return new CodeEmitter(context, method.GetILGenerator(), method.DeclaringType); } -#if IMPORTER == false - /// /// Creates a new instance. /// @@ -88,11 +86,9 @@ public CodeEmitter Create(IMethodBaseSymbolBuilder method) /// public CodeEmitter Create(DynamicMethod dm) { - return new CodeEmitter(context, new ReflectionILGenerator((ReflectionSymbolContext)context.Resolver.Symbols, dm.GetILGenerator()), null); + return new CodeEmitter(context, new ReflectionILGenerator((ReflectionSymbolContext)context.Resolver.Symbols, dm.GetILGenerator(), true), null); } -#endif - } sealed class CodeEmitter From 73e95bc1571deb8f5f81afd381ed425159624f23 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Tue, 8 Oct 2024 18:58:33 -0500 Subject: [PATCH 40/59] Return null on tail. --- src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs | 5 +++-- .../HarnessObserverInterceptor.cs | 2 +- src/IKVM.JTReg.TestAdapter.Core/JTRegTypes.cs | 2 +- 3 files changed, 5 insertions(+), 4 deletions(-) diff --git a/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs b/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs index 611f02bfde..4bbf7b61a2 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs +++ b/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs @@ -8,7 +8,7 @@ namespace IKVM.JTReg.TestAdapter.Core /// /// Generates an implementation of 'com.sun.javatest.TestFinder$ErrorHandler'. /// - class ErrorHandlerInterceptor : DispatchProxy + public class ErrorHandlerInterceptor : DispatchProxy { static readonly MethodInfo CreateMethodInfo = typeof(DispatchProxy).GetMethods() @@ -52,13 +52,14 @@ protected override object Invoke(MethodInfo targetMethod, object[] args) break; } - throw new InvalidOperationException(); + return null; } void error(string msg) { logger.SendMessage(JTRegTestMessageLevel.Error, msg); } + } } diff --git a/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs b/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs index aeb21f7489..1d2d086e4c 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs +++ b/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs @@ -78,7 +78,7 @@ protected override object Invoke(MethodInfo targetMethod, object[] args) break; } - throw new InvalidOperationException(); + return null; } void startingTestRun(dynamic parameters) diff --git a/src/IKVM.JTReg.TestAdapter.Core/JTRegTypes.cs b/src/IKVM.JTReg.TestAdapter.Core/JTRegTypes.cs index cd24bff1c7..5f8248c445 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/JTRegTypes.cs +++ b/src/IKVM.JTReg.TestAdapter.Core/JTRegTypes.cs @@ -13,7 +13,7 @@ namespace IKVM.JTReg.TestAdapter.Core /// /// Provides information and accessors for JTReg types, which are dynamically loaded. /// - internal static class JTRegTypes + public static class JTRegTypes { static readonly string[] libs = Directory.GetFiles(Path.Combine(Path.GetDirectoryName(typeof(JTRegTestManager).Assembly.Location), "jtreg"), "*.jar"); From 4f9e56943fcfe0ada27733827a8ffebbb6b573bd Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Tue, 8 Oct 2024 19:28:33 -0500 Subject: [PATCH 41/59] public --- src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs b/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs index 1d2d086e4c..ffcfee1f52 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs +++ b/src/IKVM.JTReg.TestAdapter.Core/HarnessObserverInterceptor.cs @@ -10,7 +10,7 @@ namespace IKVM.JTReg.TestAdapter.Core /// /// Generates an implementation of 'com.sun.javatest.Harness$Observer'. /// - class HarnessObserverInterceptor : DispatchProxy + public class HarnessObserverInterceptor : DispatchProxy { static readonly MethodInfo CreateMethodInfo = typeof(DispatchProxy).GetMethods() From d4eab6a3fe51946e66048940019a73917fb5d2fd Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 9 Oct 2024 00:20:31 -0500 Subject: [PATCH 42/59] Add IncompleteMethods back in. --- .../Emit/ReflectionTypeSymbolBuilder.cs | 61 +++++++++++++++++++ .../Reflection/ReflectionTypeSymbolBase.cs | 20 +++--- 2 files changed, 71 insertions(+), 10 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 5ce8a95be5..7b9f0fb8a0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; +using System.Linq; using System.Reflection; using System.Reflection.Emit; using System.Runtime.InteropServices; @@ -311,6 +312,66 @@ public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) #endregion + /// + public override IMethodSymbol? GetMethod(string name) + { + if (IsComplete) + return base.GetMethod(name); + else + return GetIncompleteMethods().FirstOrDefault(i => i.Name == name); + } + + /// + public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + if (IsComplete) + return base.GetMethod(name, bindingAttr, types, modifiers); + else + throw new NotImplementedException(); + } + + /// + public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + if (IsComplete) + return base.GetMethod(name, bindingAttr, callConvention, types, modifiers); + else + throw new NotImplementedException(); + } + + /// + public override IMethodSymbol[] GetMethods() + { + if (IsComplete) + return base.GetMethods(); + else + return GetIncompleteMethods(); + } + + /// + public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + { + if (IsComplete) + return base.GetMethods(bindingAttr); + else + return GetIncompleteMethods(bindingAttr); + } + + /// + /// Gets the set of incomplete methods. + /// + /// + IMethodSymbol[] GetIncompleteMethods(BindingFlags bindingAttr = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance) + { + if (_incompleteMethods == null) + return []; + else + return SymbolUtil.FilterMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); + } + + /// + public override bool IsComplete => _type != null; + /// public void Complete() { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs index 33c07a976c..fbc1bd6784 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs @@ -483,49 +483,49 @@ public IMemberSymbol[] GetMembers() } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); } /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public virtual IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) { return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); } /// - public IMethodSymbol? GetMethod(string name) + public virtual IMethodSymbol? GetMethod(string name) { return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) { return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } @@ -537,13 +537,13 @@ public IMemberSymbol[] GetMembers() } /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + public virtual IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) { return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); } /// - public IMethodSymbol[] GetMethods() + public virtual IMethodSymbol[] GetMethods() { return ResolveMethodSymbols(UnderlyingType.GetMethods()); } From 2daab5a4c3ade6170bb2e598b555f89ccb0311be Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Wed, 9 Oct 2024 13:44:07 -0500 Subject: [PATCH 43/59] , --- .../Emit/ReflectionTypeSymbolBuilder.cs | 16 +- .../ReflectionGenericSpecTypeSymbol.cs | 1 + .../Reflection/ReflectionTypeSpecSymbol.cs | 7 - .../Reflection/ReflectionTypeSymbolBase.cs | 236 +++++++++--------- 4 files changed, 127 insertions(+), 133 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 7b9f0fb8a0..df41d1cb6c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -32,10 +32,10 @@ public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionM } /// - public override Type UnderlyingType => _type ?? _builder; + public override Type UnderlyingType => UnderlyingTypeBuilder; /// - public override Type UnderlyingEmitType => _builder; + public override Type UnderlyingEmitType => UnderlyingTypeBuilder; /// public override Type UnderlyingDynamicEmitType => _type ?? throw new InvalidOperationException(); @@ -392,27 +392,27 @@ public void OnComplete() { const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static; - foreach (var i in GetGenericArguments()) + foreach (var i in GetGenericArguments() ?? []) if (i is IReflectionGenericTypeParameterSymbolBuilder b) b.OnComplete(); - foreach (var i in GetConstructors(DefaultBindingFlags)) + foreach (var i in GetConstructors(DefaultBindingFlags) ?? []) if (i is IReflectionConstructorSymbolBuilder b) b.OnComplete(); - foreach (var i in GetMethods(DefaultBindingFlags)) + foreach (var i in GetMethods(DefaultBindingFlags) ?? []) if (i is IReflectionMethodSymbolBuilder b) b.OnComplete(); - foreach (var i in GetFields(DefaultBindingFlags)) + foreach (var i in GetFields(DefaultBindingFlags) ?? []) if (i is IReflectionFieldSymbolBuilder b) b.OnComplete(); - foreach (var i in GetProperties(DefaultBindingFlags)) + foreach (var i in GetProperties(DefaultBindingFlags) ?? []) if (i is IReflectionPropertySymbolBuilder b) b.OnComplete(); - foreach (var m in GetEvents(DefaultBindingFlags)) + foreach (var m in GetEvents(DefaultBindingFlags) ?? []) if (m is IReflectionPropertySymbolBuilder b) b.OnComplete(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs index bba26a6ad4..f7c5cadfcf 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs @@ -15,6 +15,7 @@ class ReflectionGenericSpecTypeSymbol : ReflectionTypeSpecSymbol /// /// /// + /// public ReflectionGenericSpecTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, IReflectionTypeSymbol[] genericTypeArguments) : base(context, resolvingModule, elementType) { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs index bc68441c57..121f36a586 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs @@ -8,13 +8,6 @@ abstract class ReflectionTypeSpecSymbol : ReflectionTypeSymbolBase readonly IReflectionTypeSymbol _elementType; - ReflectionMethodTable _methodTable; - ReflectionFieldTable _fieldTable; - ReflectionPropertyTable _propertyTable; - ReflectionEventTable _eventTable; - ReflectionGenericTypeParameterTable _genericTypeParameterTable; - ReflectionTypeSpecTable _specTable; - /// /// Initializes a new instance. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs index fbc1bd6784..8335710697 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs @@ -141,310 +141,310 @@ public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParame #region ITypeSymbol /// - public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); + public virtual IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); /// - public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; + public virtual string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; /// - public TypeAttributes Attributes => UnderlyingType.Attributes; + public virtual TypeAttributes Attributes => UnderlyingType.Attributes; /// - public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); + public virtual ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); /// - public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; + public virtual bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; /// - public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); + public virtual IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); /// - public string? FullName => UnderlyingType.FullName; + public virtual string? FullName => UnderlyingType.FullName; /// - public string? Namespace => UnderlyingType.Namespace; + public virtual string? Namespace => UnderlyingType.Namespace; /// - public GenericParameterAttributes GenericParameterAttributes => UnderlyingType.GenericParameterAttributes; + public virtual GenericParameterAttributes GenericParameterAttributes => UnderlyingType.GenericParameterAttributes; /// - public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; + public virtual int GenericParameterPosition => UnderlyingType.GenericParameterPosition; /// - public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); + public virtual ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); /// - public bool HasElementType => UnderlyingType.HasElementType; + public virtual bool HasElementType => UnderlyingType.HasElementType; /// - public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); + public virtual TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); /// - public bool IsAbstract => UnderlyingType.IsAbstract; + public virtual bool IsAbstract => UnderlyingType.IsAbstract; /// - public bool IsSZArray => UnderlyingType.IsSZArray(); + public virtual bool IsSZArray => UnderlyingType.IsSZArray(); /// - public bool IsArray => UnderlyingType.IsArray; + public virtual bool IsArray => UnderlyingType.IsArray; /// - public bool IsAutoLayout => UnderlyingType.IsAutoLayout; + public virtual bool IsAutoLayout => UnderlyingType.IsAutoLayout; /// - public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; + public virtual bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; /// - public bool IsByRef => UnderlyingType.IsByRef; + public virtual bool IsByRef => UnderlyingType.IsByRef; /// - public bool IsClass => UnderlyingType.IsClass; + public virtual bool IsClass => UnderlyingType.IsClass; /// - public bool IsEnum => UnderlyingType.IsEnum; + public virtual bool IsEnum => UnderlyingType.IsEnum; /// - public bool IsInterface => UnderlyingType.IsInterface; + public virtual bool IsInterface => UnderlyingType.IsInterface; /// - public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; + public virtual bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; /// - public bool IsGenericParameter => UnderlyingType.IsGenericParameter; + public virtual bool IsGenericParameter => UnderlyingType.IsGenericParameter; /// - public bool IsGenericType => UnderlyingType.IsGenericType; + public virtual bool IsGenericType => UnderlyingType.IsGenericType; /// - public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; + public virtual bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; /// - public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; + public virtual bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; /// - public bool IsNested => UnderlyingType.IsNested; + public virtual bool IsNested => UnderlyingType.IsNested; /// - public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; + public virtual bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; /// - public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; + public virtual bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; /// - public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; + public virtual bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; /// - public bool IsNestedFamily => UnderlyingType.IsNestedFamily; + public virtual bool IsNestedFamily => UnderlyingType.IsNestedFamily; /// - public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; + public virtual bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; /// - public bool IsNestedPublic => UnderlyingType.IsNestedPublic; + public virtual bool IsNestedPublic => UnderlyingType.IsNestedPublic; /// - public bool IsNotPublic => UnderlyingType.IsNotPublic; + public virtual bool IsNotPublic => UnderlyingType.IsNotPublic; /// - public bool IsPointer => UnderlyingType.IsPointer; + public virtual bool IsPointer => UnderlyingType.IsPointer; #if NET8_0_OR_GREATER /// - public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; + public virtual bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; /// - public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; + public virtual bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; #else /// - public bool IsFunctionPointer => throw new NotImplementedException(); + public virtual bool IsFunctionPointer => throw new NotImplementedException(); /// - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + public virtual bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); #endif /// - public bool IsPrimitive => UnderlyingType.IsPrimitive; + public virtual bool IsPrimitive => UnderlyingType.IsPrimitive; /// - public bool IsPublic => UnderlyingType.IsPublic; + public virtual bool IsPublic => UnderlyingType.IsPublic; /// - public bool IsSealed => UnderlyingType.IsSealed; + public virtual bool IsSealed => UnderlyingType.IsSealed; /// - public bool IsSerializable => UnderlyingType.IsSerializable; + public virtual bool IsSerializable => UnderlyingType.IsSerializable; /// - public bool IsValueType => UnderlyingType.IsValueType; + public virtual bool IsValueType => UnderlyingType.IsValueType; /// - public bool IsVisible => UnderlyingType.IsVisible; + public virtual bool IsVisible => UnderlyingType.IsVisible; /// - public bool IsSignatureType => throw new NotImplementedException(); + public virtual bool IsSignatureType => throw new NotImplementedException(); /// - public bool IsSpecialName => UnderlyingType.IsSpecialName; + public virtual bool IsSpecialName => UnderlyingType.IsSpecialName; /// - public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); + public virtual IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); /// - public int GetArrayRank() + public virtual int GetArrayRank() { return UnderlyingType.GetArrayRank(); } /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + public virtual IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) { return ResolveConstructorSymbol(UnderlyingType.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null)); } /// - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + public virtual IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); } /// - public IConstructorSymbol[] GetConstructors() + public virtual IConstructorSymbol[] GetConstructors() { return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); } /// - public IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + public virtual IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) { return ResolveConstructorSymbols(UnderlyingType.GetConstructors(bindingAttr)); } /// - public IMemberSymbol[] GetDefaultMembers() + public virtual IMemberSymbol[] GetDefaultMembers() { return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); } /// - public ITypeSymbol? GetElementType() + public virtual ITypeSymbol? GetElementType() { return ResolveTypeSymbol(UnderlyingType.GetElementType()); } /// - public string? GetEnumName(object value) + public virtual string? GetEnumName(object value) { return UnderlyingType.GetEnumName(value); } /// - public string[] GetEnumNames() + public virtual string[] GetEnumNames() { return UnderlyingType.GetEnumNames(); } /// - public ITypeSymbol GetEnumUnderlyingType() + public virtual ITypeSymbol GetEnumUnderlyingType() { return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); } /// - public Array GetEnumValues() + public virtual Array GetEnumValues() { return UnderlyingType.GetEnumValues(); } /// - public IEventSymbol? GetEvent(string name) + public virtual IEventSymbol? GetEvent(string name) { return ResolveEventSymbol(UnderlyingType.GetEvent(name)); } /// - public IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + public virtual IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) { return ResolveEventSymbol(UnderlyingType.GetEvent(name, bindingAttr)); } /// - public IEventSymbol[] GetEvents() + public virtual IEventSymbol[] GetEvents() { return ResolveEventSymbols(UnderlyingType.GetEvents()); } /// - public IEventSymbol[] GetEvents(BindingFlags bindingAttr) + public virtual IEventSymbol[] GetEvents(BindingFlags bindingAttr) { return ResolveEventSymbols(UnderlyingType.GetEvents(bindingAttr)); } /// - public IFieldSymbol? GetField(string name) + public virtual IFieldSymbol? GetField(string name) { return ResolveFieldSymbol(UnderlyingType.GetField(name)); } /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + public virtual IFieldSymbol? GetField(string name, BindingFlags bindingAttr) { return ResolveFieldSymbol(UnderlyingType.GetField(name, bindingAttr)); } /// - public IFieldSymbol[] GetFields() + public virtual IFieldSymbol[] GetFields() { return ResolveFieldSymbols(UnderlyingType.GetFields()); } /// - public IFieldSymbol[] GetFields(BindingFlags bindingAttr) + public virtual IFieldSymbol[] GetFields(BindingFlags bindingAttr) { return ResolveFieldSymbols(UnderlyingType.GetFields(bindingAttr)); } /// - public ITypeSymbol[] GetGenericArguments() + public virtual ITypeSymbol[] GetGenericArguments() { return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); } /// - public ITypeSymbol[] GetGenericParameterConstraints() + public virtual ITypeSymbol[] GetGenericParameterConstraints() { return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); } /// - public ITypeSymbol GetGenericTypeDefinition() + public virtual ITypeSymbol GetGenericTypeDefinition() { return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); } /// - public ITypeSymbol? GetInterface(string name) + public virtual ITypeSymbol? GetInterface(string name) { return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); } /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) + public virtual ITypeSymbol? GetInterface(string name, bool ignoreCase) { return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); } /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + public virtual InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); } /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) + public virtual ITypeSymbol[] GetInterfaces(bool inherit = true) { if (inherit) return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); @@ -453,85 +453,85 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) } /// - public IMemberSymbol[] GetMember(string name) + public virtual IMemberSymbol[] GetMember(string name) { return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public virtual IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public virtual IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); + return ResolveMemberSymbols(UnderlyingType.GetMember(name, type, bindingAttr)); } /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) + public virtual IMemberSymbol[] GetMembers(BindingFlags bindingAttr) { - return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); + return ResolveMemberSymbols(UnderlyingType.GetMembers(bindingAttr)); } /// - public IMemberSymbol[] GetMembers() + public virtual IMemberSymbol[] GetMembers() { return ResolveMemberSymbols(UnderlyingType.GetMembers()); } /// - public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) + public virtual IMethodSymbol? GetMethod(string name) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); } /// - public virtual IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr)); } /// - public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) + public virtual IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); } /// - public virtual IMethodSymbol? GetMethod(string name) + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); } /// - public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers?.Unpack())); } /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) { throw new NotImplementedException(); } /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - throw new NotImplementedException(); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public virtual IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + throw new NotImplementedException(); } /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { throw new NotImplementedException(); } @@ -549,115 +549,115 @@ public virtual IMethodSymbol[] GetMethods() } /// - public ITypeSymbol? GetNestedType(string name) + public virtual ITypeSymbol? GetNestedType(string name) { return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); } /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + public virtual ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); } /// - public ITypeSymbol[] GetNestedTypes() + public virtual ITypeSymbol[] GetNestedTypes() { return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); } /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + public virtual ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) { return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); } /// - public IPropertySymbol[] GetProperties() + public virtual IPropertySymbol[] GetProperties() { return ResolvePropertySymbols(UnderlyingType.GetProperties()); } /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + public virtual IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) { return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) { return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) { return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); } /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + public virtual IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) { return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); } /// - public IPropertySymbol? GetProperty(string name) + public virtual IPropertySymbol? GetProperty(string name) { return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); } /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) { return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); } /// - public bool IsAssignableFrom(ITypeSymbol? c) + public virtual bool IsAssignableFrom(ITypeSymbol? c) { return UnderlyingType.IsAssignableFrom(c?.Unpack()); } /// - public bool IsEnumDefined(object value) + public virtual bool IsEnumDefined(object value) { return UnderlyingType.IsEnumDefined(value); } /// - public bool IsSubclassOf(ITypeSymbol c) + public virtual bool IsSubclassOf(ITypeSymbol c) { return UnderlyingType.IsSubclassOf(c.Unpack()); } /// - public ITypeSymbol MakeArrayType() + public virtual ITypeSymbol MakeArrayType() { return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); } /// - public ITypeSymbol MakeArrayType(int rank) + public virtual ITypeSymbol MakeArrayType(int rank) { return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); } /// - public ITypeSymbol MakeByRefType() + public virtual ITypeSymbol MakeByRefType() { return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); } /// - public ITypeSymbol MakePointerType() + public virtual ITypeSymbol MakePointerType() { return ResolveTypeSymbol(UnderlyingType.MakePointerType()); } /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + public virtual ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) { return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } From b7b2716de1768f0d3b2f7e520dca33279dd2ba00 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 13 Oct 2024 16:08:52 -0500 Subject: [PATCH 44/59] . --- .../Reflection/ReflectionSymbolTests.cs | 79 ++- .../Reflection/ReflectionExtensions.cs | 75 ++ src/IKVM.CoreLib/Symbols/CustomAttribute.cs | 148 +++- .../Symbols/Emit/IAssemblySymbolBuilder.cs | 15 +- .../Symbols/Emit/ICustomAttributeBuilder.cs | 11 - .../Emit/ICustomAttributeProviderBuilder.cs | 15 + .../Symbols/Emit/IEventSymbolBuilder.cs | 13 - .../Symbols/Emit/IFieldSymbolBuilder.cs | 13 - .../Symbols/Emit/IMemberSymbolBuilder.cs | 2 +- .../Symbols/Emit/IMethodBaseSymbolBuilder.cs | 13 - .../Symbols/Emit/IModuleSymbolBuilder.cs | 15 +- .../Symbols/Emit/IParameterSymbolBuilder.cs | 16 +- .../Symbols/Emit/IPropertySymbolBuilder.cs | 13 - .../Symbols/Emit/ITypeSymbolBuilder.cs | 13 - .../Symbols/ICustomAttributeProvider.cs | 2 +- src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 45 +- ...eflectionCustomAttributeProviderBuilder.cs | 13 + .../IIkvmReflectionMemberSymbolBuilder.cs | 3 +- .../IkvmReflectionAssemblySymbolBuilder.cs | 11 +- .../IkvmReflectionConstructorSymbolBuilder.cs | 12 +- .../IkvmReflectionCustomAttributeBuilder.cs | 29 - .../Emit/IkvmReflectionEventSymbolBuilder.cs | 12 +- .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 22 +- ...ectionGenericTypeParameterSymbolBuilder.cs | 11 + .../Emit/IkvmReflectionMemberSymbolBuilder.cs | 9 +- .../IkvmReflectionMethodBaseSymbolBuilder.cs | 6 - .../Emit/IkvmReflectionMethodSymbolBuilder.cs | 22 +- .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 10 +- .../IkvmReflectionParameterSymbolBuilder.cs | 10 +- .../IkvmReflectionPropertySymbolBuilder.cs | 12 +- .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 21 +- .../IkvmReflectionSymbolContext.cs | 29 +- .../IkvmReflection/IkvmReflectionTypeTable.cs | 2 +- .../IkvmReflection/IkvmReflectionUtil.cs | 107 ++- ...eflectionCustomAttributeProviderBuilder.cs | 13 + ...ectionGenericTypeParameterSymbolBuilder.cs | 7 +- .../IReflectionMethodBaseSymbolBuilder.cs | 11 +- .../Emit/IReflectionMethodSymbolBuilder.cs | 7 - .../Emit/IReflectionModuleSymbolBuilder.cs | 57 -- .../Emit/IReflectionPropertySymbolBuilder.cs | 7 - .../Emit/IReflectionSymbolBuilder.cs | 72 -- .../Emit/IReflectionTypeSymbolBuilder.cs | 42 -- .../Emit/ReflectionAssemblySymbolBuilder.cs | 168 +---- .../ReflectionConstructorSymbolBuilder.cs | 91 ++- .../Emit/ReflectionCustomAttributeBuilder.cs | 29 - .../Emit/ReflectionEventBuilderInfo.cs | 1 + .../Emit/ReflectionEventSymbolBuilder.cs | 96 +-- .../Emit/ReflectionFieldSymbolBuilder.cs | 99 +-- ...ectionGenericTypeParameterSymbolBuilder.cs | 662 +----------------- .../Reflection/Emit/ReflectionILGenerator.cs | 17 +- .../Emit/ReflectionMemberSymbolBuilder.cs | 348 --------- .../Emit/ReflectionMethodBaseSymbolBuilder.cs | 167 ----- .../Emit/ReflectionMethodSymbolBuilder.cs | 144 ++-- .../Emit/ReflectionModuleSymbolBuilder.cs | 397 +---------- .../Emit/ReflectionParameterSymbolBuilder.cs | 22 +- .../Emit/ReflectionPropertySymbolBuilder.cs | 141 +--- .../Emit/ReflectionSymbolBuilder.cs | 12 +- .../Emit/ReflectionTypeSymbolBuilder.cs | 118 ++-- .../Reflection/IReflectionAssemblySymbol.cs | 5 + .../IReflectionConstructorSymbol.cs | 7 +- .../Reflection/IReflectionEventSymbol.cs | 4 +- .../Reflection/IReflectionFieldSymbol.cs | 9 +- .../Reflection/IReflectionMemberSymbol.cs | 4 +- .../Reflection/IReflectionMethodBaseSymbol.cs | 12 +- .../Reflection/IReflectionMethodSymbol.cs | 17 +- .../Reflection/IReflectionModuleSymbol.cs | 65 ++ .../Reflection/IReflectionParameterSymbol.cs | 4 +- .../Reflection/IReflectionPropertySymbol.cs | 14 +- .../Symbols/Reflection/IReflectionSymbol.cs | 83 +++ .../Reflection/IReflectionTypeSymbol.cs | 62 +- .../Reflection/ReflectionArrayTypeSymbol.cs | 5 +- .../Reflection/ReflectionAssemblySymbol.cs | 9 +- .../Reflection/ReflectionByRefTypeSymbol.cs | 5 +- .../Reflection/ReflectionConstructorSymbol.cs | 8 +- .../Reflection/ReflectionEventSymbol.cs | 7 +- .../Reflection/ReflectionFieldSymbol.cs | 10 +- .../ReflectionGenericSpecTypeSymbol.cs | 5 +- .../ReflectionGenericTypeParameterSymbol.cs | 54 +- .../Reflection/ReflectionMemberSymbol.cs | 9 +- .../Reflection/ReflectionMethodBaseSymbol.cs | 16 +- .../Reflection/ReflectionMethodSymbol.cs | 17 +- .../Reflection/ReflectionModuleSymbol.cs | 72 +- .../Reflection/ReflectionModuleTable.cs | 11 - .../Reflection/ReflectionParameterSymbol.cs | 2 +- .../Reflection/ReflectionPointerTypeSymbol.cs | 5 +- .../Reflection/ReflectionPropertySymbol.cs | 16 +- .../Reflection/ReflectionSZArrayTypeSymbol.cs | 5 +- .../Symbols/Reflection/ReflectionSymbol.cs | 31 + .../Reflection/ReflectionSymbolContext.cs | 38 +- .../Reflection/ReflectionTypeSymbol.cs | 3 + .../Reflection/ReflectionTypeSymbolBase.cs | 80 ++- .../Symbols/Reflection/ReflectionUtil.cs | 95 ++- src/IKVM.CoreLib/Symbols/SymbolUtil.cs | 26 +- .../ErrorHandlerInterceptor.cs | 4 +- src/IKVM.Runtime/AttributeHelper.cs | 158 ++--- src/IKVM.Runtime/ByteCodeHelper.cs | 6 +- src/IKVM.Runtime/DynamicClassLoader.cs | 14 +- src/IKVM.Runtime/JNI/JNIEnv.cs | 14 +- src/IKVM.Runtime/JVM.Internal.cs | 2 +- src/IKVM.Runtime/JVM.Properties.cs | 2 +- .../Java/Externs/ikvm/runtime/Util.cs | 9 +- .../Java/Externs/java/io/ObjectStreamClass.cs | 8 +- .../Java/Externs/java/lang/Package.cs | 2 +- .../java/lang/invoke/MethodHandleNatives.cs | 4 +- .../Java/Externs/java/lang/reflect/Array.cs | 4 +- .../Java/Externs/sun/misc/Unsafe.cs | 32 +- src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs | 2 +- .../Externs/sun/reflect/ReflectionFactory.cs | 20 +- .../MethodHandleUtil.jniexport.cs | 12 +- src/IKVM.Runtime/ReflectUtil.cs | 4 +- .../RuntimeAssemblyClassLoader.cs | 26 +- .../RuntimeByteCodeJavaType.FinishContext.cs | 6 +- .../RuntimeByteCodeJavaType.JavaTypeImpl.cs | 28 +- src/IKVM.Runtime/RuntimeConstantJavaField.cs | 2 +- src/IKVM.Runtime/RuntimeJavaField.cs | 20 +- src/IKVM.Runtime/RuntimeJavaMethod.cs | 2 +- src/IKVM.Runtime/RuntimeJavaType.cs | 8 +- ...ntimeManagedByteCodeAccessStubJavaField.cs | 4 +- ...meManagedByteCodeJavaType.GhostJavaType.cs | 4 +- ...agedByteCodeJavaType.RemappedJavaMethod.cs | 2 +- .../RuntimeManagedByteCodeJavaType.cs | 16 +- ...RuntimeManagedByteCodePropertyJavaField.cs | 4 +- ...gedJavaType.AttributeAnnotationJavaType.cs | 10 +- ...RuntimeManagedJavaType.EnumEnumJavaType.cs | 4 +- ...ntimeManagedJavaType.EnumWrapJavaMethod.cs | 2 +- ...JavaType.ValueTypeDefaultCtorJavaMethod.cs | 2 +- src/IKVM.Runtime/RuntimeManagedJavaType.cs | 2 +- src/IKVM.Runtime/RuntimeSimpleJavaField.cs | 4 +- src/IKVM.Runtime/Serialization.cs | 8 +- src/IKVM.Runtime/SymbolExtensions.cs | 66 +- .../Invoke/NativeInvokerBytecodeGenerator.cs | 4 +- src/IKVM.Tools.Importer/ImportClassLoader.cs | 17 +- 132 files changed, 1662 insertions(+), 3248 deletions(-) delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionCustomAttributeProviderBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index edf8cf48e6..31e4ecaea2 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -21,6 +21,38 @@ public class ReflectionSymbolTests class Foo { T? field; + } + + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)] + class AttributeWithWithDefaultCtor : Attribute + { + + public AttributeWithWithDefaultCtor() + { + + } + + } + + [AttributeUsage(AttributeTargets.Class)] + class AttributeWithType : Attribute + { + + public AttributeWithType(Type type) + { + Type = type; + } + + public Type Type { get; } + + } + + [AttributeWithType(typeof(object))] + class ClassWithAttributeWithType + { + + + } [TestMethod] @@ -183,35 +215,44 @@ public void CanResolveParameters() p[1].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(typeof(object))); } - [AttributeUsage(AttributeTargets.Class)] - class AttributeWithType : Attribute + [TestMethod] + public void CanReadCustomAttributes() { - - public AttributeWithType(Type type) - { - Type = type; - } - - public Type Type { get; } - + var c = new ReflectionSymbolContext(); + var s = c.GetOrCreateTypeSymbol(typeof(ClassWithAttributeWithType)); + var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithType))); + var v = a.Value.ConstructorArguments[0].Value; + v.Should().BeOfType(); } - [AttributeWithType(typeof(object))] - class ClassWithAttributeWithType + [TestMethod] + public void CanReadCustomAttributesFromTypeBuilder() { + var c = new ReflectionSymbolContext(); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); + var m = a.DefineModule("DynamicModule"); + var type = m.DefineType("DynamicType"); - - + type.SetCustomAttribute(CustomAttribute.Create(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor)).GetConstructors()[0], [])); + var ca = type.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor))); + ca.Should().NotBeNull(); } [TestMethod] - public void CanReadCustomAttributes() + public void CanReadCustomAttributesFromMethodBuilder() { var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(ClassWithAttributeWithType)); - var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithType))); - var v = a.Value.ConstructorArguments[0].Value; - v.Should().BeOfType(); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); + var m = a.DefineModule("DynamicModule"); + var type = m.DefineType("DynamicType"); + + var method = type.DefineMethod("DynamicMethod1", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); + var il = method.GetILGenerator(); + il.Emit(OpCodes.Ret); + + method.SetCustomAttribute(CustomAttribute.Create(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor)).GetConstructors()[0], [])); + var ca = method.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor))); + ca.Should().NotBeNull(); } [TestMethod] diff --git a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs index 7ce0795da3..ee2c0b7b98 100644 --- a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs +++ b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Linq.Expressions; using System.Reflection; using System.Reflection.Emit; @@ -590,6 +591,80 @@ public static bool IsSZArray(this Type type) #endif } + /// + /// Implements GetcustomAttributeData with support for examining inheritence. + /// + /// + public static IEnumerable GetCustomAttributesData(this Type type, bool inherit) + { + foreach (var i in type.GetCustomAttributesData()) + yield return i; + + if (inherit) + for (var baseType = type.BaseType; baseType != null; baseType = baseType.BaseType) + foreach (var cad in baseType.GetCustomAttributesData()) + if (cad.AttributeType.GetCustomAttribute()?.Inherited ?? false) + yield return cad; + } + + /// + /// Implements GetcustomAttributeData with support for examining inheritence. + /// + /// + public static IEnumerable GetInheritedCustomAttributesData(this Type type) + { + for (var baseType = type.BaseType; baseType != null; baseType = baseType.BaseType) + foreach (var cad in baseType.GetCustomAttributesData()) + if (cad.AttributeType.GetCustomAttribute()?.Inherited ?? false) + yield return cad; + } + + /// + /// Implements GetcustomAttributeData with support for examining inheritence. + /// + /// + /// + public static IEnumerable GetCustomAttributesData(this MethodInfo method, bool inherit) + { + foreach (var i in method.GetCustomAttributesData()) + yield return i; + + if (inherit) + for (var baseMethod = method.GetBaseDefinition(); baseMethod != null; baseMethod = baseMethod.GetBaseDefinition()) + foreach (var cad in baseMethod.GetCustomAttributesData()) + if (cad.AttributeType.GetCustomAttribute()?.Inherited ?? false) + yield return cad; + } + + /// + /// Implements GetcustomAttributeData with support for examining inheritence. + /// + /// + /// + public static IEnumerable GetInheritedCustomAttributesData(this MethodInfo method) + { + for (var baseMethod = method.GetBaseDefinition(); baseMethod != null; baseMethod = baseMethod.GetBaseDefinition()) + foreach (var cad in baseMethod.GetCustomAttributesData()) + if (cad.AttributeType.GetCustomAttribute()?.Inherited ?? false) + yield return cad; + } + + /// + /// Implements GetcustomAttributeData with support for examining inheritence. + /// + /// + /// + public static IEnumerable GetCustomAttributesData(this MemberInfo member, bool inherit) + { + if (member is Type type) + return GetCustomAttributesData(type, inherit); + + if (member is MethodInfo method) + return GetCustomAttributesData(method, inherit); + + return member.GetCustomAttributesData(); + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/CustomAttribute.cs b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs index 7b1af0a9d5..a910c5aa80 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttribute.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs @@ -1,4 +1,6 @@ -using System.Collections.Immutable; +using System; +using System.Collections.Immutable; +using System.Linq; namespace IKVM.CoreLib.Symbols { @@ -7,7 +9,149 @@ readonly record struct CustomAttribute( ITypeSymbol AttributeType, IConstructorSymbol Constructor, ImmutableArray ConstructorArguments, - ImmutableArray NamedArguments); + ImmutableArray NamedArguments) + { + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. + /// + /// + /// + /// + public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs) + { + return new CustomAttribute( + ctor.DeclaringType ?? throw new InvalidOperationException(), + ctor, + PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + ImmutableArray.Empty); + } + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, and a set of named field/value pairs. + /// + /// + /// + /// + /// + public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) + { + return new CustomAttribute( + ctor.DeclaringType ?? throw new InvalidOperationException(), + ctor, + PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + PackNamedArgs([], [], namedFields, fieldValues)); + } + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, and a set of named property or value pairs. + /// + /// + /// + /// + /// + public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) + { + return new CustomAttribute( + ctor.DeclaringType ?? throw new InvalidOperationException(), + ctor, + PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + PackNamedArgs(namedProperties, propertyValues, [], [])); + } + + /// + /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, a set of named property or value pairs, and a set of named field or value pairs. + /// + /// + /// + /// + /// + /// + /// + public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) + { + return new CustomAttribute( + ctor.DeclaringType ?? throw new InvalidOperationException(), + ctor, + PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + PackNamedArgs(namedProperties, propertyValues, namedFields, fieldValues)); + } + + /// + /// Packs the types as typed arguments. + /// + /// + /// + /// + /// + /// + static ImmutableArray PackTypedArgs(ITypeSymbol[] types, object?[] values) + { + if (types is null) + throw new ArgumentNullException(nameof(types)); + if (values is null) + throw new ArgumentNullException(nameof(values)); + if (types.Length != values.Length) + throw new ArgumentException(); + + var a = ImmutableArray.CreateBuilder(types.Length); + for (int i = 0; i < types.Length; i++) + a.Add(PackTypedArg(types[i], values[i])); + + return a.ToImmutable(); + } + + /// + /// Packs the type as a typed argument. + /// + /// + /// + /// + static CustomAttributeTypedArgument PackTypedArg(ITypeSymbol type, object? value) + { + return new CustomAttributeTypedArgument(type, value); + } + + /// + /// Packages the members and args as a named argument. + /// + /// + /// + /// + static ImmutableArray PackNamedArgs(IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) + { + var a = ImmutableArray.CreateBuilder(namedProperties.Length + namedFields.Length); + for (int i = 0; i < namedProperties.Length; i++) + a.Add(PackNamedArg(namedProperties[i], propertyValues[i])); + for (int i = 0; i < namedFields.Length; i++) + a.Add(PackNamedArg(namedFields[i], fieldValues[i])); + + return a.ToImmutable(); + } + + /// + /// Packs the property and arg as a named argument. + /// + /// + /// + /// + static CustomAttributeNamedArgument PackNamedArg(IPropertySymbol property, object? v) + { + return new CustomAttributeNamedArgument(false, property, property.Name, PackTypedArg(property.PropertyType, v)); + } + + /// + /// Packs the field and arg as a named argument. + /// + /// + /// + /// + static CustomAttributeNamedArgument PackNamedArg(IFieldSymbol field, object? v) + { + return new CustomAttributeNamedArgument(false, field, field.Name, PackTypedArg(field.FieldType, v)); + } + + } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs index 8c9ab94eff..bda4b9a53a 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs @@ -3,7 +3,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySymbol + interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySymbol, ICustomAttributeProviderBuilder { /// @@ -30,19 +30,6 @@ interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySym /// IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - /// /// Sets a Win32 icon on the generated assembly. /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs deleted file mode 100644 index e30a02e211..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs +++ /dev/null @@ -1,11 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface ICustomAttributeBuilder - { - - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs new file mode 100644 index 0000000000..d07fbc431f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs @@ -0,0 +1,15 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface ICustomAttributeProviderBuilder + { + + /// + /// Set a custom attribute on this object. + /// + /// + public void SetCustomAttribute(CustomAttribute attribute); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs index 36b7257650..719f270b57 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs @@ -28,19 +28,6 @@ interface IEventSymbolBuilder : ISymbolBuilder, IMemberSymbolBuild /// void AddOtherMethod(IMethodSymbolBuilder mdBuilder); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs index ad3048c16a..9cd676798b 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs @@ -16,19 +16,6 @@ interface IFieldSymbolBuilder : ISymbolBuilder, IMemberSymbolBuild /// void SetOffset(int iOffset); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs index b787c9ced2..a2d87e08e7 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs @@ -1,7 +1,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IMemberSymbolBuilder : ISymbolBuilder, IMemberSymbol + interface IMemberSymbolBuilder : ISymbolBuilder, IMemberSymbol, ICustomAttributeProviderBuilder { diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs index c3173daf10..162146f11a 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs @@ -34,19 +34,6 @@ interface IMethodBaseSymbolBuilder : ISymbolBuilder, IMemberS /// IILGenerator GetILGenerator(); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index 1ad74cf09e..efdd7a7ad7 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -9,7 +9,7 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol + interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, ICustomAttributeProviderBuilder { /// @@ -163,19 +163,6 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol /// ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - /// /// Explicitely adds a reference to the specified assembly. /// diff --git a/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs index 860f872f79..ec2148e7bf 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs @@ -1,27 +1,15 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IParameterSymbolBuilder : ISymbolBuilder, IParameterSymbol + interface IParameterSymbolBuilder : ISymbolBuilder, IParameterSymbol, ICustomAttributeProviderBuilder { + /// /// Sets the default value of the parameter. /// /// void SetConstant(object? defaultValue); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs index c1f200f2ff..29dd90ed45 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs @@ -28,19 +28,6 @@ interface IPropertySymbolBuilder : ISymbolBuilder, IMemberSymbo /// void AddOtherMethod(IMethodSymbolBuilder mdBuilder); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs index 1afc22d77d..dfa306cf8a 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs @@ -318,19 +318,6 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); - /// - /// Set a custom attribute using a custom attribute builder. - /// - /// - void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - /// Sets a custom attribute using a specified custom attribute blob. - /// - /// - /// - void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - /// /// Finishes the type, updating the associated symbol. /// diff --git a/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs index 447839f6a3..a8747edc43 100644 --- a/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs +++ b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs @@ -4,7 +4,7 @@ /// /// Provides custom attributes for reflection objects that support them. /// - interface ICustomAttributeProvider + interface ICustomAttributeProvider : ISymbol { /// diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index f014a0a5bb..776a0d8623 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -1,5 +1,4 @@ -using System.Reflection; -using System.Reflection.Emit; +using System.Collections.Immutable; using IKVM.CoreLib.Symbols.Emit; @@ -22,49 +21,11 @@ interface ISymbolContext /// Defines a dynamic assembly that has the specified name and access rights. /// /// - /// + /// /// /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes, bool collectable = true, bool saveable = false); - - /// - /// Initializes an instance of the interface given the constructor for the custom attribute and the arguments to the constructor. - /// - /// - /// - /// - ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs); - - /// - /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, and a set of named field/value pairs. - /// - /// - /// - /// - /// - ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues); - - /// - /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, and a set of named property or value pairs. - /// - /// - /// - /// - /// - ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues); - - /// - /// Initializes an instance of the interface given the constructor for the custom attribute, the arguments to the constructor, a set of named property or value pairs, and a set of named field or value pairs. - /// - /// - /// - /// - /// - /// - /// - ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues); - + IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes, bool collectable = true, bool saveable = false); } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionCustomAttributeProviderBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionCustomAttributeProviderBuilder.cs new file mode 100644 index 0000000000..e4fd3ea672 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionCustomAttributeProviderBuilder.cs @@ -0,0 +1,13 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit +{ + + interface IIkvmReflectionCustomAttributeProviderBuilder : ICustomAttributeProviderBuilder + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs index 3008c8e063..f7b637f27f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs @@ -1,10 +1,9 @@ using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection.Emit; namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit { - interface IIkvmReflectionMemberSymbolBuilder : IIkvmReflectionSymbolBuilder, IMemberSymbolBuilder, IIkvmReflectionMemberSymbol + interface IIkvmReflectionMemberSymbolBuilder : IIkvmReflectionSymbolBuilder, IMemberSymbolBuilder, IIkvmReflectionMemberSymbol, IIkvmReflectionCustomAttributeProviderBuilder { /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs index 13cc310439..8f245c446b 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs @@ -1,7 +1,6 @@ using System; using System.Collections.Generic; using System.IO; -using System.Linq; using IKVM.CoreLib.Symbols.Emit; using IKVM.Reflection; @@ -76,15 +75,9 @@ public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emit } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingAssemblyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingAssemblyBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingAssemblyBuilder.SetCustomAttribute(attribute.Unpack()); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs index 8c776fbff4..0ab2e76733 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs @@ -68,16 +68,14 @@ public override IILGenerator GetILGenerator(int streamSize) return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator(streamSize)); } - /// - public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingConstructorBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } + #endregion + + #region ICustomAttributeProviderBuilder /// - public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public override void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingConstructorBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingConstructorBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs deleted file mode 100644 index 3e9abec0fb..0000000000 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionCustomAttributeBuilder.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.IkvmReflection.Emit -{ - - class IkvmReflectionCustomAttributeBuilder : ICustomAttributeBuilder - { - - readonly CustomAttributeBuilder _builder; - - /// - /// Initializes a new instance. - /// - public IkvmReflectionCustomAttributeBuilder(CustomAttributeBuilder builder) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Gets the underlying reflection . - /// - internal CustomAttributeBuilder UnderlyingBuilder => _builder; - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs index 4f388a3b2c..45a4169e42 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs @@ -63,16 +63,14 @@ public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) UnderlyingEventBuilder.AddOtherMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingEventBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } + #endregion + + #region ICustomAttributeProviderBuilder /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public override void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingEventBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingEventBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs index 8472497807..cb49715892 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs @@ -51,18 +51,6 @@ public void SetOffset(int iOffset) UnderlyingFieldBuilder.SetOffset(iOffset); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingFieldBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingFieldBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } - #endregion #region IFieldSymbol @@ -132,6 +120,16 @@ public ITypeSymbol[] GetRequiredCustomModifiers() #endregion + #region ICustomAttributeProviderBuilder + + /// + public override void SetCustomAttribute(CustomAttribute attribute) + { + UnderlyingFieldBuilder.SetCustomAttribute(attribute.Unpack()); + } + + #endregion + /// public override void OnComplete() { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs index 3e455d9d83..ad8e18c994 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -1,5 +1,6 @@ using System; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -696,6 +697,16 @@ public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) #endregion + #region ICustomAttributeProviderBuilder + + /// + public override void SetCustomAttribute(CustomAttribute attribute) + { + UnderlyingGenericTypeParameterBuilder.SetCustomAttribute(attribute.Unpack()); + } + + #endregion + /// public override void OnComplete() { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs index b174dd069a..693bdb19e7 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs @@ -2,6 +2,7 @@ using System.Diagnostics.CodeAnalysis; using System.Linq; +using IKVM.CoreLib.Symbols.Emit; using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -335,6 +336,13 @@ public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) #endregion + #region ICustomAttributeProviderBuilder + + /// + public abstract void SetCustomAttribute(CustomAttribute attribute); + + #endregion + /// public virtual void OnComplete() { @@ -343,7 +351,6 @@ public virtual void OnComplete() /// public override string ToString() => UnderlyingMember.ToString()!; - } } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs index 60499625ab..9770fd84f0 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs @@ -52,12 +52,6 @@ public IIkvmReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo p /// public abstract IILGenerator GetILGenerator(int streamSize); - /// - public abstract void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - - /// - public abstract void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - /// public IIkvmReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs index 2b5270b6d4..e486d31ccf 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs @@ -106,18 +106,6 @@ public override IILGenerator GetILGenerator(int streamSize) return _il ??= new IkvmReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); } - /// - public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingMethodBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } - #endregion #region IMethodSymbolBuilder @@ -186,6 +174,16 @@ public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) #endregion + #region ICustomAttributeProviderBuilder + + /// + public override void SetCustomAttribute(CustomAttribute attribute) + { + UnderlyingMethodBuilder.SetCustomAttribute(attribute.Unpack()); + } + + #endregion + /// public override void OnComplete() { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs index a1ee9f91d2..273dfcd758 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs @@ -284,15 +284,9 @@ public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttribut } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingModuleBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingModuleBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingModuleBuilder.SetCustomAttribute(attribute.Unpack()); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs index f0e7aed502..648ac97c37 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs @@ -56,15 +56,9 @@ public void SetConstant(object? defaultValue) } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingParameterBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingParameterBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingParameterBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs index f4416773b7..6b71a089dc 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs @@ -86,16 +86,14 @@ public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) UnderlyingPropertyBuilder.AddOtherMethod(((IIkvmReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingPropertyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } + #endregion + + #region ICustomAttributeProviderBuilder /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public override void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingPropertyBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingPropertyBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index babaa086ad..376f463cc4 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -378,17 +378,6 @@ public IConstructorSymbolBuilder DefineTypeInitializer() { return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineTypeInitializer()); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingTypeBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingTypeBuilder.SetCustomAttribute(((IkvmReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } #endregion @@ -945,6 +934,16 @@ public ITypeSymbol MakeByRefType() #endregion + #region ICustomAttributeProviderBuilder + + /// + public override void SetCustomAttribute(CustomAttribute attribute) + { + UnderlyingTypeBuilder.SetCustomAttribute(attribute.Unpack()); + } + + #endregion + /// public void Complete() { diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs index a3e8d19a56..c97a3b836f 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolContext.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Concurrent; +using System.Collections.Immutable; using System.Runtime.CompilerServices; using IKVM.CoreLib.Symbols.Emit; @@ -46,7 +47,7 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, bool collect } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes, bool collectable, bool saveable) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes, bool collectable, bool saveable) { if (name is null) throw new ArgumentNullException(nameof(name)); @@ -55,7 +56,7 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttri if (saveable == false) throw new NotSupportedException("IKVM Reflection can only produce saveable assemblies."); - return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Save, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(_universe.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Save, attributes.Unpack())); } /// @@ -332,30 +333,6 @@ public IIkvmReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypePa return GetOrCreateModuleSymbol((ModuleBuilder)genericTypeParameter.Module).GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); } - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs) - { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs))); - } - - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) - { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedFields.Unpack(), UnpackArguments(fieldValues))); - } - - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) - { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues))); - } - - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) - { - return new IkvmReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues), namedFields.Unpack(), UnpackArguments(fieldValues))); - } - /// /// Unpacks a single constructor argument. /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs index 706ffe0124..dfc0291da1 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs @@ -23,7 +23,7 @@ struct IkvmReflectionTypeTable IndexRangeDictionary _table = new(); ReaderWriterLockSlim? _lock; - ConcurrentDictionary _byName; + ConcurrentDictionary? _byName; ConcurrentDictionary? _byToken; /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs index 600292ba80..2dddc4c98b 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionUtil.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Collections.Immutable; using System.Linq; @@ -397,28 +398,112 @@ public static Label[] Unpack(this ILabel[] labels) } /// - /// Unpacks the . + /// Unpacks the . /// - /// + /// /// - public static CustomAttributeBuilder Unpack(this ICustomAttributeBuilder customAttributes) + public static CustomAttributeBuilder Unpack(this CustomAttribute attributes) { - return ((IkvmReflectionCustomAttributeBuilder)customAttributes).UnderlyingBuilder; + // unpack constructor arg values + var constructorValues = new object?[attributes.ConstructorArguments.Length]; + for (int i = 0; i < attributes.ConstructorArguments.Length; i++) + constructorValues[i] = UnpackCustomAttributeValue(attributes.ConstructorArguments[i]); + + // unpack named arguments into sets of properties and fields + List? namedProperties = null; + List? propertyValues = null; + List? namedFields = null; + List? fieldValues = null; + + // split named arguments into two sets + foreach (var i in attributes.NamedArguments) + { + var v = UnpackCustomAttributeValue(i.TypedValue.Value); + if (i.IsField == false) + { + namedProperties ??= new(); + namedProperties.Add(((IPropertySymbol)i.MemberInfo).Unpack()); + propertyValues ??= new(); + propertyValues.Add(v); + } + else + { + namedFields ??= new(); + namedFields.Add(((IFieldSymbol)i.MemberInfo).Unpack()); + fieldValues ??= new(); + fieldValues.Add(v); + } + } + + return new CustomAttributeBuilder( + attributes.Constructor.Unpack(), + constructorValues, + namedProperties?.ToArray() ?? [], + propertyValues?.ToArray() ?? [], + namedFields?.ToArray() ?? [], + fieldValues?.ToArray() ?? []); } /// - /// Unpacks the s. + /// Unpacks the s. /// - /// + /// /// - public static CustomAttributeBuilder[] Unpack(this ICustomAttributeBuilder[] customAttributes) + public static CustomAttributeBuilder[] Unpack(this CustomAttribute[] attributes) { - if (customAttributes.Length == 0) + if (attributes.Length == 0) return []; - var a = new CustomAttributeBuilder[customAttributes.Length]; - for (int i = 0; i < customAttributes.Length; i++) - a[i] = customAttributes[i].Unpack(); + var a = new CustomAttributeBuilder[attributes.Length]; + for (int i = 0; i < attributes.Length; i++) + a[i] = attributes[i].Unpack(); + + return a; + } + + /// + /// Unpacks the s. + /// + /// + /// + public static CustomAttributeBuilder[] Unpack(this ImmutableArray attributes) + { + if (attributes.Length == 0) + return []; + + var a = new CustomAttributeBuilder[attributes.Length]; + for (int i = 0; i < attributes.Length; i++) + a[i] = attributes[i].Unpack(); + + return a; + } + + /// + /// Unpacks the attribute value object. + /// + /// + /// + static object? UnpackCustomAttributeValue(object? value) + { + return value switch + { + IReadOnlyList l => UnpackCustomAttributeArrayValue(l), + ITypeSymbol t => t.Unpack(), + CustomAttributeTypedArgument a => UnpackCustomAttributeValue(a.Value), + _ => value, + }; + } + + /// + /// Unpacks the attribute value array. + /// + /// + /// + static object?[] UnpackCustomAttributeArrayValue(IReadOnlyList l) + { + var a = new object?[l.Count]; + for (int i = 0; i < l.Count; i++) + a[i] = UnpackCustomAttributeValue(l[i]); return a; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs new file mode 100644 index 0000000000..8f78217a97 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs @@ -0,0 +1,13 @@ +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols.Reflection.Emit +{ + + interface IReflectionCustomAttributeProviderBuilder : ICustomAttributeProviderBuilder + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs index c02f275dda..8e5789c04b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs @@ -1,4 +1,5 @@ -using System.Reflection.Emit; +using System; +using System.Reflection.Emit; using IKVM.CoreLib.Symbols.Emit; @@ -14,9 +15,9 @@ interface IReflectionGenericTypeParameterSymbolBuilder : IReflectionSymbolBuilde GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder { get; } /// - /// Invoked when the type containing this generic type parameter is completed. + /// Invoked when the type containing this generic type parameter is completed. Passed the completed type. /// - void OnComplete(); + void OnComplete(Type type); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs index bdc1c996f5..cf15d47d49 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs @@ -1,6 +1,4 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -8,12 +6,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit interface IReflectionMethodBaseSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IReflectionMethodBaseSymbol { - /// - /// Gets or creates a for the given . - /// - /// - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs index 76cbe97c51..87d35faebb 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs @@ -13,13 +13,6 @@ interface IReflectionMethodSymbolBuilder : IReflectionSymbolBuilder, IReflection /// MethodBuilder UnderlyingMethodBuilder { get; } - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs index 695568f4f5..8affb7ef25 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs @@ -13,63 +13,6 @@ interface IReflectionModuleSymbolBuilder : IReflectionSymbolBuilder, IModuleSymb /// ModuleBuilder UnderlyingModuleBuilder { get; } - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - /// - IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs index c010b01963..6028d6de6f 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs @@ -13,13 +13,6 @@ interface IReflectionPropertySymbolBuilder : IReflectionSymbolBuilder, IReflecti /// PropertyBuilder UnderlyingPropertyBuilder { get; } - /// - /// Gets or creates a for the given . - /// - /// - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs index b7795a7d32..1f88cf8c8e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs @@ -9,78 +9,6 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit interface IReflectionSymbolBuilder : ISymbolBuilder { - /// - /// Resolves the symbol for the specified assembly builder. - /// - /// - /// - [return: NotNullIfNotNull(nameof(assembly))] - IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); - - /// - /// Resolves the symbol for the specified module. - /// - /// - /// - [return: NotNullIfNotNull(nameof(module))] - IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - [return: NotNullIfNotNull(nameof(type))] - IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); - - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - [return: NotNullIfNotNull(nameof(ctor))] - IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - [return: NotNullIfNotNull(nameof(method))] - IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - [return: NotNullIfNotNull(nameof(field))] - IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); - - /// - /// Resolves the symbol for the specified property. - /// - /// - /// - [return: NotNullIfNotNull(nameof(property))] - IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - [return: NotNullIfNotNull(nameof(@event))] - IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); - - /// - /// Resolves the symbol for the specified generic type parameter. - /// - /// - /// - [return: NotNullIfNotNull(nameof(genericTypeParameter))] - IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs index d5ed37b227..835835b8ec 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs @@ -13,48 +13,6 @@ interface IReflectionTypeSymbolBuilder : IReflectionMemberSymbolBuilder, ITypeSy /// TypeBuilder UnderlyingTypeBuilder { get; } - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs index eae10821bd..7588f2e389 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs @@ -1,7 +1,4 @@ using System; -using System.Collections.Generic; -using System.IO; -using System.Linq; using System.Reflection; using System.Reflection.Emit; @@ -10,12 +7,11 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionAssemblySymbolBuilder : ReflectionSymbolBuilder, IReflectionAssemblySymbolBuilder + class ReflectionAssemblySymbolBuilder : ReflectionAssemblySymbol, IReflectionAssemblySymbolBuilder { readonly AssemblyBuilder _builder; - - ReflectionModuleTable _moduleTable; + Assembly? _assembly; /// /// Initializes a new instance. @@ -23,34 +19,23 @@ class ReflectionAssemblySymbolBuilder : ReflectionSymbolBuilder, IReflectionAsse /// /// public ReflectionAssemblySymbolBuilder(ReflectionSymbolContext context, AssemblyBuilder builder) : - base(context) + base(context, builder) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _moduleTable = new ReflectionModuleTable(context, this); } /// - public Assembly UnderlyingAssembly => UnderlyingAssemblyBuilder; + public AssemblyBuilder UnderlyingAssemblyBuilder => _builder; /// - public AssemblyBuilder UnderlyingAssemblyBuilder => _builder; + public override Assembly UnderlyingRuntimeAssembly => _assembly ?? throw new InvalidOperationException(); #region IReflectionAssemblySymbolBuilder /// public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) { - return _moduleTable.GetOrCreateModuleSymbol(module); - } - - #endregion - - #region IReflectionAssemblySymbol - - /// - public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - return _moduleTable.GetOrCreateModuleSymbol(module); + return (IReflectionModuleSymbolBuilder)base.GetOrCreateModuleSymbol(module); } #endregion @@ -90,15 +75,9 @@ public IModuleSymbolBuilder DefineModule(string name, string fileName, bool emit } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingAssemblyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingAssemblyBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingAssemblyBuilder.SetCustomAttribute(attribute.Unpack()); } /// @@ -160,7 +139,7 @@ public void AddResourceFile(string name, string fileName) } /// - public void Save(string assemblyFileName, System.Reflection.PortableExecutableKinds portableExecutableKind, IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine) + public void Save(string assemblyFileName, PortableExecutableKinds portableExecutableKind, IKVM.CoreLib.Symbols.ImageFileMachine imageFileMachine) { #if NETFRAMEWORK UnderlyingAssemblyBuilder.Save(assemblyFileName, portableExecutableKind, (System.Reflection.ImageFileMachine)imageFileMachine); @@ -174,134 +153,7 @@ public void Save(string assemblyFileName, System.Reflection.PortableExecutableKi #region IAssemblySymbol /// - public IEnumerable DefinedTypes => ResolveTypeSymbols(UnderlyingAssembly.DefinedTypes); - - /// - public IMethodSymbol? EntryPoint => ResolveMethodSymbol(UnderlyingAssembly.EntryPoint); - - /// - public IEnumerable ExportedTypes => ResolveTypeSymbols(UnderlyingAssembly.ExportedTypes); - - /// - public string? FullName => UnderlyingAssembly.FullName; - - /// - public string ImageRuntimeVersion => UnderlyingAssembly.ImageRuntimeVersion; - - /// - public IModuleSymbol ManifestModule => ResolveModuleSymbol(UnderlyingAssembly.ManifestModule); - - /// - public IEnumerable Modules => ResolveModuleSymbols(UnderlyingAssembly.Modules); - - /// - public override bool IsComplete => _builder == null; - - public string Location => throw new NotImplementedException(); - - /// - public ITypeSymbol[] GetExportedTypes() - { - return ResolveTypeSymbols(UnderlyingAssembly.GetExportedTypes()); - } - - /// - public IModuleSymbol? GetModule(string name) - { - return ResolveModuleSymbol(UnderlyingAssembly.GetModule(name)); - } - - /// - public IModuleSymbol[] GetModules() - { - return ResolveModuleSymbols(UnderlyingAssembly.GetModules()); - } - - /// - public IModuleSymbol[] GetModules(bool getResourceModules) - { - return ResolveModuleSymbols(UnderlyingAssembly.GetModules(getResourceModules)); - } - - /// - public AssemblyIdentity GetIdentity() - { - return UnderlyingAssembly.GetName().Pack(); - } - - /// - public AssemblyIdentity[] GetReferencedAssemblies() - { - return UnderlyingAssembly.GetReferencedAssemblies().Pack(); - } - - /// - public ITypeSymbol? GetType(string name, bool throwOnError) - { - return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError)); - } - - /// - public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError, ignoreCase)); - } - - /// - public ITypeSymbol? GetType(string name) - { - return ResolveTypeSymbol(UnderlyingAssembly.GetType(name)); - } - - /// - public ITypeSymbol[] GetTypes() - { - return ResolveTypeSymbols(UnderlyingAssembly.GetTypes()); - } - - /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData()); - } - - /// - public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); - } - - /// - public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttribute(UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); - } - - /// - public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); - } - - /// - public ManifestResourceInfo? GetManifestResourceInfo(string resourceName) - { - return ResolveManifestResourceInfo(UnderlyingAssembly.GetManifestResourceInfo(resourceName)); - } - - /// - public Stream? GetManifestResourceStream(string name) - { - return UnderlyingAssembly.GetManifestResourceStream(name); - } - - /// - public Stream? GetManifestResourceStream(ITypeSymbol type, string name) - { - return UnderlyingAssembly.GetManifestResourceStream(type.Unpack(), name); - } + public override bool IsComplete => _assembly != null; #endregion diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs index ab93503cd6..58c089f672 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs @@ -1,19 +1,25 @@ using System; +using System.Collections.Generic; +using System.Diagnostics; +using System.Linq; using System.Reflection; using System.Reflection.Emit; +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflectionConstructorSymbolBuilder + class ReflectionConstructorSymbolBuilder : ReflectionConstructorSymbol, IReflectionConstructorSymbolBuilder { readonly ConstructorBuilder _builder; ConstructorInfo? _ctor; ReflectionILGenerator? _il; + List? _incompleteCustomAttributes; /// /// Initializes a new instance. @@ -24,39 +30,30 @@ class ReflectionConstructorSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IR /// /// public ReflectionConstructorSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder resolvingType, ConstructorBuilder builder) : - base(context, resolvingModule, resolvingType) + base(context, resolvingModule, resolvingType, builder) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); } /// - public ConstructorInfo UnderlyingConstructor => _ctor ?? _builder; - - /// - public ConstructorInfo UnderlyingEmitConstructor => _builder; - - /// - public ConstructorInfo UnderlyingDynamicEmitConstructor => _ctor ?? throw new InvalidOperationException(); - - /// - public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; + public ConstructorBuilder UnderlyingConstructorBuilder => _builder; /// - public override MethodBase UnderlyingEmitMethodBase => UnderlyingEmitConstructor; + public override ConstructorInfo UnderlyingRuntimeConstructor => _ctor ?? throw new InvalidOperationException(); /// - public ConstructorBuilder UnderlyingConstructorBuilder => _builder; + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => (IReflectionModuleSymbolBuilder)ResolvingModule; #region IConstructorSymbolBuilder /// - public override void SetImplementationFlags(MethodImplAttributes attributes) + public void SetImplementationFlags(MethodImplAttributes attributes) { UnderlyingConstructorBuilder.SetImplementationFlags(attributes); } /// - public override IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) + public IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName) { if (iSequence <= 0) throw new ArgumentOutOfRangeException(nameof(iSequence)); @@ -65,54 +62,80 @@ public override IParameterSymbolBuilder DefineParameter(int iSequence, Parameter } /// - public override IILGenerator GetILGenerator() + public IILGenerator GetILGenerator() { return _il ??= new ReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator()); } /// - public override IILGenerator GetILGenerator(int streamSize) + public IILGenerator GetILGenerator(int streamSize) { return _il ??= new ReflectionILGenerator(Context, UnderlyingConstructorBuilder.GetILGenerator(streamSize)); } + #endregion + + #region IConstructorSymbol + /// - public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingConstructorBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } + public override bool IsComplete => _ctor != null; + + #endregion + + #region ICustomAttributeProviderBuilder /// - public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingConstructorBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); + UnderlyingConstructorBuilder.SetCustomAttribute(attribute.Unpack()); + _incompleteCustomAttributes ??= []; + _incompleteCustomAttributes.Add(attribute); } #endregion - #region IConstructorSymbol + #region ICustomAttributeProvider /// - public override bool IsComplete => _ctor != null; - - #endregion + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + if (IsComplete) + return ResolveCustomAttributes(UnderlyingRuntimeConstructor.GetCustomAttributesData(inherit).ToArray()); + else + return _incompleteCustomAttributes?.ToArray() ?? []; + } - #region IMethodBaseSymbol + /// + public override CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + if (IsComplete) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingRuntimeConstructor.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); + } + else + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + } /// - public override ITypeSymbol[] GetGenericArguments() + public override CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - // constructor never has generic arguments - return []; + if (IsComplete) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingRuntimeConstructor.GetCustomAttributesData().FirstOrDefault(i => i.AttributeType == _attributeType)); + } + else + return GetCustomAttributes(inherit).FirstOrDefault(i => i.AttributeType == attributeType); } #endregion /// - public override void OnComplete() + public void OnComplete() { _ctor = (ConstructorInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); - base.OnComplete(); + _incompleteCustomAttributes = null; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs deleted file mode 100644 index eed10e2cb1..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionCustomAttributeBuilder.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - class ReflectionCustomAttributeBuilder : ICustomAttributeBuilder - { - - readonly CustomAttributeBuilder _builder; - - /// - /// Initializes a new instance. - /// - public ReflectionCustomAttributeBuilder(CustomAttributeBuilder builder) - { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - } - - /// - /// Gets the underlying reflection . - /// - internal CustomAttributeBuilder UnderlyingBuilder => _builder; - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs index 7a87c506d2..58f0919466 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs @@ -1,6 +1,7 @@ using System; using System.Reflection; using System.Reflection.Emit; + using IKVM.CoreLib.Reflection; namespace IKVM.CoreLib.Symbols.Reflection.Emit diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs index 9525d00455..2ca8260cd4 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs @@ -7,11 +7,10 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionEventSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionEventSymbolBuilder + class ReflectionEventSymbolBuilder : ReflectionEventSymbol, IReflectionEventSymbolBuilder { readonly EventBuilder _builder; - readonly ReflectionEventBuilderInfo _builderInfo; EventInfo? _event; /// @@ -23,23 +22,19 @@ class ReflectionEventSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionE /// /// public ReflectionEventSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder resolvingType, EventBuilder builder) : - base(context, resolvingModule, resolvingType) + base(context, resolvingModule, resolvingType, new ReflectionEventBuilderInfo(builder)) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _builderInfo = new ReflectionEventBuilderInfo(_builder); } /// - public EventInfo UnderlyingEvent => _event ?? _builderInfo; + public EventBuilder UnderlyingEventBuilder => _builder; /// - public EventInfo UnderlyingEmitEvent => UnderlyingEvent; + public override EventInfo UnderlyingRuntimeEvent => _event ?? throw new InvalidOperationException(); /// - public EventBuilder UnderlyingEventBuilder => _builder ?? throw new NotImplementedException(); - - /// - public override MemberInfo UnderlyingMember => UnderlyingEvent; + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => (IReflectionModuleSymbolBuilder)ResolvingModule; #region IEventSymbolBuilder @@ -67,98 +62,29 @@ public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) UnderlyingEventBuilder.AddOtherMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingEventBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } + #endregion + + #region ICustomAttributeProviderBuilder /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingEventBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingEventBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion #region IEventSymbol - /// - public System.Reflection.EventAttributes Attributes => UnderlyingEvent.Attributes; - - /// - public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); - - /// - public bool IsSpecialName => UnderlyingEvent.IsSpecialName; - - /// - public IMethodSymbol? AddMethod => ResolveMethodSymbol(UnderlyingEvent.AddMethod); - - /// - public IMethodSymbol? RemoveMethod => ResolveMethodSymbol(UnderlyingEvent.RemoveMethod); - - /// - public IMethodSymbol? RaiseMethod => ResolveMethodSymbol(UnderlyingEvent.RaiseMethod); - /// public override bool IsComplete => _event != null; - /// - public IMethodSymbol? GetAddMethod() - { - return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod()); - } - - /// - public IMethodSymbol? GetAddMethod(bool nonPublic) - { - return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod(nonPublic)); - } - - /// - public IMethodSymbol? GetRemoveMethod() - { - return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod()); - } - - /// - public IMethodSymbol? GetRemoveMethod(bool nonPublic) - { - return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod(nonPublic)); - } - - /// - public IMethodSymbol? GetRaiseMethod() - { - return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod()); - } - - /// - public IMethodSymbol? GetRaiseMethod(bool nonPublic) - { - return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod(nonPublic)); - } - - /// - public IMethodSymbol[] GetOtherMethods() - { - return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods()); - } - - /// - public IMethodSymbol[] GetOtherMethods(bool nonPublic) - { - return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods(nonPublic)); - } - #endregion /// - public override void OnComplete() + public void OnComplete() { _event = (EventInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); - base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs index 91186b5ad4..6e99440cf8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs @@ -7,7 +7,7 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionFieldSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionFieldSymbolBuilder + class ReflectionFieldSymbolBuilder : ReflectionFieldSymbol, IReflectionFieldSymbolBuilder { readonly FieldBuilder _builder; @@ -22,25 +22,26 @@ class ReflectionFieldSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionF /// /// public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType, FieldBuilder builder) : - base(context, resolvingModule, resolvingType) + base(context, resolvingModule, resolvingType, builder) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); } /// - public FieldInfo UnderlyingField => _field ?? _builder; + public FieldBuilder UnderlyingFieldBuilder => _builder; /// - public FieldInfo UnderlyingEmitField => _builder; + public override FieldInfo UnderlyingRuntimeField => _field ?? throw new InvalidOperationException(); /// - public FieldInfo UnderlyingDynamicEmitField => _field ?? throw new InvalidOperationException(); + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => (IReflectionModuleSymbolBuilder)ResolvingModule; - /// - public override MemberInfo UnderlyingMember => UnderlyingField; + #region IFieldSymbol - /// - public FieldBuilder UnderlyingFieldBuilder => _builder; + /// + public override bool IsComplete => _field != null; + + #endregion #region IFieldSymbolBuilder @@ -56,92 +57,22 @@ public void SetOffset(int iOffset) UnderlyingFieldBuilder.SetOffset(iOffset); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingFieldBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingFieldBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } - #endregion - #region IFieldSymbol - - /// - public FieldAttributes Attributes => UnderlyingField.Attributes; - - /// - public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); - - /// - public bool IsSpecialName => UnderlyingField.IsSpecialName; - - /// - public bool IsAssembly => UnderlyingField.IsAssembly; - - /// - public bool IsFamily => UnderlyingField.IsFamily; - - /// - public bool IsFamilyAndAssembly => UnderlyingField.IsFamilyAndAssembly; + #region ICustomAttributeProviderBuilder - /// - public bool IsFamilyOrAssembly => UnderlyingField.IsFamilyOrAssembly; - - /// - public bool IsInitOnly => UnderlyingField.IsInitOnly; - - /// - public bool IsLiteral => UnderlyingField.IsLiteral; - - /// - public bool IsNotSerialized => UnderlyingField.IsNotSerialized; - - /// - public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; - - /// - public bool IsPrivate => UnderlyingField.IsPrivate; - - /// - public bool IsPublic => UnderlyingField.IsPublic; - - /// - public bool IsStatic => UnderlyingField.IsStatic; - - /// - public override bool IsComplete => _field != null; - - /// - public ITypeSymbol[] GetOptionalCustomModifiers() - { - return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); - } - - /// - public ITypeSymbol[] GetRequiredCustomModifiers() - { - return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); - } - - /// - public object? GetRawConstantValue() + /// + public void SetCustomAttribute(CustomAttribute attribute) { - return UnderlyingField.GetRawConstantValue(); + UnderlyingFieldBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion /// - public override void OnComplete() + public void OnComplete() { _field = ResolvingModule.UnderlyingModule.ResolveField(MetadataToken) ?? throw new InvalidOperationException(); - base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs index 37c8c2b5c8..f181b5f3d0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs @@ -1,21 +1,15 @@ using System; -using System.Reflection; using System.Reflection.Emit; -using IKVM.CoreLib.Reflection; - namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionGenericTypeParameterSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionGenericTypeParameterSymbolBuilder + class ReflectionGenericTypeParameterSymbolBuilder : ReflectionGenericTypeParameterSymbol, IReflectionGenericTypeParameterSymbolBuilder { - readonly IReflectionMemberSymbol? _resolvingMember; readonly GenericTypeParameterBuilder _builder; Type? _type; - ReflectionTypeSpecTable _specTable; - /// /// Initializes a new instance. /// @@ -25,145 +19,28 @@ class ReflectionGenericTypeParameterSymbolBuilder : ReflectionMemberSymbolBuilde /// /// public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionMemberSymbolBuilder resolvingMember, GenericTypeParameterBuilder builder) : - base(context, resolvingModule, resolvingMember as IReflectionTypeSymbolBuilder) + base(context, resolvingModule, resolvingMember, builder) { - _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _specTable = new ReflectionTypeSpecTable(); } /// - public Type UnderlyingType => _type ?? _builder; - - /// - public Type UnderlyingEmitType => UnderlyingType; - - /// - public Type UnderlyingDynamicEmitType => _type ?? throw new InvalidOperationException(); - - /// - public override MemberInfo UnderlyingMember => UnderlyingType; + public override Type UnderlyingRuntimeType => _type ?? throw new InvalidOperationException(); #region IReflectionGenericTypeParameterSymbolBuilder /// public GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder => _builder ?? throw new InvalidOperationException(); - #endregion - - #region IReflectionTypeSymbol - - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - throw new NotSupportedException(); - } - - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - throw new NotSupportedException(); - } - - /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - throw new NotSupportedException(); - } - - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - throw new NotSupportedException(); - } - - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - throw new NotSupportedException(); - } - - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - throw new NotSupportedException(); - } - - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - throw new NotSupportedException(); - } - - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - throw new NotSupportedException(); - } - - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - throw new NotSupportedException(); - } - - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - throw new NotSupportedException(); - } - - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - throw new NotSupportedException(); - } - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type type) - { - throw new NotSupportedException(); - } - - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeSymbol(GenericTypeParameterBuilder genericType) - { - throw new NotSupportedException(); - } - - /// - public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() - { - return _specTable.GetOrCreateSZArrayTypeSymbol(); - } - /// - public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + public void OnComplete(Type type) { - return _specTable.GetOrCreateArrayTypeSymbol(rank); - } - - /// - public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() - { - return _specTable.GetOrCreatePointerTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() - { - return _specTable.GetOrCreateByRefTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) - { - return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + _type = type; } #endregion - #region ITypeSymbolBuilder + #region IGenericTypeParameterSymbolBuilder /// public void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint) @@ -174,7 +51,7 @@ public void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint) /// public void SetGenericParameterAttributes(System.Reflection.GenericParameterAttributes genericParameterAttributes) { - UnderlyingGenericTypeParameterBuilder.SetGenericParameterAttributes((GenericParameterAttributes)genericParameterAttributes); + UnderlyingGenericTypeParameterBuilder.SetGenericParameterAttributes(genericParameterAttributes); } /// @@ -188,535 +65,20 @@ public void SetInterfaceConstraints(params ITypeSymbol[]? interfaceConstraints) #region ITypeSymbol /// - public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); - - /// - public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; - - /// - public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; - - /// - public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); - - /// - public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; - - /// - public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); - - /// - public string? FullName => UnderlyingType.FullName; - - /// - public string? Namespace => UnderlyingType.Namespace; - - /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; - - /// - public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; - - /// - public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); - - /// - public bool HasElementType => UnderlyingType.HasElementType; - - /// - public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); - - /// - public bool IsAbstract => UnderlyingType.IsAbstract; - - /// - public bool IsSZArray => UnderlyingType.IsSZArray(); - - /// - public bool IsArray => UnderlyingType.IsArray; - - /// - public bool IsAutoLayout => UnderlyingType.IsAutoLayout; - - /// - public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; - - /// - public bool IsByRef => UnderlyingType.IsByRef; - - /// - public bool IsClass => UnderlyingType.IsClass; - - /// - public bool IsEnum => UnderlyingType.IsEnum; - - /// - public bool IsInterface => UnderlyingType.IsInterface; - - /// - public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; - - /// - public bool IsGenericParameter => UnderlyingType.IsGenericParameter; - - /// - public bool IsGenericType => UnderlyingType.IsGenericType; - - /// - public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; - - /// - public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; - - /// - public bool IsNested => UnderlyingType.IsNested; - - /// - public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; - - /// - public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; - - /// - public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; - - /// - public bool IsNestedFamily => UnderlyingType.IsNestedFamily; - - /// - public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; - - /// - public bool IsNestedPublic => UnderlyingType.IsNestedPublic; - - /// - public bool IsNotPublic => UnderlyingType.IsNotPublic; - - /// - public bool IsPointer => UnderlyingType.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; - - /// - public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; - -#else - - /// - public bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public bool IsPrimitive => UnderlyingType.IsPrimitive; - - /// - public bool IsPublic => UnderlyingType.IsPublic; - - /// - public bool IsSealed => UnderlyingType.IsSealed; - - /// - public bool IsSerializable => UnderlyingType.IsSerializable; - - /// - public bool IsValueType => UnderlyingType.IsValueType; - - /// - public bool IsVisible => UnderlyingType.IsVisible; - - /// - public bool IsSignatureType => throw new NotImplementedException(); - - /// - public bool IsSpecialName => UnderlyingType.IsSpecialName; - - /// - public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); - - /// - public int GetArrayRank() - { - return UnderlyingType.GetArrayRank(); - } - - /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); - } - - /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetDefaultMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); - } - - /// - public ITypeSymbol? GetElementType() - { - return ResolveTypeSymbol(UnderlyingType.GetElementType()); - } - - /// - public string? GetEnumName(object value) - { - return UnderlyingType.GetEnumName(value); - } - - /// - public string[] GetEnumNames() - { - return UnderlyingType.GetEnumNames(); - } - - /// - public ITypeSymbol GetEnumUnderlyingType() - { - return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public Array GetEnumValues() - { - return UnderlyingType.GetEnumValues(); - } - - /// - public IEventSymbol? GetEvent(string name) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name)); - } - - /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); - } - - /// - public IEventSymbol[] GetEvents() - { - return ResolveEventSymbols(UnderlyingType.GetEvents()); - } - - /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) - { - return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name)); - } - - /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingType.GetFields()); - } - - /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); - } - - /// - public ITypeSymbol[] GetGenericParameterConstraints() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public ITypeSymbol GetGenericTypeDefinition() - { - return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public ITypeSymbol? GetInterface(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); - } - - /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); - } + public override bool IsComplete => _type != null; - /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public IMemberSymbol[] GetMember(string name) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name)); - } - - /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetMembers()); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); - } - - /// - public IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(UnderlyingType.GetMethods()); - } - - /// - public ITypeSymbol? GetNestedType(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); - } - - /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetNestedTypes() - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); - } - - /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol[] GetProperties() - { - return ResolvePropertySymbols(UnderlyingType.GetProperties()); - } - - /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public bool IsAssignableFrom(ITypeSymbol? c) - { - return UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public bool IsEnumDefined(object value) - { - return UnderlyingType.IsEnumDefined(value); - } - - /// - public bool IsSubclassOf(ITypeSymbol c) - { - return UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public ITypeSymbol MakeArrayType() - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); - } - - /// - public ITypeSymbol MakeArrayType(int rank) - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); - } + #endregion - /// - public ITypeSymbol MakeByRefType() - { - return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); - } + #region ICustomAttributeProviderBuilder /// - public ITypeSymbol MakePointerType() + public void SetCustomAttribute(CustomAttribute attribute) { - return ResolveTypeSymbol(UnderlyingType.MakePointerType()); - } - - /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); + UnderlyingGenericTypeParameterBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion - /// - public override void OnComplete() - { - - } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs index 4cbac54c0b..43505cd318 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs @@ -42,11 +42,10 @@ public ReflectionILGenerator(ReflectionSymbolContext context, ILGenerator il, bo [return: NotNullIfNotNull(nameof(symbol))] Type? GetEmitType(ITypeSymbol? symbol) { - var n = symbol.Name; if (_dynamic) - return ((IReflectionTypeSymbol?)symbol)?.UnderlyingDynamicEmitType; + return ((IReflectionTypeSymbol?)symbol)?.UnderlyingRuntimeType; else - return ((IReflectionTypeSymbol?)symbol)?.UnderlyingEmitType; + return ((IReflectionTypeSymbol?)symbol)?.UnderlyingType; } /// @@ -58,9 +57,9 @@ public ReflectionILGenerator(ReflectionSymbolContext context, ILGenerator il, bo FieldInfo? GetEmitField(IFieldSymbol? symbol) { if (_dynamic) - return ((IReflectionFieldSymbol?)symbol)?.UnderlyingDynamicEmitField; + return ((IReflectionFieldSymbol?)symbol)?.UnderlyingRuntimeField; else - return ((IReflectionFieldSymbol?)symbol)?.UnderlyingEmitField; + return ((IReflectionFieldSymbol?)symbol)?.UnderlyingField; } /// @@ -72,9 +71,9 @@ public ReflectionILGenerator(ReflectionSymbolContext context, ILGenerator il, bo ConstructorInfo? GetEmitConstructor(IConstructorSymbol? symbol) { if (_dynamic) - return ((IReflectionConstructorSymbol?)symbol)?.UnderlyingDynamicEmitConstructor; + return ((IReflectionConstructorSymbol?)symbol)?.UnderlyingRuntimeConstructor; else - return ((IReflectionConstructorSymbol?)symbol)?.UnderlyingEmitConstructor; + return ((IReflectionConstructorSymbol?)symbol)?.UnderlyingConstructor; } /// @@ -86,9 +85,9 @@ public ReflectionILGenerator(ReflectionSymbolContext context, ILGenerator il, bo MethodInfo? GetEmitMethod(IMethodSymbol? symbol) { if (_dynamic) - return ((IReflectionMethodSymbol?)symbol)?.UnderlyingDynamicEmitMethod; + return ((IReflectionMethodSymbol?)symbol)?.UnderlyingRuntimeMethod; else - return ((IReflectionMethodSymbol?)symbol)?.UnderlyingEmitMethod; + return ((IReflectionMethodSymbol?)symbol)?.UnderlyingMethod; } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs deleted file mode 100644 index b093a18e12..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMemberSymbolBuilder.cs +++ /dev/null @@ -1,348 +0,0 @@ -using System; -using System.Diagnostics.CodeAnalysis; -using System.Linq; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - abstract class ReflectionMemberSymbolBuilder : ReflectionSymbolBuilder, IReflectionMemberSymbolBuilder - { - - readonly IReflectionModuleSymbolBuilder _resolvingModule; - readonly IReflectionTypeSymbolBuilder? _resolvingType; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionMemberSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType) : - base(context) - { - _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingType = resolvingType; - } - - #region IReflectionMemberSymbol - - /// - public abstract MemberInfo UnderlyingMember { get; } - - /// - public virtual MemberInfo UnderlyingEmitMember => UnderlyingMember; - - /// - public IReflectionModuleSymbol ResolvingModule => _resolvingModule; - - /// - public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => _resolvingModule; - - /// - public IReflectionTypeSymbol? ResolvingType => _resolvingType; - - #endregion - - #region IReflectionSymbolBuilder - - /// - [return: NotNullIfNotNull("type")] - public override IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - - if (UnderlyingMember == type) - return (IReflectionTypeSymbolBuilder)this; - - if (_resolvingType != null && type == _resolvingType.UnderlyingType) - return (IReflectionTypeSymbolBuilder)_resolvingType; - - if (type.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateTypeSymbol(type); - - return base.ResolveTypeSymbol(type); - } - - /// - [return: NotNullIfNotNull(nameof(ctor))] - public override IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) - { - if (ctor is null) - throw new ArgumentNullException(nameof(ctor)); - - if (UnderlyingMember == ctor) - return (IReflectionConstructorSymbolBuilder)this; - - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); - - return base.ResolveConstructorSymbol(ctor); - } - - /// - [return: NotNullIfNotNull(nameof(method))] - public override IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - if (UnderlyingMember == method) - return (IReflectionMethodSymbolBuilder)this; - - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); - - return base.ResolveMethodSymbol(method); - } - - /// - [return: NotNullIfNotNull(nameof(field))] - public override IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - if (UnderlyingMember == field) - return (IReflectionFieldSymbolBuilder)this; - - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); - - return base.ResolveFieldSymbol(field); - } - - /// - [return: NotNullIfNotNull(nameof(property))] - public override IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - if (UnderlyingMember == property) - return (IReflectionPropertySymbolBuilder)this; - - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); - - return base.ResolvePropertySymbol(property); - } - - /// - [return: NotNullIfNotNull(nameof(@event))] - public override IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - if (@event.GetModuleBuilder() == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); - - return base.ResolveEventSymbol(@event); - } - - /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionMethodBaseSymbolBuilder method, ParameterBuilder parameter) - { - if (parameter is null) - return null; - - if (parameter.GetModuleBuilder() == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(method, parameter); - - return base.ResolveParameterSymbol(method, parameter); - } - - /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionPropertySymbolBuilder property, ParameterBuilder parameter) - { - if (parameter is null) - return null; - - if (parameter.GetMethodBuilder().Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(property, parameter); - - return base.ResolveParameterSymbol(property, parameter); - } - - #endregion - - #region IReflectionSymbol - - /// - [return: NotNullIfNotNull(nameof(type))] - public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) - { - if (type is null) - return null; - - if (UnderlyingMember == type) - return (IReflectionTypeSymbol)this; - - if (_resolvingType != null && type == _resolvingType.UnderlyingType) - return _resolvingType; - - if (type.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateTypeSymbol(type); - - return base.ResolveTypeSymbol(type); - } - - /// - [return: NotNullIfNotNull(nameof(ctor))] - public override IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) - { - if (ctor is null) - return null; - - if (UnderlyingMember == ctor) - return (IReflectionConstructorSymbol)this; - - if (ctor.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateConstructorSymbol(ctor); - - return base.ResolveConstructorSymbol(ctor); - } - - /// - [return: NotNullIfNotNull(nameof(method))] - public override IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) - { - if (method is null) - return null; - - if (UnderlyingMember == method) - return (IReflectionMethodSymbol)this; - - if (method.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateMethodSymbol(method); - - return base.ResolveMethodSymbol(method); - } - - /// - [return: NotNullIfNotNull(nameof(field))] - public override IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) - { - if (field is null) - return null; - - if (UnderlyingMember == field) - return (IReflectionFieldSymbol)this; - - if (field.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateFieldSymbol(field); - - return base.ResolveFieldSymbol(field); - } - - /// - [return: NotNullIfNotNull(nameof(property))] - public override IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) - { - if (property is null) - return null; - - if (UnderlyingMember == property) - return (IReflectionPropertySymbol)this; - - if (property.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreatePropertySymbol(property); - - return base.ResolvePropertySymbol(property); - } - - /// - [return: NotNullIfNotNull(nameof(@event))] - public override IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) - { - if (@event is null) - return null; - - if (UnderlyingMember == @event) - return (IReflectionEventSymbol)this; - - if (@event.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateEventSymbol(@event); - - return base.ResolveEventSymbol(@event); - } - - /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - if (parameter.Member.Module == _resolvingModule.UnderlyingModule) - return _resolvingModule.GetOrCreateParameterSymbol(parameter); - - return base.ResolveParameterSymbol(parameter); - } - - #endregion - - #region IMemberSymbol - - /// - public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; - - /// - public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; - - /// - public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; - - /// - public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); - - /// - public virtual string Name => UnderlyingMember.Name; - - /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData()); - } - - /// - public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); - } - - /// - public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttribute(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); - } - - /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); - } - - #endregion - - /// - public virtual void OnComplete() - { - - } - - /// - public override string? ToString() => UnderlyingMember.ToString(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs deleted file mode 100644 index eabf450d17..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodBaseSymbolBuilder.cs +++ /dev/null @@ -1,167 +0,0 @@ -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - abstract class ReflectionMethodBaseSymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionMethodBaseSymbolBuilder - { - - ReflectionParameterTable _parameterTable; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionMethodBaseSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType) : - base(context, resolvingModule, resolvingType) - { - _parameterTable = new ReflectionParameterTable(context, resolvingModule, this); - } - - /// - public abstract MethodBase UnderlyingMethodBase { get; } - - /// - public virtual MethodBase UnderlyingEmitMethodBase => UnderlyingMethodBase; - - /// - public override MemberInfo UnderlyingMember => UnderlyingMethodBase; - - /// - public override MemberInfo UnderlyingEmitMember => UnderlyingEmitMethodBase; - - #region IReflectionMethodBaseSymbol - - /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - return _parameterTable.GetOrCreateParameterSymbol(parameter); - } - - #endregion - - #region IMethodBaseSymbolBuilder - - /// - public abstract void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes); - - /// - public abstract IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName); - - /// - public abstract IILGenerator GetILGenerator(); - - /// - public abstract IILGenerator GetILGenerator(int streamSize); - - /// - public abstract void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute); - - /// - public abstract void SetCustomAttribute(ICustomAttributeBuilder customBuilder); - - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return _parameterTable.GetOrCreateParameterSymbol(parameter); - } - - #endregion - - #region IMethodBaseSymbol - - /// - public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; - - /// - public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; - - /// - public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; - - /// - public bool IsAbstract => UnderlyingMethodBase.IsAbstract; - - /// - public bool IsAssembly => UnderlyingMethodBase.IsAssembly; - - /// - public bool IsConstructor => UnderlyingMethodBase.IsConstructor; - - /// - public bool IsFamily => UnderlyingMethodBase.IsFamily; - - /// - public bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; - - /// - public bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; - - /// - public bool IsFinal => UnderlyingMethodBase.IsFinal; - - /// - public bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; - - /// - public bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; - - /// - public bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; - - /// - public bool IsPrivate => UnderlyingMethodBase.IsPrivate; - - /// - public bool IsPublic => UnderlyingMethodBase.IsPublic; - - /// - public bool IsStatic => UnderlyingMethodBase.IsStatic; - - /// - public bool IsVirtual => UnderlyingMethodBase.IsVirtual; - - /// - public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; - - /// - public MethodImplAttributes MethodImplementationFlags => UnderlyingMethodBase.MethodImplementationFlags; - - /// - public virtual ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); - } - - /// - public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() - { - return UnderlyingMethodBase.GetMethodImplementationFlags(); - } - - /// - public IParameterSymbol[] GetParameters() - { - return ResolveParameterSymbols(UnderlyingMethodBase.GetParameters()); - } - - #endregion - - /// - public override void OnComplete() - { - foreach (var i in GetGenericArguments()) - if (i is IReflectionGenericTypeParameterSymbolBuilder b) - b.OnComplete(); - - base.OnComplete(); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index c43c266183..2dc1d53f13 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -1,22 +1,23 @@ using System; +using System.Collections.Generic; +using System.Linq; using System.Reflection; using System.Reflection.Emit; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflectionMethodSymbolBuilder + class ReflectionMethodSymbolBuilder : ReflectionMethodSymbol, IReflectionMethodSymbolBuilder { readonly MethodBuilder _builder; MethodInfo? _method; - ReflectionGenericTypeParameterTable _genericTypeParameterTable; - ReflectionMethodSpecTable _specTable; - ReflectionILGenerator? _il; + List? _incompleteCustomAttributes; /// /// Initializes a new instance. @@ -27,103 +28,43 @@ class ReflectionMethodSymbolBuilder : ReflectionMethodBaseSymbolBuilder, IReflec /// /// public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType, MethodBuilder builder) : - base(context, resolvingModule, resolvingType) + base(context, resolvingModule, resolvingType, builder) { - _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, resolvingModule, this); - _specTable = new ReflectionMethodSpecTable(context, resolvingModule, resolvingType, this); + _builder = builder; } - /// - public MethodInfo UnderlyingMethod => _method ?? _builder; - - /// - public MethodInfo UnderlyingEmitMethod => _builder; - - /// - public MethodInfo UnderlyingDynamicEmitMethod => _method ?? throw new InvalidOperationException(); - - /// - public override MethodBase UnderlyingMethodBase => UnderlyingMethod; - - /// - public override MethodBase UnderlyingEmitMethodBase => UnderlyingEmitMethod; - /// public MethodBuilder UnderlyingMethodBuilder => _builder; - #region IReflectionMethodSymbolBuilder - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - - #endregion - - #region IReflectionMethodSymbol - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - - /// - public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) - { - return _specTable.GetOrCreateGenericMethodSymbol(ResolveTypeSymbols(method.GetGenericArguments())); - } - - #endregion - - #region IReflectionMethodBaseSymbol - - #endregion - - #region IReflectionMethodBaseSymbolBuilder - - #endregion + public override MethodInfo UnderlyingRuntimeMethod => _method ?? throw new InvalidOperationException(); #region IMethodBaseSymbolBuilder /// - public override void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) { UnderlyingMethodBuilder.SetImplementationFlags((MethodImplAttributes)attributes); } /// - public override IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) + public IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) { return ResolveParameterSymbol(this, UnderlyingMethodBuilder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); } /// - public override IILGenerator GetILGenerator() + public IILGenerator GetILGenerator() { return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator()); } /// - public override IILGenerator GetILGenerator(int streamSize) + public IILGenerator GetILGenerator(int streamSize) { return _il ??= new ReflectionILGenerator(Context, UnderlyingMethodBuilder.GetILGenerator(streamSize)); } - /// - public override void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingMethodBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public override void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingMethodBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } - #endregion #region IMethodSymbolBuilder @@ -161,43 +102,76 @@ public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params strin #region IMethodSymbol /// - public IParameterSymbol ReturnParameter => ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); + public override bool IsComplete => _method != null; - /// - public ITypeSymbol ReturnType => ResolveTypeSymbol(UnderlyingMethod.ReturnType); + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => throw new NotImplementedException(); - /// - public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + #endregion + + #region ICustomAttributeProviderBuilder /// - public override bool IsComplete => _method != null; + public void SetCustomAttribute(CustomAttribute attribute) + { + UnderlyingMethodBuilder.SetCustomAttribute(attribute.Unpack()); + _incompleteCustomAttributes ??= []; + _incompleteCustomAttributes.Add(attribute); + } + + #endregion + + #region ICustomAttributeProvider /// - public IMethodSymbol GetBaseDefinition() + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) { - return ResolveMethodSymbol(UnderlyingMethod.GetBaseDefinition()); + if (IsComplete) + return ResolveCustomAttributes(UnderlyingRuntimeMethod.GetCustomAttributesData(inherit).ToArray()); + else if (inherit == false || GetBaseDefinition() == null) + return _incompleteCustomAttributes?.ToArray() ?? []; + else + return Enumerable.Concat(_incompleteCustomAttributes?.ToArray() ?? [], ResolveCustomAttributes(GetBaseDefinition().Unpack().GetInheritedCustomAttributesData())).ToArray(); } /// - public IMethodSymbol GetGenericMethodDefinition() + public override CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) { - return ResolveMethodSymbol(UnderlyingMethod.GetGenericMethodDefinition()); + if (IsComplete) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttributes(UnderlyingRuntimeMethod.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); + } + else + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); } /// - public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) + public override CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) { - return ResolveMethodSymbol(UnderlyingMethod.MakeGenericMethod(typeArguments.Unpack())); + if (IsComplete) + { + var _attributeType = attributeType.Unpack(); + return ResolveCustomAttribute(UnderlyingRuntimeMethod.GetCustomAttributesData().FirstOrDefault(i => i.AttributeType == _attributeType)); + } + else + return GetCustomAttributes(inherit).FirstOrDefault(i => i.AttributeType == attributeType); } #endregion /// - public override void OnComplete() + public void OnComplete() { _method = (MethodInfo?)ResolvingModule.UnderlyingModule.ResolveMethod(MetadataToken) ?? throw new InvalidOperationException(); - base.OnComplete(); + _incompleteCustomAttributes = null; + + // apply the runtime generic type parameters + var genericTypeParameters = ResolveTypeSymbols(UnderlyingRuntimeMethod.GetGenericArguments()) ?? []; + for (int i = 0; i < genericTypeParameters.Length; i++) + if (genericTypeParameters[i] is IReflectionGenericTypeParameterSymbolBuilder b) + b.OnComplete(genericTypeParameters[i].UnderlyingRuntimeType); } + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs index 9882c333a6..527bd3f7b3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs @@ -1,27 +1,20 @@ using System; using System.Diagnostics.SymbolStore; using System.IO; -using System.Linq; using System.Reflection; using System.Reflection.Emit; using System.Resources; -using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionModuleSymbolBuilder : ReflectionSymbolBuilder, IReflectionModuleSymbolBuilder + class ReflectionModuleSymbolBuilder : ReflectionModuleSymbol, IReflectionModuleSymbolBuilder { - readonly IReflectionAssemblySymbol _resolvingAssembly; - Module _module; - ModuleBuilder? _builder; - - ReflectionTypeTable _typeTable; - ReflectionMethodTable _methodTable; - ReflectionFieldTable _fieldTable; + readonly ModuleBuilder _builder; + Module? _module; /// /// Initializes a new instance. @@ -31,173 +24,47 @@ class ReflectionModuleSymbolBuilder : ReflectionSymbolBuilder, IReflectionModule /// /// public ReflectionModuleSymbolBuilder(ReflectionSymbolContext context, IReflectionAssemblySymbol resolvingAssembly, ModuleBuilder builder) : - base(context) + base(context, resolvingAssembly, builder) { - _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _module = _builder; - - _typeTable = new ReflectionTypeTable(context, this, null); - _methodTable = new ReflectionMethodTable(context, this, null); - _fieldTable = new ReflectionFieldTable(context, this, null); } - /// - public Module UnderlyingModule => _module; - /// public ModuleBuilder UnderlyingModuleBuilder => _builder ?? throw new InvalidOperationException(); /// - public IReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; - - #region IReflectionModuleSymbol + public override Module UnderlyingRuntimeModule => _module ?? throw new InvalidOperationException(); - /// - public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - if (type.IsTypeDefinition()) - return _typeTable.GetOrCreateTypeSymbol(type); - else if (type.IsGenericType) - return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); - else if (type.IsSZArray()) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateSZArrayTypeSymbol(); - else if (type.IsArray) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateArrayTypeSymbol(type.GetArrayRank()); - else if (type.IsPointer) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreatePointerTypeSymbol(); - else if (type.IsByRef) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateByRefTypeSymbol(); - else if (type.IsGenericParameter && type.DeclaringMethod is MethodInfo dm) - return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(type); - else if (type.IsGenericParameter) - return ResolveTypeSymbol(type.DeclaringType!).GetOrCreateGenericTypeParameterSymbol(type); - else - throw new InvalidOperationException(); - } - - /// - public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - return (IReflectionTypeSymbolBuilder)_typeTable.GetOrCreateTypeSymbol((Type)type); - } - - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method.DeclaringType is { } dt) - return ResolveTypeSymbol(dt).GetOrCreateMethodBaseSymbol(method); - else - return _methodTable.GetOrCreateMethodBaseSymbol(method); - } - - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return ResolveTypeSymbol(ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return ResolveTypeSymbol((TypeBuilder)ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - if (method.DeclaringType is { } dt) - return ResolveTypeSymbol(dt).GetOrCreateMethodSymbol(method); - else - return _methodTable.GetOrCreateMethodSymbol(method); - } - - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - if (method.DeclaringType is { } dt) - return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateMethodSymbol(method); - else - return _methodTable.GetOrCreateMethodSymbol(method); - } - - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - if (field.DeclaringType is { } dt) - return ResolveTypeSymbol(dt).GetOrCreateFieldSymbol(field); - else - return _fieldTable.GetOrCreateFieldSymbol(field); - } - - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - if (field.DeclaringType is { } dt) - return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateFieldSymbol(field); - else - return _fieldTable.GetOrCreateFieldSymbol(field); - } - - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return ResolveTypeSymbol(property.DeclaringType!).GetOrCreatePropertySymbol(property); - } + #region IModuleSymbol /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return ResolveTypeSymbol(property.GetTypeBuilder()).GetOrCreatePropertySymbol(property); - } + public override bool IsComplete => _module != null; - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return ResolveTypeSymbol(@event.DeclaringType!).GetOrCreateEventSymbol(@event); - } + #endregion - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return ResolveTypeSymbol(@event.GetTypeBuilder()).GetOrCreateEventSymbol(@event); - } + #region IModuleSymbolBuilder /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + public ulong ImageBase { - return ResolveMemberSymbol(parameter.Member) switch - { - IReflectionMethodBaseSymbol method => method.GetOrCreateParameterSymbol(parameter), - IReflectionPropertySymbol property => property.GetOrCreateParameterSymbol(parameter), - _ => throw new InvalidOperationException(), - }; + get => throw new NotSupportedException(); + set => throw new NotSupportedException(); } /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter) + public uint FileAlignment { - return member switch - { - IReflectionMethodBaseSymbolBuilder method => method.GetOrCreateParameterSymbol(parameter), - IReflectionPropertySymbolBuilder property => property.GetOrCreateParameterSymbol(parameter), - _ => throw new InvalidOperationException(), - }; + get => throw new NotSupportedException(); + set => throw new NotSupportedException(); } /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) + public System.Reflection.PortableExecutable.DllCharacteristics DllCharacteristics { - if (genericParameterType.DeclaringMethod is MethodBuilder dm) - return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(genericParameterType); - else - return ResolveTypeSymbol((TypeBuilder)genericParameterType.DeclaringType!).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + get => throw new NotSupportedException(); + set => throw new NotSupportedException(); } - #endregion - - #region IModuleSymbolBuilder - /// public ISymbolDocumentWriter? DefineDocument(string url, Guid language, Guid languageVendor, Guid documentType) { @@ -299,15 +166,9 @@ public ITypeSymbolBuilder DefineType(string name, System.Reflection.TypeAttribut } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingModuleBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingModuleBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingModuleBuilder.SetCustomAttribute(attribute.Unpack()); } /// @@ -331,7 +192,7 @@ public void Complete() if (type is IReflectionTypeSymbolBuilder t) t.Complete(); - _builder = null; + _module = _builder; } /// @@ -342,222 +203,6 @@ public void Save(System.Reflection.PortableExecutableKinds portableExecutableKin #endregion - #region IModuleSymbol - - /// - public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingModule.Assembly); - - /// - public string FullyQualifiedName => UnderlyingModule.FullyQualifiedName; - - /// - public int MetadataToken => UnderlyingModule.MetadataToken; - - /// - public Guid ModuleVersionId => UnderlyingModule.ModuleVersionId; - - /// - public string Name => UnderlyingModule.Name; - - /// - public string ScopeName => UnderlyingModule.ScopeName; - - /// - public ulong ImageBase - { - get => throw new NotSupportedException(); - set => throw new NotSupportedException(); - } - - /// - public uint FileAlignment - { - get => throw new NotSupportedException(); - set => throw new NotSupportedException(); - } - - /// - public System.Reflection.PortableExecutable.DllCharacteristics DllCharacteristics - { - get => throw new NotSupportedException(); - set => throw new NotSupportedException(); - } - - /// - public override bool IsComplete => _builder == null; - - /// - public IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingModule.GetField(name)); - } - - /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingModule.GetField(name, (BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingFlags) - { - return ResolveFieldSymbols(UnderlyingModule.GetFields((BindingFlags)bindingFlags))!; - } - - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingModule.GetFields())!; - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return ResolveMethodSymbol(UnderlyingModule.GetMethod(name)); - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, types.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); - } - - /// - public IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(UnderlyingModule.GetMethods())!; - } - - /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingFlags) - { - return ResolveMethodSymbols(UnderlyingModule.GetMethods((BindingFlags)bindingFlags))!; - } - - /// - public ITypeSymbol? GetType(string className) - { - return ResolveTypeSymbol(UnderlyingModule.GetType(className)); - } - - /// - public ITypeSymbol? GetType(string className, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingModule.GetType(className, ignoreCase)); - } - - /// - public ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingModule.GetType(className, throwOnError, ignoreCase)); - } - - /// - public ITypeSymbol[] GetTypes() - { - return ResolveTypeSymbols(UnderlyingModule.GetTypes())!; - } - - /// - public bool IsResource() - { - return UnderlyingModule.IsResource(); - } - - /// - public IFieldSymbol? ResolveField(int metadataToken) - { - return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken)); - } - - /// - public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public IMemberSymbol? ResolveMember(int metadataToken) - { - return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken)); - } - - /// - public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public IMethodBaseSymbol? ResolveMethod(int metadataToken) - { - return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken)); - } - - /// - public byte[] ResolveSignature(int metadataToken) - { - return UnderlyingModule.ResolveSignature(metadataToken); - } - - /// - public string ResolveString(int metadataToken) - { - return UnderlyingModule.ResolveString(metadataToken); - } - - /// - public ITypeSymbol ResolveType(int metadataToken) - { - return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken)); - } - - /// - public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData()); - } - - /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); - } - - /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttribute(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); - } - - /// - public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingModule.IsDefined(attributeType.Unpack(), false); - } - - #endregion - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs index 760ce9921a..47c5ee0362 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs @@ -16,7 +16,7 @@ class ReflectionParameterSymbolBuilder : ReflectionSymbolBuilder, IReflectionPar readonly ParameterBuilder _builder; readonly ReflectionParameterBuilderInfo _builderInfo; - ParameterInfo _parameter; + ParameterInfo? _parameter; object? _constant; @@ -37,19 +37,19 @@ public ReflectionParameterSymbolBuilder(ReflectionSymbolContext context, IReflec } /// - public IReflectionModuleSymbol ResolvingModule => _module; + public ParameterBuilder UnderlyingParameterBuilder => _builder; /// - public IReflectionMemberSymbol ResolvingMember => _member; + public ParameterInfo UnderlyingParameter => _builderInfo; /// - public ParameterInfo UnderlyingParameter => _parameter ?? _builderInfo; + public ParameterInfo UnderlyingRuntimeParameter => _parameter ?? throw new InvalidOperationException(); /// - public ParameterInfo UnderlyingEmitParameter => _parameter ?? throw new InvalidOperationException(); + public IReflectionModuleSymbol ResolvingModule => _module; /// - public ParameterBuilder UnderlyingParameterBuilder => _builder; + public IReflectionMemberSymbol ResolvingMember => _member; #region IParameterSymbolBuilder @@ -60,15 +60,9 @@ public void SetConstant(object? defaultValue) } /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingParameterBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingParameterBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingParameterBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs index d25067236e..3fa9773c67 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs @@ -7,14 +7,12 @@ namespace IKVM.CoreLib.Symbols.Reflection.Emit { - class ReflectionPropertySymbolBuilder : ReflectionMemberSymbolBuilder, IReflectionPropertySymbolBuilder + class ReflectionPropertySymbolBuilder : ReflectionPropertySymbol, IReflectionPropertySymbolBuilder { - PropertyBuilder _builder; + readonly PropertyBuilder _builder; PropertyInfo? _property; - ReflectionParameterTable _parameterTable; - /// /// Initializes a new instance. /// @@ -24,44 +22,34 @@ class ReflectionPropertySymbolBuilder : ReflectionMemberSymbolBuilder, IReflecti /// /// public ReflectionPropertySymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder resolvingType, PropertyBuilder builder) : - base(context, resolvingModule, resolvingType) + base(context, resolvingModule, resolvingType, builder) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); - _parameterTable = new ReflectionParameterTable(context, resolvingModule, this); } - /// - public PropertyInfo UnderlyingProperty => _property ?? _builder; - - /// - public PropertyInfo UnderlyingEmitProperty => UnderlyingProperty; - /// public PropertyBuilder UnderlyingPropertyBuilder => _builder ?? throw new InvalidOperationException(); /// - public override MemberInfo UnderlyingMember => UnderlyingProperty; + public override PropertyInfo UnderlyingRuntimeProperty => _property ?? throw new InvalidOperationException(); /// - public override MemberInfo UnderlyingEmitMember => UnderlyingEmitProperty; + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => (IReflectionModuleSymbolBuilder)ResolvingModule; - #region IReflectionPropertySymbolBuilder + #region ICustomAttributeProviderBuilder /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + public void SetCustomAttribute(CustomAttribute attribute) { - return _parameterTable.GetOrCreateParameterSymbol(parameter); + UnderlyingPropertyBuilder.SetCustomAttribute(attribute.Unpack()); } #endregion - #region IReflectionPropertySymbol + #region IPropertySymbol /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - return _parameterTable.GetOrCreateParameterSymbol(parameter); - } + public override bool IsComplete => _property != null; #endregion @@ -91,119 +79,12 @@ public void AddOtherMethod(IMethodSymbolBuilder mdBuilder) UnderlyingPropertyBuilder.AddOtherMethod(((IReflectionMethodSymbolBuilder)mdBuilder).UnderlyingMethodBuilder); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingPropertyBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } - - /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) - { - UnderlyingPropertyBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); - } - - #endregion - - #region IPropertySymbol - - /// - public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)UnderlyingProperty.Attributes; - - /// - public bool CanRead => UnderlyingProperty.CanRead; - - /// - public bool CanWrite => UnderlyingProperty.CanWrite; - - /// - public bool IsSpecialName => UnderlyingProperty.IsSpecialName; - - /// - public ITypeSymbol PropertyType => ResolveTypeSymbol(UnderlyingProperty.PropertyType); - - /// - public IMethodSymbol? GetMethod => ResolveMethodSymbol(UnderlyingProperty.GetMethod); - - /// - public IMethodSymbol? SetMethod => ResolveMethodSymbol(UnderlyingProperty.SetMethod); - - /// - public override bool IsComplete => _property != null; - - /// - public object? GetRawConstantValue() - { - return UnderlyingProperty.GetRawConstantValue(); - } - - /// - public IMethodSymbol[] GetAccessors() - { - return ResolveMethodSymbols(UnderlyingProperty.GetAccessors()); - } - - /// - public IMethodSymbol[] GetAccessors(bool nonPublic) - { - return ResolveMethodSymbols(UnderlyingProperty.GetAccessors(nonPublic)); - } - - /// - public IParameterSymbol[] GetIndexParameters() - { - return ResolveParameterSymbols(UnderlyingProperty.GetIndexParameters()); - } - - /// - public IMethodSymbol? GetGetMethod() - { - return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod()); - } - - /// - public IMethodSymbol? GetGetMethod(bool nonPublic) - { - return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod(nonPublic)); - } - - /// - public IMethodSymbol? GetSetMethod() - { - return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod()); - } - - /// - public IMethodSymbol? GetSetMethod(bool nonPublic) - { - return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod(nonPublic)); - } - - /// - public ITypeSymbol GetModifiedPropertyType() - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol[] GetOptionalCustomModifiers() - { - return ResolveTypeSymbols(UnderlyingProperty.GetOptionalCustomModifiers()); - } - - /// - public ITypeSymbol[] GetRequiredCustomModifiers() - { - return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); - } - #endregion /// - public override void OnComplete() + public void OnComplete() { _property = (PropertyInfo?)ResolvingModule.UnderlyingModule.ResolveMember(MetadataToken) ?? throw new InvalidOperationException(); - base.OnComplete(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs index a21ac89444..aff7f03006 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs @@ -1,7 +1,4 @@ -using System.Diagnostics.CodeAnalysis; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; +using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -22,13 +19,6 @@ protected ReflectionSymbolBuilder(ReflectionSymbolContext context) : } - /// - [return: NotNullIfNotNull(nameof(genericTypeParameter))] - public IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return Context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index df41d1cb6c..9130e6a358 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -1,11 +1,12 @@ using System; using System.Collections.Generic; -using System.Diagnostics.CodeAnalysis; +using System.Diagnostics; using System.Linq; using System.Reflection; using System.Reflection.Emit; using System.Runtime.InteropServices; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; namespace IKVM.CoreLib.Symbols.Reflection.Emit @@ -18,6 +19,7 @@ class ReflectionTypeSymbolBuilder : ReflectionTypeSymbolBase, IReflectionTypeSym Type? _type; List? _incompleteMethods; + List? _incompleteCustomAttributes; /// /// Initializes a new instance. @@ -31,65 +33,17 @@ public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionM _builder = builder ?? throw new ArgumentNullException(nameof(builder)); } - /// - public override Type UnderlyingType => UnderlyingTypeBuilder; - - /// - public override Type UnderlyingEmitType => UnderlyingTypeBuilder; - - /// - public override Type UnderlyingDynamicEmitType => _type ?? throw new InvalidOperationException(); - /// public TypeBuilder UnderlyingTypeBuilder => _builder; /// - public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => (IReflectionModuleSymbolBuilder)ResolvingModule; - - #region IReflectionSymbolBuilder - - /// - [return: NotNullIfNotNull("genericTypeParameter")] - public IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return Context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - - #endregion - - #region IReflectionTypeSymbolBuilder - - /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return _methodTable.GetOrCreateConstructorSymbol(ctor); - } + public override Type UnderlyingType => _builder; /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return _methodTable.GetOrCreateMethodSymbol(method); - } + public override Type UnderlyingRuntimeType => _type ?? throw new InvalidOperationException(); /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) - { - return _fieldTable.GetOrCreateFieldSymbol(field); - } - - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return _propertyTable.GetOrCreatePropertySymbol(property); - } - - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return _eventTable.GetOrCreateEventSymbol(@event); - } - - #endregion + public IReflectionModuleSymbolBuilder ResolvingModuleBuilder => (IReflectionModuleSymbolBuilder)ResolvingModule; #region ITypeSymbolBuilder @@ -298,20 +252,22 @@ public IConstructorSymbolBuilder DefineTypeInitializer() { return (IConstructorSymbolBuilder)ResolveConstructorSymbol(UnderlyingTypeBuilder.DefineTypeInitializer()); } - /// - public void SetCustomAttribute(IConstructorSymbol con, byte[] binaryAttribute) - { - UnderlyingTypeBuilder.SetCustomAttribute(con.Unpack(), binaryAttribute); - } /// - public void SetCustomAttribute(ICustomAttributeBuilder customBuilder) + public void SetCustomAttribute(CustomAttribute attribute) { - UnderlyingTypeBuilder.SetCustomAttribute(((ReflectionCustomAttributeBuilder)customBuilder).UnderlyingBuilder); + UnderlyingTypeBuilder.SetCustomAttribute(attribute.Unpack()); + _incompleteCustomAttributes ??= []; + _incompleteCustomAttributes.Add(attribute); } #endregion + #region ITypeSymbol + + /// + public override bool IsComplete => _type != null; + /// public override IMethodSymbol? GetMethod(string name) { @@ -369,8 +325,34 @@ IMethodSymbol[] GetIncompleteMethods(BindingFlags bindingAttr = BindingFlags.Pub return SymbolUtil.FilterMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); } + #endregion + + #region ICustomAttributeProvider + /// - public override bool IsComplete => _type != null; + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + if (IsComplete) + return ResolveCustomAttributes(UnderlyingRuntimeMember.GetCustomAttributesData(inherit).ToArray()); + else if (inherit == false || BaseType == null) + return _incompleteCustomAttributes?.ToArray() ?? []; + else + return Enumerable.Concat(_incompleteCustomAttributes?.ToArray() ?? [], ResolveCustomAttributes(BaseType.Unpack().GetInheritedCustomAttributesData())).ToArray(); + } + + /// + public override CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(inherit).FirstOrDefault(i => i.AttributeType == attributeType); + } + + /// + public override CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + } + + #endregion /// public void Complete() @@ -379,7 +361,11 @@ public void Complete() { // complete type if (_builder.IsCreated() == false) - _type = _builder.CreateType()!; + { + _type = _builder.CreateType() ?? throw new InvalidOperationException(); + _incompleteMethods = null; + _incompleteCustomAttributes = null; + } // force module to reresolve Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); @@ -392,9 +378,13 @@ public void OnComplete() { const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static; - foreach (var i in GetGenericArguments() ?? []) - if (i is IReflectionGenericTypeParameterSymbolBuilder b) - b.OnComplete(); + // apply the runtime generic type parameters and pass them to the symbols for completion + var srcGenericArgs = UnderlyingRuntimeType.GetGenericArguments() ?? []; + var dstGenericArgs = GetGenericArguments() ?? []; + Debug.Assert(srcGenericArgs.Length == dstGenericArgs.Length); + for (int i = 0; i < srcGenericArgs.Length; i++) + if (dstGenericArgs[i] is IReflectionGenericTypeParameterSymbolBuilder b) + b.OnComplete(srcGenericArgs[i]); foreach (var i in GetConstructors(DefaultBindingFlags) ?? []) if (i is IReflectionConstructorSymbolBuilder b) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs index b858654043..73a6c9c3cd 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs @@ -11,6 +11,11 @@ interface IReflectionAssemblySymbol : IReflectionSymbol, IAssemblySymbol /// Assembly UnderlyingAssembly { get; } + /// + /// Gets a reference to the underlying . + /// + Assembly UnderlyingRuntimeAssembly { get; } + /// /// Gets or creates a for the specified . /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs index 43d1160302..f477b99df7 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs @@ -14,12 +14,7 @@ interface IReflectionConstructorSymbol : IReflectionMethodBaseSymbol, IConstruct /// /// Gets the underlying used for IL emit operations. /// - ConstructorInfo UnderlyingEmitConstructor { get; } - - /// - /// Gets the underlying used for IL emit operations against dynamic methods. - /// - ConstructorInfo UnderlyingDynamicEmitConstructor { get; } + ConstructorInfo UnderlyingRuntimeConstructor { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs index f2c411fc95..2f0374c380 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs @@ -12,9 +12,9 @@ interface IReflectionEventSymbol : IReflectionMemberSymbol, IEventSymbol EventInfo UnderlyingEvent { get; } /// - /// Gets the underlying used for IL emit operations. + /// Gets the underlying . /// - EventInfo UnderlyingEmitEvent { get; } + EventInfo UnderlyingRuntimeEvent { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs index 86094cd8da..e21b606ba1 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs @@ -12,14 +12,9 @@ interface IReflectionFieldSymbol : IReflectionMemberSymbol, IFieldSymbol FieldInfo UnderlyingField { get; } /// - /// Gets the underlying used for IL emit operations. - /// - FieldInfo UnderlyingEmitField { get; } - - /// - /// Gets the underlying used for IL emit operations against dynamic methods. + /// Gets the underlying . /// - FieldInfo UnderlyingDynamicEmitField { get; } + FieldInfo UnderlyingRuntimeField { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs index b62765637e..b309b0ee07 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs @@ -22,9 +22,9 @@ interface IReflectionMemberSymbol : IReflectionSymbol, IMemberSymbol MemberInfo UnderlyingMember { get; } /// - /// Gets the underlying used for IL emit operations. + /// Gets the underlying used when the runtime information is required. /// - MemberInfo UnderlyingEmitMember { get; } + MemberInfo UnderlyingRuntimeMember { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs index b46e914f7c..f3e89783f7 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs @@ -1,4 +1,7 @@ using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -14,7 +17,7 @@ interface IReflectionMethodBaseSymbol : IReflectionMemberSymbol, IMethodBaseSymb /// /// Gets the underlying . /// - MethodBase UnderlyingEmitMethodBase { get; } + MethodBase UnderlyingRuntimeMethodBase { get; } /// /// Gets or creates a for the given . @@ -23,6 +26,13 @@ interface IReflectionMethodBaseSymbol : IReflectionMemberSymbol, IMethodBaseSymb /// public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + /// + /// Gets or creates a for the given . + /// + /// + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs index 07cc3b2531..21dfd7dcfe 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs @@ -1,5 +1,8 @@ using System; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -13,21 +16,23 @@ interface IReflectionMethodSymbol : IReflectionMethodBaseSymbol, IMethodSymbol MethodInfo UnderlyingMethod { get; } /// - /// Gets the underlying used for IL emit operations. + /// Gets the underlying . /// - MethodInfo UnderlyingEmitMethod { get; } + MethodInfo UnderlyingRuntimeMethod { get; } /// - /// Gets the underlying used for IL emit operations against dynamic methods. + /// Gets or creates a for the given generic type parameter. /// - MethodInfo UnderlyingDynamicEmitMethod { get; } + /// + /// + IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); /// - /// Gets or creates a for the given generic type parameter. + /// Gets or creates a for the given . /// /// /// - IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); + IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); /// /// Gets or creates a for the given generic version of this method definition. diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs index d91499c770..9b559b5773 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs @@ -1,5 +1,8 @@ using System; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -17,6 +20,11 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// Module UnderlyingModule { get; } + /// + /// Gets the underlying . + /// + Module UnderlyingRuntimeModule { get; } + /// /// Gets or creates a for the specified . /// @@ -24,6 +32,13 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type); + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); + /// /// Gets or creates a for the specified . /// @@ -38,6 +53,13 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + /// /// Gets or creates a for the specified . /// @@ -45,6 +67,13 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + /// /// Gets or creates a for the specified . /// @@ -52,6 +81,13 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + /// /// Gets or creates a for the specified . /// @@ -59,6 +95,13 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + /// /// Gets or creates a for the specified . /// @@ -66,6 +109,13 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + /// /// Gets or creates a for the specified . /// @@ -73,6 +123,21 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + /// + /// Gets or creates a for the specified . + /// + /// + /// + /// + IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter); + + /// + /// Gets or creates a for the specified . + /// + /// + /// + IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs index 55d9de63c2..3c02883549 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs @@ -22,9 +22,9 @@ interface IReflectionParameterSymbol : IReflectionSymbol, IParameterSymbol ParameterInfo UnderlyingParameter { get; } /// - /// Gets the underlying used for IL emit operations. + /// Gets the underlying . /// - ParameterInfo UnderlyingEmitParameter { get; } + ParameterInfo UnderlyingRuntimeParameter { get; } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs index c1f545f79c..12da5d1a98 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs @@ -1,4 +1,7 @@ using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -12,9 +15,9 @@ interface IReflectionPropertySymbol : IReflectionMemberSymbol, IPropertySymbol PropertyInfo UnderlyingProperty { get; } /// - /// Gets the underlying used for IL emit operations. + /// Gets the underlying . /// - PropertyInfo UnderlyingEmitProperty { get; } + PropertyInfo UnderlyingRuntimeProperty { get; } /// /// Gets or creates a for the given . @@ -23,6 +26,13 @@ interface IReflectionPropertySymbol : IReflectionMemberSymbol, IPropertySymbol /// public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); + /// + /// Gets or creates a for the given . + /// + /// + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs index c2a970c280..3928a4815d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs @@ -3,6 +3,9 @@ using System.Collections.Immutable; using System.Diagnostics.CodeAnalysis; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -31,6 +34,14 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(assemblies))] IReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies); + /// + /// Resolves the symbol for the specified assembly builder. + /// + /// + /// + [return: NotNullIfNotNull(nameof(assembly))] + IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); + /// /// Resolves the symbol for the specified module. /// @@ -54,6 +65,14 @@ interface IReflectionSymbol : ISymbol /// IEnumerable ResolveModuleSymbols(IEnumerable modules); + /// + /// Resolves the symbol for the specified module. + /// + /// + /// + [return: NotNullIfNotNull(nameof(module))] + IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); + /// /// Resolves the symbol for the specified member. /// @@ -93,6 +112,14 @@ interface IReflectionSymbol : ISymbol /// IEnumerable ResolveTypeSymbols(IEnumerable types); + /// + /// Resolves the symbol for the specified type. + /// + /// + /// + [return: NotNullIfNotNull(nameof(type))] + IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); + /// /// Resolves the symbol for the specified method. /// @@ -117,6 +144,14 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(ctors))] IReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors); + /// + /// Resolves the symbol for the specified constructor. + /// + /// + /// + [return: NotNullIfNotNull(nameof(ctor))] + IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); + /// /// Resolves the symbol for the specified method. /// @@ -133,6 +168,14 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(methods))] IReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods); + /// + /// Resolves the symbol for the specified method. + /// + /// + /// + [return: NotNullIfNotNull(nameof(method))] + IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); + /// /// Resolves the symbol for the specified field. /// @@ -149,6 +192,14 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(fields))] IReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields); + /// + /// Resolves the symbol for the specified field. + /// + /// + /// + [return: NotNullIfNotNull(nameof(field))] + IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); + /// /// Resolves the symbol for the specified property. /// @@ -165,6 +216,14 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(properties))] IReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties); + /// + /// Resolves the symbol for the specified property. + /// + /// + /// + [return: NotNullIfNotNull(nameof(property))] + IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); + /// /// Resolves the symbol for the specified event. /// @@ -181,6 +240,14 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(events))] IReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events); + /// + /// Resolves the symbol for the specified event. + /// + /// + /// + [return: NotNullIfNotNull(nameof(@event))] + IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); + /// /// Resolves the symbol for the specified parameter. /// @@ -197,6 +264,22 @@ interface IReflectionSymbol : ISymbol [return: NotNullIfNotNull(nameof(parameters))] IReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters); + /// + /// Resolves the symbol for the specified generic type parameter. + /// + /// + /// + [return: NotNullIfNotNull(nameof(genericTypeParameter))] + IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder? genericTypeParameter); + + /// + /// Resolves the symbol for the specified generic type parameters. + /// + /// + /// + [return: NotNullIfNotNull(nameof(genericTypeParameters))] + IReflectionGenericTypeParameterSymbolBuilder[]? ResolveGenericTypeParameterSymbols(GenericTypeParameterBuilder[]? genericTypeParameters); + /// /// Transforms a custom set of custom attribute data records to a symbol record. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs index a36c6f0a47..47da7f1b40 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs @@ -1,5 +1,8 @@ using System; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -13,14 +16,16 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol Type UnderlyingType { get; } /// - /// Gets the underlying used for IL emit operations. + /// Gets the underlying used for IL emit operations for dynamic methods. /// - Type UnderlyingEmitType { get; } + Type UnderlyingRuntimeType { get; } /// - /// Gets the underlying used for IL emit operations for dynamic methods. + /// Gets or creates a for the given element type. /// - Type UnderlyingDynamicEmitType { get; } + /// + /// + IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition); /// /// Gets or creates a for the given . @@ -36,6 +41,13 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); + /// /// Gets or creates a for the given . /// @@ -43,6 +55,13 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); + /// /// Gets or creates a for the given . /// @@ -50,6 +69,13 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + /// /// Gets or creates a for the given . /// @@ -57,6 +83,13 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); + /// /// Gets or creates a for the given . /// @@ -64,6 +97,13 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); + /// /// Gets or creates a for the given generic type parameter type. /// @@ -71,6 +111,13 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); + /// + /// Gets or creates a for the given . + /// + /// + /// + IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); + /// /// Gets or creates a for the given element type. /// @@ -96,13 +143,6 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// IReflectionTypeSymbol GetOrCreateByRefTypeSymbol(); - /// - /// Gets or creates a for the given element type. - /// - /// - /// - IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs index 99a1f0236e..d11a94fcf5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs @@ -24,10 +24,7 @@ public ReflectionArrayTypeSymbol(ReflectionSymbolContext context, IReflectionMod public override Type UnderlyingType => ElementType.UnderlyingType.MakeArrayType(rank); /// - public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeArrayType(rank); - - /// - public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeArrayType(rank); + public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeArrayType(rank); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index 7496acfff8..c5dffa008d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -29,9 +29,14 @@ public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly assemb /// /// Gets the underlying instance. /// - public Assembly UnderlyingAssembly => _assembly; + public virtual Assembly UnderlyingAssembly => _assembly; - #region IAssemblySymbol + /// + /// Gets the underlying instance. + /// + public virtual Assembly UnderlyingRuntimeAssembly => _assembly; + + #region IReflectionAssemblySymbol /// public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs index 70320ff0b9..9e0c79d87e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs @@ -22,10 +22,7 @@ public ReflectionByRefTypeSymbol(ReflectionSymbolContext context, IReflectionMod public override Type UnderlyingType => ElementType.UnderlyingType.MakeByRefType(); /// - public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeByRefType(); - - /// - public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeByRefType(); + public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeByRefType(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs index ce5d37ac29..6049e8f842 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs @@ -23,16 +23,16 @@ public ReflectionConstructorSymbol(ReflectionSymbolContext context, IReflectionM } /// - public ConstructorInfo UnderlyingConstructor => _ctor; + public virtual ConstructorInfo UnderlyingConstructor => _ctor; /// - public ConstructorInfo UnderlyingEmitConstructor => UnderlyingConstructor; + public virtual ConstructorInfo UnderlyingRuntimeConstructor => UnderlyingConstructor; /// - public ConstructorInfo UnderlyingDynamicEmitConstructor => UnderlyingEmitConstructor; + public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; /// - public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; + public override MethodBase UnderlyingRuntimeMethodBase => UnderlyingRuntimeConstructor; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs index 33a0c5721f..b62385d455 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs @@ -23,14 +23,17 @@ public ReflectionEventSymbol(ReflectionSymbolContext context, IReflectionModuleS } /// - public EventInfo UnderlyingEvent => _event; + public virtual EventInfo UnderlyingEvent => _event; /// - public EventInfo UnderlyingEmitEvent => _event; + public virtual EventInfo UnderlyingRuntimeEvent => _event; /// public override MemberInfo UnderlyingMember => UnderlyingEvent; + /// + public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeEvent; + #region IEventSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index 39b5c32736..f6095d471e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -23,21 +23,21 @@ public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleS } /// - public FieldInfo UnderlyingField => _field; + public virtual FieldInfo UnderlyingField => _field; /// - public FieldInfo UnderlyingEmitField => UnderlyingField; + public virtual FieldInfo UnderlyingRuntimeField => _field; /// - public FieldInfo UnderlyingDynamicEmitField => UnderlyingEmitField; + public override MemberInfo UnderlyingMember => UnderlyingField; /// - public override MemberInfo UnderlyingMember => UnderlyingField; + public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeField; #region IFieldSymbol /// - public System.Reflection.FieldAttributes Attributes => (System.Reflection.FieldAttributes)UnderlyingField.Attributes; + public FieldAttributes Attributes => UnderlyingField.Attributes; /// public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs index f7c5cadfcf..3470c6b2fa 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs @@ -26,10 +26,7 @@ public ReflectionGenericSpecTypeSymbol(ReflectionSymbolContext context, IReflect public override Type UnderlyingType => ElementType.UnderlyingType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingType).ToArray()); /// - public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingEmitType).ToArray()); - - /// - public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingDynamicEmitType).ToArray()); + public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingRuntimeType).ToArray()); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs index 5000896e34..5aa9ccfada 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs @@ -1,8 +1,10 @@ using System; using System.Diagnostics.CodeAnalysis; using System.Reflection; +using System.Reflection.Emit; using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -32,16 +34,16 @@ public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IRe } /// - public Type UnderlyingType => _type; + public virtual Type UnderlyingType => _type; /// - public Type UnderlyingEmitType => UnderlyingType; + public virtual Type UnderlyingRuntimeType => _type; /// - public Type UnderlyingDynamicEmitType => _type; + public override MemberInfo UnderlyingMember => UnderlyingType; /// - public override MemberInfo UnderlyingMember => UnderlyingType; + public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeType; /// /// Gets the method base that declares this type parameter. @@ -64,6 +66,12 @@ public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IRe #region IReflectionTypeSymbol + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + /// public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) { @@ -76,36 +84,66 @@ public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo throw new NotSupportedException(); } + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + throw new NotImplementedException(); + } + /// public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { throw new NotSupportedException(); } + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + throw new NotImplementedException(); + } + /// public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { throw new NotSupportedException(); } + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + throw new NotImplementedException(); + } + /// public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { throw new NotSupportedException(); } + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + throw new NotImplementedException(); + } + /// public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { throw new NotSupportedException(); } + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + throw new NotImplementedException(); + } + /// public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type type) { throw new NotSupportedException(); } + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + throw new NotImplementedException(); + } + /// public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() { @@ -130,12 +168,6 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() return _specTable.GetOrCreateByRefTypeSymbol(); } - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) - { - return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); - } - #endregion #region ITypeSymbol @@ -662,7 +694,7 @@ public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); } -#endregion + #endregion } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 2292781123..783d68a8d4 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -3,6 +3,8 @@ using System.Linq; using System.Reflection; +using IKVM.CoreLib.Reflection; + namespace IKVM.CoreLib.Symbols.Reflection { @@ -21,7 +23,6 @@ abstract class ReflectionMemberSymbol : ReflectionSymbol, IReflectionMemberSymbo /// /// /// - /// public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : base(context) { @@ -33,7 +34,7 @@ public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModule public abstract MemberInfo UnderlyingMember { get; } /// - public virtual MemberInfo UnderlyingEmitMember => UnderlyingMember; + public abstract MemberInfo UnderlyingRuntimeMember { get; } /// /// Gets the which contains the metadata of this member. @@ -166,10 +167,10 @@ public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModule public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; /// - public virtual System.Reflection.MemberTypes MemberType => (System.Reflection.MemberTypes)UnderlyingMember.MemberType; + public virtual MemberTypes MemberType => UnderlyingMember.MemberType; /// - public virtual int MetadataToken => UnderlyingMember.MetadataToken; + public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); /// public virtual string Name => UnderlyingMember.Name; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs index c16020d4c8..8e7fdc1263 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs @@ -1,4 +1,7 @@ using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -28,6 +31,12 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param return _parameterTable.GetOrCreateParameterSymbol(parameter); } + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + #endregion #region IMethodBaseSymbol @@ -36,10 +45,13 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param public abstract MethodBase UnderlyingMethodBase { get; } /// - public virtual MethodBase UnderlyingEmitMethodBase => UnderlyingMethodBase; + public abstract MethodBase UnderlyingRuntimeMethodBase { get; } + + /// + public override sealed MemberInfo UnderlyingMember => UnderlyingMethodBase; /// - public override MemberInfo UnderlyingMember => UnderlyingMethodBase; + public override sealed MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeMethodBase; /// public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index 35b421e48b..358d8b8864 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -1,5 +1,8 @@ using System; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -28,16 +31,16 @@ public ReflectionMethodSymbol(ReflectionSymbolContext context, IReflectionModule } /// - public MethodInfo UnderlyingMethod => _method; + public virtual MethodInfo UnderlyingMethod => _method; /// - public MethodInfo UnderlyingEmitMethod => UnderlyingMethod; + public virtual MethodInfo UnderlyingRuntimeMethod => _method; /// - public MethodInfo UnderlyingDynamicEmitMethod => UnderlyingEmitMethod; + public override MethodBase UnderlyingMethodBase => UnderlyingMethod; /// - public override MethodBase UnderlyingMethodBase => UnderlyingMethod; + public override MethodBase UnderlyingRuntimeMethodBase => UnderlyingRuntimeMethod; #region IReflectionMethodSymbol @@ -47,6 +50,12 @@ public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericT return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); } + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + /// public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 7f1bd1ed16..5e6ba8deb5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -1,8 +1,10 @@ using System; using System.Linq; using System.Reflection; +using System.Reflection.Emit; using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -39,7 +41,10 @@ public ReflectionModuleSymbol(ReflectionSymbolContext context, IReflectionAssemb } /// - public Module UnderlyingModule => _module; + public virtual Module UnderlyingModule => _module; + + /// + public virtual Module UnderlyingRuntimeModule => _module; /// public IReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; @@ -261,6 +266,15 @@ public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) throw new InvalidOperationException(); } + /// + public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + { + if (type.IsTypeDefinition()) + return (IReflectionTypeSymbolBuilder)_typeTable.GetOrCreateTypeSymbol(type); + + throw new InvalidOperationException(); + } + /// public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) { @@ -276,6 +290,12 @@ public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo return ResolveTypeSymbol(ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); } + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return ResolveTypeSymbol((TypeBuilder)ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); + } + /// public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) { @@ -285,6 +305,15 @@ public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) return _methodTable.GetOrCreateMethodSymbol(method); } + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + if (method.DeclaringType is { } dt) + return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateMethodSymbol(method); + else + return _methodTable.GetOrCreateMethodSymbol(method); + } + /// public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { @@ -294,18 +323,39 @@ public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) return _fieldTable.GetOrCreateFieldSymbol(field); } + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + if (field.DeclaringType is { } dt) + return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateFieldSymbol(field); + else + return _fieldTable.GetOrCreateFieldSymbol(field); + } + /// public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { return ResolveTypeSymbol(property.DeclaringType!).GetOrCreatePropertySymbol(property); } + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return ResolveTypeSymbol(property.GetTypeBuilder()).GetOrCreatePropertySymbol(property); + } + /// public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { return ResolveTypeSymbol(@event.DeclaringType!).GetOrCreateEventSymbol(@event); } + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return ResolveTypeSymbol(@event.GetTypeBuilder()).GetOrCreateEventSymbol(@event); + } + /// public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) { @@ -317,6 +367,26 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param }; } + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter) + { + return member switch + { + IReflectionMethodBaseSymbolBuilder method => method.GetOrCreateParameterSymbol(parameter), + IReflectionPropertySymbolBuilder property => property.GetOrCreateParameterSymbol(parameter), + _ => throw new InvalidOperationException(), + }; + } + + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) + { + if (genericParameterType.DeclaringMethod is MethodBuilder dm) + return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + else + return ResolveTypeSymbol((TypeBuilder)genericParameterType.DeclaringType!).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + } + #endregion /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs index 38f8172721..951bb374bd 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs @@ -1,7 +1,6 @@ using System; using System.Reflection; using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; using System.Threading; using IKVM.CoreLib.Collections; @@ -60,16 +59,6 @@ public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) } } - /// - /// Gets or creates the cached for the module. - /// - /// - /// - public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) - { - return (IReflectionModuleSymbolBuilder)GetOrCreateModuleSymbol((Module)module); - } - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index 5d9c954461..ff2e53811a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -37,7 +37,7 @@ public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionMod public ParameterInfo UnderlyingParameter => _parameter; /// - public ParameterInfo UnderlyingEmitParameter => UnderlyingParameter; + public ParameterInfo UnderlyingRuntimeParameter => UnderlyingParameter; #region IParameterSymbol diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs index 0ac8787703..195f155448 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs @@ -22,10 +22,7 @@ public ReflectionPointerTypeSymbol(ReflectionSymbolContext context, IReflectionM public override Type UnderlyingType => ElementType.UnderlyingType.MakePointerType(); /// - public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakePointerType(); - - /// - public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakePointerType(); + public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakePointerType(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs index ca77f5d845..fab3b8cde1 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs @@ -1,5 +1,8 @@ using System; using System.Reflection; +using System.Reflection.Emit; + +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -26,14 +29,17 @@ public ReflectionPropertySymbol(ReflectionSymbolContext context, IReflectionModu } /// - public PropertyInfo UnderlyingProperty => _property; + public virtual PropertyInfo UnderlyingProperty => _property; /// - public PropertyInfo UnderlyingEmitProperty => UnderlyingProperty; + public virtual PropertyInfo UnderlyingRuntimeProperty => UnderlyingProperty; /// public override MemberInfo UnderlyingMember => UnderlyingProperty; + /// + public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeProperty; + #region IReflectionPropertySymbol /// @@ -42,6 +48,12 @@ public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo param return _parameterTable.GetOrCreateParameterSymbol(parameter); } + /// + public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) + { + return _parameterTable.GetOrCreateParameterSymbol(parameter); + } + #endregion #region IPropertySymbol diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs index 63845863fe..c50573f6c8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs @@ -22,10 +22,7 @@ public ReflectionSZArrayTypeSymbol(ReflectionSymbolContext context, IReflectionM public override Type UnderlyingType => ElementType.UnderlyingType.MakeArrayType(); /// - public override Type UnderlyingEmitType => ElementType.UnderlyingEmitType.MakeArrayType(); - - /// - public override Type UnderlyingDynamicEmitType => ElementType.UnderlyingDynamicEmitType.MakeArrayType(); + public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeArrayType(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index ae1c1f3171..b6c191b516 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -27,6 +27,8 @@ public ReflectionSymbol(ReflectionSymbolContext context) _context = context ?? throw new ArgumentNullException(nameof(context)); } + #region IReflectionSymbol + /// /// Gets the associated . /// @@ -433,6 +435,33 @@ public virtual IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBu return a; } + /// + [return: NotNullIfNotNull(nameof(genericTypeParameter))] + public IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder? genericTypeParameter) + { + if (genericTypeParameter == null) + return null; + + return _context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + + /// + [return: NotNullIfNotNull(nameof(genericTypeParameters))] + public IReflectionGenericTypeParameterSymbolBuilder[]? ResolveGenericTypeParameterSymbols(GenericTypeParameterBuilder[]? genericTypeParameters) + { + if (genericTypeParameters == null) + return null; + if (genericTypeParameters.Length == 0) + return []; + + var a = new IReflectionGenericTypeParameterSymbolBuilder[genericTypeParameters.Length]; + for (int i = 0; i < genericTypeParameters.Length; i++) + if (ResolveGenericTypeParameterSymbol(genericTypeParameters[i]) is { } symbol) + a[i] = symbol; + + return a; + } + /// [return: NotNullIfNotNull(nameof(attributes))] public CustomAttribute[]? ResolveCustomAttributes(IList? attributes) @@ -553,6 +582,8 @@ public InterfaceMapping ResolveInterfaceMapping(System.Reflection.InterfaceMappi return info != null ? new ManifestResourceInfo((System.Reflection.ResourceLocation)info.ResourceLocation, info.FileName, ResolveAssemblySymbol(info.ReferencedAssembly)) : null; } + #endregion + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index d4f421bb90..b10d2f16ae 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Concurrent; +using System.Collections.Immutable; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; @@ -54,11 +55,10 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, bool collect } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttributeBuilder[]? assemblyAttributes, bool collectable, bool saveable) + public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes, bool collectable, bool saveable) { if (name is null) throw new ArgumentNullException(nameof(name)); - if (collectable && saveable) throw new NotSupportedException("Assembly cannot be both colletable and saveable."); @@ -66,16 +66,16 @@ public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ICustomAttri if (saveable) throw new NotSupportedException("Assembly cannot be saveable."); else if (collectable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, attributes.Unpack())); else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, attributes.Unpack())); #else if (saveable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave, attributes.Unpack())); else if (collectable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, attributes.Unpack())); else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, assemblyAttributes?.Unpack())); + return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, attributes.Unpack())); #endif } @@ -349,30 +349,6 @@ public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParame return GetOrCreateModuleSymbol((ModuleBuilder)genericTypeParameter.Module).GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); } - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs) - { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs))); - } - - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) - { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedFields.Unpack(), UnpackArguments(fieldValues))); - } - - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) - { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues))); - } - - /// - public ICustomAttributeBuilder CreateCustomAttribute(IConstructorSymbol con, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) - { - return new ReflectionCustomAttributeBuilder(new CustomAttributeBuilder(con.Unpack(), UnpackArguments(constructorArgs), namedProperties.Unpack(), UnpackArguments(propertyValues), namedFields.Unpack(), UnpackArguments(fieldValues))); - } - /// /// Unpacks a single constructor argument. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs index f8476934b8..1f10ce4395 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -24,6 +24,9 @@ public ReflectionTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSy /// public override Type UnderlyingType => _type; + /// + public override Type UnderlyingRuntimeType => _type; + #region IReflectionSymbol /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs index 8335710697..4edd57cb35 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs @@ -38,22 +38,34 @@ public ReflectionTypeSymbolBase(ReflectionSymbolContext context, IReflectionModu public abstract Type UnderlyingType { get; } /// - public virtual Type UnderlyingEmitType => UnderlyingType; + public abstract Type UnderlyingRuntimeType { get; } /// - public virtual Type UnderlyingDynamicEmitType => UnderlyingEmitType; + public override sealed MemberInfo UnderlyingMember => UnderlyingType; /// - public override MemberInfo UnderlyingMember => UnderlyingType; + public override sealed MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeType; #region IReflectionTypeSymbol + /// + public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) + { + return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); + } + /// public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) { return _methodTable.GetOrCreateConstructorSymbol(ctor); } + /// + public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + { + return _methodTable.GetOrCreateConstructorSymbol(ctor); + } + /// public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) { @@ -72,30 +84,60 @@ public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) return ResolveMethodSymbol(method.GetGenericMethodDefinition()).GetOrCreateGenericMethodSymbol(method); } + /// + public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + { + return _methodTable.GetOrCreateMethodSymbol(method); + } + /// public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { return _fieldTable.GetOrCreateFieldSymbol(field); } + /// + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + { + return _fieldTable.GetOrCreateFieldSymbol(field); + } + /// public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) { return _propertyTable.GetOrCreatePropertySymbol(property); } + /// + public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + { + return _propertyTable.GetOrCreatePropertySymbol(property); + } + /// public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) { return _eventTable.GetOrCreateEventSymbol(@event); } + /// + public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + { + return _eventTable.GetOrCreateEventSymbol(@event); + } + /// public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericType) { return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericType); } + /// + public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + { + return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + } + /// public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() { @@ -120,22 +162,6 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() return _specTable.GetOrCreateByRefTypeSymbol(); } - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) - { - return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); - } - - #endregion - - #region IReflectionTypeSymbolBuilder - - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - #endregion #region ITypeSymbol @@ -513,19 +539,19 @@ public virtual IMemberSymbol[] GetMembers() } /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - throw new NotImplementedException(); + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); } /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); + throw new NotImplementedException(); } /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) { throw new NotImplementedException(); } @@ -537,9 +563,9 @@ public virtual IMemberSymbol[] GetMembers() } /// - public virtual IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) + public virtual IMethodSymbol[] GetMethods(BindingFlags bindingAttr) { - return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); + return ResolveMethodSymbols(UnderlyingType.GetMethods(bindingAttr)); } /// @@ -557,7 +583,7 @@ public virtual IMethodSymbol[] GetMethods() /// public virtual ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, bindingAttr)); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index 5a19f7b9ae..d8991850db 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Collections.Immutable; using System.Reflection; using System.Reflection.Emit; @@ -383,21 +384,58 @@ public static Label[] Unpack(this ILabel[] labels) } /// - /// Unpacks the . + /// Unpacks the . /// /// /// - public static CustomAttributeBuilder Unpack(this ICustomAttributeBuilder customAttributes) + public static CustomAttributeBuilder Unpack(this CustomAttribute attributes) { - return ((ReflectionCustomAttributeBuilder)customAttributes).UnderlyingBuilder; + // unpack constructor arg values + var constructorValues = new object?[attributes.ConstructorArguments.Length]; + for (int i = 0; i < attributes.ConstructorArguments.Length; i++) + constructorValues[i] = UnpackCustomAttributeValue(attributes.ConstructorArguments[i]); + + // unpack named arguments into sets of properties and fields + List? namedProperties = null; + List? propertyValues = null; + List? namedFields = null; + List? fieldValues = null; + + // split named arguments into two sets + foreach (var i in attributes.NamedArguments) + { + var v = UnpackCustomAttributeValue(i.TypedValue.Value); + if (i.IsField == false) + { + namedProperties ??= new(); + namedProperties.Add(((IPropertySymbol)i.MemberInfo).Unpack()); + propertyValues ??= new(); + propertyValues.Add(v); + } + else + { + namedFields ??= new(); + namedFields.Add(((IFieldSymbol)i.MemberInfo).Unpack()); + fieldValues ??= new(); + fieldValues.Add(v); + } + } + + return new CustomAttributeBuilder( + attributes.Constructor.Unpack(), + constructorValues, + namedProperties?.ToArray() ?? [], + propertyValues?.ToArray() ?? [], + namedFields?.ToArray() ?? [], + fieldValues?.ToArray() ?? []); } /// - /// Unpacks the s. + /// Unpacks the s. /// /// /// - public static CustomAttributeBuilder[] Unpack(this ICustomAttributeBuilder[] customAttributes) + public static CustomAttributeBuilder[] Unpack(this CustomAttribute[] customAttributes) { if (customAttributes.Length == 0) return []; @@ -409,6 +447,53 @@ public static CustomAttributeBuilder[] Unpack(this ICustomAttributeBuilder[] cus return a; } + /// + /// Unpacks the s. + /// + /// + /// + public static CustomAttributeBuilder[] Unpack(this ImmutableArray attributes) + { + if (attributes.Length == 0) + return []; + + var a = new CustomAttributeBuilder[attributes.Length]; + for (int i = 0; i < attributes.Length; i++) + a[i] = attributes[i].Unpack(); + + return a; + } + + /// + /// Unpacks the attribute value object. + /// + /// + /// + static object? UnpackCustomAttributeValue(object? value) + { + return value switch + { + IReadOnlyList l => UnpackCustomAttributeArrayValue(l), + ITypeSymbol t => t.Unpack(), + CustomAttributeTypedArgument a => UnpackCustomAttributeValue(a.Value), + _ => value, + }; + } + + /// + /// Unpacks the attribute value array. + /// + /// + /// + static object?[] UnpackCustomAttributeArrayValue(IReadOnlyList items) + { + var a = new object?[items.Count]; + for (int i = 0; i < items.Count; i++) + a[i] = UnpackCustomAttributeValue(items[i]); + + return a; + } + /// /// Returns true if the given type represents a type definition. /// diff --git a/src/IKVM.CoreLib/Symbols/SymbolUtil.cs b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs index 7727345ac2..2d7c431420 100644 --- a/src/IKVM.CoreLib/Symbols/SymbolUtil.cs +++ b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs @@ -1,4 +1,6 @@ using System.Collections.Generic; +using System.ComponentModel; +using System.Reflection; namespace IKVM.CoreLib.Symbols { @@ -14,40 +16,40 @@ static class SymbolUtil /// /// /// - static bool BindingFlagsMatch(bool state, System.Reflection.BindingFlags flags, System.Reflection.BindingFlags trueFlag, System.Reflection.BindingFlags falseFlag) + static bool BindingFlagsMatch(bool state, BindingFlags flags, BindingFlags trueFlag, BindingFlags falseFlag) { return (state && (flags & trueFlag) == trueFlag) || (!state && (flags & falseFlag) == falseFlag); } /// - /// Evaluates whether the specified would match the . + /// Evaluates whether the specified would match the . /// /// /// /// - public static bool BindingFlagsMatch(IMethodSymbol member, System.Reflection.BindingFlags flags) + public static bool BindingFlagsMatch(IMethodSymbol member, BindingFlags flags) { - return BindingFlagsMatch(member.IsPublic, flags, System.Reflection.BindingFlags.Public, System.Reflection.BindingFlags.NonPublic) - && BindingFlagsMatch(member.IsStatic, flags, System.Reflection.BindingFlags.Static, System.Reflection.BindingFlags.Instance); + return BindingFlagsMatch(member.IsPublic, flags, BindingFlags.Public, BindingFlags.NonPublic) + && BindingFlagsMatch(member.IsStatic, flags, BindingFlags.Static, BindingFlags.Instance); } /// - /// Evaluates whether the specified would match the . + /// Evaluates whether the specified would match the . /// /// /// /// - public static bool BindingFlagsMatchInherited(IMethodSymbol method, System.Reflection.BindingFlags flags) + public static bool BindingFlagsMatchInherited(IMethodSymbol method, BindingFlags flags) { - return BindingFlagsMatch(method.IsPublic, flags, System.Reflection.BindingFlags.Public, System.Reflection.BindingFlags.NonPublic) - && BindingFlagsMatch(method.IsStatic, flags, System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.FlattenHierarchy, System.Reflection.BindingFlags.Instance); + return BindingFlagsMatch(method.IsPublic, flags, BindingFlags.Public, BindingFlags.NonPublic) + && BindingFlagsMatch(method.IsStatic, flags, BindingFlags.Static | BindingFlags.FlattenHierarchy, BindingFlags.Instance); } /// /// Filters the set of methods by the binding attributes. /// /// - public static IEnumerable FilterMethods(ITypeSymbol type, IEnumerable methods, System.Reflection.BindingFlags bindingAttr = System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance) + public static IEnumerable FilterMethods(ITypeSymbol type, IEnumerable methods, BindingFlags bindingAttr = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance) { var list = new HashSet(); @@ -59,7 +61,7 @@ public static IEnumerable FilterMethods(ITypeSymbol type, IEnumer yield return mi; } - if ((bindingAttr & System.Reflection.BindingFlags.DeclaredOnly) == 0) + if ((bindingAttr & BindingFlags.DeclaredOnly) == 0) { var baseMethods = new List(); foreach (var mi in list) @@ -68,7 +70,7 @@ public static IEnumerable FilterMethods(ITypeSymbol type, IEnumer for (var baseType = type.BaseType; baseType != null; baseType = baseType.BaseType) { - foreach (var mi in baseType.GetMethods(System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Instance)) + foreach (var mi in baseType.GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance)) { if (BindingFlagsMatchInherited(mi, bindingAttr)) { diff --git a/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs b/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs index 4bbf7b61a2..70dfa03009 100644 --- a/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs +++ b/src/IKVM.JTReg.TestAdapter.Core/ErrorHandlerInterceptor.cs @@ -11,7 +11,7 @@ namespace IKVM.JTReg.TestAdapter.Core public class ErrorHandlerInterceptor : DispatchProxy { - static readonly MethodInfo CreateMethodInfo = typeof(DispatchProxy).GetMethods() + static readonly MethodInfo CreateMethodInfo = typeof(DispatchProxy).GetMethods(BindingFlags.Static | BindingFlags.Public) .Where(i => i.Name == "Create") .Where(i => i.GetGenericArguments().Length == 2) .First(); @@ -22,7 +22,7 @@ public class ErrorHandlerInterceptor : DispatchProxy /// public static ErrorHandlerInterceptor Create(IJTRegLoggerContext logger) { - var proxy = (ErrorHandlerInterceptor)CreateMethodInfo.MakeGenericMethod(JTRegTypes.TestFinder.ErrorHandler.Type, typeof(ErrorHandlerInterceptor)).Invoke(null, []); + var proxy = (ErrorHandlerInterceptor)CreateMethodInfo.MakeGenericMethod([JTRegTypes.TestFinder.ErrorHandler.Type, typeof(ErrorHandlerInterceptor)]).Invoke(null, []); proxy.SetLogger(logger); return proxy; } diff --git a/src/IKVM.Runtime/AttributeHelper.cs b/src/IKVM.Runtime/AttributeHelper.cs index 6bf07f89b6..0373a8c056 100644 --- a/src/IKVM.Runtime/AttributeHelper.cs +++ b/src/IKVM.Runtime/AttributeHelper.cs @@ -49,10 +49,10 @@ class AttributeHelper readonly RuntimeContext context; - ICustomAttributeBuilder compilerGeneratedAttribute; - ICustomAttributeBuilder ghostInterfaceAttribute; - ICustomAttributeBuilder deprecatedAttribute; - ICustomAttributeBuilder editorBrowsableNever; + CustomAttribute? compilerGeneratedAttribute; + CustomAttribute? ghostInterfaceAttribute; + CustomAttribute? deprecatedAttribute; + CustomAttribute? editorBrowsableNever; IConstructorSymbol implementsAttribute; IConstructorSymbol throwsAttribute; IConstructorSymbol sourceFileAttribute; @@ -63,7 +63,7 @@ class AttributeHelper IConstructorSymbol methodParametersAttribute; IConstructorSymbol runtimeVisibleTypeAnnotationsAttribute; IConstructorSymbol constantPoolAttribute; - ICustomAttributeBuilder paramArrayAttribute; + CustomAttribute? paramArrayAttribute; IConstructorSymbol nonNestedInnerClassAttribute; IConstructorSymbol nonNestedOuterClassAttribute; @@ -95,8 +95,8 @@ class AttributeHelper ITypeSymbol typeofConstantPoolAttribute; ITypeSymbol typeofDebuggableAttribute; ITypeSymbol typeofCustomAssemblyClassLoaderAttribute; - ICustomAttributeBuilder hideFromJavaAttribute; - ICustomAttributeBuilder hideFromReflection; + CustomAttribute? hideFromJavaAttribute; + CustomAttribute? hideFromReflection; IConstructorSymbol debuggableAttribute; ITypeSymbol TypeOfModifiers => typeofModifiers ??= context.Resolver.ResolveRuntimeType(typeof(Modifiers).FullName); @@ -153,9 +153,9 @@ class AttributeHelper ITypeSymbol TypeOfCustomAssemblyClassLoaderAttribute => typeofCustomAssemblyClassLoaderAttribute ??= context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.CustomAssemblyClassLoaderAttribute).FullName); - ICustomAttributeBuilder HideFromJavaAttributeBuilder => hideFromJavaAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([]), []); + CustomAttribute HideFromJavaAttributeBuilder => hideFromJavaAttribute ??= CustomAttribute.Create(TypeOfHideFromJavaAttribute.GetConstructor([]), []); - ICustomAttributeBuilder HideFromReflectionBuilder => hideFromReflection ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [HideFromJavaFlags.Reflection | HideFromJavaFlags.StackTrace | HideFromJavaFlags.StackWalk]); + CustomAttribute HideFromReflectionBuilder => hideFromReflection ??= CustomAttribute.Create(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [HideFromJavaFlags.Reflection | HideFromJavaFlags.StackTrace | HideFromJavaFlags.StackWalk]); /// /// Initializes a new instance. @@ -292,7 +292,7 @@ void GetAttributeArgsAndTypes(RuntimeClassLoader loader, IKVM.Tools.Importer.Map } } - ICustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr) + CustomAttribute CreateCustomAttribute(RuntimeClassLoader loader, IKVM.Tools.Importer.MapXml.Attribute attr) { // TODO add error handling GetAttributeArgsAndTypes(loader, attr, out var argTypes, out var args); @@ -331,7 +331,7 @@ ICustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.To } } - return context.Resolver.Symbols.CreateCustomAttribute(ci, args, namedProperties, propertyValues, namedFields, fieldValues); + return CustomAttribute.Create(ci, args, namedProperties, propertyValues, namedFields, fieldValues); } else { @@ -363,33 +363,31 @@ ICustomAttributeBuilder CreateCustomAttribute(RuntimeClassLoader loader, IKVM.To mw.Link(); var ci = (mw.GetMethod() as IConstructorSymbol) ?? ((IConstructorSymbol)mw.GetMethod()); - return context.Resolver.Symbols.CreateCustomAttribute(ci, args, namedFields, fieldValues); + return CustomAttribute.Create(ci, args, namedFields, fieldValues); } } - ICustomAttributeBuilder GetEditorBrowsableNever() + CustomAttribute GetEditorBrowsableNever() { if (editorBrowsableNever == null) { var typeofEditorBrowsableAttribute = context.Resolver.ResolveSystemType(typeof(EditorBrowsableAttribute).FullName); var typeofEditorBrowsableState = context.Resolver.ResolveSystemType(typeof(EditorBrowsableState).FullName); var ctor = typeofEditorBrowsableAttribute.GetConstructor([typeofEditorBrowsableState]); - editorBrowsableNever = context.Resolver.Symbols.CreateCustomAttribute(ctor, [EditorBrowsableState.Never]); + editorBrowsableNever = CustomAttribute.Create(ctor, [EditorBrowsableState.Never]); } - return editorBrowsableNever; + return editorBrowsableNever.Value; } internal void SetCompilerGenerated(ITypeSymbolBuilder tb) { - compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); - tb.SetCustomAttribute(compilerGeneratedAttribute); + tb.SetCustomAttribute(compilerGeneratedAttribute ??= CustomAttribute.Create(context.Resolver.ResolveSystemType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), [])); } internal void SetCompilerGenerated(IMethodBaseSymbolBuilder mb) { - compilerGeneratedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), []); - mb.SetCustomAttribute(compilerGeneratedAttribute); + mb.SetCustomAttribute(compilerGeneratedAttribute ??= CustomAttribute.Create(context.Resolver.ResolveSystemType(typeof(CompilerGeneratedAttribute).FullName).GetConstructor([]), [])); } internal void SetEditorBrowsableNever(ITypeSymbolBuilder tb) @@ -409,26 +407,22 @@ internal void SetEditorBrowsableNever(IPropertySymbolBuilder pb) internal void SetDeprecatedAttribute(IMethodBaseSymbolBuilder mb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); - mb.SetCustomAttribute(deprecatedAttribute); + mb.SetCustomAttribute(deprecatedAttribute ??= CustomAttribute.Create(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), [])); } internal void SetDeprecatedAttribute(ITypeSymbolBuilder tb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); - tb.SetCustomAttribute(deprecatedAttribute); + tb.SetCustomAttribute(deprecatedAttribute ??= CustomAttribute.Create(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), [])); } internal void SetDeprecatedAttribute(IFieldSymbolBuilder fb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); - fb.SetCustomAttribute(deprecatedAttribute); + fb.SetCustomAttribute(CustomAttribute.Create(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), [])); } internal void SetDeprecatedAttribute(IPropertySymbolBuilder pb) { - deprecatedAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), []); - pb.SetCustomAttribute(deprecatedAttribute); + pb.SetCustomAttribute(deprecatedAttribute ??= CustomAttribute.Create(context.Resolver.ResolveSystemType(typeof(ObsoleteAttribute).FullName).GetConstructor([]), [])); } internal void SetThrowsAttribute(IMethodBaseSymbolBuilder mb, string[] exceptions) @@ -437,26 +431,25 @@ internal void SetThrowsAttribute(IMethodBaseSymbolBuilder mb, string[] exception { throwsAttribute ??= TypeOfThrowsAttribute.GetConstructor([context.Types.String.MakeArrayType()]); exceptions = UnicodeUtil.EscapeInvalidSurrogates(exceptions); - mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(throwsAttribute, [exceptions])); + mb.SetCustomAttribute(CustomAttribute.Create(throwsAttribute, [exceptions])); } } internal void SetGhostInterface(ITypeSymbolBuilder typeBuilder) { - ghostInterfaceAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(TypeOfGhostInterfaceAttribute.GetConstructor([]), []); - typeBuilder.SetCustomAttribute(ghostInterfaceAttribute); + typeBuilder.SetCustomAttribute(ghostInterfaceAttribute ??= CustomAttribute.Create(TypeOfGhostInterfaceAttribute.GetConstructor([]), [])); } internal void SetNonNestedInnerClass(ITypeSymbolBuilder typeBuilder, string className) { nonNestedInnerClassAttribute ??= TypeOfNonNestedInnerClassAttribute.GetConstructor([context.Types.String]); - typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(nonNestedInnerClassAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className)])); + typeBuilder.SetCustomAttribute(CustomAttribute.Create(nonNestedInnerClassAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className)])); } internal void SetNonNestedOuterClass(ITypeSymbolBuilder typeBuilder, string className) { nonNestedOuterClassAttribute ??= TypeOfNonNestedOuterClassAttribute.GetConstructor([context.Types.String]); - typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(nonNestedOuterClassAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className)])); + typeBuilder.SetCustomAttribute(CustomAttribute.Create(nonNestedOuterClassAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className)])); } #endif // IMPORTER @@ -488,7 +481,7 @@ internal void HideFromJava(IMethodBaseSymbolBuilder ctor) internal void HideFromJava(IMethodBaseSymbolBuilder mb, HideFromJavaFlags flags) { - mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [flags])); + mb.SetCustomAttribute(CustomAttribute.Create(TypeOfHideFromJavaAttribute.GetConstructor([TypeOfHideFromJavaFlags]), [flags])); } internal void HideFromJava(IFieldSymbolBuilder fb) @@ -547,7 +540,7 @@ internal void SetImplementsAttribute(ITypeSymbolBuilder typeBuilder, RuntimeJava if (implementsAttribute == null) implementsAttribute = TypeOfImplementsAttribute.GetConstructor([context.Types.String.MakeArrayType()]); - typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(implementsAttribute, [interfaces])); + typeBuilder.SetCustomAttribute(CustomAttribute.Create(implementsAttribute, [interfaces])); } internal bool IsGhostInterface(ITypeSymbol type) @@ -694,56 +687,20 @@ internal ExModifiers GetModifiers(IFieldSymbol fi, bool assemblyIsPrivate) internal void SetDebuggingModes(IAssemblySymbolBuilder assemblyBuilder, DebuggableAttribute.DebuggingModes modes) { debuggableAttribute ??= TypeOfDebuggableAttribute.GetConstructor([TypeOfDebuggableAttribute.GetNestedType(nameof(DebuggableAttribute.DebuggingModes))]); - assemblyBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(debuggableAttribute, [modes])); + assemblyBuilder.SetCustomAttribute(CustomAttribute.Create(debuggableAttribute, [modes])); } - internal void SetModifiers(IMethodBaseSymbolBuilder mb, Modifiers modifiers, bool isInternal) + internal void SetModifiers(ICustomAttributeProviderBuilder fb, Modifiers modifiers, bool isInternal) { - ICustomAttributeBuilder customAttributeBuilder; if (isInternal) - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); + fb.SetCustomAttribute(CustomAttribute.Create(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal])); else - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); - - mb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetModifiers(IFieldSymbolBuilder fb, Modifiers modifiers, bool isInternal) - { - ICustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); - else - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); - - fb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetModifiers(IPropertySymbolBuilder pb, Modifiers modifiers, bool isInternal) - { - ICustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); - else - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); - - pb.SetCustomAttribute(customAttributeBuilder); - } - - internal void SetModifiers(ITypeSymbolBuilder tb, Modifiers modifiers, bool isInternal) - { - ICustomAttributeBuilder customAttributeBuilder; - if (isInternal) - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers, context.Types.Boolean]), [modifiers, isInternal]); - else - customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers]); - - tb.SetCustomAttribute(customAttributeBuilder); + fb.SetCustomAttribute(CustomAttribute.Create(TypeOfModifiersAttribute.GetConstructor([TypeOfModifiers]), [modifiers])); } internal void SetNameSig(IMethodBaseSymbolBuilder mb, string name, string sig) { - var customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(TypeOfNameSigAttribute.GetConstructor([context.Types.String, context.Types.String]), [UnicodeUtil.EscapeInvalidSurrogates(name), UnicodeUtil.EscapeInvalidSurrogates(sig)]); + var customAttributeBuilder = CustomAttribute.Create(TypeOfNameSigAttribute.GetConstructor([context.Types.String, context.Types.String]), [UnicodeUtil.EscapeInvalidSurrogates(name), UnicodeUtil.EscapeInvalidSurrogates(sig)]); mb.SetCustomAttribute(customAttributeBuilder); } @@ -752,20 +709,20 @@ internal void SetInnerClass(ITypeSymbolBuilder typeBuilder, string innerClass, M var argTypes = new ITypeSymbol[] { context.Types.String, TypeOfModifiers }; var args = new object[] { UnicodeUtil.EscapeInvalidSurrogates(innerClass), modifiers }; var ci = TypeOfInnerClassAttribute.GetConstructor(argTypes); - var customAttributeBuilder = context.Resolver.Symbols.CreateCustomAttribute(ci, args); + var customAttributeBuilder = CustomAttribute.Create(ci, args); typeBuilder.SetCustomAttribute(customAttributeBuilder); } internal void SetSourceFile(ITypeSymbolBuilder typeBuilder, string filename) { sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor([context.Types.String]); - typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(sourceFileAttribute, [filename])); + typeBuilder.SetCustomAttribute(CustomAttribute.Create(sourceFileAttribute, [filename])); } internal void SetSourceFile(IModuleSymbolBuilder moduleBuilder, string filename) { sourceFileAttribute ??= TypeOfSourceFileAttribute.GetConstructor([context.Types.String]); - moduleBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(sourceFileAttribute, [filename])); + moduleBuilder.SetCustomAttribute(CustomAttribute.Create(sourceFileAttribute, [filename])); } internal void SetLineNumberTable(IMethodBaseSymbolBuilder mb, IKVM.Attributes.LineNumberTableAttribute.LineNumberWriter writer) @@ -785,37 +742,37 @@ internal void SetLineNumberTable(IMethodBaseSymbolBuilder mb, IKVM.Attributes.Li arg = writer.ToArray(); } - mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(con, [arg])); + mb.SetCustomAttribute(CustomAttribute.Create(con, [arg])); } internal void SetEnclosingMethodAttribute(ITypeSymbolBuilder tb, string className, string methodName, string methodSig) { enclosingMethodAttribute ??= TypeOfEnclosingMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String]); - tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(enclosingMethodAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className), UnicodeUtil.EscapeInvalidSurrogates(methodName), UnicodeUtil.EscapeInvalidSurrogates(methodSig)])); + tb.SetCustomAttribute(CustomAttribute.Create(enclosingMethodAttribute, [UnicodeUtil.EscapeInvalidSurrogates(className), UnicodeUtil.EscapeInvalidSurrogates(methodName), UnicodeUtil.EscapeInvalidSurrogates(methodSig)])); } internal void SetSignatureAttribute(ITypeSymbolBuilder tb, string signature) { signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); - tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + tb.SetCustomAttribute(CustomAttribute.Create(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } internal void SetSignatureAttribute(IFieldSymbolBuilder fb, string signature) { signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); - fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + fb.SetCustomAttribute(CustomAttribute.Create(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } internal void SetSignatureAttribute(IMethodBaseSymbolBuilder mb, string signature) { signatureAttribute ??= TypeOfSignatureAttribute.GetConstructor([context.Types.String]); - mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); + mb.SetCustomAttribute(CustomAttribute.Create(signatureAttribute, [UnicodeUtil.EscapeInvalidSurrogates(signature)])); } internal void SetMethodParametersAttribute(IMethodBaseSymbolBuilder mb, Modifiers[] modifiers) { methodParametersAttribute ??= TypeOfMethodParametersAttribute.GetConstructor([TypeOfModifiers.MakeArrayType()]); - mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(methodParametersAttribute, [modifiers])); + mb.SetCustomAttribute(CustomAttribute.Create(methodParametersAttribute, [modifiers])); } internal void SetRuntimeVisibleTypeAnnotationsAttribute(ITypeSymbolBuilder tb, ref readonly TypeAnnotationTable table) @@ -825,7 +782,7 @@ internal void SetRuntimeVisibleTypeAnnotationsAttribute(ITypeSymbolBuilder tb, r table.WriteTo(ref encoder); runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); + tb.SetCustomAttribute(CustomAttribute.Create(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); } internal void SetRuntimeVisibleTypeAnnotationsAttribute(IFieldSymbolBuilder fb, ref readonly TypeAnnotationTable table) @@ -835,7 +792,7 @@ internal void SetRuntimeVisibleTypeAnnotationsAttribute(IFieldSymbolBuilder fb, table.WriteTo(ref encoder); runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); + fb.SetCustomAttribute(CustomAttribute.Create(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); } internal void SetRuntimeVisibleTypeAnnotationsAttribute(IMethodBaseSymbolBuilder mb, ref readonly TypeAnnotationTable table) @@ -845,19 +802,18 @@ internal void SetRuntimeVisibleTypeAnnotationsAttribute(IMethodBaseSymbolBuilder table.WriteTo(ref encoder); runtimeVisibleTypeAnnotationsAttribute ??= TypeOfRuntimeVisibleTypeAnnotationsAttribute.GetConstructor([context.Types.Byte.MakeArrayType()]); - mb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); + mb.SetCustomAttribute(CustomAttribute.Create(runtimeVisibleTypeAnnotationsAttribute, [builder.ToArray()])); } internal void SetConstantPoolAttribute(ITypeSymbolBuilder tb, object[] constantPool) { constantPoolAttribute ??= TypeOfConstantPoolAttribute.GetConstructor([context.Types.Object.MakeArrayType()]); - tb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(constantPoolAttribute, [constantPool])); + tb.SetCustomAttribute(CustomAttribute.Create(constantPoolAttribute, [constantPool])); } internal void SetParamArrayAttribute(IParameterSymbolBuilder pb) { - paramArrayAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName).GetConstructor([]), []); - pb.SetCustomAttribute(paramArrayAttribute); + pb.SetCustomAttribute(paramArrayAttribute ??= CustomAttribute.Create(context.Resolver.ResolveCoreType(typeof(ParamArrayAttribute).FullName).GetConstructor([]), [])); } internal NameSigAttribute GetNameSig(IMemberSymbol member) @@ -903,11 +859,11 @@ internal ThrowsAttribute GetThrows(IMethodBaseSymbol mb) } else if (args[0].ArgumentType == context.Types.Type.MakeArrayType()) { - return new ThrowsAttribute(DecodeArray(args[0]).AsReflection()); + return new ThrowsAttribute(DecodeArray(args[0]).GetUnderlyingTypes()); } else { - return new ThrowsAttribute(((ITypeSymbol)args[0].Value).AsReflection()); + return new ThrowsAttribute(((ITypeSymbol)args[0].Value).GetUnderlyingType()); } } @@ -989,7 +945,7 @@ internal RemappedInterfaceMethodAttribute[] GetRemappedInterfaceMethods(ITypeSym internal RemappedTypeAttribute GetRemappedType(ITypeSymbol type) { foreach (var cad in type.GetCustomAttributes(TypeOfRemappedTypeAttribute)) - return new RemappedTypeAttribute(((ITypeSymbol)cad.ConstructorArguments[0].Value).AsReflection()); + return new RemappedTypeAttribute(((ITypeSymbol)cad.ConstructorArguments[0].Value).GetUnderlyingType()); return null; } @@ -1004,7 +960,7 @@ internal RemappedClassAttribute[] GetRemappedClasses(IAssemblySymbol coreAssembl foreach (var cad in coreAssembly.GetCustomAttributes(TypeOfRemappedClassAttribute)) { var args = cad.ConstructorArguments; - attrs.Add(new RemappedClassAttribute((string)args[0].Value, ((ITypeSymbol)args[1].Value).AsReflection())); + attrs.Add(new RemappedClassAttribute((string)args[0].Value, ((ITypeSymbol)args[1].Value).GetUnderlyingType())); } return attrs.ToArray(); @@ -1097,43 +1053,43 @@ internal IKVM.Attributes.EnclosingMethodAttribute GetEnclosingMethodAttribute(IT internal void SetRemappedClass(IAssemblySymbolBuilder assemblyBuilder, string name, ITypeSymbol shadowType) { var remappedClassAttribute = TypeOfRemappedClassAttribute.GetConstructor([context.Types.String, context.Types.Type]); - assemblyBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(remappedClassAttribute, [name, shadowType])); + assemblyBuilder.SetCustomAttribute(CustomAttribute.Create(remappedClassAttribute, [name, shadowType])); } internal void SetRemappedType(ITypeSymbolBuilder typeBuilder, ITypeSymbol shadowType) { var remappedTypeAttribute = TypeOfRemappedTypeAttribute.GetConstructor([context.Types.Type]); - typeBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(remappedTypeAttribute, [shadowType])); + typeBuilder.SetCustomAttribute(CustomAttribute.Create(remappedTypeAttribute, [shadowType])); } internal void SetRemappedInterfaceMethod(ITypeSymbolBuilder typeBuilder, string name, string mappedTo, string[] throws) { - var cab = context.Resolver.Symbols.CreateCustomAttribute(TypeOfRemappedInterfaceMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String.MakeArrayType()]), [name, mappedTo, throws]); + var cab = CustomAttribute.Create(TypeOfRemappedInterfaceMethodAttribute.GetConstructor([context.Types.String, context.Types.String, context.Types.String.MakeArrayType()]), [name, mappedTo, throws]); typeBuilder.SetCustomAttribute(cab); } internal void SetExceptionIsUnsafeForMapping(ITypeSymbolBuilder typeBuilder) { - var cab = context.Resolver.Symbols.CreateCustomAttribute(TypeOfExceptionIsUnsafeForMappingAttribute.GetConstructor([]), []); + var cab = CustomAttribute.Create(TypeOfExceptionIsUnsafeForMappingAttribute.GetConstructor([]), []); typeBuilder.SetCustomAttribute(cab); } internal void SetRuntimeCompatibilityAttribute(IAssemblySymbolBuilder assemblyBuilder) { var runtimeCompatibilityAttribute = context.Resolver.ResolveCoreType(typeof(RuntimeCompatibilityAttribute).FullName); - assemblyBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(runtimeCompatibilityAttribute.GetConstructor([]), [], [runtimeCompatibilityAttribute.GetProperty("WrapNonExceptionThrows")], [true], [], [])); + assemblyBuilder.SetCustomAttribute(CustomAttribute.Create(runtimeCompatibilityAttribute.GetConstructor([]), [], [runtimeCompatibilityAttribute.GetProperty("WrapNonExceptionThrows")], [true], [], [])); } internal void SetInternalsVisibleToAttribute(IAssemblySymbolBuilder assemblyBuilder, string assemblyName) { var internalsVisibleToAttribute = context.Resolver.ResolveCoreType(typeof(InternalsVisibleToAttribute).FullName); - var cab = context.Resolver.Symbols.CreateCustomAttribute(internalsVisibleToAttribute.GetConstructor([context.Types.String]), [assemblyName]); + var cab = CustomAttribute.Create(internalsVisibleToAttribute.GetConstructor([context.Types.String]), [assemblyName]); assemblyBuilder.SetCustomAttribute(cab); } internal void SetCustomAssemblyClassLoaderAttribute(IAssemblySymbolBuilder assemblyBuilder, ITypeSymbol classLoaderType) { - var cab = context.Resolver.Symbols.CreateCustomAttribute(TypeOfCustomAssemblyClassLoaderAttribute.GetConstructor([context.Types.Type]), [classLoaderType]); + var cab = CustomAttribute.Create(TypeOfCustomAssemblyClassLoaderAttribute.GetConstructor([context.Types.Type]), [classLoaderType]); assemblyBuilder.SetCustomAttribute(cab); } diff --git a/src/IKVM.Runtime/ByteCodeHelper.cs b/src/IKVM.Runtime/ByteCodeHelper.cs index 5ba3bd6354..a4b6db89aa 100644 --- a/src/IKVM.Runtime/ByteCodeHelper.cs +++ b/src/IKVM.Runtime/ByteCodeHelper.cs @@ -128,7 +128,7 @@ public static object DynamicMultianewarray(int[] lengths, global::java.lang.Clas Profiler.Count("DynamicMultianewarray"); var wrapper = RuntimeJavaType.FromClass(clazz); - var obj = multianewarray(wrapper.TypeAsArrayType.AsReflection().TypeHandle, lengths); + var obj = multianewarray(wrapper.TypeAsArrayType.GetUnderlyingType().TypeHandle, lengths); if (wrapper.IsGhostArray) GhostTag.SetTag(obj, wrapper); @@ -147,7 +147,7 @@ public static object DynamicNewarray(int length, global::java.lang.Class clazz) throw new global::java.lang.NegativeArraySizeException(); var wrapper = RuntimeJavaType.FromClass(clazz); - var obj = Array.CreateInstance(wrapper.TypeAsArrayType.AsReflection(), length); + var obj = Array.CreateInstance(wrapper.TypeAsArrayType.GetUnderlyingType(), length); if (wrapper.IsGhost || wrapper.IsGhostArray) GhostTag.SetTag(obj, wrapper.MakeArrayType(1)); @@ -1108,7 +1108,7 @@ public static Exception DynamicMapException(Exception x, MapFlags mode, global:: mode |= MapFlags.NoRemapping; var exceptionType = exceptionTypeWrapper == JVM.Context.JavaBase.TypeOfjavaLangThrowable ? JVM.Context.Resolver.ResolveCoreType(typeof(System.Exception).FullName) : exceptionTypeWrapper.TypeAsBaseType; - return (Exception)JVM.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(exceptionType).AsReflection().Invoke(null, [x, mode]); + return (Exception)JVM.Context.ByteCodeHelperMethods.MapException.MakeGenericMethod(exceptionType).GetUnderlyingMethod().Invoke(null, [x, mode]); #endif } diff --git a/src/IKVM.Runtime/DynamicClassLoader.cs b/src/IKVM.Runtime/DynamicClassLoader.cs index ab9860866e..2e906c98e6 100644 --- a/src/IKVM.Runtime/DynamicClassLoader.cs +++ b/src/IKVM.Runtime/DynamicClassLoader.cs @@ -34,6 +34,8 @@ Jeroen Frijters using static System.Diagnostics.DebuggableAttribute; using IKVM.CoreLib.Symbols.Reflection; +using System.Collections.Immutable; + @@ -108,7 +110,7 @@ Assembly Resolve(ConcurrentDictionary dict, string name try { type.Finish(); - return type.TypeAsTBD.Assembly.AsReflection(); + return type.TypeAsTBD.Assembly.GetUnderlyingAssembly(); } catch (RetargetableJavaException e) { @@ -450,7 +452,7 @@ internal void FinishAll() internal static IModuleSymbolBuilder CreateJniProxyModuleBuilder(RuntimeContext context) { - jniProxyAssemblyBuilder = DefineDynamicAssembly(context, new AssemblyIdentity("jniproxy"), null); + jniProxyAssemblyBuilder = DefineDynamicAssembly(context, new AssemblyIdentity("jniproxy"), []); return jniProxyAssemblyBuilder.DefineModule("jniproxy.dll"); } @@ -545,9 +547,9 @@ public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, A name.ContentType, name.ProcessorArchitecture); - var attribs = Array.Empty(); + var attribs = ImmutableArray.Empty; if (AppDomain.CurrentDomain.IsFullyTrusted == false) - attribs = [context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(System.Security.SecurityTransparentAttribute).FullName).GetConstructor([]), [])]; + attribs = [CustomAttribute.Create(context.Resolver.ResolveCoreType(typeof(System.Security.SecurityTransparentAttribute).FullName).GetConstructor([]), [])]; var assemblyBuilder = DefineDynamicAssembly(context, name, attribs); context.AttributeHelper.SetRuntimeCompatibilityAttribute(assemblyBuilder); @@ -562,7 +564,7 @@ public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, A // create new module var moduleBuilder = assemblyBuilder.DefineModule(name.Name, null, context.Options.EmitSymbols); - moduleBuilder.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.JavaModuleAttribute).FullName).GetConstructor([]), [])); + moduleBuilder.SetCustomAttribute(CustomAttribute.Create(context.Resolver.ResolveRuntimeType(typeof(IKVM.Attributes.JavaModuleAttribute).FullName).GetConstructor([]), [])); return moduleBuilder; } @@ -573,7 +575,7 @@ public static IModuleSymbolBuilder CreateModuleBuilder(RuntimeContext context, A /// /// /// - static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyIdentity name, ICustomAttributeBuilder[] assemblyAttributes) + static IAssemblySymbolBuilder DefineDynamicAssembly(RuntimeContext context, AssemblyIdentity name, ImmutableArray assemblyAttributes) { return context.Resolver.Symbols.DefineAssembly(name, assemblyAttributes, false, false); } diff --git a/src/IKVM.Runtime/JNI/JNIEnv.cs b/src/IKVM.Runtime/JNI/JNIEnv.cs index 6daad51be8..789832c734 100644 --- a/src/IKVM.Runtime/JNI/JNIEnv.cs +++ b/src/IKVM.Runtime/JNI/JNIEnv.cs @@ -628,9 +628,9 @@ static nint AllocObjectImpl(JNIEnv* pEnv, RuntimeJavaType wrapper) wrapper.Finish(); #if NETFRAMEWORK - return pEnv->MakeLocalRef(FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection())); + return pEnv->MakeLocalRef(FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType())); #else - return pEnv->MakeLocalRef(RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection())); + return pEnv->MakeLocalRef(RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType())); #endif } catch (RetargetableJavaException e) @@ -709,7 +709,7 @@ static object InvokeHelper(JNIEnv* pEnv, nint objHandle, nint methodID, JValue* // possible with remapped types throw new NotSupportedException($"Remapped type {mw.DeclaringType.Name} doesn't support constructor invocation on an existing instance"); } - else if (!mb.DeclaringType.AsReflection().IsInstanceOfType(obj)) + else if (!mb.DeclaringType.GetUnderlyingType().IsInstanceOfType(obj)) { // we're trying to initialize an existing instance of a remapped type throw new NotSupportedException($"Unable to partially construct object of type {obj.GetType().FullName} to type {mb.DeclaringType.FullName}"); @@ -734,10 +734,10 @@ static object InvokeNonVirtual(JNIEnvContext env, RuntimeJavaMethod mw, object o if (mw.HasCallerID || mw.IsDynamicOnly) throw new NotSupportedException(); - if (mw.DeclaringType.IsRemapped && !mw.DeclaringType.TypeAsBaseType.AsReflection().IsInstanceOfType(obj)) + if (mw.DeclaringType.IsRemapped && !mw.DeclaringType.TypeAsBaseType.GetUnderlyingType().IsInstanceOfType(obj)) return mw.InvokeNonvirtualRemapped(obj, argarray); - var del = (Delegate)Activator.CreateInstance(mw.GetDelegateType().AsReflection(), [obj, mw.GetMethod().AsReflection().MethodHandle.GetFunctionPointer()]); + var del = (Delegate)Activator.CreateInstance(mw.GetDelegateType().GetUnderlyingType(), [obj, mw.GetMethod().GetUnderlyingMethodBase().MethodHandle.GetFunctionPointer()]); try { return del.DynamicInvoke(argarray); @@ -2157,7 +2157,7 @@ internal static nint NewObjectArray(JNIEnv* pEnv, jsize len, nint clazz, nint in try { // we want to support (non-primitive) value types so we can't cast to object[] - var a = Array.CreateInstance(RuntimeJavaType.FromClass((java.lang.Class)pEnv->UnwrapRef(clazz)).TypeAsArrayType.AsReflection(), len); + var a = Array.CreateInstance(RuntimeJavaType.FromClass((java.lang.Class)pEnv->UnwrapRef(clazz)).TypeAsArrayType.GetUnderlyingType(), len); var o = pEnv->UnwrapRef(init); if (o != null) for (int i = 0; i < a.Length; i++) @@ -2776,7 +2776,7 @@ internal static jint RegisterNatives(JNIEnv* pEnv, nint clazz, JNINativeMethod* // don't allow dotted names! if (methodSig.IndexOf('.') < 0) - fi = wrapper.TypeAsTBD.GetField(METHOD_PTR_FIELD_PREFIX + methodName + methodSig, BindingFlags.Static | BindingFlags.NonPublic).AsReflection(); + fi = wrapper.TypeAsTBD.GetField(METHOD_PTR_FIELD_PREFIX + methodName + methodSig, BindingFlags.Static | BindingFlags.NonPublic).GetUnderlyingField(); if (fi == null) { diff --git a/src/IKVM.Runtime/JVM.Internal.cs b/src/IKVM.Runtime/JVM.Internal.cs index c2c71d6156..1ff5d56f9e 100644 --- a/src/IKVM.Runtime/JVM.Internal.cs +++ b/src/IKVM.Runtime/JVM.Internal.cs @@ -39,7 +39,7 @@ internal static class Internal static ThreadGroupAccessor threadGroupAccessor; static SystemAccessor systemAccessor; - internal static AccessorCache BaseAccessors => AccessorCache.Get(ref baseAccessors, context.Resolver.GetBaseAssembly().AsReflection()); + internal static AccessorCache BaseAccessors => AccessorCache.Get(ref baseAccessors, context.Resolver.GetBaseAssembly().GetUnderlyingAssembly()); internal static ThreadGroupAccessor ThreadGroupAccessor => BaseAccessors.Get(ref threadGroupAccessor); diff --git a/src/IKVM.Runtime/JVM.Properties.cs b/src/IKVM.Runtime/JVM.Properties.cs index f97f9f49ea..0d3af177de 100644 --- a/src/IKVM.Runtime/JVM.Properties.cs +++ b/src/IKVM.Runtime/JVM.Properties.cs @@ -272,7 +272,7 @@ static void InitSystemProperties(Dictionary p) p["java.ext.dirs"] = Path.Combine(HomePath, "lib", "ext"); p["java.endorsed.dirs"] = Path.Combine(HomePath, "lib", "endorsed"); p["sun.boot.library.path"] = GetBootLibraryPath(); - p["sun.boot.class.path"] = VfsTable.GetAssemblyClassesPath(Vfs.Context, Context.Resolver.GetBaseAssembly().AsReflection(), HomePath); + p["sun.boot.class.path"] = VfsTable.GetAssemblyClassesPath(Vfs.Context, Context.Resolver.GetBaseAssembly().GetUnderlyingAssembly(), HomePath); p["sun.cds.enableSharedLookupCache"] = "false"; // unlimited direct memory diff --git a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs index 2da52208a7..530a596975 100644 --- a/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs +++ b/src/IKVM.Runtime/Java/Externs/ikvm/runtime/Util.cs @@ -24,7 +24,6 @@ Jeroen Frijters using System; using IKVM.Attributes; -using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Symbols.Emit; using IKVM.Runtime; @@ -168,9 +167,9 @@ public static Type getInstanceTypeFromClass(global::java.lang.Class classObject) { var wrapper = RuntimeJavaType.FromClass(classObject); if (wrapper.IsRemapped && wrapper.IsFinal) - return wrapper.TypeAsTBD.AsReflection(); + return wrapper.TypeAsTBD.GetUnderlyingRuntimeType(); else - return wrapper.TypeAsBaseType.AsReflection(); + return wrapper.TypeAsBaseType.GetUnderlyingRuntimeType(); } /// @@ -184,9 +183,9 @@ public static Type getRuntimeTypeFromClass(global::java.lang.Class classObject) wrapper.Finish(); if (wrapper.IsRemapped && wrapper.IsFinal) - return wrapper.TypeAsTBD.AsReflection(); + return wrapper.TypeAsTBD.GetUnderlyingRuntimeType(); else - return wrapper.TypeAsBaseType.AsReflection(); + return wrapper.TypeAsBaseType.GetUnderlyingRuntimeType(); } [HideFromJava] diff --git a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs index abe35f9526..9208087fd1 100644 --- a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs +++ b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs @@ -256,10 +256,10 @@ internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) throw x.ToJava(); } - var dmObjGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(object[])]); - var dmPrimGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(byte[])]); - var dmObjSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(object[])]); - var dmPrimSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.AsReflection(), true, null, [typeof(object), typeof(byte[])]); + var dmObjGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(object[])]); + var dmPrimGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(byte[])]); + var dmObjSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(object[])]); + var dmPrimSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(byte[])]); var ilgenObjGetter = JVM.Context.CodeEmitterFactory.Create(dmObjGetter); var ilgenPrimGetter = JVM.Context.CodeEmitterFactory.Create(dmPrimGetter); var ilgenObjSetter = JVM.Context.CodeEmitterFactory.Create(dmObjSetter); diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs b/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs index e98641d5fb..051ccbe755 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/Package.cs @@ -48,7 +48,7 @@ static void LazyInitSystemPackages() if (systemPackages == null) { var dict = new Dictionary(); - var path = Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, JVM.Context.Resolver.GetBaseAssembly().AsReflection(), JVM.Properties.HomePath), "resources.jar"); + var path = Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, JVM.Context.Resolver.GetBaseAssembly().GetUnderlyingAssembly(), JVM.Properties.HomePath), "resources.jar"); foreach (var pkgs in JVM.Context.ClassLoaderFactory.GetBootstrapClassLoader().GetPackageInfo()) foreach (var pkg in pkgs.Value) dict[pkg.Replace('.', '/') + "/"] = path; diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs b/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs index db53ee23ab..778db45f8f 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs @@ -378,7 +378,7 @@ static Delegate CreateMemberNameDelegate(RuntimeJavaMethod mw, global::java.lang && tw.Context.MethodHandleUtil.HasOnlyBasicTypes(mw.GetParameters(), mw.ReturnType) && type.parameterCount() <= MethodHandleUtil.MaxArity) { - return Delegate.CreateDelegate(tw.Context.MethodHandleUtil.CreateMemberWrapperDelegateType(mw.GetParameters(), mw.ReturnType).AsReflection(), mi); + return Delegate.CreateDelegate(tw.Context.MethodHandleUtil.CreateMemberWrapperDelegateType(mw.GetParameters(), mw.ReturnType).GetUnderlyingType(), mi); } else { @@ -466,7 +466,7 @@ public static object staticFieldBase(global::java.lang.invoke.MemberName self) internal static void InitializeCallSite(global::java.lang.invoke.CallSite site) { - var type = typeof(IKVM.Runtime.IndyCallSite<>).MakeGenericType(JVM.Context.MethodHandleUtil.GetDelegateTypeForInvokeExact(site.type()).AsReflection()); + var type = typeof(IKVM.Runtime.IndyCallSite<>).MakeGenericType(JVM.Context.MethodHandleUtil.GetDelegateTypeForInvokeExact(site.type()).GetUnderlyingType()); var ics = (IKVM.Runtime.IIndyCallSite)Activator.CreateInstance(type, true); Interlocked.CompareExchange(ref site.ics, ics, null); } diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs index f19c102feb..a42d11e82c 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/reflect/Array.cs @@ -609,7 +609,7 @@ public static object newArray(global::java.lang.Class componentType, int length) var wrapper = RuntimeJavaType.FromClass(componentType); wrapper.Finish(); - var obj = global::System.Array.CreateInstance(wrapper.TypeAsArrayType.AsReflection(), length); + var obj = global::System.Array.CreateInstance(wrapper.TypeAsArrayType.GetUnderlyingType(), length); if (wrapper.IsGhost || wrapper.IsGhostArray) IKVM.Runtime.GhostTag.SetTag(obj, wrapper.MakeArrayType(1)); @@ -646,7 +646,7 @@ public static object multiNewArray(global::java.lang.Class componentType, int[] var wrapper = RuntimeJavaType.FromClass(componentType).MakeArrayType(dimensions.Length); wrapper.Finish(); - var obj = IKVM.Runtime.ByteCodeHelper.multianewarray(wrapper.TypeAsArrayType.AsReflection().TypeHandle, dimensions); + var obj = IKVM.Runtime.ByteCodeHelper.multianewarray(wrapper.TypeAsArrayType.GetUnderlyingType().TypeHandle, dimensions); if (wrapper.IsGhostArray) IKVM.Runtime.GhostTag.SetTag(obj, wrapper); diff --git a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs index d27e19065c..f2faef90c5 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs @@ -1734,9 +1734,9 @@ public static object allocateInstance(object self, global::java.lang.Class cls) } #if NETFRAMEWORK - return FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection()); + return FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType()); #else - return RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.AsReflection()); + return RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType()); #endif } @@ -1854,8 +1854,8 @@ static void PutFieldVolatile(object o, long offset, T value) /// static Delegate CreateGetArrayVolatileDelegate(RuntimeJavaType tw) { - var et = tw.IsPrimitive ? tw.TypeAsTBD.AsReflection() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.AsReflection(), true, et, new[] { typeof(object[]), typeof(long) }); + var et = tw.IsPrimitive ? tw.TypeAsTBD.GetUnderlyingType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.GetUnderlyingType(), true, et, new[] { typeof(object[]), typeof(long) }); var il = dm.GetILGenerator(); // load reference to element @@ -1865,17 +1865,17 @@ static Delegate CreateGetArrayVolatileDelegate(RuntimeJavaType tw) il.Emit(OpCodes.Ldc_I4, ArrayIndexScale(tw.MakeArrayType(1))); il.Emit(OpCodes.Div); il.Emit(OpCodes.Conv_Ovf_I); - il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.AsReflection()); + il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.GetUnderlyingType()); if (tw.IsWidePrimitive == false) { il.Emit(OpCodes.Volatile); - EmitLdind(il, tw.TypeAsLocalOrStackType.AsReflection()); + EmitLdind(il, tw.TypeAsLocalOrStackType.GetUnderlyingType()); } else { // Java volatile semantics require atomicity, CLR volatile semantics do not - var mi = typeof(Unsafe).GetMethod(nameof(InterlockedRead), BindingFlags.NonPublic | BindingFlags.Static, null, new[] { tw.TypeAsTBD.MakeByRefType().AsReflection() }, null); + var mi = typeof(Unsafe).GetMethod(nameof(InterlockedRead), BindingFlags.NonPublic | BindingFlags.Static, null, new[] { tw.TypeAsTBD.MakeByRefType().GetUnderlyingType() }, null); il.Emit(OpCodes.Call, mi); } @@ -1912,8 +1912,8 @@ static object GetArrayObjectVolatile(object[] array, long offset) /// static Delegate CreatePutArrayVolatileDelegate(RuntimeJavaType tw) { - var et = tw.IsPrimitive ? tw.TypeAsTBD.AsReflection() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.AsReflection(), true, typeof(void), new[] { typeof(object[]), typeof(long), et }); + var et = tw.IsPrimitive ? tw.TypeAsTBD.GetUnderlyingType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.GetUnderlyingType(), true, typeof(void), new[] { typeof(object[]), typeof(long), et }); var il = dm.GetILGenerator(); // load reference to element @@ -1923,19 +1923,19 @@ static Delegate CreatePutArrayVolatileDelegate(RuntimeJavaType tw) il.Emit(OpCodes.Ldc_I4, ArrayIndexScale(tw.MakeArrayType(1))); il.Emit(OpCodes.Div); il.Emit(OpCodes.Conv_Ovf_I); - il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.AsReflection()); + il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.GetUnderlyingType()); il.Emit(OpCodes.Ldarg_2); if (tw.IsWidePrimitive == false) { il.Emit(OpCodes.Volatile); - EmitStind(il, tw.TypeAsLocalOrStackType.AsReflection()); + EmitStind(il, tw.TypeAsLocalOrStackType.GetUnderlyingType()); } else { // Java volatile semantics require atomicity, CLR volatile semantics do not - var mi = typeof(Interlocked).GetMethod(nameof(Interlocked.Exchange), new[] { tw.TypeAsTBD.MakeByRefType().AsReflection() }); + var mi = typeof(Interlocked).GetMethod(nameof(Interlocked.Exchange), new[] { tw.TypeAsTBD.MakeByRefType().GetUnderlyingType() }); il.Emit(OpCodes.Call, mi); } @@ -2475,11 +2475,11 @@ static Delegate CreateCompareExchangeArrayDelegate(RuntimeJavaType tw) var e = Expression.Parameter(typeof(object)); return Expression.Lambda>( Expression.Call( - compareAndSwapArrayMethodInfo.MakeGenericMethod(tw.TypeAsTBD.AsReflection()), - Expression.Convert(p, tw.MakeArrayType(1).TypeAsTBD.AsReflection()), + compareAndSwapArrayMethodInfo.MakeGenericMethod(tw.TypeAsTBD.GetUnderlyingType()), + Expression.Convert(p, tw.MakeArrayType(1).TypeAsTBD.GetUnderlyingType()), i, - Expression.Convert(v, tw.TypeAsTBD.AsReflection()), - Expression.Convert(e, tw.TypeAsTBD.AsReflection())), + Expression.Convert(v, tw.TypeAsTBD.GetUnderlyingType()), + Expression.Convert(e, tw.TypeAsTBD.GetUnderlyingType())), p, i, v, e) .Compile(); } diff --git a/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs b/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs index 02e611e845..4a99fea263 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/misc/VM.cs @@ -64,7 +64,7 @@ public static void initialize() // check that the assembly isn't the .NET corelib or the IKVM runtime var clw = tw.ClassLoader; if (clw is RuntimeAssemblyClassLoader acl) - if (acl.GetAssembly(tw) == JVM.Context.Types.Object.Assembly || acl.GetAssembly(tw).AsReflection() == typeof(VM).Assembly) + if (acl.GetAssembly(tw) == JVM.Context.Types.Object.Assembly || acl.GetAssembly(tw).GetUnderlyingAssembly() == typeof(VM).Assembly) continue; // associated Java class loader is our nearest diff --git a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs index ab9c1a1b17..c898acb333 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs @@ -286,9 +286,9 @@ internal SerializationConstructorAccessorImpl(global::java.lang.reflect.Construc public object newInstance(object[] args) { #if NETFRAMEWORK - var obj = FormatterServices.GetUninitializedObject(type.AsReflection()); + var obj = FormatterServices.GetUninitializedObject(type.GetUnderlyingType()); #else - var obj = RuntimeHelpers.GetUninitializedObject(type.AsReflection()); + var obj = RuntimeHelpers.GetUninitializedObject(type.GetUnderlyingType()); #endif if (mw != null) mw.Invoke(obj, ConvertArgs(mw.DeclaringType.ClassLoader, mw.GetParameters(), args)); @@ -587,7 +587,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) // generate new dynamic method var np = !mw.IsPublic || !mw.DeclaringType.IsPublic; - var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsBaseType.AsReflection(), np, typeof(object), new[] { typeof(object), typeof(object[]), typeof(global::ikvm.@internal.CallerID) }); + var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsBaseType.GetUnderlyingType(), np, typeof(object), new[] { typeof(object), typeof(object[]), typeof(global::ikvm.@internal.CallerID) }); var il = JVM.Context.CodeEmitterFactory.Create(dm); // labels @@ -831,7 +831,7 @@ internal FastConstructorAccessorImpl(global::java.lang.reflect.Constructor const // resolve the runtime method info mw.ResolveMethod(); var np = !mw.IsPublic || !mw.DeclaringType.IsPublic; - var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsTBD.AsReflection(), np, typeof(object), new[] { typeof(object[]) }); + var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsTBD.GetUnderlyingType(), np, typeof(object), new[] { typeof(object[]) }); var il = JVM.Context.CodeEmitterFactory.Create(dm); // labels @@ -1007,7 +1007,7 @@ internal FastSerializationConstructorAccessorImpl(global::java.lang.reflect.Cons throw x.ToJava(); } - var dm = DynamicMethodUtil.Create("__", constructor.DeclaringType.TypeAsBaseType.AsReflection(), true, typeof(object), null); + var dm = DynamicMethodUtil.Create("__", constructor.DeclaringType.TypeAsBaseType.GetUnderlyingType(), true, typeof(object), null); var il = JVM.Context.CodeEmitterFactory.Create(dm); il.Emit(OpCodes.Ldtoken, type); il.Emit(OpCodes.Call, GetTypeFromHandleMethod); @@ -1052,7 +1052,7 @@ public object newInstance(object[] objarr) try { - return Activator.CreateInstance(type.AsReflection()); + return Activator.CreateInstance(type.GetUnderlyingType()); } catch (TargetInvocationException x) { @@ -1319,7 +1319,7 @@ private T lazyGet(object obj) { throw GetIllegalArgumentException(obj); } - else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.AsReflection().IsInstanceOfType(obj)) + else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.GetUnderlyingType().IsInstanceOfType(obj)) { throw GetUnsupportedRemappedFieldException(obj); } @@ -1364,7 +1364,7 @@ private void lazySet(object obj, T value) { throw SetIllegalArgumentException(obj); } - else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.AsReflection().IsInstanceOfType(obj)) + else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.GetUnderlyingType().IsInstanceOfType(obj)) { throw GetUnsupportedRemappedFieldException(obj); } @@ -2070,7 +2070,7 @@ private Delegate GenerateFastGetter(Type delegateType, Type fieldType, RuntimeJa fw.ResolveField(); - var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.AsReflection(), !fw.IsPublic || !fw.DeclaringType.IsPublic, fieldType, [typeof(IReflectionException), typeof(object), typeof(object)]); + var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.GetUnderlyingType(), !fw.IsPublic || !fw.DeclaringType.IsPublic, fieldType, [typeof(IReflectionException), typeof(object), typeof(object)]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (fw.IsStatic) { @@ -2118,7 +2118,7 @@ private Delegate GenerateFastSetter(Type delegateType, Type fieldType, RuntimeJa fw.ResolveField(); - var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.AsReflection(), !fw.IsPublic || !fw.DeclaringType.IsPublic, null, [typeof(IReflectionException), typeof(object), fieldType, typeof(object)]); + var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.GetUnderlyingType(), !fw.IsPublic || !fw.DeclaringType.IsPublic, null, [typeof(IReflectionException), typeof(object), fieldType, typeof(object)]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (fw.IsStatic) { diff --git a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs index 9a6044702d..b44ab8b5b7 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs @@ -59,7 +59,7 @@ Type CreateMethodHandleDelegateType(java.lang.invoke.MethodType type) var ret = RuntimeJavaType.FromClass(type.returnType()); ret.Finish(); - return CreateMethodHandleDelegateType(args, ret).AsReflection(); + return CreateMethodHandleDelegateType(args, ret).GetUnderlyingType(); } static ITypeSymbol[] GetParameterTypes(IMethodBaseSymbol mb) @@ -194,7 +194,7 @@ public Container(T1 target, T2 value) if (!ReflectUtil.CanOwnDynamicMethod(owner)) owner = typeof(DynamicMethodBuilder); - dm = new DynamicMethod(name, mi.ReturnType.AsReflection(), paramTypes.AsReflection(), owner, true); + dm = new DynamicMethod(name, mi.ReturnType.GetUnderlyingType(), paramTypes.GetUnderlyingTypes(), owner, true); ilgen = context.CodeEmitterFactory.Create(dm); if (type.parameterCount() > MaxArity) @@ -348,7 +348,7 @@ internal static Delegate CreateMemberName(RuntimeContext context, RuntimeJavaMet FinishTypes(type); var tw = mw.DeclaringType; - var owner = tw.TypeAsBaseType.AsReflection(); + var owner = tw.TypeAsBaseType.GetUnderlyingType(); var dm = new DynamicMethodBuilder(context, "MemberName:" + mw.DeclaringType.Name + "::" + mw.Name + mw.Signature, type, null, mw.HasCallerID ? DynamicCallerIDProvider.Instance : null, null, owner, true); for (int i = 0, count = type.parameterCount(); i < count; i++) { @@ -516,8 +516,8 @@ internal Delegate CreateDelegate() //ilgen.DumpMethod(); ilgen.DoEmit(); return ValidateDelegate(firstArg == 0 - ? dm.CreateDelegate(delegateType.AsReflection()) - : dm.CreateDelegate(delegateType.AsReflection(), container == null ? firstBoundValue : Activator.CreateInstance(container.AsReflection(), firstBoundValue, secondBoundValue))); + ? dm.CreateDelegate(delegateType.GetUnderlyingType()) + : dm.CreateDelegate(delegateType.GetUnderlyingType(), container == null ? firstBoundValue : Activator.CreateInstance(container.GetUnderlyingType(), firstBoundValue, secondBoundValue))); } internal void BoxArgs(int start) @@ -644,7 +644,7 @@ internal T GetDelegateForInvokeExact(global::java.lang.invoke.MethodHandle mh if (mh._invokeExactDelegate == null) { type._invokeExactDynamicMethod ??= DynamicMethodBuilder.CreateInvokeExact(context, type); - mh._invokeExactDelegate = type._invokeExactDynamicMethod.CreateDelegate(GetDelegateTypeForInvokeExact(type).AsReflection(), mh); + mh._invokeExactDelegate = type._invokeExactDynamicMethod.CreateDelegate(GetDelegateTypeForInvokeExact(type).GetUnderlyingType(), mh); var del = mh._invokeExactDelegate as T; if (del != null) return del; diff --git a/src/IKVM.Runtime/ReflectUtil.cs b/src/IKVM.Runtime/ReflectUtil.cs index 69c23a0a99..7c88196d26 100644 --- a/src/IKVM.Runtime/ReflectUtil.cs +++ b/src/IKVM.Runtime/ReflectUtil.cs @@ -67,7 +67,7 @@ internal static bool IsDynamicAssembly(IAssemblySymbol asm) #if IMPORTER || EXPORTER return false; #else - return asm.AsReflection().IsDynamic; + return asm.GetUnderlyingAssembly().IsDynamic; #endif } @@ -77,7 +77,7 @@ internal static bool IsReflectionOnly(ITypeSymbol type) type = type.GetElementType(); var asm = type.Assembly; - if (asm != null && asm.AsReflection().ReflectionOnly) + if (asm != null && asm.GetUnderlyingAssembly().ReflectionOnly) return true; if (!type.IsGenericType || type.IsGenericTypeDefinition) diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index e8c275675d..9b2f65e229 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -487,11 +487,11 @@ void DoInitializeExports() { if (delegates == null) { - if (ReflectUtil.IsDynamicAssembly(assemblyLoader.Assembly) == false && assemblyLoader.Assembly.AsReflection().GetManifestResourceInfo("ikvm.exports") != null) + if (ReflectUtil.IsDynamicAssembly(assemblyLoader.Assembly) == false && assemblyLoader.Assembly.GetUnderlyingAssembly().GetManifestResourceInfo("ikvm.exports") != null) { var wildcardExports = new List(); - using (var stream = assemblyLoader.Assembly.AsReflection().GetManifestResourceStream("ikvm.exports")) + using (var stream = assemblyLoader.Assembly.GetUnderlyingAssembly().GetManifestResourceStream("ikvm.exports")) { var rdr = new BinaryReader(stream); var assemblyCount = rdr.ReadInt32(); @@ -847,7 +847,7 @@ static java.net.URL MakeResourceURL(IAssemblySymbol asm, string name) #if FIRST_PASS throw new NotImplementedException(); #else - return new java.io.File(Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, asm.AsReflection(), JVM.Properties.HomePath), name)).toURI().toURL(); + return new java.io.File(Path.Combine(VfsTable.GetAssemblyResourcesPath(JVM.Vfs.Context, asm.GetUnderlyingAssembly(), JVM.Properties.HomePath), name)).toURI().toURL(); #endif } @@ -857,7 +857,7 @@ static java.net.URL MakeResourceURL(IAssemblySymbol asm, string name) throw new NotImplementedException(); #else // cannot find resources in dynamic assembly - if (assemblyLoader.Assembly.AsReflection().IsDynamic) + if (assemblyLoader.Assembly.GetUnderlyingAssembly().IsDynamic) yield break; var found = false; @@ -873,14 +873,14 @@ static java.net.URL MakeResourceURL(IAssemblySymbol asm, string name) if (assemblyLoader.HasJavaModule == false) { // attempt to find an assembly resource with the exact name - if (unmangledName != "" && assemblyLoader.Assembly.AsReflection().GetManifestResourceInfo(unmangledName) != null) + if (unmangledName != "" && assemblyLoader.Assembly.GetUnderlyingAssembly().GetManifestResourceInfo(unmangledName) != null) { found = true; yield return MakeResourceURL(assemblyLoader.Assembly, unmangledName); } // the JavaResourceAttribute can be used to manufacture a named Java resource - foreach (var res in assemblyLoader.Assembly.AsReflection().GetCustomAttributes()) + foreach (var res in assemblyLoader.Assembly.GetUnderlyingAssembly().GetCustomAttributes()) { if (res.JavaName == unmangledName) { @@ -892,7 +892,7 @@ static java.net.URL MakeResourceURL(IAssemblySymbol asm, string name) // find an assembly resource with the managed resource name var name = JVM.MangleResourceName(unmangledName); - if (assemblyLoader.Assembly.AsReflection().GetManifestResourceInfo(name) != null) + if (assemblyLoader.Assembly.GetUnderlyingAssembly().GetManifestResourceInfo(name) != null) { found = true; yield return MakeResourceURL(assemblyLoader.Assembly, name); @@ -921,7 +921,7 @@ static java.net.URL MakeResourceURL(IAssemblySymbol asm, string name) yield return (java.net.URL)urls.nextElement(); } - if (loader.Assembly.AsReflection().GetManifestResourceInfo(name) != null) + if (loader.Assembly.GetUnderlyingAssembly().GetManifestResourceInfo(name) != null) { found = true; yield return MakeResourceURL(loader.Assembly, name); @@ -934,7 +934,7 @@ static java.net.URL MakeResourceURL(IAssemblySymbol asm, string name) { var tw = FindLoadedClass(unmangledName.Substring(0, unmangledName.Length - 6).Replace('/', '.')); if (tw != null && tw.ClassLoader == this && !tw.IsArray && !tw.IsDynamic) - yield return new java.io.File(Path.Combine(VfsTable.GetAssemblyClassesPath(JVM.Vfs.Context, assemblyLoader.Assembly.AsReflection(), JVM.Properties.HomePath), unmangledName)).toURI().toURL(); + yield return new java.io.File(Path.Combine(VfsTable.GetAssemblyClassesPath(JVM.Vfs.Context, assemblyLoader.Assembly.GetUnderlyingAssembly(), JVM.Properties.HomePath), unmangledName)).toURI().toURL(); } #endif } @@ -1070,7 +1070,7 @@ internal override java.lang.ClassLoader GetJavaClassLoader() internal virtual java.security.ProtectionDomain GetProtectionDomain() { if (protectionDomain == null) - Interlocked.CompareExchange(ref protectionDomain, new java.security.ProtectionDomain(assemblyLoader.Assembly.AsReflection()), null); + Interlocked.CompareExchange(ref protectionDomain, new java.security.ProtectionDomain(assemblyLoader.Assembly.GetUnderlyingAssembly()), null); return protectionDomain; } @@ -1129,7 +1129,7 @@ internal List> GetPackageInfo() var list = new List>(); foreach (var m in assemblyLoader.Assembly.GetModules(false)) { - var attr = m.AsReflection().GetCustomAttributes(); + var attr = m.GetUnderlyingModule().GetCustomAttributes(); foreach (var p in attr) list.Add(new KeyValuePair(p.jar, p.packages)); } @@ -1174,7 +1174,7 @@ Type GetCustomClassLoaderType() var attribs = assembly.GetCustomAttribute(Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName), false); if (attribs.HasValue) - return ((ITypeSymbol)attribs.Value.ConstructorArguments[0].Value).AsReflection(); + return ((ITypeSymbol)attribs.Value.ConstructorArguments[0].Value).GetUnderlyingType(); return null; } @@ -1301,7 +1301,7 @@ internal CustomClassLoaderCtorCaller(ConstructorInfo ctor, object classLoader, I public object run() { - ctor.Invoke(classLoader, [assembly.AsReflection()]); + ctor.Invoke(classLoader, [assembly.GetUnderlyingAssembly()]); return null; } } diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs index 1cbe1c18ff..f94982e0fb 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.FinishContext.cs @@ -737,7 +737,7 @@ internal ITypeSymbol FinishImpl() } #if !IMPORTER if (liveObjects != null) - context.Resolver.ResolveRuntimeType("IKVM.Runtime.LiveObjectHolder`1").GetField("values", BindingFlags.Static | BindingFlags.Public).AsReflection().SetValue(null, liveObjects.ToArray()); + context.Resolver.ResolveRuntimeType("IKVM.Runtime.LiveObjectHolder`1").GetField("values", BindingFlags.Static | BindingFlags.Public).GetUnderlyingField().SetValue(null, liveObjects.ToArray()); #endif } finally @@ -1593,7 +1593,7 @@ internal static class JniProxyBuilder static JniProxyBuilder() { mod = DynamicClassLoader.CreateJniProxyModuleBuilder(JVM.Context); - var cab = JVM.Context.Resolver.Symbols.CreateCustomAttribute(JVM.Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName).GetConstructor([]), []); + var cab = CustomAttribute.Create(JVM.Context.Resolver.ResolveRuntimeType(typeof(JavaModuleAttribute).FullName).GetConstructor([]), []); mod.SetCustomAttribute(cab); } @@ -2181,7 +2181,7 @@ internal IConstructorSymbolBuilder DefineThreadLocalType() int id = nestedTypeBuilders == null ? 0 : nestedTypeBuilders.Count; var tb = typeBuilder.DefineNestedType(NestedTypeName.ThreadLocal + id, TypeAttributes.NestedPrivate | TypeAttributes.Sealed, threadLocal.TypeAsBaseType); var fb = tb.DefineField("field", context.Types.Object, FieldAttributes.Private | FieldAttributes.Static); - fb.SetCustomAttribute(context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(ThreadStaticAttribute).FullName).GetConstructor([]), [])); + fb.SetCustomAttribute(CustomAttribute.Create(context.Resolver.ResolveCoreType(typeof(ThreadStaticAttribute).FullName).GetConstructor([]), [])); var mbGet = tb.DefineMethod("get", MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.Final, context.Types.Object, []); var ilgen = mbGet.GetILGenerator(); diff --git a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs index 21106db457..0d4ee8d9a7 100644 --- a/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs +++ b/src/IKVM.Runtime/RuntimeByteCodeJavaType.JavaTypeImpl.cs @@ -1104,10 +1104,7 @@ internal override IFieldSymbol LinkField(RuntimeJavaField fw) } if (fld.IsTransient) - { - var transientAttrib = wrapper.Context.Resolver.Symbols.CreateCustomAttribute(wrapper.Context.Resolver.ResolveCoreType(typeof(NonSerializedAttribute).FullName).GetConstructor([]), []); - field.SetCustomAttribute(transientAttrib); - } + field.SetCustomAttribute(CustomAttribute.Create(wrapper.Context.Resolver.ResolveCoreType(typeof(NonSerializedAttribute).FullName).GetConstructor([]), [])); #if IMPORTER { @@ -1264,10 +1261,7 @@ FinishedTypeImpl FinishCore() #if IMPORTER if (annotationBuilder != null) - { - var cab = wrapper.Context.Resolver.Symbols.CreateCustomAttribute(wrapper.Context.Resolver.ResolveRuntimeType(typeof(AnnotationAttributeAttribute).FullName).GetConstructor([wrapper.Context.Types.String]), [UnicodeUtil.EscapeInvalidSurrogates(annotationBuilder.AttributeTypeName)]); - typeBuilder.SetCustomAttribute(cab); - } + typeBuilder.SetCustomAttribute(CustomAttribute.Create(wrapper.Context.Resolver.ResolveRuntimeType(typeof(AnnotationAttributeAttribute).FullName).GetConstructor([wrapper.Context.Types.String]), [UnicodeUtil.EscapeInvalidSurrogates(annotationBuilder.AttributeTypeName)])); if (!wrapper.IsInterface && wrapper.IsMapUnsafeException) { @@ -1470,7 +1464,7 @@ internal void Link() if (o.classFile.Annotations != null) { - ICustomAttributeBuilder attributeUsageAttribute = null; + CustomAttribute? attributeUsageAttribute = null; bool hasAttributeUsageAttribute = false; foreach (object[] def in o.classFile.Annotations) { @@ -1523,7 +1517,9 @@ internal void Link() } } - attributeUsageAttribute = context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName).GetConstructor([context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName)]), [targets]); + attributeUsageAttribute = CustomAttribute.Create( + context.Resolver.ResolveCoreType(typeof(AttributeUsageAttribute).FullName).GetConstructor([context.Resolver.ResolveCoreType(typeof(AttributeTargets).FullName)]), + [targets]); } } } @@ -1542,7 +1538,7 @@ internal void Link() if (attributeUsageAttribute != null && !hasAttributeUsageAttribute) { - attributeTypeBuilder.SetCustomAttribute(attributeUsageAttribute); + attributeTypeBuilder.SetCustomAttribute(attributeUsageAttribute.Value); } } @@ -1839,12 +1835,12 @@ internal void Finish(JavaTypeImpl o) attributeTypeBuilder.Complete(); } - ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) + CustomAttribute MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { Link(); var ctor = defineConstructor != null ? defineConstructor : context.Resolver.ResolveRuntimeType("IKVM.Attributes.DynamicAnnotationAttribute").GetConstructor([context.Types.Object.MakeArrayType()]); - return context.Resolver.Symbols.CreateCustomAttribute(ctor, new object[] { AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation)) }); + return CustomAttribute.Create(ctor, [AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation))]); } internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) @@ -2851,12 +2847,10 @@ IMethodSymbolBuilder GenerateMethod(int index, ClassFile.Method m, ref bool setM ilgen.Emit(System.Reflection.Emit.OpCodes.Ret); ilgen.DoEmit(); } + #if IMPORTER if (classFile.Methods[index].AnnotationDefault != null) - { - var cab = wrapper.Context.Resolver.Symbols.CreateCustomAttribute(wrapper.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.AnnotationDefaultAttribute").GetConstructor([wrapper.Context.Types.Object]), [AnnotationDefaultAttribute.Escape(classFile.Methods[index].AnnotationDefault)]); - mb.SetCustomAttribute(cab); - } + mb.SetCustomAttribute(CustomAttribute.Create(wrapper.Context.Resolver.ResolveRuntimeType("IKVM.Attributes.AnnotationDefaultAttribute").GetConstructor([wrapper.Context.Types.Object]), [AnnotationDefaultAttribute.Escape(classFile.Methods[index].AnnotationDefault)])); #endif } diff --git a/src/IKVM.Runtime/RuntimeConstantJavaField.cs b/src/IKVM.Runtime/RuntimeConstantJavaField.cs index 8403202e46..bec2dd0fa8 100644 --- a/src/IKVM.Runtime/RuntimeConstantJavaField.cs +++ b/src/IKVM.Runtime/RuntimeConstantJavaField.cs @@ -141,7 +141,7 @@ protected override void EmitSetImpl(CodeEmitter ilgen) internal override object GetValue(object obj) { var field = GetField(); - return FieldTypeWrapper.IsPrimitive || field == null ? GetConstantValue() : field.AsReflection().GetValue(null); + return FieldTypeWrapper.IsPrimitive || field == null ? GetConstantValue() : field.GetUnderlyingField().GetValue(null); } internal override void SetValue(object obj, object value) diff --git a/src/IKVM.Runtime/RuntimeJavaField.cs b/src/IKVM.Runtime/RuntimeJavaField.cs index f36a6325c3..9b3398eeff 100644 --- a/src/IKVM.Runtime/RuntimeJavaField.cs +++ b/src/IKVM.Runtime/RuntimeJavaField.cs @@ -500,8 +500,8 @@ Delegate CreateUnsafeGetDelegate() FieldTypeWrapper.Finish(); ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, ft, [typeof(object)]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, ft, [typeof(object)]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -547,8 +547,8 @@ Delegate CreateUnsafeSetDelegate() FieldTypeWrapper.Finish(); ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, typeof(void), [typeof(object), ft]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, typeof(void), [typeof(object), ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -592,8 +592,8 @@ Delegate GetUnsafeVolatileGetDelegate() Delegate CreateUnsafeVolatileGetDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); - var dm = new DynamicMethod($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", ft, [typeof(object)], DeclaringType.TypeAsTBD.Module.AsReflection(), true); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); + var dm = new DynamicMethod($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", ft, [typeof(object)], DeclaringType.TypeAsTBD.Module.GetUnderlyingModule(), true); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -637,8 +637,8 @@ Delegate GetUnsafeVolatileSetDelegate() Delegate CreateUnsafeVolatileSetDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, typeof(void), [typeof(object), ft]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, typeof(void), [typeof(object), ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -685,8 +685,8 @@ Delegate GetUnsafeCompareAndSwapDelegate() Delegate CreateUnsafeCompareAndSwapDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.AsReflection() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.AsReflection(), true, typeof(bool), [typeof(object), ft, ft]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, typeof(bool), [typeof(object), ft, ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) diff --git a/src/IKVM.Runtime/RuntimeJavaMethod.cs b/src/IKVM.Runtime/RuntimeJavaMethod.cs index d416dc4516..066546208e 100644 --- a/src/IKVM.Runtime/RuntimeJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeJavaMethod.cs @@ -491,7 +491,7 @@ protected static object InvokeAndUnwrapException(IMethodBaseSymbol mb, object ob #else try { - return mb.AsReflection().Invoke(obj, args); + return mb.GetUnderlyingMethodBase().Invoke(obj, args); } catch (TargetInvocationException e) { diff --git a/src/IKVM.Runtime/RuntimeJavaType.cs b/src/IKVM.Runtime/RuntimeJavaType.cs index 7a5e44cf17..908f89d9f5 100644 --- a/src/IKVM.Runtime/RuntimeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeJavaType.cs @@ -254,9 +254,9 @@ private void LazyInitClass() { var type = GetClassLiteralType(); if (IsForbiddenTypeParameterType(type)) - clazz = new java.lang.Class(type.AsReflection()); + clazz = new java.lang.Class(type.GetUnderlyingRuntimeType()); else - clazz = (java.lang.Class)typeof(ClassLiteral<>).MakeGenericType(type.AsReflection()).GetProperty("Value").GetGetMethod().Invoke(null, []); + clazz = (java.lang.Class)typeof(ClassLiteral<>).MakeGenericType(type.GetUnderlyingRuntimeType()).GetProperty("Value").GetGetMethod().Invoke(null, []); } clazz.typeWrapper = this; @@ -1205,7 +1205,7 @@ internal void RunClassInit() { var t = IsRemapped ? TypeAsBaseType : TypeAsTBD; if (t != null) - System.Runtime.CompilerServices.RuntimeHelpers.RunClassConstructor(t.AsReflection().TypeHandle); + System.Runtime.CompilerServices.RuntimeHelpers.RunClassConstructor(t.GetUnderlyingRuntimeType().TypeHandle); } #endif @@ -1503,7 +1503,7 @@ internal virtual object GetAnnotationDefault(RuntimeJavaMethod mw) var mb = mw.GetMethod(); if (mb != null) { - var attr = mb.AsReflection().GetCustomAttribute(); + var attr = mb.GetUnderlyingMethodBase().GetCustomAttribute(); if (attr != null) return JVM.NewAnnotationElementValue(mw.DeclaringType.ClassLoader.GetJavaClassLoader(), mw.ReturnType.ClassObject, attr.Value); } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs index 3b965b99ae..b8bbd3e1e7 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeAccessStubJavaField.cs @@ -108,13 +108,13 @@ protected override void EmitSetImpl(CodeEmitter ilgen) internal override object GetValue(object obj) { // we can only be invoked on type 2 access stubs (because type 1 access stubs are HideFromReflection), so we know we have a field - return GetField().AsReflection().GetValue(obj); + return GetField().GetUnderlyingField().GetValue(obj); } internal override void SetValue(object obj, object value) { // we can only be invoked on type 2 access stubs (because type 1 access stubs are HideFromReflection), so we know we have a field - GetField().AsReflection().SetValue(obj, value); + GetField().GetUnderlyingField().SetValue(obj, value); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs index db1e751010..cd880c2611 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.GhostJavaType.cs @@ -57,12 +57,12 @@ internal GhostJavaType(RuntimeContext context, string name, ITypeSymbol type) : internal override object GhostWrap(object obj) { - return type.GetMethod("Cast").AsReflection().Invoke(null, [obj]); + return type.GetMethod("Cast").GetUnderlyingMethod().Invoke(null, [obj]); } internal override object GhostUnwrap(object obj) { - return type.GetMethod("ToObject").AsReflection().Invoke(obj, []); + return type.GetMethod("ToObject").GetUnderlyingMethod().Invoke(obj, []); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs index dc6311ad04..87eff23723 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.RemappedJavaMethod.cs @@ -149,7 +149,7 @@ internal override object CreateInstance(object[] args) internal override object InvokeNonvirtualRemapped(object obj, object[] args) { var mi = mbNonvirtualHelper ?? mbHelper; - return mi.AsReflection().Invoke(null, ArrayUtil.Concat(obj, args)); + return mi.GetUnderlyingMethod().Invoke(null, ArrayUtil.Concat(obj, args)); } #endif // !IMPORTER && !FIRST_PASS && !EXPORTER diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index 73fa252736..94939dec1e 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -1115,7 +1115,7 @@ object[] CastArray(object[] l) internal override object[] GetDeclaredAnnotations() { - return CastArray(type.AsReflection().GetCustomAttributes(false)); + return CastArray(type.GetUnderlyingType().GetCustomAttributes(false)); } internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) @@ -1127,7 +1127,7 @@ internal override object[] GetMethodAnnotations(RuntimeJavaMethod mw) return null; } - return CastArray(mb.AsReflection().GetCustomAttributes(false)); + return CastArray(mb.GetUnderlyingMethodBase().GetCustomAttributes(false)); } internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) @@ -1150,7 +1150,7 @@ internal override object[][] GetParameterAnnotations(RuntimeJavaMethod mw) var attribs = new object[parameters.Length - skip - skipEnd][]; for (int i = skip; i < parameters.Length - skipEnd; i++) - attribs[i - skip] = CastArray(parameters[i].AsReflection().GetCustomAttributes(false)); + attribs[i - skip] = CastArray(parameters[i].GetUnderlyingParameter().GetCustomAttributes(false)); return attribs; } @@ -1159,10 +1159,10 @@ internal override object[] GetFieldAnnotations(RuntimeJavaField fw) { var field = fw.GetField(); if (field != null) - return CastArray(field.AsReflection().GetCustomAttributes(false)); + return CastArray(field.GetUnderlyingField().GetCustomAttributes(false)); if (fw is RuntimeManagedByteCodePropertyJavaField prop) - return CastArray(prop.GetProperty().AsReflection().GetCustomAttributes(false)); + return CastArray(prop.GetProperty().GetUnderlyingProperty().GetCustomAttributes(false)); return Array.Empty(); } @@ -1186,9 +1186,9 @@ internal CompiledAnnotation(RuntimeContext context, ITypeSymbol type) constructor = type.GetConstructor([context.Types.Object.MakeArrayType()]); } - private ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) + private CustomAttribute MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { - return context.Resolver.Symbols.CreateCustomAttribute(constructor, [AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation))]); + return CustomAttribute.Create(constructor, [AnnotationDefaultAttribute.Escape(QualifyClassNames(loader, annotation))]); } internal override void Apply(RuntimeClassLoader loader, ITypeSymbolBuilder tb, object annotation) @@ -1274,7 +1274,7 @@ internal override int GetSourceLineNumber(IMethodBaseSymbol mb, int ilOffset) { var attr = type.GetCustomAttribute(Context.Resolver.GetSymbol(typeof(LineNumberTableAttribute))); if (attr.HasValue && attr.Value.Constructor != null) - return ((LineNumberTableAttribute)attr.Value.Constructor.AsReflection().Invoke(attr.Value.ConstructorArguments.Cast().ToArray())).GetLineNumber(ilOffset); + return ((LineNumberTableAttribute)attr.Value.Constructor.GetUnderlyingConstructor().Invoke(attr.Value.ConstructorArguments.Cast().ToArray())).GetLineNumber(ilOffset); return -1; } diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs b/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs index 0f1222e26c..09f5dba60c 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodePropertyJavaField.cs @@ -104,7 +104,7 @@ internal override object GetValue(object obj) if (getter == null) throw new java.lang.NoSuchMethodError(); - return getter.AsReflection().Invoke(obj, []); + return getter.GetUnderlyingMethod().Invoke(obj, []); } internal override void SetValue(object obj, object value) @@ -113,7 +113,7 @@ internal override void SetValue(object obj, object value) if (setter == null) throw new java.lang.NoSuchMethodError(); - setter.AsReflection().Invoke(obj, new object[] { value }); + setter.GetUnderlyingMethod().Invoke(obj, new object[] { value }); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs index b762ef1011..d17358d079 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs @@ -376,7 +376,7 @@ internal override object GetAnnotationDefault(RuntimeJavaMethod mw) } else if (mw.ReturnType.IsArray) { - return Array.CreateInstance(mw.ReturnType.TypeAsArrayType.AsReflection(), 0); + return Array.CreateInstance(mw.ReturnType.TypeAsArrayType.GetUnderlyingType(), 0); } } @@ -491,7 +491,7 @@ internal AttributeAnnotation(ITypeSymbol type) this.type = type; } - ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) + CustomAttribute MakeCustomAttributeBuilder(RuntimeClassLoader loader, object annotation) { object[] arr = (object[])annotation; object ctorArg = null; @@ -534,7 +534,7 @@ ICustomAttributeBuilder MakeCustomAttributeBuilder(RuntimeClassLoader loader, ob // TODO required argument is missing } - return loader.Context.Resolver.Symbols.CreateCustomAttribute( + return CustomAttribute.Create( ctorArg == null ? defCtor : singleOneArgCtor, ctorArg == null ? [] : new object[] { ctorArg }, properties.ToArray(), @@ -583,11 +583,11 @@ internal override void Apply(RuntimeClassLoader loader, IParameterSymbolBuilder internal override void Apply(RuntimeClassLoader loader, IAssemblySymbolBuilder assemblyBuilder, object annotation) { #if IMPORTER - var ab = assemblyBuilder.AsReflection(); + var ab = assemblyBuilder.GetUnderlyingAssemblyBuilder(); if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Runtime.CompilerServices.TypeForwardedToAttribute).FullName)) { - ab.__AddTypeForwarder((Type)ConvertValue(loader, loader.Context.Types.Type, ((object[])annotation)[3])); + assemblyBuilder.AddTypeForwarder((ITypeSymbol)ConvertValue(loader, loader.Context.Types.Type, ((object[])annotation)[3])); } else if (type == loader.Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyVersionAttribute).FullName)) { diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs index 709b007046..35eba0393a 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs @@ -98,7 +98,7 @@ internal EnumJavaField(RuntimeJavaType tw, string name, int ordinal) : internal override object GetValue(object obj) { if (val == null) - System.Threading.Interlocked.CompareExchange(ref val, Activator.CreateInstance(this.DeclaringType.TypeAsTBD.AsReflection(), BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new object[] { this.Name, ordinal }, null), null); + System.Threading.Interlocked.CompareExchange(ref val, Activator.CreateInstance(this.DeclaringType.TypeAsTBD.GetUnderlyingType(), BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new object[] { this.Name, ordinal }, null), null); return val; } @@ -147,7 +147,7 @@ internal EnumValuesJavaMethod(RuntimeJavaType declaringType) : internal override object Invoke(object obj, object[] args) { var values = DeclaringType.GetFields(); - var array = (object[])Array.CreateInstance(DeclaringType.TypeAsArrayType.AsReflection(), values.Length); + var array = (object[])Array.CreateInstance(DeclaringType.TypeAsArrayType.GetUnderlyingType(), values.Length); for (int i = 0; i < values.Length; i++) array[i] = values[i].GetValue(null); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs index b412e502e8..d706a90314 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs @@ -67,7 +67,7 @@ internal override void EmitCall(CodeEmitter ilgen) internal override object Invoke(object obj, object[] args) { - return Enum.ToObject(DeclaringType.TypeAsTBD.AsReflection(), args[0]); + return Enum.ToObject(DeclaringType.TypeAsTBD.GetUnderlyingType(), args[0]); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs index 730a30941b..6de44f611b 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs @@ -65,7 +65,7 @@ internal override void EmitCall(CodeEmitter ilgen) internal override object CreateInstance(object[] args) { - return Activator.CreateInstance(DeclaringType.TypeAsTBD.AsReflection()); + return Activator.CreateInstance(DeclaringType.TypeAsTBD.GetUnderlyingType()); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.cs index 7b20b06a86..a26fefa205 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.cs @@ -270,7 +270,7 @@ internal static bool IsAllowedOutside(ITypeSymbol type) // since the reflection implementation lives inside this assembly, all internal members would // be accessible through Java reflection. #if !FIRST_PASS && !IMPORTER && !EXPORTER - if (type.Assembly.AsReflection() == typeof(RuntimeManagedJavaType).Assembly) + if (type.Assembly.GetUnderlyingAssembly() == typeof(RuntimeManagedJavaType).Assembly) return false; #endif diff --git a/src/IKVM.Runtime/RuntimeSimpleJavaField.cs b/src/IKVM.Runtime/RuntimeSimpleJavaField.cs index 4045ad61d3..72d41974f6 100644 --- a/src/IKVM.Runtime/RuntimeSimpleJavaField.cs +++ b/src/IKVM.Runtime/RuntimeSimpleJavaField.cs @@ -55,12 +55,12 @@ internal RuntimeSimpleJavaField(RuntimeJavaType declaringType, RuntimeJavaType f internal override object GetValue(object obj) { - return GetField().AsReflection().GetValue(obj); + return GetField().GetUnderlyingRuntimeField().GetValue(obj); } internal override void SetValue(object obj, object value) { - GetField().AsReflection().SetValue(obj, value); + GetField().GetUnderlyingRuntimeField().SetValue(obj, value); } #endif diff --git a/src/IKVM.Runtime/Serialization.cs b/src/IKVM.Runtime/Serialization.cs index a2dfffbfbb..22c90df640 100644 --- a/src/IKVM.Runtime/Serialization.cs +++ b/src/IKVM.Runtime/Serialization.cs @@ -43,8 +43,8 @@ class Serialization readonly RuntimeContext context; - ICustomAttributeBuilder serializableAttribute; - ICustomAttributeBuilder securityCriticalAttribute; + CustomAttribute? serializableAttribute; + CustomAttribute? securityCriticalAttribute; RuntimeJavaType typeOfISerializable; RuntimeJavaType typeofIObjectreference; RuntimeJavaType typeOfExternalizable; @@ -58,9 +58,9 @@ public Serialization(RuntimeContext context) this.context = context ?? throw new ArgumentNullException(nameof(context)); } - ICustomAttributeBuilder SerializableAttribute => serializableAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(SerializableAttribute).FullName).GetConstructor([]), []); + CustomAttribute SerializableAttribute => serializableAttribute ??= CustomAttribute.Create(context.Resolver.ResolveCoreType(typeof(SerializableAttribute).FullName).GetConstructor([]), []); - ICustomAttributeBuilder SecurityCriticalAttribute => securityCriticalAttribute ??= context.Resolver.Symbols.CreateCustomAttribute(context.Resolver.ResolveCoreType(typeof(SecurityCriticalAttribute).FullName).GetConstructor([]), []); + CustomAttribute SecurityCriticalAttribute => securityCriticalAttribute ??= CustomAttribute.Create(context.Resolver.ResolveCoreType(typeof(SecurityCriticalAttribute).FullName).GetConstructor([]), []); RuntimeJavaType TypeOfISerializable => typeOfISerializable ??= context.ClassLoaderFactory.GetJavaTypeFromType(context.Resolver.ResolveCoreType(typeof(ISerializable).FullName)); diff --git a/src/IKVM.Runtime/SymbolExtensions.cs b/src/IKVM.Runtime/SymbolExtensions.cs index e98aa76975..08cf48b7d2 100644 --- a/src/IKVM.Runtime/SymbolExtensions.cs +++ b/src/IKVM.Runtime/SymbolExtensions.cs @@ -23,7 +23,7 @@ namespace IKVM.Runtime static class SymbolExtensions { - public static Assembly AsReflection(this IAssemblySymbol symbol) + public static Assembly GetUnderlyingAssembly(this IAssemblySymbol symbol) { if (symbol == null) return null; @@ -35,7 +35,7 @@ public static Assembly AsReflection(this IAssemblySymbol symbol) #endif } - public static Module AsReflection(this IModuleSymbol symbol) + public static Module GetUnderlyingModule(this IModuleSymbol symbol) { if (symbol == null) return null; @@ -47,7 +47,7 @@ public static Module AsReflection(this IModuleSymbol symbol) #endif } - public static Type AsReflection(this ITypeSymbol symbol) + public static Type GetUnderlyingType(this ITypeSymbol symbol) { if (symbol == null) return null; @@ -59,19 +59,31 @@ public static Type AsReflection(this ITypeSymbol symbol) #endif } - public static Type[] AsReflection(this ITypeSymbol[] symbols) + public static Type GetUnderlyingRuntimeType(this ITypeSymbol symbol) + { + if (symbol == null) + return null; + +#if IMPORTER || EXPORTER + throw new NotSupportedException(); +#else + return ((IReflectionTypeSymbol)symbol).UnderlyingRuntimeType; +#endif + } + + public static Type[] GetUnderlyingTypes(this ITypeSymbol[] symbols) { if (symbols == null) return null; var a = new Type[symbols.Length]; for (int i = 0; i < symbols.Length; i++) - a[i] = AsReflection(symbols[i]); + a[i] = GetUnderlyingType(symbols[i]); return a; } - public static MethodBase AsReflection(this IMethodBaseSymbol symbol) + public static MethodBase GetUnderlyingMethodBase(this IMethodBaseSymbol symbol) { if (symbol == null) return null; @@ -83,7 +95,7 @@ public static MethodBase AsReflection(this IMethodBaseSymbol symbol) #endif } - public static ConstructorInfo AsReflection(this IConstructorSymbol symbol) + public static ConstructorInfo GetUnderlyingConstructor(this IConstructorSymbol symbol) { if (symbol == null) return null; @@ -95,7 +107,7 @@ public static ConstructorInfo AsReflection(this IConstructorSymbol symbol) #endif } - public static MethodInfo AsReflection(this IMethodSymbol symbol) + public static MethodInfo GetUnderlyingMethod(this IMethodSymbol symbol) { if (symbol == null) return null; @@ -107,7 +119,7 @@ public static MethodInfo AsReflection(this IMethodSymbol symbol) #endif } - public static ParameterInfo AsReflection(this IParameterSymbol symbol) + public static ParameterInfo GetUnderlyingParameter(this IParameterSymbol symbol) { if (symbol == null) return null; @@ -119,7 +131,7 @@ public static ParameterInfo AsReflection(this IParameterSymbol symbol) #endif } - public static FieldInfo AsReflection(this IFieldSymbol symbol) + public static FieldInfo GetUnderlyingField(this IFieldSymbol symbol) { if (symbol == null) return null; @@ -131,19 +143,31 @@ public static FieldInfo AsReflection(this IFieldSymbol symbol) #endif } - public static FieldInfo[] AsReflection(this IFieldSymbol[] symbols) + public static FieldInfo GetUnderlyingRuntimeField(this IFieldSymbol symbol) + { + if (symbol == null) + return null; + +#if IMPORTER || EXPORTER + throw new NotSupportedException(); +#else + return ((IReflectionFieldSymbol)symbol).UnderlyingRuntimeField; +#endif + } + + public static FieldInfo[] GetUnderlyingFields(this IFieldSymbol[] symbols) { if (symbols == null) return null; var a = new FieldInfo[symbols.Length]; for (int i = 0; i < symbols.Length; i++) - a[i] = AsReflection(symbols[i]); + a[i] = GetUnderlyingField(symbols[i]); return a; } - public static PropertyInfo AsReflection(this IPropertySymbol symbol) + public static PropertyInfo GetUnderlyingProperty(this IPropertySymbol symbol) { if (symbol == null) return null; @@ -155,19 +179,19 @@ public static PropertyInfo AsReflection(this IPropertySymbol symbol) #endif } - public static PropertyInfo[] AsReflection(this IPropertySymbol[] symbols) + public static PropertyInfo[] GetUnderlyingProperties(this IPropertySymbol[] symbols) { if (symbols == null) return null; var a = new PropertyInfo[symbols.Length]; for (int i = 0; i < symbols.Length; i++) - a[i] = AsReflection(symbols[i]); + a[i] = GetUnderlyingProperty(symbols[i]); return a; } - public static AssemblyBuilder AsReflection(this IAssemblySymbolBuilder builder) + public static AssemblyBuilder GetUnderlyingAssemblyBuilder(this IAssemblySymbolBuilder builder) { if (builder == null) return null; @@ -179,7 +203,7 @@ public static AssemblyBuilder AsReflection(this IAssemblySymbolBuilder builder) #endif } - public static ModuleBuilder AsReflection(this IModuleSymbolBuilder builder) + public static ModuleBuilder GetUnderlyingModuleBuilder(this IModuleSymbolBuilder builder) { if (builder == null) return null; @@ -191,7 +215,7 @@ public static ModuleBuilder AsReflection(this IModuleSymbolBuilder builder) #endif } - public static TypeBuilder AsReflection(this ITypeSymbolBuilder builder) + public static TypeBuilder GetUnderlyingTypeBuilder(this ITypeSymbolBuilder builder) { if (builder == null) return null; @@ -203,7 +227,7 @@ public static TypeBuilder AsReflection(this ITypeSymbolBuilder builder) #endif } - public static ConstructorBuilder AsReflection(this IConstructorSymbolBuilder builder) + public static ConstructorBuilder GetUnderlyingConstructorBuilder(this IConstructorSymbolBuilder builder) { if (builder == null) return null; @@ -215,7 +239,7 @@ public static ConstructorBuilder AsReflection(this IConstructorSymbolBuilder bui #endif } - public static MethodBuilder AsReflection(this IMethodSymbolBuilder builder) + public static MethodBuilder GetUnderlyingMethodBuilder(this IMethodSymbolBuilder builder) { if (builder == null) return null; @@ -227,7 +251,7 @@ public static MethodBuilder AsReflection(this IMethodSymbolBuilder builder) #endif } - public static FieldBuilder AsReflection(this IFieldSymbolBuilder builder) + public static FieldBuilder GetUnderlyingFieldBuilder(this IFieldSymbolBuilder builder) { if (builder == null) return null; diff --git a/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs b/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs index 355ca04473..bfee5d1391 100644 --- a/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs +++ b/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs @@ -115,7 +115,7 @@ internal BailoutException(Bailout reason, object data) var paramTypes = MethodHandleUtil.GetParameterTypes(context.Types.Object.MakeArrayType(), mi); // HACK the code we generate is not verifiable (known issue: locals aren't typed correctly), so we stick the DynamicMethod into mscorlib (a security critical assembly) - this.dm = new DynamicMethod(lambdaForm.debugName, mi.ReturnType.AsReflection(), paramTypes.AsReflection(), typeof(object).Module, true); + this.dm = new DynamicMethod(lambdaForm.debugName, mi.ReturnType.GetUnderlyingType(), paramTypes.GetUnderlyingTypes(), typeof(object).Module, true); this.ilgen = context.CodeEmitterFactory.Create(this.dm); if (invokerType.parameterCount() > MethodHandleUtil.MaxArity) { @@ -439,7 +439,7 @@ private Delegate generateCustomizedCodeBytes() emitReturn(onStack); ilgen.DoEmit(); - return dm.CreateDelegate(delegateType.AsReflection(), constants.ToArray()); + return dm.CreateDelegate(delegateType.GetUnderlyingType(), constants.ToArray()); } void emitArrayLoad(Name name) diff --git a/src/IKVM.Tools.Importer/ImportClassLoader.cs b/src/IKVM.Tools.Importer/ImportClassLoader.cs index 7e321787bc..81e9b716bd 100644 --- a/src/IKVM.Tools.Importer/ImportClassLoader.cs +++ b/src/IKVM.Tools.Importer/ImportClassLoader.cs @@ -516,7 +516,7 @@ void SetMain(RuntimeJavaType type, IKVM.CoreLib.Symbols.Emit.PEFileKinds target, // global main method decorated with appropriate apartment type var mainMethodProxy = GetTypeWrapperFactory().ModuleBuilder.DefineGlobalMethod("Main", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static, Context.Types.Int32, [Context.Types.String.MakeArrayType()]); if (apartmentAttributeType != null) - mainMethodProxy.SetCustomAttribute(Context.Resolver.Symbols.CreateCustomAttribute(apartmentAttributeType.GetConstructor([]), [])); + mainMethodProxy.SetCustomAttribute(CustomAttribute.Create(apartmentAttributeType.GetConstructor([]), [])); var ilgen = Context.CodeEmitterFactory.Create(mainMethodProxy); @@ -605,7 +605,7 @@ void Save() foreach (object[] args in packages.ToArray()) { args[1] = UnicodeUtil.EscapeInvalidSurrogates((string[])args[1]); - mb.SetCustomAttribute(Context.Resolver.Symbols.CreateCustomAttribute(packageListAttributeCtor, args)); + mb.SetCustomAttribute(CustomAttribute.Create(packageListAttributeCtor, args)); } // We can't add the resource when we're a module, because a multi-module assembly has a single resource namespace // and since you cannot combine -target:module with -sharedclassloader we don't need an export map @@ -672,13 +672,11 @@ void AddJavaModuleAttribute(IModuleSymbolBuilder mb) } list = UnicodeUtil.EscapeInvalidSurrogates(list); - var cab = Context.Resolver.Symbols.CreateCustomAttribute(typeofJavaModuleAttribute.GetConstructor([Context.Types.String.MakeArrayType()]), [list], propInfos, propValues); - mb.SetCustomAttribute(cab); + mb.SetCustomAttribute(CustomAttribute.Create(typeofJavaModuleAttribute.GetConstructor([Context.Types.String.MakeArrayType()]), [list], propInfos, propValues)); } else { - var cab = Context.Resolver.Symbols.CreateCustomAttribute(typeofJavaModuleAttribute.GetConstructor([]), [], propInfos, propValues); - mb.SetCustomAttribute(cab); + mb.SetCustomAttribute(CustomAttribute.Create(typeofJavaModuleAttribute.GetConstructor([]), [], propInfos, propValues)); } } @@ -1490,7 +1488,7 @@ internal override IMethodBaseSymbol DoLink() DeclaringType.Context.AttributeHelper.SetModifiers(mbHelper, (Modifiers)m.Modifiers, false); DeclaringType.Context.AttributeHelper.SetNameSig(mbHelper, m.Name, m.Sig); AddDeclaredExceptions(DeclaringType.Context, mbHelper, m.Throws); - mbHelper.SetCustomAttribute(DeclaringType.Context.Resolver.Symbols.CreateCustomAttribute(DeclaringType.Context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([DeclaringType.Context.Types.String]), ["This function will be removed from future versions. Please use extension methods from ikvm.extensions namespace instead."])); + mbHelper.SetCustomAttribute(CustomAttribute.Create(DeclaringType.Context.Resolver.ResolveCoreType(typeof(ObsoleteAttribute).FullName).GetConstructor([DeclaringType.Context.Types.String]), ["This function will be removed from future versions. Please use extension methods from ikvm.extensions namespace instead."])); } return mbCore; } @@ -3011,10 +3009,7 @@ int CompilePass3() // configure Win32 file version if (state.fileversion != null) - { - var filever = Context.Resolver.Symbols.CreateCustomAttribute(Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyFileVersionAttribute).FullName).GetConstructor([Context.Types.String]), [state.fileversion]); - assemblyBuilder.SetCustomAttribute(filever); - } + assemblyBuilder.SetCustomAttribute(CustomAttribute.Create(Context.Resolver.ResolveCoreType(typeof(System.Reflection.AssemblyFileVersionAttribute).FullName).GetConstructor([Context.Types.String]), [state.fileversion])); // apply assembly annotations if (state.assemblyAttributeAnnotations != null) From b74376789c3961f06cd353684f66e3227d767eab Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 18 Oct 2024 15:56:37 -0500 Subject: [PATCH 45/59] Fix. --- .../Reflection/ReflectionSymbolTests.cs | 19 ++ .../Reflection/ReflectionExtensions.cs | 118 +++++++- .../Emit/ReflectionMethodSymbolBuilder.cs | 2 +- .../ReflectionGenericSpecTypeSymbol.cs | 280 +++++++++++++++++- .../Reflection/ReflectionMethodBaseSymbol.cs | 44 +-- .../Reflection/ReflectionMethodSymbol.cs | 88 +++++- .../Reflection/ReflectionMethodTable.cs | 4 +- .../Reflection/ReflectionParameterSpecInfo.cs | 51 ++++ .../Reflection/ReflectionTypeSpecSymbol.cs | 3 + .../Symbols/Reflection/ReflectionUtil.cs | 35 +++ .../java/lang/invoke/MethodHandleNatives.cs | 2 +- src/IKVM.Runtime/MethodHandleUtil.compiler.cs | 3 +- .../MethodHandleUtil.jniexport.cs | 2 +- 13 files changed, 613 insertions(+), 38 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index 31e4ecaea2..f12186725c 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -490,6 +490,25 @@ public void CanGetMethodsFromTypeBuilder() incompleteMethod.Should().BeSameAs(method); } + /// + /// Generics closed over a type builder need to be handled specially. + /// + [TestMethod] + public void CanCreateRuntimeGenericTypeOfTypeBuilder() + { + var c = new ReflectionSymbolContext(); + var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); + var m = a.DefineModule("DynamicModule"); + var type = m.DefineType("DynamicType"); + var funcType = c.GetOrCreateTypeSymbol(typeof(Func<,>)); + var realFuncType = funcType.MakeGenericType(type, type); + var invokeMethod = realFuncType.GetMethod("Invoke"); + invokeMethod.Should().NotBeNull(); + invokeMethod.GetParameters().Should().HaveCount(1); + invokeMethod.GetParameters()[0].ParameterType.Should().BeSameAs(type); + invokeMethod.ReturnType.Should().BeSameAs(type); + } + } } diff --git a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs index ee2c0b7b98..b7966e9d05 100644 --- a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs +++ b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs @@ -11,11 +11,19 @@ namespace IKVM.CoreLib.Reflection static class ReflectionExtensions { + static readonly ParameterExpression _constructorInfoParameter = Expression.Parameter(typeof(ConstructorInfo), "p"); + static readonly ParameterExpression _methodInfoParameter = Expression.Parameter(typeof(MethodInfo), "p"); + static readonly ParameterExpression _fieldInfoParameter = Expression.Parameter(typeof(FieldInfo), "p"); + static readonly ParameterExpression _assemblyBuilderRuntimeAssemblyParameter = Expression.Parameter(typeof(AssemblyBuilder), "p"); static readonly ParameterExpression _propertyBuilderParameter = Expression.Parameter(typeof(PropertyBuilder), "p"); static readonly ParameterExpression _eventBuilderParameter = Expression.Parameter(typeof(EventBuilder), "p"); static readonly ParameterExpression _parameterBuilderParameter = Expression.Parameter(typeof(ParameterBuilder), "p"); + static readonly Type _constructorOnTypeBuilderInstantiationType = typeof(TypeBuilder).Assembly.GetType("System.Reflection.Emit.ConstructorOnTypeBuilderInstantiation", true)!; + static readonly Type _methodOnTypeBuilderInstantiationType = typeof(TypeBuilder).Assembly.GetType("System.Reflection.Emit.MethodOnTypeBuilderInstantiation", true)!; + static readonly Type _fieldOnTypeBuilderInstantiationType = typeof(TypeBuilder).Assembly.GetType("System.Reflection.Emit.FieldOnTypeBuilderInstantiation", true)!; + #if NET #if NET8_0_OR_GREATER @@ -25,6 +33,27 @@ static class ReflectionExtensions static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.RuntimeEventBuilder", true)!; static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.RuntimeParameterBuilder", true)!; + static readonly Func _getConstructorOnTypeBuilderInstantiationConstructorFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_constructorInfoParameter, _constructorOnTypeBuilderInstantiationType), + _constructorOnTypeBuilderInstantiationType.GetField("_ctor", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _constructorInfoParameter) + .Compile(); + + static readonly Func _getMethodOnTypeBuilderInstantiationMethodFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_methodInfoParameter, _methodOnTypeBuilderInstantiationType), + _methodOnTypeBuilderInstantiationType.GetField("_method", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _methodInfoParameter) + .Compile(); + + static readonly Func _getFieldOnTypeBuilderInstantiationFieldFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_fieldInfoParameter, _fieldOnTypeBuilderInstantiationType), + _fieldOnTypeBuilderInstantiationType.GetField("_field", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _fieldInfoParameter) + .Compile(); + #else static readonly Type _assemblyBuilderType = typeof(AssemblyBuilder).Assembly.GetType("System.Reflection.Emit.AssemblyBuilder", true)!; @@ -32,6 +61,27 @@ static class ReflectionExtensions static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.EventBuilder", true)!; static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.ParameterBuilder", true)!; + static readonly Func _getConstructorOnTypeBuilderInstantiationConstructorFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_constructorInfoParameter, _constructorOnTypeBuilderInstantiationType), + _constructorOnTypeBuilderInstantiationType.GetField("m_ctor", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _constructorInfoParameter) + .Compile(); + + static readonly Func _getMethodOnTypeBuilderInstantiationMethodFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_methodInfoParameter, _methodOnTypeBuilderInstantiationType), + _methodOnTypeBuilderInstantiationType.GetField("m_method", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _methodInfoParameter) + .Compile(); + + static readonly Func _getFieldOnTypeBuilderInstantiationFieldFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_fieldInfoParameter, _fieldOnTypeBuilderInstantiationType), + _fieldOnTypeBuilderInstantiationType.GetField("m_field", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _fieldInfoParameter) + .Compile(); + #endif static readonly Func _getAssemblyBuilderRuntimeAssemblyFunc = Expression.Lambda>( @@ -75,6 +125,27 @@ static class ReflectionExtensions static readonly Type _eventBuilderType = typeof(EventBuilder).Assembly.GetType("System.Reflection.Emit.EventBuilder", true)!; static readonly Type _parameterBuilderType = typeof(ParameterBuilder).Assembly.GetType("System.Reflection.Emit.ParameterBuilder", true)!; + static readonly Func _getConstructorOnTypeBuilderInstantiationConstructorFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_constructorInfoParameter, _constructorOnTypeBuilderInstantiationType), + _constructorOnTypeBuilderInstantiationType.GetField("m_ctor", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _constructorInfoParameter) + .Compile(); + + static readonly Func _getMethodOnTypeBuilderInstantiationMethodFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_methodInfoParameter, _methodOnTypeBuilderInstantiationType), + _methodOnTypeBuilderInstantiationType.GetField("m_method", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _methodInfoParameter) + .Compile(); + + static readonly Func _getFieldOnTypeBuilderInstantiationFieldFunc = Expression.Lambda>( + Expression.Field( + Expression.ConvertChecked(_fieldInfoParameter, _fieldOnTypeBuilderInstantiationType), + _fieldOnTypeBuilderInstantiationType.GetField("m_field", BindingFlags.NonPublic | BindingFlags.Instance) ?? throw new InvalidOperationException()), + _fieldInfoParameter) + .Compile(); + static readonly Func _getAssemblyBuilderRuntimeAssemblyFunc = Expression.Lambda>( Expression.Call( Expression.ConvertChecked(_assemblyBuilderRuntimeAssemblyParameter, _assemblyBuilderType), @@ -121,6 +192,11 @@ static class ReflectionExtensions _eventBuilderParameter) .Compile(); + /// + /// Gets the type. + /// + public static Type MethodOnTypeBuilderInstantiationType => _methodOnTypeBuilderInstantiationType; + /// /// Gets the metadata token for the specified . /// @@ -212,6 +288,15 @@ public static int GetMetadataTokenSafe(this FieldInfo field) } #endif +#if NET8_0_OR_GREATER || NETFRAMEWORK + // field is instance of FieldOnTypeBuilderInstantiation + if (_fieldOnTypeBuilderInstantiationType.IsInstanceOfType(field)) + { + var f = _getFieldOnTypeBuilderInstantiationFieldFunc(field); + return f.GetMetadataTokenSafe(); + } +#endif + return field.GetMetadataToken(); } @@ -275,6 +360,15 @@ public static int GetMetadataTokenSafe(this ConstructorInfo ctor) } #endif +#if NET8_0_OR_GREATER || NETFRAMEWORK + // ctor is instance of ConstructorOnTypeBuilderInstantiation + if (_constructorOnTypeBuilderInstantiationType.IsInstanceOfType(ctor)) + { + var c = _getConstructorOnTypeBuilderInstantiationConstructorFunc(ctor); + return c.GetMetadataTokenSafe(); + } +#endif + return ctor.GetMetadataToken(); } @@ -306,17 +400,35 @@ public static int GetMetadataTokenSafe(this MethodInfo method) } #endif +#if NET8_0_OR_GREATER || NETFRAMEWORK + // method is instance of MethodOnTypeBuilderInstantiation + if (_methodOnTypeBuilderInstantiationType.IsInstanceOfType(method)) + { + var m = _getMethodOnTypeBuilderInstantiationMethodFunc(method); + return m.GetMetadataTokenSafe(); + } +#endif + +#if NET6_0 + // method is instance of MethodOnTypeBuilderInstantiation + if (_methodOnTypeBuilderInstantiationType.IsInstanceOfType(method)) + { + var m = _getMethodOnTypeBuilderInstantiationMethodFunc(method); + return m.GetMetadataTokenSafe(); + } +#endif + return method.GetMetadataToken(); } /// /// Gets the metadata row number for the specified . /// - /// + /// /// - public static int GetMetadataTokenRowNumberSafe(this MethodInfo ctor) + public static int GetMetadataTokenRowNumberSafe(this MethodInfo method) { - return MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(ctor.GetMetadataTokenSafe())); + return MetadataTokens.GetRowNumber(MetadataTokens.MethodDefinitionHandle(method.GetMetadataTokenSafe())); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index 2dc1d53f13..58fdd779ba 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -30,7 +30,7 @@ class ReflectionMethodSymbolBuilder : ReflectionMethodSymbol, IReflectionMethodS public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType, MethodBuilder builder) : base(context, resolvingModule, resolvingType, builder) { - _builder = builder; + _builder = builder ?? throw new ArgumentNullException(nameof(builder)); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs index 3470c6b2fa..e369f1e108 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs @@ -1,5 +1,7 @@ using System; using System.Linq; +using System.Reflection; +using System.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -7,7 +9,33 @@ namespace IKVM.CoreLib.Symbols.Reflection class ReflectionGenericSpecTypeSymbol : ReflectionTypeSpecSymbol { - readonly IReflectionTypeSymbol[] genericTypeArguments; + /// + /// Returns true if the type or any generic type definition or generic arguments are type builders. That is, is this a TypeBuilderInstantiation instance. + /// + /// + /// + static bool ContainsTypeBuilder(Type type) + { + // find deepest element type + while (type.HasElementType) + type = type.GetElementType() ?? throw new InvalidOperationException(); + + // type definition, or generic type definition, result is whether it is itself a type builder + if (type.IsGenericType == false || type.IsGenericTypeDefinition) + return type is TypeBuilder; + + // are arguments of closed generic themselves type builder instantiations? + foreach (var arg in type.GetGenericArguments()) + if (ContainsTypeBuilder(arg)) + return true; + + // are we a type builder? + return type.GetGenericTypeDefinition() is TypeBuilder; + } + + readonly IReflectionTypeSymbol[] _genericTypeArguments; + Type? _underlyingType; + bool? _underlyingTypeContainsTypeBuilder; /// /// Initializes a new instance. @@ -19,14 +47,258 @@ class ReflectionGenericSpecTypeSymbol : ReflectionTypeSpecSymbol public ReflectionGenericSpecTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, IReflectionTypeSymbol[] genericTypeArguments) : base(context, resolvingModule, elementType) { - this.genericTypeArguments = genericTypeArguments ?? throw new ArgumentNullException(nameof(genericTypeArguments)); + _genericTypeArguments = genericTypeArguments ?? throw new ArgumentNullException(nameof(genericTypeArguments)); + } + + /// + public override Type UnderlyingType => _underlyingType ??= ElementType.UnderlyingType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingType).ToArray()); + + /// + public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingRuntimeType).ToArray()); + + /// + /// Returns true if the underlying type contains a type builder. + /// + /// + bool UnderlyingTypeContainsTypeBuilder => _underlyingTypeContainsTypeBuilder ??= ContainsTypeBuilder(UnderlyingType); + + /// + public override IFieldSymbol[] GetFields() + { + if (UnderlyingTypeContainsTypeBuilder) + { + var l = ElementType.UnderlyingType.GetFields(); + var a = new IFieldSymbol[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, l[i])); + + return a; + } + + return base.GetFields(); + } + + /// + public override IFieldSymbol[] GetFields(BindingFlags bindingAttr) + { + if (UnderlyingTypeContainsTypeBuilder) + { + var l = ElementType.UnderlyingType.GetFields(bindingAttr); + var a = new IFieldSymbol[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, l[i])); + + return a; + } + + return base.GetFields(bindingAttr); + } + + /// + public override IFieldSymbol? GetField(string name) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetField(name) is { } f) + return ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, f)); + + return base.GetField(name); + } + + /// + public override IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetField(name, bindingAttr) is { } f) + return ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, f)); + + return base.GetField(name, bindingAttr); + } + + /// + public override IConstructorSymbol[] GetConstructors() + { + if (UnderlyingTypeContainsTypeBuilder) + { + var l = ElementType.UnderlyingType.GetConstructors(); + var a = new IConstructorSymbol[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, l[i])); + + return a; + } + + return base.GetConstructors(); + } + + /// + public override IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + { + if (UnderlyingTypeContainsTypeBuilder) + { + var l = ElementType.UnderlyingType.GetConstructors(bindingAttr); + var a = new IConstructorSymbol[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, l[i])); + + return a; + } + + return base.GetConstructors(bindingAttr); + } + + /// + public override IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetConstructor(types.Unpack()) is { } m) + return ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, m)); + + return base.GetConstructor(types); + } + + /// + public override IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetConstructor(bindingAttr, null, types.Unpack(), null) is { } m) + return ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, m)); + + return base.GetConstructor(bindingAttr, types); + } + + /// + public override IMethodSymbol[] GetMethods() + { + if (UnderlyingTypeContainsTypeBuilder) + { + var l = ElementType.UnderlyingType.GetMethods(); + var a = new IMethodSymbol[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, l[i])); + + return a; + } + + return base.GetMethods(); + } + + /// + public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + { + if (UnderlyingTypeContainsTypeBuilder) + { + var l = ElementType.UnderlyingType.GetMethods(bindingAttr); + var a = new IMethodSymbol[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, l[i])); + + return a; + } + + return base.GetMethods(bindingAttr); + } + + /// + public override IMethodSymbol? GetMethod(string name) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetMethod(name) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); + + return base.GetMethod(name); + } + + /// + public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetMethod(name, bindingAttr) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); + + return base.GetMethod(name, bindingAttr); + } + + /// + public override IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetMethod(name, types.Unpack()) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); + + return base.GetMethod(name, types); + } + + /// + public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); + + return base.GetMethod(name, bindingAttr, types); + } + + /// + public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); + + return base.GetMethod(name, bindingAttr, types, modifiers); + } + + /// + public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + if (UnderlyingTypeContainsTypeBuilder) + if (ElementType.UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); + + return base.GetMethod(name, bindingAttr, callConvention, types, modifiers); + } + + /// + public override IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + if (UnderlyingTypeContainsTypeBuilder) +#if NETFRAMEWORK + throw new NotSupportedException(); +#else + if (ElementType.UnderlyingType.GetMethod(name, genericParameterCount, types.Unpack(), modifiers) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); +#endif + + return base.GetMethod(name, genericParameterCount, types, modifiers); } /// - public override Type UnderlyingType => ElementType.UnderlyingType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingType).ToArray()); + public override IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + if (UnderlyingTypeContainsTypeBuilder) +#if NETFRAMEWORK + throw new NotSupportedException(); +#else + if (ElementType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); +#endif + + return base.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); + } /// - public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeGenericType(genericTypeArguments.Select(i => i.UnderlyingRuntimeType).ToArray()); + public override IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + if (UnderlyingTypeContainsTypeBuilder) +#if NETFRAMEWORK + throw new NotSupportedException(); +#else + if (ElementType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) + return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); +#endif + + return base.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs index 8e7fdc1263..d30f9d8a47 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs @@ -54,76 +54,76 @@ public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBui public override sealed MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeMethodBase; /// - public System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; + public virtual System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; /// - public System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; + public virtual System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; /// - public bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; + public virtual bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; /// - public bool IsAbstract => UnderlyingMethodBase.IsAbstract; + public virtual bool IsAbstract => UnderlyingMethodBase.IsAbstract; /// - public bool IsAssembly => UnderlyingMethodBase.IsAssembly; + public virtual bool IsAssembly => UnderlyingMethodBase.IsAssembly; /// - public bool IsConstructor => UnderlyingMethodBase.IsConstructor; + public virtual bool IsConstructor => UnderlyingMethodBase.IsConstructor; /// - public bool IsFamily => UnderlyingMethodBase.IsFamily; + public virtual bool IsFamily => UnderlyingMethodBase.IsFamily; /// - public bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; + public virtual bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; /// - public bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; + public virtual bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; /// - public bool IsFinal => UnderlyingMethodBase.IsFinal; + public virtual bool IsFinal => UnderlyingMethodBase.IsFinal; /// - public bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; + public virtual bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; /// - public bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; + public virtual bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; /// - public bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; + public virtual bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; /// - public bool IsPrivate => UnderlyingMethodBase.IsPrivate; + public virtual bool IsPrivate => UnderlyingMethodBase.IsPrivate; /// - public bool IsPublic => UnderlyingMethodBase.IsPublic; + public virtual bool IsPublic => UnderlyingMethodBase.IsPublic; /// - public bool IsStatic => UnderlyingMethodBase.IsStatic; + public virtual bool IsStatic => UnderlyingMethodBase.IsStatic; /// - public bool IsVirtual => UnderlyingMethodBase.IsVirtual; + public virtual bool IsVirtual => UnderlyingMethodBase.IsVirtual; /// - public bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; + public virtual bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; /// - public System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; + public virtual System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; /// - public ITypeSymbol[] GetGenericArguments() + public virtual ITypeSymbol[] GetGenericArguments() { return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); } /// - public System.Reflection.MethodImplAttributes GetMethodImplementationFlags() + public virtual System.Reflection.MethodImplAttributes GetMethodImplementationFlags() { return (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.GetMethodImplementationFlags(); } /// - public IParameterSymbol[] GetParameters() + public virtual IParameterSymbol[] GetParameters() { return ResolveParameterSymbols(UnderlyingMethodBase.GetParameters()); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index 358d8b8864..33ff9fa02f 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -1,7 +1,11 @@ using System; using System.Reflection; using System.Reflection.Emit; +using System.Threading; +using IKVM.CoreLib.Threading; +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection @@ -15,6 +19,9 @@ class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IReflectionMethodSymb ReflectionGenericTypeParameterTable _genericTypeParameterTable; ReflectionMethodSpecTable _specTable; + ReflectionParameterSpecInfo[]? _specParameters; + ReflectionParameterSpecInfo? _specReturnParameter; + /// /// Initializes a new instance. /// @@ -69,8 +76,53 @@ public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) /// public IParameterSymbol ReturnParameter => ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); + /// + /// Gets the return type of the method. + /// + /// + IParameterSymbol GetReturnParameter() + { + if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) + return GetReturnParameterForMethodOnTypeBuilderInstantiation(); + else + return ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); + } + + /// + /// Gets the return parameter in the case that this method is a . + /// + /// + IParameterSymbol GetReturnParameterForMethodOnTypeBuilderInstantiation() + { + if (_specReturnParameter == null) + Interlocked.CompareExchange(ref _specReturnParameter, new ReflectionParameterSpecInfo(_method, _method.ReturnParameter, _method.DeclaringType!.GetGenericArguments()), null); + + return ResolveParameterSymbol(_specReturnParameter); + } + /// - public ITypeSymbol ReturnType => ResolveTypeSymbol(UnderlyingMethod.ReturnType); + public ITypeSymbol ReturnType => GetReturnType(); + + /// + /// Gets the return type of the method. + /// + /// + ITypeSymbol GetReturnType() + { + if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) + return GetReturnTypeForMethodOnTypeBuilderInstantiation(); + else + return ResolveTypeSymbol(UnderlyingMethod.ReturnType); + } + + /// + /// Gets the return type in the case that this method is a . + /// + /// + ITypeSymbol GetReturnTypeForMethodOnTypeBuilderInstantiation() + { + return ResolveTypeSymbol(_method.ReturnType.SubstituteGenericTypes(_method.DeclaringType!.GetGenericArguments())); + } /// public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); @@ -87,6 +139,40 @@ public IMethodSymbol GetGenericMethodDefinition() return ResolveMethodSymbol(UnderlyingMethod.GetGenericMethodDefinition()); } + /// + public override IParameterSymbol[] GetParameters() + { + if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) + return GetParametersForMethodOnTypeBuilderInstantiation(); + else + return base.GetParameters(); + } + + /// + /// Gets the parameters in the case that this method is a . + /// + /// + IParameterSymbol[] GetParametersForMethodOnTypeBuilderInstantiation() + { + // we cache the spec parameters to avoid creating them repeatidly + if (_specParameters == null) + { + var l = _method.GetParameters(); + var a = new ReflectionParameterSpecInfo[l.Length]; + for (int i = 0; i < l.Length; i++) + a[i] = new ReflectionParameterSpecInfo(_method, l[i], _method.DeclaringType!.GetGenericArguments()); + + Interlocked.CompareExchange(ref _specParameters, a, null); + } + + // resolve into symbols + var symbols = new IParameterSymbol[_specParameters.Length]; + for (int i = 0; i < _specParameters.Length; i++) + symbols[i] = ResolveParameterSymbol(_specParameters[i]); + + return symbols; + } + /// public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) { diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs index 6e58bb23bd..47fde2273c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs @@ -1,9 +1,7 @@ using System; -using System.Collections.Concurrent; -using System.Collections.Generic; +using System.Diagnostics.Eventing.Reader; using System.Reflection; using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; using System.Threading; using IKVM.CoreLib.Collections; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs new file mode 100644 index 0000000000..42bc91d6bf --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs @@ -0,0 +1,51 @@ +using System; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + /// + /// Fake implementation that is used for instantiated method parameters. + /// + class ReflectionParameterSpecInfo : ParameterInfo + { + + readonly MemberInfo _member; + readonly ParameterInfo _parameter; + readonly Type[] _genericTypeArguments; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionParameterSpecInfo(MemberInfo member, ParameterInfo parameter, Type[] genericTypeArguments) + { + _member = member ?? throw new ArgumentNullException(nameof(member)); + _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); + _genericTypeArguments = genericTypeArguments ?? throw new ArgumentNullException(nameof(genericTypeArguments)); + } + + /// + public override ParameterAttributes Attributes => (ParameterAttributes)_parameter.Attributes; + + /// + public override MemberInfo Member => _member; + + /// + public override string? Name => _parameter.Name; + + /// + public override int Position => _parameter.Position; + + /// + public override int MetadataToken => throw new InvalidOperationException(); + + /// + public override Type ParameterType => _parameter.ParameterType.SubstituteGenericTypes(_genericTypeArguments); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs index 121f36a586..abea837975 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs @@ -25,6 +25,9 @@ public ReflectionTypeSpecSymbol(ReflectionSymbolContext context, IReflectionModu /// protected IReflectionTypeSymbol ElementType => _elementType; + /// + public override bool IsComplete => ElementType.IsComplete; + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index d8991850db..c42fa284a8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -524,6 +524,41 @@ public static bool IsMethodDefinition(this MethodBase method) return method.IsGenericMethod == false || method.IsGenericMethodDefinition; } + /// + /// Substitutes generic type parameters into the specified type. + /// + /// + /// + /// + public static Type SubstituteGenericTypes(this Type type, Type[] genericTypeArguments) + { + if (type.IsGenericParameter) + return genericTypeArguments[type.GenericParameterPosition]; + + if (type.IsGenericType) + { + var anySubstituted = false; + var typeDef = type.GetGenericTypeDefinition(); + var genericTypeParameters = typeDef.GetGenericArguments(); + + for (int i = 0; i < genericTypeParameters.Length; i++) + { + var typeParameter = SubstituteGenericTypes(genericTypeParameters[i], genericTypeArguments); + if (genericTypeParameters[i] != typeParameter) + { + genericTypeParameters[i] = typeParameter; + anySubstituted = true; + } + } + + // if any parameters were substituted + if (anySubstituted) + return typeDef.MakeGenericType(genericTypeParameters); + } + + return type; + } + } } diff --git a/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs b/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs index 778db45f8f..8bd4b0a3b5 100644 --- a/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs +++ b/src/IKVM.Runtime/Java/Externs/java/lang/invoke/MethodHandleNatives.cs @@ -466,7 +466,7 @@ public static object staticFieldBase(global::java.lang.invoke.MemberName self) internal static void InitializeCallSite(global::java.lang.invoke.CallSite site) { - var type = typeof(IKVM.Runtime.IndyCallSite<>).MakeGenericType(JVM.Context.MethodHandleUtil.GetDelegateTypeForInvokeExact(site.type()).GetUnderlyingType()); + var type = typeof(IKVM.Runtime.IndyCallSite<>).MakeGenericType(JVM.Context.MethodHandleUtil.GetDelegateTypeForInvokeExact(site.type()).GetUnderlyingRuntimeType()); var ics = (IKVM.Runtime.IIndyCallSite)Activator.CreateInstance(type, true); Interlocked.CompareExchange(ref site.ics, ics, null); } diff --git a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs index 041845bb12..f55b3879e9 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.compiler.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.compiler.cs @@ -1,5 +1,4 @@ -using System.Reflection; -using System.Reflection.Emit; +using System.Reflection.Emit; using IKVM.CoreLib.Symbols; diff --git a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs index b44ab8b5b7..7c050b8658 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs @@ -644,7 +644,7 @@ internal T GetDelegateForInvokeExact(global::java.lang.invoke.MethodHandle mh if (mh._invokeExactDelegate == null) { type._invokeExactDynamicMethod ??= DynamicMethodBuilder.CreateInvokeExact(context, type); - mh._invokeExactDelegate = type._invokeExactDynamicMethod.CreateDelegate(GetDelegateTypeForInvokeExact(type).GetUnderlyingType(), mh); + mh._invokeExactDelegate = type._invokeExactDynamicMethod.CreateDelegate(GetDelegateTypeForInvokeExact(type).GetUnderlyingRuntimeType(), mh); var del = mh._invokeExactDelegate as T; if (del != null) return del; From dbf2cd8977b005f6a9071ff1f691130e134d6935 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Fri, 18 Oct 2024 23:22:21 -0500 Subject: [PATCH 46/59] use runtime types --- src/IKVM.Runtime/ByteCodeHelper.cs | 4 +-- src/IKVM.Runtime/JNI/JNIEnv.cs | 12 +++---- .../Java/Externs/java/io/ObjectStreamClass.cs | 8 ++--- .../Java/Externs/sun/misc/Unsafe.cs | 32 +++++++++---------- .../Externs/sun/reflect/ReflectionFactory.cs | 20 ++++++------ .../MethodHandleUtil.jniexport.cs | 6 ++-- .../RuntimeAssemblyClassLoader.cs | 2 +- src/IKVM.Runtime/RuntimeJavaField.cs | 18 +++++------ ...gedJavaType.AttributeAnnotationJavaType.cs | 2 +- ...RuntimeManagedJavaType.EnumEnumJavaType.cs | 4 +-- ...ntimeManagedJavaType.EnumWrapJavaMethod.cs | 2 +- ...JavaType.ValueTypeDefaultCtorJavaMethod.cs | 2 +- src/IKVM.Runtime/SymbolExtensions.cs | 16 ++++++++-- .../Invoke/NativeInvokerBytecodeGenerator.cs | 4 +-- 14 files changed, 72 insertions(+), 60 deletions(-) diff --git a/src/IKVM.Runtime/ByteCodeHelper.cs b/src/IKVM.Runtime/ByteCodeHelper.cs index a4b6db89aa..34a288e878 100644 --- a/src/IKVM.Runtime/ByteCodeHelper.cs +++ b/src/IKVM.Runtime/ByteCodeHelper.cs @@ -128,7 +128,7 @@ public static object DynamicMultianewarray(int[] lengths, global::java.lang.Clas Profiler.Count("DynamicMultianewarray"); var wrapper = RuntimeJavaType.FromClass(clazz); - var obj = multianewarray(wrapper.TypeAsArrayType.GetUnderlyingType().TypeHandle, lengths); + var obj = multianewarray(wrapper.TypeAsArrayType.GetUnderlyingRuntimeType().TypeHandle, lengths); if (wrapper.IsGhostArray) GhostTag.SetTag(obj, wrapper); @@ -147,7 +147,7 @@ public static object DynamicNewarray(int length, global::java.lang.Class clazz) throw new global::java.lang.NegativeArraySizeException(); var wrapper = RuntimeJavaType.FromClass(clazz); - var obj = Array.CreateInstance(wrapper.TypeAsArrayType.GetUnderlyingType(), length); + var obj = Array.CreateInstance(wrapper.TypeAsArrayType.GetUnderlyingRuntimeType(), length); if (wrapper.IsGhost || wrapper.IsGhostArray) GhostTag.SetTag(obj, wrapper.MakeArrayType(1)); diff --git a/src/IKVM.Runtime/JNI/JNIEnv.cs b/src/IKVM.Runtime/JNI/JNIEnv.cs index 789832c734..03b3c897ad 100644 --- a/src/IKVM.Runtime/JNI/JNIEnv.cs +++ b/src/IKVM.Runtime/JNI/JNIEnv.cs @@ -628,9 +628,9 @@ static nint AllocObjectImpl(JNIEnv* pEnv, RuntimeJavaType wrapper) wrapper.Finish(); #if NETFRAMEWORK - return pEnv->MakeLocalRef(FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType())); + return pEnv->MakeLocalRef(FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingRuntimeType())); #else - return pEnv->MakeLocalRef(RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType())); + return pEnv->MakeLocalRef(RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingRuntimeType())); #endif } catch (RetargetableJavaException e) @@ -709,7 +709,7 @@ static object InvokeHelper(JNIEnv* pEnv, nint objHandle, nint methodID, JValue* // possible with remapped types throw new NotSupportedException($"Remapped type {mw.DeclaringType.Name} doesn't support constructor invocation on an existing instance"); } - else if (!mb.DeclaringType.GetUnderlyingType().IsInstanceOfType(obj)) + else if (!mb.DeclaringType.GetUnderlyingRuntimeType().IsInstanceOfType(obj)) { // we're trying to initialize an existing instance of a remapped type throw new NotSupportedException($"Unable to partially construct object of type {obj.GetType().FullName} to type {mb.DeclaringType.FullName}"); @@ -734,10 +734,10 @@ static object InvokeNonVirtual(JNIEnvContext env, RuntimeJavaMethod mw, object o if (mw.HasCallerID || mw.IsDynamicOnly) throw new NotSupportedException(); - if (mw.DeclaringType.IsRemapped && !mw.DeclaringType.TypeAsBaseType.GetUnderlyingType().IsInstanceOfType(obj)) + if (mw.DeclaringType.IsRemapped && !mw.DeclaringType.TypeAsBaseType.GetUnderlyingRuntimeType().IsInstanceOfType(obj)) return mw.InvokeNonvirtualRemapped(obj, argarray); - var del = (Delegate)Activator.CreateInstance(mw.GetDelegateType().GetUnderlyingType(), [obj, mw.GetMethod().GetUnderlyingMethodBase().MethodHandle.GetFunctionPointer()]); + var del = (Delegate)Activator.CreateInstance(mw.GetDelegateType().GetUnderlyingRuntimeType(), [obj, mw.GetMethod().GetUnderlyingMethodBase().MethodHandle.GetFunctionPointer()]); try { return del.DynamicInvoke(argarray); @@ -2157,7 +2157,7 @@ internal static nint NewObjectArray(JNIEnv* pEnv, jsize len, nint clazz, nint in try { // we want to support (non-primitive) value types so we can't cast to object[] - var a = Array.CreateInstance(RuntimeJavaType.FromClass((java.lang.Class)pEnv->UnwrapRef(clazz)).TypeAsArrayType.GetUnderlyingType(), len); + var a = Array.CreateInstance(RuntimeJavaType.FromClass((java.lang.Class)pEnv->UnwrapRef(clazz)).TypeAsArrayType.GetUnderlyingRuntimeType(), len); var o = pEnv->UnwrapRef(init); if (o != null) for (int i = 0; i < a.Length; i++) diff --git a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs index 9208087fd1..7d61dff836 100644 --- a/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs +++ b/src/IKVM.Runtime/Java/Externs/java/io/ObjectStreamClass.cs @@ -256,10 +256,10 @@ internal FastFieldReflector(global::java.io.ObjectStreamField[] fields) throw x.ToJava(); } - var dmObjGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(object[])]); - var dmPrimGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(byte[])]); - var dmObjSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(object[])]); - var dmPrimSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingType(), true, null, [typeof(object), typeof(byte[])]); + var dmObjGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingRuntimeType(), true, null, [typeof(object), typeof(object[])]); + var dmPrimGetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingRuntimeType(), true, null, [typeof(object), typeof(byte[])]); + var dmObjSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingRuntimeType(), true, null, [typeof(object), typeof(object[])]); + var dmPrimSetter = DynamicMethodUtil.Create("__", tw.TypeAsBaseType.GetUnderlyingRuntimeType(), true, null, [typeof(object), typeof(byte[])]); var ilgenObjGetter = JVM.Context.CodeEmitterFactory.Create(dmObjGetter); var ilgenPrimGetter = JVM.Context.CodeEmitterFactory.Create(dmPrimGetter); var ilgenObjSetter = JVM.Context.CodeEmitterFactory.Create(dmObjSetter); diff --git a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs index f2faef90c5..0d06aca917 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/misc/Unsafe.cs @@ -1734,9 +1734,9 @@ public static object allocateInstance(object self, global::java.lang.Class cls) } #if NETFRAMEWORK - return FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType()); + return FormatterServices.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingRuntimeType()); #else - return RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingType()); + return RuntimeHelpers.GetUninitializedObject(wrapper.TypeAsBaseType.GetUnderlyingRuntimeType()); #endif } @@ -1854,8 +1854,8 @@ static void PutFieldVolatile(object o, long offset, T value) /// static Delegate CreateGetArrayVolatileDelegate(RuntimeJavaType tw) { - var et = tw.IsPrimitive ? tw.TypeAsTBD.GetUnderlyingType() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.GetUnderlyingType(), true, et, new[] { typeof(object[]), typeof(long) }); + var et = tw.IsPrimitive ? tw.TypeAsTBD.GetUnderlyingRuntimeType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.GetUnderlyingRuntimeType(), true, et, [typeof(object[]), typeof(long)]); var il = dm.GetILGenerator(); // load reference to element @@ -1865,17 +1865,17 @@ static Delegate CreateGetArrayVolatileDelegate(RuntimeJavaType tw) il.Emit(OpCodes.Ldc_I4, ArrayIndexScale(tw.MakeArrayType(1))); il.Emit(OpCodes.Div); il.Emit(OpCodes.Conv_Ovf_I); - il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.GetUnderlyingType()); + il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.GetUnderlyingRuntimeType()); if (tw.IsWidePrimitive == false) { il.Emit(OpCodes.Volatile); - EmitLdind(il, tw.TypeAsLocalOrStackType.GetUnderlyingType()); + EmitLdind(il, tw.TypeAsLocalOrStackType.GetUnderlyingRuntimeType()); } else { // Java volatile semantics require atomicity, CLR volatile semantics do not - var mi = typeof(Unsafe).GetMethod(nameof(InterlockedRead), BindingFlags.NonPublic | BindingFlags.Static, null, new[] { tw.TypeAsTBD.MakeByRefType().GetUnderlyingType() }, null); + var mi = typeof(Unsafe).GetMethod(nameof(InterlockedRead), BindingFlags.NonPublic | BindingFlags.Static, null, [tw.TypeAsTBD.MakeByRefType().GetUnderlyingRuntimeType()], null); il.Emit(OpCodes.Call, mi); } @@ -1912,8 +1912,8 @@ static object GetArrayObjectVolatile(object[] array, long offset) /// static Delegate CreatePutArrayVolatileDelegate(RuntimeJavaType tw) { - var et = tw.IsPrimitive ? tw.TypeAsTBD.GetUnderlyingType() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.GetUnderlyingType(), true, typeof(void), new[] { typeof(object[]), typeof(long), et }); + var et = tw.IsPrimitive ? tw.TypeAsTBD.GetUnderlyingRuntimeType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{tw.Name.Replace(".", "_")}", tw.TypeAsTBD.GetUnderlyingRuntimeType(), true, typeof(void), new[] { typeof(object[]), typeof(long), et }); var il = dm.GetILGenerator(); // load reference to element @@ -1923,19 +1923,19 @@ static Delegate CreatePutArrayVolatileDelegate(RuntimeJavaType tw) il.Emit(OpCodes.Ldc_I4, ArrayIndexScale(tw.MakeArrayType(1))); il.Emit(OpCodes.Div); il.Emit(OpCodes.Conv_Ovf_I); - il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.GetUnderlyingType()); + il.Emit(OpCodes.Ldelema, tw.TypeAsLocalOrStackType.GetUnderlyingRuntimeType()); il.Emit(OpCodes.Ldarg_2); if (tw.IsWidePrimitive == false) { il.Emit(OpCodes.Volatile); - EmitStind(il, tw.TypeAsLocalOrStackType.GetUnderlyingType()); + EmitStind(il, tw.TypeAsLocalOrStackType.GetUnderlyingRuntimeType()); } else { // Java volatile semantics require atomicity, CLR volatile semantics do not - var mi = typeof(Interlocked).GetMethod(nameof(Interlocked.Exchange), new[] { tw.TypeAsTBD.MakeByRefType().GetUnderlyingType() }); + var mi = typeof(Interlocked).GetMethod(nameof(Interlocked.Exchange), new[] { tw.TypeAsTBD.MakeByRefType().GetUnderlyingRuntimeType() }); il.Emit(OpCodes.Call, mi); } @@ -2475,11 +2475,11 @@ static Delegate CreateCompareExchangeArrayDelegate(RuntimeJavaType tw) var e = Expression.Parameter(typeof(object)); return Expression.Lambda>( Expression.Call( - compareAndSwapArrayMethodInfo.MakeGenericMethod(tw.TypeAsTBD.GetUnderlyingType()), - Expression.Convert(p, tw.MakeArrayType(1).TypeAsTBD.GetUnderlyingType()), + compareAndSwapArrayMethodInfo.MakeGenericMethod(tw.TypeAsTBD.GetUnderlyingRuntimeType()), + Expression.Convert(p, tw.MakeArrayType(1).TypeAsTBD.GetUnderlyingRuntimeType()), i, - Expression.Convert(v, tw.TypeAsTBD.GetUnderlyingType()), - Expression.Convert(e, tw.TypeAsTBD.GetUnderlyingType())), + Expression.Convert(v, tw.TypeAsTBD.GetUnderlyingRuntimeType()), + Expression.Convert(e, tw.TypeAsTBD.GetUnderlyingRuntimeType())), p, i, v, e) .Compile(); } diff --git a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs index c898acb333..12684b2d16 100644 --- a/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs +++ b/src/IKVM.Runtime/Java/Externs/sun/reflect/ReflectionFactory.cs @@ -286,9 +286,9 @@ internal SerializationConstructorAccessorImpl(global::java.lang.reflect.Construc public object newInstance(object[] args) { #if NETFRAMEWORK - var obj = FormatterServices.GetUninitializedObject(type.GetUnderlyingType()); + var obj = FormatterServices.GetUninitializedObject(type.GetUnderlyingRuntimeType()); #else - var obj = RuntimeHelpers.GetUninitializedObject(type.GetUnderlyingType()); + var obj = RuntimeHelpers.GetUninitializedObject(type.GetUnderlyingRuntimeType()); #endif if (mw != null) mw.Invoke(obj, ConvertArgs(mw.DeclaringType.ClassLoader, mw.GetParameters(), args)); @@ -587,7 +587,7 @@ internal unsafe FastMethodAccessorImpl(RuntimeJavaMethod mw) // generate new dynamic method var np = !mw.IsPublic || !mw.DeclaringType.IsPublic; - var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsBaseType.GetUnderlyingType(), np, typeof(object), new[] { typeof(object), typeof(object[]), typeof(global::ikvm.@internal.CallerID) }); + var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsBaseType.GetUnderlyingRuntimeType(), np, typeof(object), new[] { typeof(object), typeof(object[]), typeof(global::ikvm.@internal.CallerID) }); var il = JVM.Context.CodeEmitterFactory.Create(dm); // labels @@ -831,7 +831,7 @@ internal FastConstructorAccessorImpl(global::java.lang.reflect.Constructor const // resolve the runtime method info mw.ResolveMethod(); var np = !mw.IsPublic || !mw.DeclaringType.IsPublic; - var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsTBD.GetUnderlyingType(), np, typeof(object), new[] { typeof(object[]) }); + var dm = DynamicMethodUtil.Create($"____{mw.DeclaringType.Name.Replace(".", "_")}__{mw.Name}", mw.DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType(), np, typeof(object), new[] { typeof(object[]) }); var il = JVM.Context.CodeEmitterFactory.Create(dm); // labels @@ -1007,7 +1007,7 @@ internal FastSerializationConstructorAccessorImpl(global::java.lang.reflect.Cons throw x.ToJava(); } - var dm = DynamicMethodUtil.Create("__", constructor.DeclaringType.TypeAsBaseType.GetUnderlyingType(), true, typeof(object), null); + var dm = DynamicMethodUtil.Create("__", constructor.DeclaringType.TypeAsBaseType.GetUnderlyingRuntimeType(), true, typeof(object), null); var il = JVM.Context.CodeEmitterFactory.Create(dm); il.Emit(OpCodes.Ldtoken, type); il.Emit(OpCodes.Call, GetTypeFromHandleMethod); @@ -1052,7 +1052,7 @@ public object newInstance(object[] objarr) try { - return Activator.CreateInstance(type.GetUnderlyingType()); + return Activator.CreateInstance(type.GetUnderlyingRuntimeType()); } catch (TargetInvocationException x) { @@ -1319,7 +1319,7 @@ private T lazyGet(object obj) { throw GetIllegalArgumentException(obj); } - else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.GetUnderlyingType().IsInstanceOfType(obj)) + else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.GetUnderlyingRuntimeType().IsInstanceOfType(obj)) { throw GetUnsupportedRemappedFieldException(obj); } @@ -1364,7 +1364,7 @@ private void lazySet(object obj, T value) { throw SetIllegalArgumentException(obj); } - else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.GetUnderlyingType().IsInstanceOfType(obj)) + else if (fw.DeclaringType.IsRemapped && !fw.DeclaringType.TypeAsBaseType.GetUnderlyingRuntimeType().IsInstanceOfType(obj)) { throw GetUnsupportedRemappedFieldException(obj); } @@ -2070,7 +2070,7 @@ private Delegate GenerateFastGetter(Type delegateType, Type fieldType, RuntimeJa fw.ResolveField(); - var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.GetUnderlyingType(), !fw.IsPublic || !fw.DeclaringType.IsPublic, fieldType, [typeof(IReflectionException), typeof(object), typeof(object)]); + var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.GetUnderlyingRuntimeType(), !fw.IsPublic || !fw.DeclaringType.IsPublic, fieldType, [typeof(IReflectionException), typeof(object), typeof(object)]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (fw.IsStatic) { @@ -2118,7 +2118,7 @@ private Delegate GenerateFastSetter(Type delegateType, Type fieldType, RuntimeJa fw.ResolveField(); - var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.GetUnderlyingType(), !fw.IsPublic || !fw.DeclaringType.IsPublic, null, [typeof(IReflectionException), typeof(object), fieldType, typeof(object)]); + var dm = DynamicMethodUtil.Create("__", fw.DeclaringType.TypeAsBaseType.GetUnderlyingRuntimeType(), !fw.IsPublic || !fw.DeclaringType.IsPublic, null, [typeof(IReflectionException), typeof(object), fieldType, typeof(object)]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (fw.IsStatic) { diff --git a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs index 7c050b8658..f29b4493c3 100644 --- a/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs +++ b/src/IKVM.Runtime/MethodHandleUtil.jniexport.cs @@ -194,7 +194,7 @@ public Container(T1 target, T2 value) if (!ReflectUtil.CanOwnDynamicMethod(owner)) owner = typeof(DynamicMethodBuilder); - dm = new DynamicMethod(name, mi.ReturnType.GetUnderlyingType(), paramTypes.GetUnderlyingTypes(), owner, true); + dm = new DynamicMethod(name, mi.ReturnType.GetUnderlyingRuntimeType(), paramTypes.GetUnderlyingRuntimeTypes(), owner, true); ilgen = context.CodeEmitterFactory.Create(dm); if (type.parameterCount() > MaxArity) @@ -516,8 +516,8 @@ internal Delegate CreateDelegate() //ilgen.DumpMethod(); ilgen.DoEmit(); return ValidateDelegate(firstArg == 0 - ? dm.CreateDelegate(delegateType.GetUnderlyingType()) - : dm.CreateDelegate(delegateType.GetUnderlyingType(), container == null ? firstBoundValue : Activator.CreateInstance(container.GetUnderlyingType(), firstBoundValue, secondBoundValue))); + ? dm.CreateDelegate(delegateType.GetUnderlyingRuntimeType()) + : dm.CreateDelegate(delegateType.GetUnderlyingRuntimeType(), container == null ? firstBoundValue : Activator.CreateInstance(container.GetUnderlyingRuntimeType(), firstBoundValue, secondBoundValue))); } internal void BoxArgs(int start) diff --git a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs index 9b2f65e229..591f9f636a 100644 --- a/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs +++ b/src/IKVM.Runtime/RuntimeAssemblyClassLoader.cs @@ -1174,7 +1174,7 @@ Type GetCustomClassLoaderType() var attribs = assembly.GetCustomAttribute(Context.Resolver.ResolveRuntimeType(typeof(CustomAssemblyClassLoaderAttribute).FullName), false); if (attribs.HasValue) - return ((ITypeSymbol)attribs.Value.ConstructorArguments[0].Value).GetUnderlyingType(); + return ((ITypeSymbol)attribs.Value.ConstructorArguments[0].Value).GetUnderlyingRuntimeType(); return null; } diff --git a/src/IKVM.Runtime/RuntimeJavaField.cs b/src/IKVM.Runtime/RuntimeJavaField.cs index 9b3398eeff..293132710f 100644 --- a/src/IKVM.Runtime/RuntimeJavaField.cs +++ b/src/IKVM.Runtime/RuntimeJavaField.cs @@ -500,8 +500,8 @@ Delegate CreateUnsafeGetDelegate() FieldTypeWrapper.Finish(); ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, ft, [typeof(object)]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingRuntimeType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType(), true, ft, [typeof(object)]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -547,8 +547,8 @@ Delegate CreateUnsafeSetDelegate() FieldTypeWrapper.Finish(); ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, typeof(void), [typeof(object), ft]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingRuntimeType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType(), true, typeof(void), [typeof(object), ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -592,7 +592,7 @@ Delegate GetUnsafeVolatileGetDelegate() Delegate CreateUnsafeVolatileGetDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingRuntimeType() : typeof(object); var dm = new DynamicMethod($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", ft, [typeof(object)], DeclaringType.TypeAsTBD.Module.GetUnderlyingModule(), true); var il = JVM.Context.CodeEmitterFactory.Create(dm); @@ -637,8 +637,8 @@ Delegate GetUnsafeVolatileSetDelegate() Delegate CreateUnsafeVolatileSetDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, typeof(void), [typeof(object), ft]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingRuntimeType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType(), true, typeof(void), [typeof(object), ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) @@ -685,8 +685,8 @@ Delegate GetUnsafeCompareAndSwapDelegate() Delegate CreateUnsafeCompareAndSwapDelegate() { ResolveField(); - var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingType() : typeof(object); - var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingType(), true, typeof(bool), [typeof(object), ft, ft]); + var ft = FieldTypeWrapper.IsPrimitive ? FieldTypeWrapper.TypeAsSignatureType.GetUnderlyingRuntimeType() : typeof(object); + var dm = DynamicMethodUtil.Create($"____{DeclaringType.Name.Replace(".", "_")}__{Name}", DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType(), true, typeof(bool), [typeof(object), ft, ft]); var il = JVM.Context.CodeEmitterFactory.Create(dm); if (IsStatic == false) diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs index d17358d079..c76a9a594d 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.AttributeAnnotationJavaType.cs @@ -376,7 +376,7 @@ internal override object GetAnnotationDefault(RuntimeJavaMethod mw) } else if (mw.ReturnType.IsArray) { - return Array.CreateInstance(mw.ReturnType.TypeAsArrayType.GetUnderlyingType(), 0); + return Array.CreateInstance(mw.ReturnType.TypeAsArrayType.GetUnderlyingRuntimeType(), 0); } } diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs index 35eba0393a..61be98369c 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumEnumJavaType.cs @@ -98,7 +98,7 @@ internal EnumJavaField(RuntimeJavaType tw, string name, int ordinal) : internal override object GetValue(object obj) { if (val == null) - System.Threading.Interlocked.CompareExchange(ref val, Activator.CreateInstance(this.DeclaringType.TypeAsTBD.GetUnderlyingType(), BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new object[] { this.Name, ordinal }, null), null); + System.Threading.Interlocked.CompareExchange(ref val, Activator.CreateInstance(this.DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType(), BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new object[] { this.Name, ordinal }, null), null); return val; } @@ -147,7 +147,7 @@ internal EnumValuesJavaMethod(RuntimeJavaType declaringType) : internal override object Invoke(object obj, object[] args) { var values = DeclaringType.GetFields(); - var array = (object[])Array.CreateInstance(DeclaringType.TypeAsArrayType.GetUnderlyingType(), values.Length); + var array = (object[])Array.CreateInstance(DeclaringType.TypeAsArrayType.GetUnderlyingRuntimeType(), values.Length); for (int i = 0; i < values.Length; i++) array[i] = values[i].GetValue(null); diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs index d706a90314..a02a29ed37 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.EnumWrapJavaMethod.cs @@ -67,7 +67,7 @@ internal override void EmitCall(CodeEmitter ilgen) internal override object Invoke(object obj, object[] args) { - return Enum.ToObject(DeclaringType.TypeAsTBD.GetUnderlyingType(), args[0]); + return Enum.ToObject(DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType(), args[0]); } #endif diff --git a/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs b/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs index 6de44f611b..7ca600db3a 100644 --- a/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs +++ b/src/IKVM.Runtime/RuntimeManagedJavaType.ValueTypeDefaultCtorJavaMethod.cs @@ -65,7 +65,7 @@ internal override void EmitCall(CodeEmitter ilgen) internal override object CreateInstance(object[] args) { - return Activator.CreateInstance(DeclaringType.TypeAsTBD.GetUnderlyingType()); + return Activator.CreateInstance(DeclaringType.TypeAsTBD.GetUnderlyingRuntimeType()); } #endif diff --git a/src/IKVM.Runtime/SymbolExtensions.cs b/src/IKVM.Runtime/SymbolExtensions.cs index 08cf48b7d2..40244b1157 100644 --- a/src/IKVM.Runtime/SymbolExtensions.cs +++ b/src/IKVM.Runtime/SymbolExtensions.cs @@ -59,6 +59,18 @@ public static Type GetUnderlyingType(this ITypeSymbol symbol) #endif } + public static Type[] GetUnderlyingTypes(this ITypeSymbol[] symbols) + { + if (symbols == null) + return null; + + var a = new Type[symbols.Length]; + for (int i = 0; i < symbols.Length; i++) + a[i] = GetUnderlyingType(symbols[i]); + + return a; + } + public static Type GetUnderlyingRuntimeType(this ITypeSymbol symbol) { if (symbol == null) @@ -71,14 +83,14 @@ public static Type GetUnderlyingRuntimeType(this ITypeSymbol symbol) #endif } - public static Type[] GetUnderlyingTypes(this ITypeSymbol[] symbols) + public static Type[] GetUnderlyingRuntimeTypes(this ITypeSymbol[] symbols) { if (symbols == null) return null; var a = new Type[symbols.Length]; for (int i = 0; i < symbols.Length; i++) - a[i] = GetUnderlyingType(symbols[i]); + a[i] = GetUnderlyingRuntimeType(symbols[i]); return a; } diff --git a/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs b/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs index bfee5d1391..57ecfebead 100644 --- a/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs +++ b/src/IKVM.Runtime/Util/Java/Lang/Invoke/NativeInvokerBytecodeGenerator.cs @@ -115,7 +115,7 @@ internal BailoutException(Bailout reason, object data) var paramTypes = MethodHandleUtil.GetParameterTypes(context.Types.Object.MakeArrayType(), mi); // HACK the code we generate is not verifiable (known issue: locals aren't typed correctly), so we stick the DynamicMethod into mscorlib (a security critical assembly) - this.dm = new DynamicMethod(lambdaForm.debugName, mi.ReturnType.GetUnderlyingType(), paramTypes.GetUnderlyingTypes(), typeof(object).Module, true); + this.dm = new DynamicMethod(lambdaForm.debugName, mi.ReturnType.GetUnderlyingRuntimeType(), paramTypes.GetUnderlyingRuntimeTypes(), typeof(object).Module, true); this.ilgen = context.CodeEmitterFactory.Create(this.dm); if (invokerType.parameterCount() > MethodHandleUtil.MaxArity) { @@ -439,7 +439,7 @@ private Delegate generateCustomizedCodeBytes() emitReturn(onStack); ilgen.DoEmit(); - return dm.CreateDelegate(delegateType.GetUnderlyingType(), constants.ToArray()); + return dm.CreateDelegate(delegateType.GetUnderlyingRuntimeType(), constants.ToArray()); } void emitArrayLoad(Name name) From 5eda2a69091df9d0e396e90d68eab70dbf33e051 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 20 Oct 2024 13:32:23 -0500 Subject: [PATCH 47/59] Implement GetParameters and ReturnType. --- .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 11 ++++++---- .../IkvmReflectionFieldTable.cs | 2 +- .../Emit/ReflectionFieldSymbolBuilder.cs | 21 ++++++++++++++++--- .../Emit/ReflectionMethodSymbolBuilder.cs | 17 +++++++++++---- .../Emit/ReflectionTypeSymbolBuilder.cs | 8 +++---- .../Reflection/IReflectionModuleSymbol.cs | 4 +++- .../Symbols/Reflection/IReflectionSymbol.cs | 4 +++- .../Reflection/IReflectionTypeSymbol.cs | 6 ++++-- .../Reflection/ReflectionFieldSymbol.cs | 4 ++-- .../Reflection/ReflectionFieldTable.cs | 15 +++++++------ .../ReflectionGenericTypeParameterSymbol.cs | 2 +- .../Reflection/ReflectionMemberSymbol.cs | 18 ++++++++++++++++ .../Reflection/ReflectionMethodSymbol.cs | 4 +++- .../Reflection/ReflectionModuleSymbol.cs | 8 +++---- .../Symbols/Reflection/ReflectionSymbol.cs | 4 ++-- .../Reflection/ReflectionSymbolContext.cs | 4 ++-- .../Reflection/ReflectionTypeSymbolBase.cs | 10 ++++----- src/IKVM.Runtime/StubGen/StubGenerator.cs | 2 +- 18 files changed, 100 insertions(+), 44 deletions(-) diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs index cb49715892..d1014b34b3 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs @@ -1,6 +1,5 @@ using System; -using IKVM.CoreLib.Symbols.Emit; using IKVM.Reflection; using IKVM.Reflection.Emit; @@ -12,6 +11,8 @@ class IkvmReflectionFieldSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkv FieldBuilder? _builder; FieldInfo _field; + readonly ITypeSymbol[] _optionalCustomModifiers; + readonly ITypeSymbol[] _requiredCustomModifiers; /// /// Initializes a new instance. @@ -21,11 +22,13 @@ class IkvmReflectionFieldSymbolBuilder : IkvmReflectionMemberSymbolBuilder, IIkv /// /// /// - public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder? resolvingType, FieldBuilder builder) : + public IkvmReflectionFieldSymbolBuilder(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbolBuilder resolvingModule, IIkvmReflectionTypeSymbolBuilder? resolvingType, FieldBuilder builder, ITypeSymbol[] optionalCustomModifiers, ITypeSymbol[] requiredCustomModifiers) : base(context, resolvingModule, resolvingType) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); _field = _builder; + _optionalCustomModifiers = optionalCustomModifiers; + _requiredCustomModifiers = requiredCustomModifiers; } /// @@ -103,13 +106,13 @@ public void SetOffset(int iOffset) /// public ITypeSymbol[] GetOptionalCustomModifiers() { - return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); + return _optionalCustomModifiers; } /// public ITypeSymbol[] GetRequiredCustomModifiers() { - return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); + return _requiredCustomModifiers; } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs index d493f35fae..624572ed0e 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs @@ -90,7 +90,7 @@ public IIkvmReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) static IIkvmReflectionFieldSymbol CreateFieldSymbol(IkvmReflectionSymbolContext context, IIkvmReflectionModuleSymbol module, IIkvmReflectionTypeSymbol? type, FieldInfo field) { if (field is FieldBuilder builder) - return new IkvmReflectionFieldSymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, (IIkvmReflectionTypeSymbolBuilder?)type, builder); + return new IkvmReflectionFieldSymbolBuilder(context, (IIkvmReflectionModuleSymbolBuilder)module, (IIkvmReflectionTypeSymbolBuilder?)type, builder, [], []); else return new IkvmReflectionFieldSymbol(context, module, type, field); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs index 6e99440cf8..08311c1c68 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs @@ -2,8 +2,6 @@ using System.Reflection; using System.Reflection.Emit; -using IKVM.CoreLib.Symbols.Emit; - namespace IKVM.CoreLib.Symbols.Reflection.Emit { @@ -13,6 +11,9 @@ class ReflectionFieldSymbolBuilder : ReflectionFieldSymbol, IReflectionFieldSymb readonly FieldBuilder _builder; FieldInfo? _field; + readonly ITypeSymbol[]? _requiredCustomModifiers; + readonly ITypeSymbol[]? _optionalCustomModifiers; + /// /// Initializes a new instance. /// @@ -21,10 +22,12 @@ class ReflectionFieldSymbolBuilder : ReflectionFieldSymbol, IReflectionFieldSymb /// /// /// - public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType, FieldBuilder builder) : + public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionTypeSymbolBuilder? resolvingType, FieldBuilder builder, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) : base(context, resolvingModule, resolvingType, builder) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); + _requiredCustomModifiers = requiredCustomModifiers ?? throw new ArgumentNullException(nameof(requiredCustomModifiers)); + _optionalCustomModifiers = optionalCustomModifiers ?? throw new ArgumentNullException(nameof(optionalCustomModifiers)); } /// @@ -41,6 +44,18 @@ public ReflectionFieldSymbolBuilder(ReflectionSymbolContext context, IReflection /// public override bool IsComplete => _field != null; + /// + public override ITypeSymbol[] GetRequiredCustomModifiers() + { + return _requiredCustomModifiers ?? []; + } + + /// + public override ITypeSymbol[] GetOptionalCustomModifiers() + { + return _optionalCustomModifiers ?? []; + } + #endregion #region IFieldSymbolBuilder diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index 58fdd779ba..9a30c7a88e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -42,15 +42,24 @@ public ReflectionMethodSymbolBuilder(ReflectionSymbolContext context, IReflectio #region IMethodBaseSymbolBuilder /// - public void SetImplementationFlags(System.Reflection.MethodImplAttributes attributes) + public void SetImplementationFlags(MethodImplAttributes attributes) { - UnderlyingMethodBuilder.SetImplementationFlags((MethodImplAttributes)attributes); + UnderlyingMethodBuilder.SetImplementationFlags(attributes); } /// - public IParameterSymbolBuilder DefineParameter(int position, System.Reflection.ParameterAttributes attributes, string? strParamName) + public IParameterSymbolBuilder DefineParameter(int position, ParameterAttributes attributes, string? strParamName) { - return ResolveParameterSymbol(this, UnderlyingMethodBuilder.DefineParameter(position, (ParameterAttributes)attributes, strParamName)); + return ResolveParameterSymbol(this, UnderlyingMethodBuilder.DefineParameter(position, attributes, strParamName)); + } + + /// + public override IParameterSymbol[] GetParameters() + { + if (IsComplete) + return ResolveParameterSymbols(UnderlyingRuntimeMethod.GetParameters()); + else + return base.GetParameters(); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index 9130e6a358..ac8e95076a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -103,17 +103,17 @@ public IEventSymbolBuilder DefineEvent(string name, System.Reflection.EventAttri /// public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, System.Reflection.FieldAttributes attributes) { - return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), (FieldAttributes)attributes)); + return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), attributes), [], []); } /// - public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, System.Reflection.FieldAttributes attributes) + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, FieldAttributes attributes) { - return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), (FieldAttributes)attributes)); + return ResolveFieldSymbol(UnderlyingTypeBuilder.DefineField(fieldName, type.Unpack(), requiredCustomModifiers?.Unpack(), optionalCustomModifiers?.Unpack(), attributes), requiredCustomModifiers, optionalCustomModifiers); } /// - public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); _incompleteMethods ??= []; diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs index 9b559b5773..7d679be5cf 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs @@ -85,8 +85,10 @@ interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol /// Gets or creates a for the specified . /// /// + /// + /// /// - IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? optionalCustomModifiers, ITypeSymbol[]? requiredCustomModifiers); /// /// Gets or creates a for the specified . diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs index 3928a4815d..490fe4da80 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs @@ -196,9 +196,11 @@ interface IReflectionSymbol : ISymbol /// Resolves the symbol for the specified field. /// /// + /// + /// /// [return: NotNullIfNotNull(nameof(field))] - IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field); + IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field, ITypeSymbol[] requiredCustomModifiers, ITypeSymbol[] optionalCustomModifiers); /// /// Resolves the symbol for the specified property. diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs index 47da7f1b40..f8daebcebf 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs @@ -72,9 +72,11 @@ interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol /// /// Gets or creates a for the given . /// - /// + /// + /// + /// /// - IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field); + IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers); /// /// Gets or creates a for the given . diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index f6095d471e..a9d760e500 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -79,13 +79,13 @@ public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleS public bool IsStatic => UnderlyingField.IsStatic; /// - public ITypeSymbol[] GetOptionalCustomModifiers() + public virtual ITypeSymbol[] GetOptionalCustomModifiers() { return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); } /// - public ITypeSymbol[] GetRequiredCustomModifiers() + public virtual ITypeSymbol[] GetRequiredCustomModifiers() { return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs index c2e1b3afda..984f167a89 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs @@ -1,7 +1,6 @@ using System; using System.Reflection; using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; using System.Threading; using IKVM.CoreLib.Collections; @@ -40,8 +39,10 @@ public ReflectionFieldTable(ReflectionSymbolContext context, IReflectionModuleSy /// Gets or creates the cached for the type by field. /// /// + /// + /// /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) { if (field is null) throw new ArgumentNullException(nameof(field)); @@ -58,10 +59,10 @@ public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) if (_table[row] == null) using (_lock.CreateWriteLock()) if (field is FieldBuilder builder) - return _table[row] ??= new ReflectionFieldSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder?)_type, builder); + return _table[row] ??= new ReflectionFieldSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder?)_type, builder, requiredCustomModifiers, optionalCustomModifiers); else return _table[row] ??= new ReflectionFieldSymbol(_context, _module, _type, field); - + return _table[row] ?? throw new InvalidOperationException(); } } @@ -70,10 +71,12 @@ public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) /// Gets or creates the cached for the type by field. /// /// + /// + /// /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) { - return (IReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field); + return (IReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field, requiredCustomModifiers, optionalCustomModifiers); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs index 5aa9ccfada..b33ae45c33 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs @@ -106,7 +106,7 @@ public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) throw new NotSupportedException(); } - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) { throw new NotImplementedException(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs index 783d68a8d4..c57bc860ba 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs @@ -2,8 +2,10 @@ using System.Diagnostics.CodeAnalysis; using System.Linq; using System.Reflection; +using System.Reflection.Emit; using IKVM.CoreLib.Reflection; +using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -113,6 +115,22 @@ public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModule return base.ResolveFieldSymbol(field); } + /// + [return: NotNullIfNotNull(nameof(field))] + public override IReflectionFieldSymbolBuilder? ResolveFieldSymbol(FieldBuilder? field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) + { + if (field is null) + return null; + + if (field == UnderlyingMember) + return (IReflectionFieldSymbolBuilder)this; + + if (field.Module == _module.UnderlyingModule) + return _module.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); + + return base.ResolveFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); + } + /// [return: NotNullIfNotNull(nameof(property))] public override IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index 33ff9fa02f..5822b5e616 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -74,7 +74,7 @@ public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) #region IMethodSymbol /// - public IParameterSymbol ReturnParameter => ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); + public IParameterSymbol ReturnParameter => GetReturnParameter(); /// /// Gets the return type of the method. @@ -84,6 +84,8 @@ IParameterSymbol GetReturnParameter() { if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) return GetReturnParameterForMethodOnTypeBuilderInstantiation(); + else if (IsComplete) + return ResolveParameterSymbol(UnderlyingRuntimeMethod.ReturnParameter); else return ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index 5e6ba8deb5..fcac53de7e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -320,16 +320,16 @@ public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) if (field.DeclaringType is { } dt) return ResolveTypeSymbol(dt).GetOrCreateFieldSymbol(field); else - return _fieldTable.GetOrCreateFieldSymbol(field); + return _fieldTable.GetOrCreateFieldSymbol(field, ResolveTypeSymbols(field.GetRequiredCustomModifiers()), ResolveTypeSymbols(field.GetOptionalCustomModifiers())); } /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) { if (field.DeclaringType is { } dt) - return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateFieldSymbol(field); + return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); else - return _fieldTable.GetOrCreateFieldSymbol(field); + return _fieldTable.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs index b6c191b516..0cbdc11897 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs @@ -286,12 +286,12 @@ public virtual IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder /// [return: NotNullIfNotNull(nameof(field))] - public virtual IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field) + public virtual IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) { if (field is null) throw new ArgumentNullException(nameof(field)); - return _context.GetOrCreateFieldSymbol(field); + return _context.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index b10d2f16ae..aef481677e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -290,9 +290,9 @@ public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) /// /// /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? optionalCustomModifiers, ITypeSymbol[]? requiredCustomModifiers) { - return GetOrCreateModuleSymbol((ModuleBuilder)field.Module).GetOrCreateFieldSymbol(field); + return GetOrCreateModuleSymbol((ModuleBuilder)field.Module).GetOrCreateFieldSymbol(field, optionalCustomModifiers, requiredCustomModifiers); } /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs index 4edd57cb35..50afe94770 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs @@ -93,13 +93,13 @@ public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder meth /// public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) { - return _fieldTable.GetOrCreateFieldSymbol(field); + return _fieldTable.GetOrCreateFieldSymbol(field, null, null); } /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field) + public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) { - return _fieldTable.GetOrCreateFieldSymbol(field); + return _fieldTable.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); } /// @@ -285,10 +285,10 @@ public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() #else /// - public virtual bool IsFunctionPointer => throw new NotImplementedException(); + public virtual bool IsFunctionPointer => throw new NotImplementedException(); /// - public virtual bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + public virtual bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); #endif diff --git a/src/IKVM.Runtime/StubGen/StubGenerator.cs b/src/IKVM.Runtime/StubGen/StubGenerator.cs index 9b6aa01982..b8543551e0 100644 --- a/src/IKVM.Runtime/StubGen/StubGenerator.cs +++ b/src/IKVM.Runtime/StubGen/StubGenerator.cs @@ -913,7 +913,7 @@ public PackageConstantHandle Map(PackageConstantHandle handle) object[] GetAnnotation(CustomAttribute cad) { // attribute is either a AnnotationAttributeBase or a DynamicAnnotationAttribute with a single object[] in our internal annotation format - if (cad.ConstructorArguments.Length == 1 && cad.ConstructorArguments[0].ArgumentType == context.Types.Object.MakeArrayType() && (cad.Constructor.DeclaringType.BaseType == context.Resolver.ResolveBaseType(typeof(ikvm.@internal.AnnotationAttributeBase).FullName) || cad.Constructor.DeclaringType == context.Resolver.ResolveBaseType(typeof(DynamicAnnotationAttribute).FullName))) + if (cad.ConstructorArguments.Length == 1 && cad.ConstructorArguments[0].ArgumentType == context.Types.Object.MakeArrayType() && (cad.Constructor.DeclaringType.BaseType == context.Resolver.ResolveBaseType(typeof(ikvm.@internal.AnnotationAttributeBase).FullName) || cad.Constructor.DeclaringType == context.Resolver.ResolveRuntimeType(typeof(DynamicAnnotationAttribute).FullName))) { return UnpackArray((IList)cad.ConstructorArguments[0].Value); } From 39311135a1031971974dd113795c17b513a6cc73 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sun, 20 Oct 2024 21:23:04 -0500 Subject: [PATCH 48/59] More. --- .../Reflection/ReflectionExtensions.cs | 6 ++++ .../Emit/ReflectionMethodSymbolBuilder.cs | 1 + .../Reflection/ReflectionMethodSymbol.cs | 28 +++++++++++++++++-- 3 files changed, 32 insertions(+), 3 deletions(-) diff --git a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs index b7966e9d05..1fef51a679 100644 --- a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs +++ b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs @@ -20,6 +20,7 @@ static class ReflectionExtensions static readonly ParameterExpression _eventBuilderParameter = Expression.Parameter(typeof(EventBuilder), "p"); static readonly ParameterExpression _parameterBuilderParameter = Expression.Parameter(typeof(ParameterBuilder), "p"); + static readonly Type _methodBuilderInstantiationType = typeof(TypeBuilder).Assembly.GetType("System.Reflection.Emit.MethodBuilderInstantiation", true)!; static readonly Type _constructorOnTypeBuilderInstantiationType = typeof(TypeBuilder).Assembly.GetType("System.Reflection.Emit.ConstructorOnTypeBuilderInstantiation", true)!; static readonly Type _methodOnTypeBuilderInstantiationType = typeof(TypeBuilder).Assembly.GetType("System.Reflection.Emit.MethodOnTypeBuilderInstantiation", true)!; static readonly Type _fieldOnTypeBuilderInstantiationType = typeof(TypeBuilder).Assembly.GetType("System.Reflection.Emit.FieldOnTypeBuilderInstantiation", true)!; @@ -192,6 +193,11 @@ static class ReflectionExtensions _eventBuilderParameter) .Compile(); + /// + /// Gets the type. + /// + public static Type MethodBuilderInstantiationType => _methodBuilderInstantiationType; + /// /// Gets the type. /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs index 9a30c7a88e..a4a788c0a8 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs @@ -96,6 +96,7 @@ public void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequi UnderlyingMethodBuilder.SetSignature(returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack()); } + /// public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) { var l = UnderlyingMethodBuilder.DefineGenericParameters(names); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index 5822b5e616..bc75e98a5e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -3,8 +3,6 @@ using System.Reflection.Emit; using System.Threading; -using IKVM.CoreLib.Threading; -using IKVM.CoreLib.Collections; using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Reflection.Emit; @@ -41,7 +39,31 @@ public ReflectionMethodSymbol(ReflectionSymbolContext context, IReflectionModule public virtual MethodInfo UnderlyingMethod => _method; /// - public virtual MethodInfo UnderlyingRuntimeMethod => _method; + public virtual MethodInfo UnderlyingRuntimeMethod => GetUnderlyingRuntimeMethod(); + + /// + /// Gets the underlying runtime method. + /// + /// + MethodInfo GetUnderlyingRuntimeMethod() + { + if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) + return GetUnderlyingRuntimeMethodForMethodOnTypeBuilderInstantiation(); + else if (ReflectionExtensions.MethodBuilderInstantiationType.IsInstanceOfType(_method)) + return GetUnderlyingRuntimeMethodForMethodBuilderInstantiationType(); + else + return _method; + } + + MethodInfo GetUnderlyingRuntimeMethodForMethodOnTypeBuilderInstantiation() + { + return _method; + } + + MethodInfo GetUnderlyingRuntimeMethodForMethodBuilderInstantiationType() + { + return _method; + } /// public override MethodBase UnderlyingMethodBase => UnderlyingMethod; From f86b12ae301ce3a3ab9923d3e9a344aa754af667 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Tue, 22 Oct 2024 13:13:15 -0500 Subject: [PATCH 49/59] Space. Remove folder. --- .../Diagnostics/DiagnosticChannelWriterExtensions.cs | 1 - src/IKVM.Tools.Core/IKVM.Tools.Core.csproj | 4 ---- 2 files changed, 5 deletions(-) diff --git a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelWriterExtensions.cs b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelWriterExtensions.cs index 799ae0f0eb..85c900ba40 100644 --- a/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelWriterExtensions.cs +++ b/src/IKVM.Tools.Core/Diagnostics/DiagnosticChannelWriterExtensions.cs @@ -1,6 +1,5 @@ using System; using System.Buffers; -using System.IO; namespace IKVM.Tools.Core.Diagnostics { diff --git a/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj b/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj index 5205a8c686..891c614dcb 100644 --- a/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj +++ b/src/IKVM.Tools.Core/IKVM.Tools.Core.csproj @@ -23,9 +23,5 @@ - - - - From 542c29b44e3aa74df70ee0a310fcfc8502661dfc Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Sat, 26 Oct 2024 11:31:49 -0500 Subject: [PATCH 50/59] Hmm --- Directory.Build.props | 4 + .../Reflection/ReflectionSymbolTests.cs | 4 +- src/IKVM.CoreLib/Buffers/MemoryExtensons.cs | 11 + src/IKVM.CoreLib/Buffers/SequenceReader.cs | 505 +++++++++ .../Buffers/SequenceReaderExtensions.cs | 392 +++++++ .../Collections/EnumerableExtensions.cs | 73 ++ .../GenericTypeParameterSymbolBuilderBase.cs | 606 +++++++++++ .../IGenericTypeParameterSymbolBuilder.cs | 2 +- .../Symbols/Emit/IModuleSymbolBuilder.cs | 82 +- .../Symbols/Emit/ITypeSymbolBuilder.cs | 51 +- .../Symbols/Emit/TypeSymbolBuilderBase.cs | 977 ++++++++++++++++++ src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs | 7 +- src/IKVM.CoreLib/Symbols/ITypeSymbol.cs | 161 ++- ...ectionGenericTypeParameterSymbolBuilder.cs | 6 +- .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 8 +- ...kvmReflectionGenericTypeParameterSymbol.cs | 6 +- .../IkvmReflectionTypeSymbol.cs | 6 +- ...ectionGenericTypeParameterSymbolBuilder.cs | 4 +- .../Emit/ReflectionTypeSymbolBuilder.cs | 52 +- .../Reflection/ReflectionArrayTypeSymbol.cs | 4 +- .../Reflection/ReflectionByRefTypeSymbol.cs | 4 +- ...flectionGenericInstantiationTypeSymbol.cs} | 46 +- .../ReflectionGenericTypeParameterSymbol.cs | 10 +- .../ReflectionGenericTypeParameterTable.cs | 2 +- .../Reflection/ReflectionPointerTypeSymbol.cs | 4 +- .../Reflection/ReflectionSZArrayTypeSymbol.cs | 4 +- ...peSymbol.cs => ReflectionTypeDefSymbol.cs} | 4 +- .../Reflection/ReflectionTypeSpecSymbol.cs | 12 +- .../Reflection/ReflectionTypeSpecTable.cs | 6 +- .../Reflection/ReflectionTypeSymbolBase.cs | 6 +- .../Symbols/Reflection/ReflectionTypeTable.cs | 2 +- src/IKVM.CoreLib/Symbols/SymbolUtil.cs | 164 ++- .../Symbols/TypeSymbolNameParserHelpers.cs | 393 +++++++ .../Symbols/TypeSymbolNameParserResult.cs | 41 + .../Symbols/TypeSymbolNameReader.cs | 270 +++++ src/IKVM.Reflection/Type.cs | 10 +- .../RuntimeManagedByteCodeJavaType.cs | 3 +- 37 files changed, 3691 insertions(+), 251 deletions(-) create mode 100644 src/IKVM.CoreLib/Buffers/MemoryExtensons.cs create mode 100644 src/IKVM.CoreLib/Buffers/SequenceReader.cs create mode 100644 src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs create mode 100644 src/IKVM.CoreLib/Collections/EnumerableExtensions.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs rename src/IKVM.CoreLib/Symbols/Reflection/{ReflectionGenericSpecTypeSymbol.cs => ReflectionGenericInstantiationTypeSymbol.cs} (80%) rename src/IKVM.CoreLib/Symbols/Reflection/{ReflectionTypeSymbol.cs => ReflectionTypeDefSymbol.cs} (84%) create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs diff --git a/Directory.Build.props b/Directory.Build.props index bde86f5e56..bc21f1c585 100644 --- a/Directory.Build.props +++ b/Directory.Build.props @@ -7,6 +7,10 @@ win-x64;win-x86;win-arm64;linux-x64;linux-arm;linux-arm64;linux-musl-x64;linux-musl-arm;linux-musl-arm64;osx-x64;osx-arm64 $(SupportedImageRuntimes) + win-x64;win-x86 + win-x64;win-x86 + win-x64;win-x86 + <_SupportedRuntimes>;$(SupportedRuntimes); <_EnabledRuntimes>;$(EnabledRuntimes); <_SupportedToolRuntimes>;$(SupportedToolRuntimes); diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs index f12186725c..f083a2a698 100644 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs @@ -61,7 +61,7 @@ public void SameTypeShouldBeSame() var c = new ReflectionSymbolContext(); var s1 = c.GetOrCreateTypeSymbol(typeof(object)); var s2 = c.GetOrCreateTypeSymbol(typeof(object)); - s1.Should().BeOfType(); + s1.Should().BeOfType(); s1.Should().BeSameAs(s2); } @@ -222,7 +222,7 @@ public void CanReadCustomAttributes() var s = c.GetOrCreateTypeSymbol(typeof(ClassWithAttributeWithType)); var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithType))); var v = a.Value.ConstructorArguments[0].Value; - v.Should().BeOfType(); + v.Should().BeOfType(); } [TestMethod] diff --git a/src/IKVM.CoreLib/Buffers/MemoryExtensons.cs b/src/IKVM.CoreLib/Buffers/MemoryExtensons.cs new file mode 100644 index 0000000000..4f424d01d1 --- /dev/null +++ b/src/IKVM.CoreLib/Buffers/MemoryExtensons.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Buffers +{ + + internal static class MemoryExtensons + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Buffers/SequenceReader.cs b/src/IKVM.CoreLib/Buffers/SequenceReader.cs new file mode 100644 index 0000000000..853c59328d --- /dev/null +++ b/src/IKVM.CoreLib/Buffers/SequenceReader.cs @@ -0,0 +1,505 @@ +// Copyright (c) All contributors. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +/* Licensed to the .NET Foundation under one or more agreements. + * The .NET Foundation licenses this file to you under the MIT license. + * See the LICENSE file in the project root for more information. */ + +using System; +using System.Buffers; +using System.Diagnostics; +using System.Runtime.CompilerServices; + +namespace IKVM.CoreLib.Buffers +{ + +#if NETFRAMEWORK + + internal ref partial struct SequenceReader + where T : unmanaged, IEquatable + { + + /// + /// A value indicating whether we're using (as opposed to . + /// + private bool usingSequence; + + /// + /// Backing for the entire sequence when we're not using . + /// + private ReadOnlySequence sequence; + + /// + /// The position at the start of the . + /// + private SequencePosition currentPosition; + + /// + /// The position at the end of the . + /// + private SequencePosition nextPosition; + + /// + /// Backing for the entire sequence when we're not using . + /// + private ReadOnlyMemory memory; + + /// + /// A value indicating whether there is unread data remaining. + /// + private bool moreData; + + /// + /// The total number of elements in the sequence. + /// + private long length; + + /// + /// Initializes a new instance of the struct + /// over the given . + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public SequenceReader(ReadOnlySequence sequence) + { + this.usingSequence = true; + this.CurrentSpanIndex = 0; + this.Consumed = 0; + this.sequence = sequence; + this.memory = default; + this.currentPosition = sequence.Start; + this.length = -1; + + ReadOnlySpan first = sequence.First.Span; + this.nextPosition = sequence.GetPosition(first.Length); + this.CurrentSpan = first; + this.moreData = first.Length > 0; + + if (!this.moreData && !sequence.IsSingleSegment) + { + this.moreData = true; + this.GetNextSpan(); + } + } + + /// + /// Initializes a new instance of the struct + /// over the given . + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public SequenceReader(ReadOnlyMemory memory) + { + this.usingSequence = false; + this.CurrentSpanIndex = 0; + this.Consumed = 0; + this.memory = memory; + this.CurrentSpan = memory.Span; + this.length = memory.Length; + this.moreData = memory.Length > 0; + + this.currentPosition = default; + this.nextPosition = default; + this.sequence = default; + } + + /// + /// Gets a value indicating whether there is no more data in the . + /// + public bool End => !this.moreData; + + /// + /// Gets the underlying for the reader. + /// + public ReadOnlySequence Sequence + { + get + { + if (this.sequence.IsEmpty && !this.memory.IsEmpty) + { + // We're in memory mode (instead of sequence mode). + // Lazily fill in the sequence data. + this.sequence = new ReadOnlySequence(this.memory); + this.currentPosition = this.sequence.Start; + this.nextPosition = this.sequence.End; + } + + return this.sequence; + } + } + + /// + /// Gets the current position in the . + /// + public SequencePosition Position + => this.Sequence.GetPosition(this.CurrentSpanIndex, this.currentPosition); + + /// + /// Gets the current segment in the as a span. + /// + public ReadOnlySpan CurrentSpan { get; private set; } + + /// + /// Gets the index in the . + /// + public int CurrentSpanIndex { get; private set; } + + /// + /// Gets the unread portion of the . + /// + public ReadOnlySpan UnreadSpan + { + [MethodImpl(MethodImplOptions.AggressiveInlining)] + get => this.CurrentSpan.Slice(this.CurrentSpanIndex); + } + + /// + /// Gets the total number of 's processed by the reader. + /// + public long Consumed { get; private set; } + + /// + /// Gets remaining 's in the reader's . + /// + public long Remaining => this.Length - this.Consumed; + + /// + /// Gets count of in the reader's . + /// + public long Length + { + [MethodImpl(MethodImplOptions.AggressiveInlining)] + get + { + if (this.length < 0) + { + // Cache the length + this.length = this.Sequence.Length; + } + + return this.length; + } + } + + /// + /// Peeks at the next value without advancing the reader. + /// + /// The next value or default if at the end. + /// False if at the end of the reader. + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public bool TryPeek(out T value) + { + if (this.moreData) + { + value = this.CurrentSpan[this.CurrentSpanIndex]; + return true; + } + else + { + value = default; + return false; + } + } + + /// + /// Read the next value and advance the reader. + /// + /// The next value or default if at the end. + /// False if at the end of the reader. + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public bool TryRead(out T value) + { + if (this.End) + { + value = default; + return false; + } + + value = this.CurrentSpan[this.CurrentSpanIndex]; + this.CurrentSpanIndex++; + this.Consumed++; + + if (this.CurrentSpanIndex >= this.CurrentSpan.Length) + { + if (this.usingSequence) + { + this.GetNextSpan(); + } + else + { + this.moreData = false; + } + } + + return true; + } + + /// + /// Move the reader back the specified number of items. + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public void Rewind(long count) + { + if (count < 0) + { + throw new ArgumentOutOfRangeException(nameof(count)); + } + + this.Consumed -= count; + + if (this.CurrentSpanIndex >= count) + { + this.CurrentSpanIndex -= (int)count; + this.moreData = true; + } + else if (this.usingSequence) + { + // Current segment doesn't have enough data, scan backward through segments + this.RetreatToPreviousSpan(this.Consumed); + } + else + { + throw new ArgumentOutOfRangeException("Rewind went past the start of the memory."); + } + } + + [MethodImpl(MethodImplOptions.NoInlining)] + private void RetreatToPreviousSpan(long consumed) + { + Debug.Assert(this.usingSequence, "usingSequence"); + this.ResetReader(); + this.Advance(consumed); + } + + private void ResetReader() + { + Debug.Assert(this.usingSequence, "usingSequence"); + this.CurrentSpanIndex = 0; + this.Consumed = 0; + this.currentPosition = this.Sequence.Start; + this.nextPosition = this.currentPosition; + + if (this.Sequence.TryGet(ref this.nextPosition, out ReadOnlyMemory memory, advance: true)) + { + this.moreData = true; + + if (memory.Length == 0) + { + this.CurrentSpan = default; + + // No data in the first span, move to one with data + this.GetNextSpan(); + } + else + { + this.CurrentSpan = memory.Span; + } + } + else + { + // No data in any spans and at end of sequence + this.moreData = false; + this.CurrentSpan = default; + } + } + + /// + /// Get the next segment with available data, if any. + /// + private void GetNextSpan() + { + Debug.Assert(this.usingSequence, "usingSequence"); + if (!this.Sequence.IsSingleSegment) + { + SequencePosition previousNextPosition = this.nextPosition; + while (this.Sequence.TryGet(ref this.nextPosition, out ReadOnlyMemory memory, advance: true)) + { + this.currentPosition = previousNextPosition; + if (memory.Length > 0) + { + this.CurrentSpan = memory.Span; + this.CurrentSpanIndex = 0; + return; + } + else + { + this.CurrentSpan = default; + this.CurrentSpanIndex = 0; + previousNextPosition = this.nextPosition; + } + } + } + + this.moreData = false; + } + + /// + /// Move the reader ahead the specified number of items. + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public void Advance(long count) + { + const long TooBigOrNegative = unchecked((long)0xFFFFFFFF80000000); + if ((count & TooBigOrNegative) == 0 && this.CurrentSpan.Length - this.CurrentSpanIndex > (int)count) + { + this.CurrentSpanIndex += (int)count; + this.Consumed += count; + } + else if (this.usingSequence) + { + // Can't satisfy from the current span + this.AdvanceToNextSpan(count); + } + else if (this.CurrentSpan.Length - this.CurrentSpanIndex == (int)count) + { + this.CurrentSpanIndex += (int)count; + this.Consumed += count; + this.moreData = false; + } + else + { + throw new ArgumentOutOfRangeException(nameof(count)); + } + } + + /// + /// Unchecked helper to avoid unnecessary checks where you know count is valid. + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + internal void AdvanceCurrentSpan(long count) + { + Debug.Assert(count >= 0, "count >= 0"); + + this.Consumed += count; + this.CurrentSpanIndex += (int)count; + if (this.usingSequence && this.CurrentSpanIndex >= this.CurrentSpan.Length) + { + this.GetNextSpan(); + } + } + + /// + /// Only call this helper if you know that you are advancing in the current span + /// with valid count and there is no need to fetch the next one. + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + internal void AdvanceWithinSpan(long count) + { + Debug.Assert(count >= 0, "count >= 0"); + + this.Consumed += count; + this.CurrentSpanIndex += (int)count; + + Debug.Assert(this.CurrentSpanIndex < this.CurrentSpan.Length, "this.CurrentSpanIndex < this.CurrentSpan.Length"); + } + + /// + /// Move the reader ahead the specified number of items + /// if there are enough elements remaining in the sequence. + /// + /// true if there were enough elements to advance; otherwise false. + internal bool TryAdvance(long count) + { + if (this.Remaining < count) + { + return false; + } + + this.Advance(count); + return true; + } + + private void AdvanceToNextSpan(long count) + { + Debug.Assert(this.usingSequence, "usingSequence"); + if (count < 0) + { + throw new ArgumentOutOfRangeException(nameof(count)); + } + + this.Consumed += count; + while (this.moreData) + { + int remaining = this.CurrentSpan.Length - this.CurrentSpanIndex; + + if (remaining > count) + { + this.CurrentSpanIndex += (int)count; + count = 0; + break; + } + + // As there may not be any further segments we need to + // push the current index to the end of the span. + this.CurrentSpanIndex += remaining; + count -= remaining; + Debug.Assert(count >= 0, "count >= 0"); + + this.GetNextSpan(); + + if (count == 0) + { + break; + } + } + + if (count != 0) + { + // Not enough data left- adjust for where we actually ended and throw + this.Consumed -= count; + throw new ArgumentOutOfRangeException(nameof(count)); + } + } + + /// + /// Copies data from the current to the given span. + /// + /// Destination to copy to. + /// True if there is enough data to copy to the . + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public bool TryCopyTo(Span destination) + { + ReadOnlySpan firstSpan = this.UnreadSpan; + if (firstSpan.Length >= destination.Length) + { + firstSpan.Slice(0, destination.Length).CopyTo(destination); + return true; + } + + return this.TryCopyMultisegment(destination); + } + + internal bool TryCopyMultisegment(Span destination) + { + if (this.Remaining < destination.Length) + { + return false; + } + + ReadOnlySpan firstSpan = this.UnreadSpan; + Debug.Assert(firstSpan.Length < destination.Length, "firstSpan.Length < destination.Length"); + firstSpan.CopyTo(destination); + int copied = firstSpan.Length; + + SequencePosition next = this.nextPosition; + while (this.Sequence.TryGet(ref next, out ReadOnlyMemory nextSegment, true)) + { + if (nextSegment.Length > 0) + { + ReadOnlySpan nextSpan = nextSegment.Span; + int toCopy = Math.Min(nextSpan.Length, destination.Length - copied); + nextSpan.Slice(0, toCopy).CopyTo(destination.Slice(copied)); + copied += toCopy; + if (copied >= destination.Length) + { + break; + } + } + } + + return true; + } + + } + +#endif + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs b/src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs new file mode 100644 index 0000000000..4609baa440 --- /dev/null +++ b/src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs @@ -0,0 +1,392 @@ +using System; +using System.Buffers; +using System.Buffers.Binary; +using System.Diagnostics; +using System.Numerics; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +namespace IKVM.CoreLib.Buffers +{ + + static partial class SequenceReaderExtensions + { + + /// + /// Try to read the given type out of the buffer if possible. Warning: this is dangerous to use with arbitrary + /// structs- see remarks for full details. + /// + /// + /// IMPORTANT: The read is a straight copy of bits. If a struct depends on specific state of its members to + /// behave correctly this can lead to exceptions, etc. If reading endian specific integers, use the explicit + /// overloads such as . + /// + /// + /// True if successful. will be default if failed (due to lack of space). + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static unsafe bool TryRead(ref this SequenceReader reader, out T value) + where T : unmanaged + { + var span = reader.UnreadSpan; + if (span.Length < sizeof(T)) + return TryReadMultisegment(ref reader, out value); + + value = Unsafe.ReadUnaligned(ref MemoryMarshal.GetReference(span)); + reader.Advance(sizeof(T)); + return true; + } + + static unsafe bool TryReadMultisegment(ref SequenceReader reader, out T value) + where T : unmanaged + { + Debug.Assert(reader.UnreadSpan.Length < sizeof(T), "reader.UnreadSpan.Length < sizeof(T)"); + + // Not enough data in the current segment, try to peek for the data we need. + var buffer = default(T); + var tempSpan = new Span(&buffer, sizeof(T)); + + if (!reader.TryCopyTo(tempSpan)) + { + value = default; + return false; + } + + value = Unsafe.ReadUnaligned(ref MemoryMarshal.GetReference(tempSpan)); + reader.Advance(sizeof(T)); + return true; + } + + /// + /// Reads an from the next position in the sequence. + /// + /// The reader to read from. + /// Receives the value read. + /// true if there was another byte in the sequence; false otherwise. + public static bool TryRead(ref this SequenceReader reader, out sbyte value) + { + if (TryRead(ref reader, out byte byteValue)) + { + value = unchecked((sbyte)byteValue); + return true; + } + + value = default; + return false; + } + +#if NETFRAMEWORK + + /// + /// Reads an as big endian. + /// + /// False if there wasn't enough data for an . + public static bool TryReadBigEndian(ref this SequenceReader reader, out short value) + { + if (!BitConverter.IsLittleEndian) + { + return reader.TryRead(out value); + } + + return TryReadReverseEndianness(ref reader, out value); + } + +#endif + + /// + /// Reads an as big endian. + /// + /// False if there wasn't enough data for an . + public static bool TryReadBigEndian(ref this SequenceReader reader, out ushort value) + { + if (reader.TryReadBigEndian(out short shortValue)) + { + value = unchecked((ushort)shortValue); + return true; + } + + value = default; + return false; + } + + private static bool TryReadReverseEndianness(ref SequenceReader reader, out short value) + { + if (reader.TryRead(out value)) + { + value = BinaryPrimitives.ReverseEndianness(value); + return true; + } + + return false; + } + +#if NETFRAMEWORK + + /// + /// Reads an as big endian. + /// + /// False if there wasn't enough data for an . + public static bool TryReadBigEndian(ref this SequenceReader reader, out int value) + { + return BitConverter.IsLittleEndian ? TryReadReverseEndianness(ref reader, out value) : reader.TryRead(out value); + } + +#endif + + /// + /// Reads an as big endian. + /// + /// False if there wasn't enough data for an . + public static bool TryReadBigEndian(ref this SequenceReader reader, out uint value) + { + if (reader.TryReadBigEndian(out int intValue)) + { + value = unchecked((uint)intValue); + return true; + } + + value = default; + return false; + } + + static bool TryReadReverseEndianness(ref SequenceReader reader, out int value) + { + if (reader.TryRead(out value)) + { + value = BinaryPrimitives.ReverseEndianness(value); + return true; + } + + return false; + } + +#if NETFRAMEWORK + + /// + /// Reads an as big endian. + /// + /// False if there wasn't enough data for an . + public static bool TryReadBigEndian(ref this SequenceReader reader, out long value) + { + return BitConverter.IsLittleEndian ? TryReadReverseEndianness(ref reader, out value) : reader.TryRead(out value); + } + +#endif + + /// + /// Reads an as big endian. + /// + /// False if there wasn't enough data for an . + public static bool TryReadBigEndian(ref this SequenceReader reader, out ulong value) + { + if (reader.TryReadBigEndian(out long longValue)) + { + value = unchecked((ulong)longValue); + return true; + } + + value = default; + return false; + } + + static bool TryReadReverseEndianness(ref SequenceReader reader, out long value) + { + if (reader.TryRead(out value)) + { + value = BinaryPrimitives.ReverseEndianness(value); + return true; + } + + return false; + } + + /// + /// Reads a as big endian. + /// + /// False if there wasn't enough data for a . + public static unsafe bool TryReadBigEndian(ref this SequenceReader reader, out float value) + { + if (reader.TryReadBigEndian(out int intValue)) + { + value = *(float*)&intValue; + return true; + } + + value = default; + return false; + } + + /// + /// Reads a as big endian. + /// + /// False if there wasn't enough data for a . + public static unsafe bool TryReadBigEndian(ref this SequenceReader reader, out double value) + { + if (reader.TryReadBigEndian(out long longValue)) + { + value = *(double*)&longValue; + return true; + } + + value = default; + return false; + } + + /// + /// Try to read data with given . + /// + /// Read count. + /// The read data, if successfully read requested data. + /// true if remaining items in current is enough for . + public static bool TryReadExact(ref this SequenceReader reader, int count, out ReadOnlySequence sequence) + where T : unmanaged, IEquatable + { + if (count < 0) + throw new ArgumentOutOfRangeException(nameof(count)); + + if (count > reader.Remaining) + { + sequence = default; + return false; + } + + sequence = reader.Sequence.Slice(reader.Position, count); + if (count != 0) + reader.Advance(count); + + return true; + } + + /// + /// Try to read data with given . + /// + /// Read count. + /// The read data, if successfully read requested data. + /// true if remaining items in current is enough for . + public static bool TryReadExact(ref this SequenceReader reader, long count, out ReadOnlySequence sequence) + where T : unmanaged, IEquatable + { + if (count < 0) + throw new ArgumentOutOfRangeException(nameof(count)); + + if (count > reader.Remaining) + { + sequence = default; + return false; + } + + sequence = reader.Sequence.Slice(reader.Position, count); + if (count != 0) + reader.Advance(count); + + return true; + } + + /// + /// Tries to advance the reader over the specified number of bytes. + /// + /// + /// + /// + public static bool TryAdvance(ref this SequenceReader reader, long count) + where T : unmanaged, IEquatable + { + return reader.TryReadExact(count, out _); + } + + + /// + /// Advances bytes up until the alignment is met. + /// + public static bool TryAlign(ref this SequenceReader reader, int alignment) + where T : unmanaged, IEquatable + { + var position = (int)reader.Consumed; + return TryAdvance(ref reader, CalculateAlignment(position, alignment) - position); + } + + /// + /// Returns the number of bits set on the specified . + /// + /// + /// + static int PopCount(int v) + { + return PopCount(unchecked((uint)v)); + } + + /// + /// Returns the number of bits set on the specified . + /// + /// + /// + static int PopCount(uint v) + { +#if NET + return BitOperations.PopCount(v); +#else + unchecked + { + v -= ((v >> 1) & 0x55555555u); + v = (v & 0x33333333u) + ((v >> 2) & 0x33333333u); + return (int)((v + (v >> 4) & 0xF0F0F0Fu) * 0x1010101u) >> 24; + } +#endif + } + + /// + /// Calculates the alignment based on the current position and alignment. + /// + /// + /// + /// + static int CalculateAlignment(int position, int alignment) + { + Debug.Assert(position >= 0 && alignment > 0); + Debug.Assert(PopCount(alignment) == 1); + + int result = position & ~(alignment - 1); + if (result == position) + return result; + + return result + alignment; + } + + /// + /// Skip consecutive instances of any of the given . + /// + /// How many positions the reader has been advanced. + public static long AdvancePastAny(this ref SequenceReader reader, scoped ReadOnlySpan values) + where T : unmanaged, IEquatable + { + var start = reader.Consumed; + + do + { + // Advance past all matches in the current span + int i; + for (i = reader.CurrentSpanIndex; i < reader.CurrentSpan.Length && values.IndexOf(reader.CurrentSpan[i]) != -1; i++) + { + continue; + } + + int advanced = i - reader.CurrentSpanIndex; + if (advanced == 0) + { + // Didn't advance at all in this span, exit. + break; + } + + reader.Advance(advanced); + + // If we're at position 0 after advancing and not at the End, + // we're in a new span and should continue the loop. + } + while (reader.CurrentSpanIndex == 0 && !reader.End); + + return reader.Consumed - start; + } + + } + +} diff --git a/src/IKVM.CoreLib/Collections/EnumerableExtensions.cs b/src/IKVM.CoreLib/Collections/EnumerableExtensions.cs new file mode 100644 index 0000000000..c62a088114 --- /dev/null +++ b/src/IKVM.CoreLib/Collections/EnumerableExtensions.cs @@ -0,0 +1,73 @@ +using System; +using System.Collections.Generic; + +namespace IKVM.CoreLib.Collections +{ + + static class EnumerableExtensions + { + + public static TSource? SingleOrDefaultOrThrow(this IEnumerable source, Func exception) + { + if (source == null) + throw new ArgumentNullException(nameof(source)); + if (exception == null) + throw new ArgumentNullException(nameof(exception)); + + if (source is IReadOnlyList list) + { + switch (list.Count) + { + case 0: + return default; + case 1: + return list[0]; + } + } + else + { + using IEnumerator enumerator = source.GetEnumerator(); + if (enumerator.MoveNext() == false) + return default; + + var current = enumerator.Current; + if (enumerator.MoveNext() == false) + return current; + } + + throw exception(); + } + + public static TSource? SingleOrDefaultOrThrow(this IEnumerable source, Predicate predicate, Func exception) + { + if (source == null) + throw new ArgumentNullException(nameof(source)); + if (predicate == null) + throw new ArgumentNullException(nameof(predicate)); + if (exception == null) + throw new ArgumentNullException(nameof(exception)); + + var val = default(TSource); + var num = 0; + + foreach (var item in source) + { + if (predicate(item)) + { + val = item; + if ((++num) >= 2) + throw exception(); + } + } + + return num switch + { + 0 => default, + 1 => val, + _ => throw new InvalidOperationException(), + }; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs b/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs new file mode 100644 index 0000000000..b7fa430396 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs @@ -0,0 +1,606 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class GenericTypeParameterSymbolBuilderBase : IGenericTypeParameterSymbolBuilder + { + + readonly ISymbolContext _context; + readonly IModuleSymbolBuilder _module; + readonly IMemberSymbolBuilder _member; + readonly string _name; + + GenericParameterAttributes _attributes; + ITypeSymbol? _baseTypeConstraint; + ImmutableArray _interfaceConstraints = ImmutableArray.Empty; + ImmutableList _customAttributes = ImmutableList.Empty; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public GenericTypeParameterSymbolBuilderBase(ISymbolContext context, IModuleSymbolBuilder module, IMemberSymbolBuilder member, string name) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _member = member ?? throw new ArgumentNullException(nameof(member)); + _name = name ?? throw new ArgumentNullException(nameof(name)); + } + + /// + public ISymbolContext Context => _context; + + /// + public IModuleSymbolBuilder ResolvingModuleBuilder => _module; + + /// + public IMemberSymbolBuilder ResolvingMemberBuilder => _member; + + #region IGenericTypeParameterSymbolBuilder + + /// + public void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint) + { + _baseTypeConstraint = baseTypeConstraint; + } + + /// + public void SetGenericParameterAttributes(GenericParameterAttributes attributes) + { + _attributes = attributes; + } + + /// + public void SetInterfaceConstraints(params ITypeSymbol[] interfaceConstraints) + { + _interfaceConstraints = interfaceConstraints.ToImmutableArray(); + } + + #endregion + + #region ICustomAttributeProviderBuilder + + /// + public void SetCustomAttribute(CustomAttribute attribute) + { + _customAttributes = _customAttributes.Add(attribute); + } + + #endregion + + #region ITypeSymbol + + /// + public virtual IAssemblySymbol Assembly => ResolvingModuleBuilder.Assembly; + + /// + public virtual string? AssemblyQualifiedName => System.Reflection.Assembly.CreateQualifiedName(Assembly.FullName, FullName); + + /// + public virtual TypeAttributes Attributes => _attributes; + + /// + public virtual ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); + + /// + public virtual bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; + + /// + public virtual IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); + + /// + public virtual string? FullName => UnderlyingType.FullName; + + /// + public virtual string? Namespace => UnderlyingType.Namespace; + + /// + public virtual GenericParameterAttributes GenericParameterAttributes => UnderlyingType.GenericParameterAttributes; + + /// + public virtual int GenericParameterPosition => UnderlyingType.GenericParameterPosition; + + /// + public virtual ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); + + /// + public virtual bool HasElementType => UnderlyingType.HasElementType; + + /// + public virtual TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); + + /// + public virtual bool IsAbstract => UnderlyingType.IsAbstract; + + /// + public virtual bool IsSZArray => UnderlyingType.IsSZArray(); + + /// + public virtual bool IsArray => UnderlyingType.IsArray; + + /// + public virtual bool IsAutoLayout => UnderlyingType.IsAutoLayout; + + /// + public virtual bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; + + /// + public virtual bool IsByRef => UnderlyingType.IsByRef; + + /// + public virtual bool IsClass => UnderlyingType.IsClass; + + /// + public virtual bool IsEnum => UnderlyingType.IsEnum; + + /// + public virtual bool IsInterface => UnderlyingType.IsInterface; + + /// + public virtual bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; + + /// + public virtual bool IsGenericParameter => UnderlyingType.IsGenericParameter; + + /// + public virtual bool IsGenericType => UnderlyingType.IsGenericType; + + /// + public virtual bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; + + /// + public virtual bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; + + /// + public virtual bool IsNested => UnderlyingType.IsNested; + + /// + public virtual bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; + + /// + public virtual bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; + + /// + public virtual bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; + + /// + public virtual bool IsNestedFamily => UnderlyingType.IsNestedFamily; + + /// + public virtual bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; + + /// + public virtual bool IsNestedPublic => UnderlyingType.IsNestedPublic; + + /// + public virtual bool IsNotPublic => UnderlyingType.IsNotPublic; + + /// + public virtual bool IsPointer => UnderlyingType.IsPointer; + +#if NET8_0_OR_GREATER + + /// + public virtual bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; + + /// + public virtual bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; + +#else + + /// + public virtual bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public virtual bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + +#endif + + /// + public virtual bool IsPrimitive => UnderlyingType.IsPrimitive; + + /// + public virtual bool IsPublic => UnderlyingType.IsPublic; + + /// + public virtual bool IsSealed => UnderlyingType.IsSealed; + + /// + public virtual bool IsSerializable => UnderlyingType.IsSerializable; + + /// + public virtual bool IsValueType => UnderlyingType.IsValueType; + + /// + public virtual bool IsVisible => UnderlyingType.IsVisible; + + /// + public virtual bool IsSignatureType => throw new NotImplementedException(); + + /// + public virtual bool IsSpecialName => UnderlyingType.IsSpecialName; + + /// + public virtual IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); + + /// + public virtual int GetArrayRank() + { + return UnderlyingType.GetArrayRank(); + } + + /// + public virtual IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) + { + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null)); + } + + /// + public virtual IConstructorSymbol? GetConstructor(ITypeSymbol[] types) + { + return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); + } + + /// + public virtual IConstructorSymbol[] GetConstructors() + { + return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); + } + + /// + public virtual IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) + { + return ResolveConstructorSymbols(UnderlyingType.GetConstructors(bindingAttr)); + } + + /// + public virtual IMemberSymbol[] GetDefaultMembers() + { + return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); + } + + /// + public virtual ITypeSymbol? GetElementType() + { + return ResolveTypeSymbol(UnderlyingType.GetElementType()); + } + + /// + public virtual string? GetEnumName(object value) + { + return UnderlyingType.GetEnumName(value); + } + + /// + public virtual string[] GetEnumNames() + { + return UnderlyingType.GetEnumNames(); + } + + /// + public virtual ITypeSymbol GetEnumUnderlyingType() + { + return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); + } + + /// + public virtual Array GetEnumValues() + { + return UnderlyingType.GetEnumValues(); + } + + /// + public virtual IEventSymbol? GetEvent(string name) + { + return ResolveEventSymbol(UnderlyingType.GetEvent(name)); + } + + /// + public virtual IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) + { + return ResolveEventSymbol(UnderlyingType.GetEvent(name, bindingAttr)); + } + + /// + public virtual IEventSymbol[] GetEvents() + { + return ResolveEventSymbols(UnderlyingType.GetEvents()); + } + + /// + public virtual IEventSymbol[] GetEvents(BindingFlags bindingAttr) + { + return ResolveEventSymbols(UnderlyingType.GetEvents(bindingAttr)); + } + + /// + public virtual IFieldSymbol? GetField(string name) + { + return ResolveFieldSymbol(UnderlyingType.GetField(name)); + } + + /// + public virtual IFieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + return ResolveFieldSymbol(UnderlyingType.GetField(name, bindingAttr)); + } + + /// + public virtual IFieldSymbol[] GetFields() + { + return ResolveFieldSymbols(UnderlyingType.GetFields()); + } + + /// + public virtual IFieldSymbol[] GetFields(BindingFlags bindingAttr) + { + return ResolveFieldSymbols(UnderlyingType.GetFields(bindingAttr)); + } + + /// + public virtual ITypeSymbol[] GetGenericArguments() + { + return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); + } + + /// + public virtual ITypeSymbol[] GetGenericParameterConstraints() + { + return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); + } + + /// + public virtual ITypeSymbol GetGenericTypeDefinition() + { + return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); + } + + /// + public virtual ITypeSymbol? GetInterface(string name) + { + return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); + } + + /// + public virtual ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); + } + + /// + public virtual InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); + } + + /// + public virtual ITypeSymbol[] GetInterfaces(bool inherit = true) + { + if (inherit) + return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); + else + throw new NotImplementedException(); + } + + /// + public virtual IMemberSymbol[] GetMembers(string name) + { + return ResolveMemberSymbols(UnderlyingType.GetMember(name)); + } + + /// + public virtual IMemberSymbol[] GetMembers(string name, BindingFlags bindingAttr) + { + return ResolveMemberSymbols(UnderlyingType.GetMember(name, bindingAttr)); + } + + /// + public virtual IMemberSymbol[] GetMembers(string name, MemberTypes type, BindingFlags bindingAttr) + { + return ResolveMemberSymbols(UnderlyingType.GetMember(name, type, bindingAttr)); + } + + /// + public virtual IMemberSymbol[] GetMembers(BindingFlags bindingAttr) + { + return ResolveMemberSymbols(UnderlyingType.GetMembers(bindingAttr)); + } + + /// + public virtual IMemberSymbol[] GetMembers() + { + return ResolveMemberSymbols(UnderlyingType.GetMembers()); + } + + /// + public virtual IMethodSymbol? GetMethod(string name) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr)); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers?.Unpack())); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) + { + throw new NotImplementedException(); + } + + /// + public virtual IMethodSymbol[] GetMethods(BindingFlags bindingAttr) + { + return ResolveMethodSymbols(UnderlyingType.GetMethods(bindingAttr)); + } + + /// + public virtual IMethodSymbol[] GetMethods() + { + return ResolveMethodSymbols(UnderlyingType.GetMethods()); + } + + /// + public virtual ITypeSymbol? GetNestedType(string name) + { + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); + } + + /// + public virtual ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, bindingAttr)); + } + + /// + public virtual ITypeSymbol[] GetNestedTypes() + { + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); + } + + /// + public virtual ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) + { + return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); + } + + /// + public virtual IPropertySymbol[] GetProperties() + { + return ResolvePropertySymbols(UnderlyingType.GetProperties()); + } + + /// + public virtual IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) + { + return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); + } + + /// + public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); + } + + /// + public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); + } + + /// + public virtual IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); + } + + /// + public virtual IPropertySymbol? GetProperty(string name) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); + } + + /// + public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); + } + + /// + public virtual bool IsAssignableFrom(ITypeSymbol? c) + { + return UnderlyingType.IsAssignableFrom(c?.Unpack()); + } + + /// + public virtual bool IsEnumDefined(object value) + { + return UnderlyingType.IsEnumDefined(value); + } + + /// + public virtual bool IsSubclassOf(ITypeSymbol c) + { + return UnderlyingType.IsSubclassOf(c.Unpack()); + } + + /// + public virtual ITypeSymbol MakeArrayType() + { + return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); + } + + /// + public virtual ITypeSymbol MakeArrayType(int rank) + { + return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); + } + + /// + public virtual ITypeSymbol MakeByRefType() + { + return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); + } + + /// + public virtual ITypeSymbol MakePointerType() + { + return ResolveTypeSymbol(UnderlyingType.MakePointerType()); + } + + /// + public virtual ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) + { + return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); + } + +#endregion + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs index cfd742441a..575c05d768 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs @@ -20,7 +20,7 @@ interface IGenericTypeParameterSymbolBuilder : ISymbolBuilder, ITyp /// Sets the interfaces a type must implement in order to be substituted for the type parameter. /// /// - void SetInterfaceConstraints(params ITypeSymbol[]? interfaceConstraints); + void SetInterfaceConstraints(params ITypeSymbol[] interfaceConstraints); } diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs index efdd7a7ad7..7413e2fad1 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Immutable; using System.Diagnostics.SymbolStore; using System.IO; using System.Reflection; @@ -71,7 +72,7 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes); /// /// Defines a global method with the specified name, attributes, calling convention, return type, custom modifiers for the return type, parameter types, and custom modifiers for the parameter types. @@ -86,7 +87,7 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? requiredReturnTypeCustomModifiers, ITypeSymbol[]? optionalReturnTypeCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredParameterTypeCustomModifiers, ITypeSymbol[][]? optionalParameterTypeCustomModifiers); + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList requiredReturnTypeCustomModifiers, IImmutableList optionalReturnTypeCustomModifiers, IImmutableList parameterTypes, IImmutableList> requiredParameterTypeCustomModifiers, IImmutableList> optionalParameterTypeCustomModifiers); /// /// Defines a global method with the specified name, attributes, return type, and parameter types. @@ -96,7 +97,7 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes); /// /// Constructs a TypeBuilder for a private type with the specified name in this module. @@ -161,7 +162,79 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces); + ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces); + + /// + /// Defines a nested type, given its name. + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name); + + /// + /// Defines a nested type, given its name and attributes. + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr); + + /// + /// Defines a nested type, given its name, attributes, and the type that it extends. + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent); + + /// + /// Defines a nested type, given its name, attributes, the type that it extends, and the interfaces that it implements. + /// + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces); + + /// + /// Defines a nested type, given its name, attributes, size, and the type that it extends. + /// + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize); + + /// + /// Defines a nested type, given its name, attributes, the type that it extends, and the packing size. + /// + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize); + + /// + /// Defines a nested type, given its name, attributes, size, and the type that it extends. + /// + /// + /// + /// + /// + /// + /// + /// + ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize); /// /// Explicitely adds a reference to the specified assembly. @@ -180,6 +253,7 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// void Save(PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine); + } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs index dfa306cf8a..5a05624bb5 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs @@ -1,4 +1,7 @@ -using System.Reflection; +using System.Collections.Immutable; +using System.Reflection; +using System.Reflection.Emit; +using System.Runtime.InteropServices; namespace IKVM.CoreLib.Symbols.Emit { @@ -17,7 +20,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names); + IImmutableList DefineGenericParameters(IImmutableList names); /// /// Defines the initializer for this type. @@ -37,7 +40,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, ITypeSymbol[]? parameterTypes); + IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, IImmutableList parameterTypes); /// /// Adds a new constructor to the type, with the given attributes and signature. @@ -46,7 +49,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IConstructorSymbolBuilder DefineConstructor(System.Reflection.MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol[]? parameterTypes); + IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes); /// /// Adds a new constructor to the type, with the given attributes, signature, and custom modifiers. @@ -57,7 +60,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? requiredCustomModifiers, ITypeSymbol[][]? optionalCustomModifiers); + IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, IImmutableList> optionalCustomModifiers); /// /// Defines the parameterless constructor. The constructor defined here will simply call the parameterless constructor of the parent. @@ -93,7 +96,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers, FieldAttributes attributes); + IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, IImmutableList requiredCustomModifiers, IImmutableList optionalCustomModifiers, FieldAttributes attributes); /// /// Adds a new method to the type, with the specified name, method attributes, calling convention, method signature, and custom modifiers. @@ -108,7 +111,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); + IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); /// /// Adds a new method to the type, with the specified name, method attributes, calling convention, and method signature. @@ -119,7 +122,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes); /// /// Adds a new method to the type, with the specified name, method attributes, and calling convention. @@ -128,7 +131,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention); + IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention); /// /// Adds a new method to the type, with the specified name and method attributes. @@ -136,7 +139,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes); + IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes); /// /// Adds a new method to the type, with the specified name, method attributes, and method signature. @@ -146,7 +149,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes); /// /// Specifies a given method body that implements a given method declaration, potentially with a different name. @@ -163,7 +166,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, ITypeSymbol[]? interfaces); + ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces); /// /// Defines a nested type, given its name, attributes, size, and the type that it extends. @@ -174,7 +177,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize, int typeSize); + ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize); /// /// Defines a nested type, given its name, attributes, the type that it extends, and the packing size. @@ -184,7 +187,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, System.Reflection.Emit.PackingSize packSize); + ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize); /// /// Defines a nested type, given its name. @@ -200,7 +203,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent); + ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent); /// /// Defines a nested type, given its name and attributes. @@ -208,7 +211,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr); + ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr); /// /// Defines a nested type, given its name, attributes, the total size of the type, and the type that it extends. @@ -218,7 +221,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - ITypeSymbolBuilder DefineNestedType(string name, System.Reflection.TypeAttributes attr, ITypeSymbol? parent, int typeSize); + ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize); /// /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. @@ -232,7 +235,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); + IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); /// /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. @@ -247,7 +250,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); + IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); /// /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, the PInvoke flags, and custom modifiers for the parameters and return type. @@ -266,7 +269,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); + IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet); /// /// Adds a new property to the type, with the given name and property signature. @@ -276,7 +279,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes); + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList parameterTypes); /// /// Adds a new property to the type, with the given name, attributes, calling convention, and property signature. @@ -287,7 +290,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? parameterTypes); + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList parameterTypes); /// /// Adds a new property to the type, with the given name, property signature, and custom modifiers. @@ -301,7 +304,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); /// /// Adds a new property to the type, with the given name, calling convention, property signature, and custom modifiers. @@ -316,7 +319,7 @@ interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder /// /// /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); + IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); /// /// Finishes the type, updating the associated symbol. diff --git a/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs b/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs new file mode 100644 index 0000000000..5c0818432b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs @@ -0,0 +1,977 @@ +using System; +using System.Collections.Immutable; +using System.Diagnostics; +using System.Linq; +using System.Reflection; +using System.Reflection.Emit; +using System.Runtime.InteropServices; + +using IKVM.CoreLib.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + abstract class TypeSymbolBuilderBase : ITypeSymbolBuilder + { + + const BindingFlags DefaultBindingFlags = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance; + + readonly ISymbolContext _context; + readonly IModuleSymbolBuilder _module; + + string _name; + TypeAttributes _attributes; + ITypeSymbol? _parentType; + ImmutableList _genericTypeParameters = ImmutableList.Empty; + ImmutableList _interfaces = ImmutableList.Empty; + ImmutableList _fields = ImmutableList.Empty; + ImmutableList _constructors = ImmutableList.Empty; + ImmutableList _methods = ImmutableList.Empty; + ImmutableList<(IMethodSymbol, IMethodSymbol)> _methodOverrides = ImmutableList<(IMethodSymbol, IMethodSymbol)>.Empty; + ImmutableList _properties = ImmutableList.Empty; + ImmutableList _events = ImmutableList.Empty; + ImmutableList _customAttributes = ImmutableList.Empty; + + /// + /// Initializes a new instance. + /// + /// + /// + public TypeSymbolBuilderBase(ISymbolContext context, IModuleSymbolBuilder module, TypeAttributes attributes) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _attributes = attributes; + } + + /// + public ISymbolContext Context => _context; + + /// + public IModuleSymbolBuilder ResolvingModuleBuilder => _module; + + #region ITypeSymbolBuilder + + /// + public void SetParent(ITypeSymbol? parent) + { + _parentType = parent; + } + + /// + public IImmutableList DefineGenericParameters(IImmutableList names) + { + if (names.Count >= 1 && _genericTypeParameters.IsEmpty == false) + throw new InvalidOperationException("Generic parameters already defined."); + + var a = ImmutableList.Create(); + for (int i = 0; i < names.Count; i++) + a = a.Add(CreateGenericParameter(names[i])); + + return _genericTypeParameters = a; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + protected abstract IGenericTypeParameterSymbolBuilder CreateGenericParameter(string name); + + /// + public void AddInterfaceImplementation(ITypeSymbol interfaceType) + { + _interfaces = _interfaces.Add(interfaceType); + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + /// + /// + /// + public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, IImmutableList> optionalCustomModifiers) + { + var constructor = CreateConstructorBuilder(attributes, callingConvention, parameterTypes, requiredCustomModifiers, optionalCustomModifiers); + _constructors = _constructors.Add(constructor); + return constructor; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + /// + /// + protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, IImmutableList> optionalCustomModifiers); + + /// + public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, IImmutableList parameterTypes) + { + var constructor = CreateConstructorBuilder(attributes, parameterTypes); + _constructors = _constructors.Add(constructor); + return constructor; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, IImmutableList parameterTypes); + + /// + public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes) + { + var constructor = CreateConstructorBuilder(attributes, callingConvention, parameterTypes); + _constructors = _constructors.Add(constructor); + return constructor; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes); + + /// + public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, ImmutableArray> optionalCustomModifiers) + { + var constructor = CreateConstructorBuilder(attributes, callingConvention, parameterTypes, requiredCustomModifiers, optionalCustomModifiers); + _constructors = _constructors.Add(constructor); + return constructor; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + /// + /// + protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, ImmutableArray> optionalCustomModifiers); + + /// + public IConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes) + { + var constructor = CreateConstructorBuilder(attributes); + _constructors = _constructors.Add(constructor); + return constructor; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes); + + /// + public IEventSymbolBuilder DefineEvent(string name, EventAttributes attributes, ITypeSymbol eventtype) + { + var @event = CreateEventBuilder(name, attributes, eventtype); + _events = _events.Add(@event); + return @event; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + protected abstract IEventSymbolBuilder CreateEventBuilder(string name, EventAttributes attributes, ITypeSymbol eventtype); + + /// + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, FieldAttributes attributes) + { + var field = CreateFieldBuilder(fieldName, type, attributes); + _fields = _fields.Add(field); + return field; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + protected abstract IFieldSymbolBuilder CreateFieldBuilder(string fieldName, ITypeSymbol type, FieldAttributes attributes); + + /// + public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, IImmutableList requiredCustomModifiers, IImmutableList optionalCustomModifiers, FieldAttributes attributes) + { + var field = CreateFieldBuilder(fieldName, type, requiredCustomModifiers, optionalCustomModifiers, attributes); + _fields = _fields.Add(field); + return field; + } + + /// + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + /// + /// + protected abstract IFieldSymbolBuilder CreateFieldBuilder(string fieldName, ITypeSymbol type, IImmutableList requiredCustomModifiers, IImmutableList optionalCustomModifiers, FieldAttributes attributes); + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers) + { + var method = CreateMethodBuilder(name, attributes, callingConvention, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers); + _methods = _methods.Add(method); + return method; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes) + { + var method = CreateMethodBuilder(name, attributes, callingConvention, returnType, parameterTypes); + _methods = _methods.Add(method); + return method; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + /// + /// + protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes); + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention) + { + var method = CreateMethodBuilder(name, attributes, callingConvention); + _methods = _methods.Add(method); + return method; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, CallingConventions callingConvention); + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes) + { + var method = CreateMethodBuilder(name, attributes); + _methods = _methods.Add(method); + return method; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes); + + /// + public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes) + { + var method = CreateMethodBuilder(name, attributes, returnType, parameterTypes); + _methods = _methods.Add(method); + return method; + } + + /// + /// Override this method to implement the creation of a . + /// + /// + /// + /// + /// + /// + protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes); + + /// + public void DefineMethodOverride(IMethodSymbol methodInfoBody, IMethodSymbol methodInfoDeclaration) + { + _methodOverrides = _methodOverrides.Add((methodInfoBody, methodInfoDeclaration)); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name) + { + return _module.DefineNestedType(this, name); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr) + { + return _module.DefineNestedType(this, name, attr); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent) + { + return _module.DefineNestedType(this, name, attr, parent); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces) + { + return _module.DefineNestedType(this, name, attr, parent, interfaces); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize) + { + return _module.DefineNestedType(this, name, attr, parent, typeSize); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize) + { + return _module.DefineNestedType(this, name, attr, parent, packSize); + } + + /// + public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize) + { + return _module.DefineNestedType(this, name, attr, parent, packSize, typeSize); + } + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + var method = CreatePInvokeMethodBuilder(name, dllName, attributes, callingConvention, returnType, parameterTypes, nativeCallConv, nativeCharSet); + _methods = _methods.Add(method); + return method; + } + + protected abstract IMethodSymbolBuilder CreatePInvokeMethodBuilder(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet); + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + var method = CreatePInvokeMethodBuilder(name, dllName, entryName, attributes, callingConvention, returnType, parameterTypes, nativeCallConv, nativeCharSet); + _methods = _methods.Add(method); + return method; + } + + protected abstract IMethodSymbolBuilder CreatePInvokeMethodBuilder(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet); + + /// + public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + var method = CreatePInvokeMethodBuilder(name, dllName, entryName, attributes, callingConvention, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers, nativeCallConv, nativeCharSet); + _methods = _methods.Add(method); + return method; + } + + protected abstract IMethodSymbolBuilder CreatePInvokeMethodBuilder(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet); + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList parameterTypes) + { + var property = CreatePropertyBuilder(name, attributes, returnType, parameterTypes); + _properties = _properties.Add(property); + return property; + } + + protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList parameterTypes); + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList parameterTypes) + { + var property = CreatePropertyBuilder(name, attributes, callingConvention, returnType, parameterTypes); + _properties = _properties.Add(property); + return property; + } + + protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList parameterTypes); + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers) + { + var property = CreatePropertyBuilder(name, attributes, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers); + _properties = _properties.Add(property); + return property; + } + + protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); + + /// + public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers) + { + var property = CreatePropertyBuilder(name, attributes, callingConvention, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers); + _properties = _properties.Add(property); + return property; + } + + protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); + + /// + public IConstructorSymbolBuilder DefineTypeInitializer() + { + var constructor = CreateTypeInitializerBuilder(); + _constructors = _constructors.Add(constructor); + return constructor; + } + + protected abstract IConstructorSymbolBuilder CreateTypeInitializerBuilder(); + + #endregion + + #region ICustomAttributeProviderBuilder + + /// + public void SetCustomAttribute(CustomAttribute attribute) + { + _customAttributes = _customAttributes.Add(attribute); + } + + #endregion + + #region ITypeSymbol + + public void Foo() + { + System.Reflection.Metadata.TypeName t; + } + + public TypeAttributes Attributes => _attributes; + + public IAssemblySymbol Assembly => _module.Assembly; + + public IMethodBaseSymbol? DeclaringMethod => null; + + public string? AssemblyQualifiedName => System.Reflection.Assembly.CreateQualifiedName(Assembly.FullName, FullName); + + public string? FullName => _name; + + public string? Namespace => throw new NotImplementedException(); + + public TypeCode TypeCode => throw new NotImplementedException(); + + public ITypeSymbol? BaseType => throw new NotImplementedException(); + + public bool ContainsGenericParameters => throw new NotImplementedException(); + + public GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); + + public int GenericParameterPosition => throw new NotImplementedException(); + + public IImmutableList GenericTypeArguments => throw new NotImplementedException(); + + public bool IsConstructedGenericType => throw new NotImplementedException(); + + public bool IsGenericType => throw new NotImplementedException(); + + public bool IsGenericTypeDefinition => throw new NotImplementedException(); + + public bool IsGenericParameter => throw new NotImplementedException(); + + public bool IsAutoLayout => throw new NotImplementedException(); + + public bool IsExplicitLayout => throw new NotImplementedException(); + + public bool IsLayoutSequential => throw new NotImplementedException(); + + public bool HasElementType => throw new NotImplementedException(); + + public bool IsClass => throw new NotImplementedException(); + + public bool IsValueType => throw new NotImplementedException(); + + public bool IsInterface => throw new NotImplementedException(); + + public bool IsPrimitive => throw new NotImplementedException(); + + public bool IsSZArray => throw new NotImplementedException(); + + public bool IsArray => throw new NotImplementedException(); + + public bool IsEnum => throw new NotImplementedException(); + + public bool IsPointer => throw new NotImplementedException(); + + public bool IsFunctionPointer => throw new NotImplementedException(); + + public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + + public bool IsByRef => throw new NotImplementedException(); + + public bool IsAbstract => throw new NotImplementedException(); + + public bool IsSealed => throw new NotImplementedException(); + + public bool IsVisible => throw new NotImplementedException(); + + public bool IsPublic => throw new NotImplementedException(); + + public bool IsNotPublic => throw new NotImplementedException(); + + public bool IsNested => throw new NotImplementedException(); + + public bool IsNestedAssembly => throw new NotImplementedException(); + + public bool IsNestedFamANDAssem => throw new NotImplementedException(); + + public bool IsNestedFamily => throw new NotImplementedException(); + + public bool IsNestedFamORAssem => throw new NotImplementedException(); + + public bool IsNestedPrivate => throw new NotImplementedException(); + + public bool IsNestedPublic => throw new NotImplementedException(); + + public bool IsSerializable => throw new NotImplementedException(); + + public bool IsSignatureType => throw new NotImplementedException(); + + public bool IsSpecialName => throw new NotImplementedException(); + + public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); + + public IModuleSymbol Module => throw new NotImplementedException(); + + public ITypeSymbol? DeclaringType => throw new NotImplementedException(); + + public MemberTypes MemberType => throw new NotImplementedException(); + + public int MetadataToken => throw new NotImplementedException(); + + public string Name => throw new NotImplementedException(); + + public bool IsMissing => throw new NotImplementedException(); + + public bool ContainsMissing => throw new NotImplementedException(); + + public bool IsComplete => throw new NotImplementedException(); + + public int GetArrayRank() + { + throw new NotImplementedException(); + } + + public IImmutableList GetDefaultMembers() + { + throw new NotImplementedException(); + } + + public ITypeSymbol? GetElementType() + { + throw new NotImplementedException(); + } + + public string? GetEnumName(object value) + { + throw new NotImplementedException(); + } + + public IImmutableList GetEnumNames() + { + throw new NotImplementedException(); + } + + public ITypeSymbol GetEnumUnderlyingType() + { + throw new NotImplementedException(); + } + + public IImmutableList GetGenericArguments() + { + throw new NotImplementedException(); + } + + public IImmutableList GetGenericParameterConstraints() + { + throw new NotImplementedException(); + } + + public ITypeSymbol GetGenericTypeDefinition() + { + throw new NotImplementedException(); + } + + public ITypeSymbol? GetInterface(string name) + { + throw new NotImplementedException(); + } + + public ITypeSymbol? GetInterface(string name, bool ignoreCase) + { + throw new NotImplementedException(); + } + + public IImmutableList GetInterfaces(bool inherit = true) + { + throw new NotImplementedException(); + } + + public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) + { + throw new NotImplementedException(); + } + + public IImmutableList GetDeclaredConstructors() + { + throw new NotImplementedException(); + } + + public IConstructorSymbol? GetConstructor(IImmutableList types) + { + throw new NotImplementedException(); + } + + public IConstructorSymbol? GetConstructor(BindingFlags bindingFlags, IImmutableList types) + { + throw new NotImplementedException(); + } + + public IImmutableList GetConstructors() + { + throw new NotImplementedException(); + } + + public IImmutableList GetConstructors(BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IFieldSymbol? GetField(string name) + { + throw new NotImplementedException(); + } + + public IFieldSymbol? GetField(string name, BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IImmutableList GetFields() + { + throw new NotImplementedException(); + } + + public IImmutableList GetFields(BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IImmutableList GetDeclaredMethods() + { + throw new NotImplementedException(); + } + + /// + public IMethodSymbol? GetMethod(string name) + { + return SymbolUtil.SelectMethod(this, DefaultBindingFlags, name, null, null); + } + + /// + public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList? types, IImmutableList? modifiers) + { + return SymbolUtil.SelectMethod(this, DefaultBindingFlags, name, types, modifiers); + } + + public IMethodSymbol? GetMethod(string name, IImmutableList types) + { + throw new NotImplementedException(); + } + + public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList types) + { + throw new NotImplementedException(); + } + + public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers) + { + throw new NotImplementedException(); + } + + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers) + { + throw new NotImplementedException(); + } + + public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, IImmutableList types, IImmutableList modifiers) + { + throw new NotImplementedException(); + } + + public IMethodSymbol? GetMethod(string name, int genericParameterCount, IImmutableList types, IImmutableList modifiers) + { + throw new NotImplementedException(); + } + + /// + public IImmutableList GetMethods() + { + return SymbolUtil.SelectMethods(this, DefaultBindingFlags, null, null, null); + } + + /// + public IImmutableList GetMethods(BindingFlags bindingFlags) + { + return SymbolUtil.SelectMethods(this, bindingFlags, null, null, null); + } + + public IImmutableList GetDeclaredProperties() + { + throw new NotImplementedException(); + } + + public IPropertySymbol? GetProperty(string name) + { + throw new NotImplementedException(); + } + + public IPropertySymbol? GetProperty(string name, BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IPropertySymbol? GetProperty(string name, IImmutableList types) + { + throw new NotImplementedException(); + } + + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, IImmutableList types) + { + throw new NotImplementedException(); + } + + public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) + { + throw new NotImplementedException(); + } + + public IImmutableList GetProperties() + { + throw new NotImplementedException(); + } + + public IImmutableList GetProperties(BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IImmutableList GetDeclaredEvents() + { + throw new NotImplementedException(); + } + + public IEventSymbol? GetEvent(string name) + { + throw new NotImplementedException(); + } + + public IEventSymbol? GetEvent(string name, BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IImmutableList GetEvents() + { + throw new NotImplementedException(); + } + + public IImmutableList GetEvents(BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public ITypeSymbol? GetNestedType(string name) + { + throw new NotImplementedException(); + } + + public ITypeSymbol? GetNestedType(string name, BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public IImmutableList GetNestedTypes() + { + throw new NotImplementedException(); + } + + public IImmutableList GetNestedTypes(BindingFlags bindingFlags) + { + throw new NotImplementedException(); + } + + public bool IsAssignableFrom(ITypeSymbol? c) + { + throw new NotImplementedException(); + } + + public bool IsSubclassOf(ITypeSymbol c) + { + throw new NotImplementedException(); + } + + public bool IsEnumDefined(object value) + { + throw new NotImplementedException(); + } + + public ITypeSymbol MakeArrayType() + { + throw new NotImplementedException(); + } + + public ITypeSymbol MakeArrayType(int rank) + { + throw new NotImplementedException(); + } + + public ITypeSymbol MakeGenericType(IImmutableList typeArguments) + { + throw new NotImplementedException(); + } + + public ITypeSymbol MakePointerType() + { + throw new NotImplementedException(); + } + + public ITypeSymbol MakeByRefType() + { + throw new NotImplementedException(); + } + + CustomAttribute[] ICustomAttributeProvider.GetCustomAttributes(bool inherit) + { + throw new NotImplementedException(); + } + + public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + { + throw new NotImplementedException(); + } + + #endregion + + #region ICustomAttributeProvider + + /// + public override IImmutableList GetCustomAttributes(bool inherit = false) + { + if (inherit == false || BaseType == null) + return _customAttributes?.ToArray() ?? []; + else + return Enumerable.Concat(_customAttributes?.ToArray() ?? [], ResolveCustomAttributes(BaseType.Unpack().GetInheritedCustomAttributesData())).ToArray(); + } + + /// + public override CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(inherit).FirstOrDefault(i => i.AttributeType == attributeType); + } + + /// + public override CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + { + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); + } + + #endregion + + /// + public void Complete() + { + if (_builder != null) + { + // complete type + if (_builder.IsCreated() == false) + { + _type = _builder.CreateType() ?? throw new InvalidOperationException(); + _methods = null; + _customAttributes = null; + } + + // force module to reresolve + Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); + OnComplete(); + } + } + + /// + public void OnComplete() + { + const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static; + + // apply the runtime generic type parameters and pass them to the symbols for completion + var srcGenericArgs = UnderlyingRuntimeType.GetGenericArguments() ?? []; + var dstGenericArgs = GetGenericArguments() ?? []; + Debug.Assert(srcGenericArgs.Length == dstGenericArgs.Length); + for (int i = 0; i < srcGenericArgs.Length; i++) + if (dstGenericArgs[i] is IReflectionGenericTypeParameterSymbolBuilder b) + b.OnComplete(srcGenericArgs[i]); + + foreach (var i in GetConstructors(DefaultBindingFlags) ?? []) + if (i is IReflectionConstructorSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetMethods(DefaultBindingFlags) ?? []) + if (i is IReflectionMethodSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetFields(DefaultBindingFlags) ?? []) + if (i is IReflectionFieldSymbolBuilder b) + b.OnComplete(); + + foreach (var i in GetProperties(DefaultBindingFlags) ?? []) + if (i is IReflectionPropertySymbolBuilder b) + b.OnComplete(); + + foreach (var m in GetEvents(DefaultBindingFlags) ?? []) + if (m is IReflectionPropertySymbolBuilder b) + b.OnComplete(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs index 00b6144a0e..99c9a74735 100644 --- a/src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs @@ -1,4 +1,5 @@ -using System.Reflection; +using System.Collections.Immutable; +using System.Reflection; namespace IKVM.CoreLib.Symbols { @@ -108,13 +109,13 @@ interface IMethodBaseSymbol : IMemberSymbol /// Returns an array of objects that represent the type arguments of a generic method or the type parameters of a generic method definition. /// /// - ITypeSymbol[] GetGenericArguments(); + ImmutableArray GetGenericArguments(); /// /// When overridden in a derived class, gets the parameters of the specified method or constructor. /// /// - IParameterSymbol[] GetParameters(); + ImmutableArray GetParameters(); /// /// When overridden in a derived class, returns the MethodImplAttributes flags. diff --git a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs index 21926c44b1..47f1d65324 100644 --- a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs @@ -1,4 +1,6 @@ using System; +using System.Collections.Generic; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols @@ -68,7 +70,7 @@ interface ITypeSymbol : IMemberSymbol /// /// Gets an array of the generic type arguments for this type. /// - ITypeSymbol[] GenericTypeArguments { get; } + IImmutableList GenericTypeArguments { get; } /// /// Gets a value that indicates whether this object represents a constructed generic type. You can create instances of a constructed generic type. @@ -255,7 +257,7 @@ interface ITypeSymbol : IMemberSymbol /// Searches for the members defined for the current whose DefaultMemberAttribute is set. /// /// - IMemberSymbol[] GetDefaultMembers(); + IImmutableList GetDefaultMembers(); /// /// When overridden in a derived class, returns the of the object encompassed or referred to by the current array, pointer or reference type. @@ -274,7 +276,7 @@ interface ITypeSymbol : IMemberSymbol /// Returns the names of the members of the current enumeration type. /// /// - string[] GetEnumNames(); + IImmutableList GetEnumNames(); /// /// Returns the underlying type of the current enumeration type. @@ -286,13 +288,13 @@ interface ITypeSymbol : IMemberSymbol /// Returns an array of objects that represent the type arguments of a closed generic type or the type parameters of a generic type definition. /// /// - ITypeSymbol[] GetGenericArguments(); + IImmutableList GetGenericArguments(); /// /// Returns an array of objects that represent the constraints on the current generic type parameter. /// /// - ITypeSymbol[] GetGenericParameterConstraints(); + IImmutableList GetGenericParameterConstraints(); /// /// Returns a object that represents a generic type definition from which the current generic type can be constructed. @@ -319,7 +321,7 @@ interface ITypeSymbol : IMemberSymbol /// When overridden in a derived class, gets all the interfaces implemented or if specified,inherited by the current . /// /// - ITypeSymbol[] GetInterfaces(bool inherit = true); + IImmutableList GetInterfaces(bool inherit = true); /// /// Returns an interface mapping for the specified interface type. @@ -329,69 +331,38 @@ interface ITypeSymbol : IMemberSymbol InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType); /// - /// Searches for the public members with the specified name. + /// Returns all the declared constructors of the current . /// - /// - /// - IMemberSymbol[] GetMember(string name); - - /// - /// Searches for the specified members, using the specified binding constraints. - /// - /// - /// - /// - IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr); - - /// - /// Searches for the specified members of the specified member type, using the specified binding constraints. - /// - /// - /// - /// /// - IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr); - - /// - /// Returns all the public members of the current . - /// - /// - IMemberSymbol[] GetMembers(); - - /// - /// When overridden in a derived class, searches for the members defined for the current , using the specified binding constraints. - /// - /// - /// - IMemberSymbol[] GetMembers(BindingFlags bindingAttr); + IImmutableList GetDeclaredConstructors(); /// /// Searches for a public instance constructor whose parameters match the types in the specified array. /// /// /// - IConstructorSymbol? GetConstructor(ITypeSymbol[] types); + IConstructorSymbol? GetConstructor(IImmutableList types); /// /// Searches for a constructor whose parameters match the specified argument types, using the specified binding constraints. /// - /// + /// /// /// - IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types); + IConstructorSymbol? GetConstructor(BindingFlags bindingFlags, IImmutableList types); /// /// Returns all the public constructors defined for the current . /// /// - IConstructorSymbol[] GetConstructors(); + IImmutableList GetConstructors(); /// /// When overridden in a derived class, searches for the constructors defined for the current , using the specified BindingFlags. /// - /// + /// /// - IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr); + IImmutableList GetConstructors(BindingFlags bindingFlags); /// /// Searches for the public field with the specified name. @@ -404,22 +375,28 @@ interface ITypeSymbol : IMemberSymbol /// Searches for the specified field, using the specified binding constraints. /// /// - /// + /// /// - IFieldSymbol? GetField(string name, BindingFlags bindingAttr); + IFieldSymbol? GetField(string name, BindingFlags bindingFlags); /// /// Returns all the public fields of the current . /// /// - IFieldSymbol[] GetFields(); + IImmutableList GetFields(); /// /// When overridden in a derived class, searches for the fields defined for the current , using the specified binding constraints. /// - /// + /// /// - IFieldSymbol[] GetFields(BindingFlags bindingAttr); + IImmutableList GetFields(BindingFlags bindingFlags); + + /// + /// Returns all the declared methods of the current . + /// + /// + IImmutableList GetDeclaredMethods(); /// /// Searches for the public method with the specified name. @@ -434,58 +411,58 @@ interface ITypeSymbol : IMemberSymbol /// /// /// - IMethodSymbol? GetMethod(string name, ITypeSymbol[] types); + IMethodSymbol? GetMethod(string name, IImmutableList types); /// /// Searches for the specified method, using the specified binding constraints. /// /// - /// + /// /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr); + IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags); /// /// Searches for the specified method whose parameters match the specified argument types, using the specified binding constraints. /// /// - /// + /// /// /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types); + IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList types); /// /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints and the specified calling convention. /// /// - /// + /// /// /// /// /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers); + IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers); /// /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints and the specified calling convention. /// /// /// - /// + /// /// /// /// /// - IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers); + IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers); /// /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints. /// /// /// - /// + /// /// /// /// - IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers); + IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, IImmutableList types, IImmutableList modifiers); /// /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints. @@ -495,7 +472,7 @@ interface ITypeSymbol : IMemberSymbol /// /// /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers); + IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, IImmutableList types, IImmutableList modifiers); /// /// Searches for the specified public method whose parameters match the specified generic parameter count, argument types and modifiers. @@ -505,20 +482,26 @@ interface ITypeSymbol : IMemberSymbol /// /// /// - IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers); + IMethodSymbol? GetMethod(string name, int genericParameterCount, IImmutableList types, IImmutableList modifiers); /// /// Returns all the public methods of the current . /// /// - IMethodSymbol[] GetMethods(); + IImmutableList GetMethods(); /// /// When overridden in a derived class, searches for the methods defined for the current , using the specified binding constraints. /// - /// + /// /// - IMethodSymbol[] GetMethods(BindingFlags bindingAttr); + IImmutableList GetMethods(BindingFlags bindingFlags); + + /// + /// Returns all the declared properties of the current . + /// + /// + IImmutableList GetDeclaredProperties(); /// /// Searches for the public property with the specified name. @@ -531,9 +514,9 @@ interface ITypeSymbol : IMemberSymbol /// Searches for the specified property, using the specified binding constraints. /// /// - /// + /// /// - IPropertySymbol? GetProperty(string name, BindingFlags bindingAttr); + IPropertySymbol? GetProperty(string name, BindingFlags bindingFlags); /// /// Searches for the specified public property whose parameters match the specified argument types. @@ -541,7 +524,7 @@ interface ITypeSymbol : IMemberSymbol /// /// /// - IPropertySymbol? GetProperty(string name, ITypeSymbol[] types); + IPropertySymbol? GetProperty(string name, IImmutableList types); /// /// Searches for the specified public property whose parameters match the specified argument types. @@ -550,7 +533,7 @@ interface ITypeSymbol : IMemberSymbol /// /// /// - IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types); + IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, IImmutableList types); /// /// Searches for the public property with the specified name and return type. @@ -564,42 +547,48 @@ interface ITypeSymbol : IMemberSymbol /// Returns all the public properties of the current . /// /// - IPropertySymbol[] GetProperties(); + IImmutableList GetProperties(); /// /// When overridden in a derived class, searches for the properties of the current , using the specified binding constraints. /// - /// + /// + /// + IImmutableList GetProperties(BindingFlags bindingFlags); + + /// + /// Returns all the declared events of the current . + /// /// - IPropertySymbol[] GetProperties(BindingFlags bindingAttr); + IImmutableList GetDeclaredEvents(); /// - /// Returns the EventInfo object representing the specified public event. + /// Returns the object representing the specified public event. /// /// /// IEventSymbol? GetEvent(string name); /// - /// When overridden in a derived class, returns the EventInfo object representing the specified event, using the specified binding constraints. + /// When overridden in a derived class, returns the object representing the specified event, using the specified binding constraints. /// /// - /// + /// /// - IEventSymbol? GetEvent(string name, BindingFlags bindingAttr); + IEventSymbol? GetEvent(string name, BindingFlags bindingFlags); /// /// Returns all the public events that are declared or inherited by the current . /// /// - IEventSymbol[] GetEvents(); + IImmutableList GetEvents(); /// /// When overridden in a derived class, searches for events that are declared or inherited by the current , using the specified binding constraints. /// - /// + /// /// - IEventSymbol[] GetEvents(BindingFlags bindingAttr); + IImmutableList GetEvents(BindingFlags bindingFlags); /// /// Searches for the public nested type with the specified name. @@ -612,22 +601,22 @@ interface ITypeSymbol : IMemberSymbol /// When overridden in a derived class, searches for the specified nested type, using the specified binding constraints. /// /// - /// + /// /// - ITypeSymbol? GetNestedType(string name, BindingFlags bindingAttr); + ITypeSymbol? GetNestedType(string name, BindingFlags bindingFlags); /// /// Returns the public types nested in the current . /// /// - ITypeSymbol[] GetNestedTypes(); + IImmutableList GetNestedTypes(); /// /// When overridden in a derived class, searches for the types nested in the current , using the specified binding constraints. /// - /// + /// /// - ITypeSymbol[] GetNestedTypes(BindingFlags bindingAttr); + IImmutableList GetNestedTypes(BindingFlags bindingFlags); /// /// Determines whether an instance of a specified type c can be assigned to a variable of the current type. @@ -668,7 +657,7 @@ interface ITypeSymbol : IMemberSymbol /// /// /// - ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments); + ITypeSymbol MakeGenericType(IImmutableList typeArguments); /// /// Returns a object that represents a pointer to the current type. diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs index ad8e18c994..a392b60621 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs @@ -486,19 +486,19 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) } /// - public IMemberSymbol[] GetMember(string name) + public IMemberSymbol[] GetMembers(string name) { return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs index 376f463cc4..948889034d 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs @@ -687,19 +687,19 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) } /// - public IMemberSymbol[] GetMember(string name) + public IMemberSymbol[] GetMembers(string name) { return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } @@ -815,7 +815,7 @@ IMethodSymbol[] GetIncompleteMethods(System.Reflection.BindingFlags bindingAttr if (_incompleteMethods == null) return []; else - return SymbolUtil.FilterMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); + return SymbolUtil.SelectMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); } /// diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs index 1b92b0131b..5ab7b330b0 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs @@ -436,19 +436,19 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) } /// - public IMemberSymbol[] GetMember(string name) + public IMemberSymbol[] GetMembers(string name) { return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } diff --git a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs index f9ab22f98b..153e846d51 100644 --- a/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSymbol.cs @@ -446,19 +446,19 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) } /// - public IMemberSymbol[] GetMember(string name) + public IMemberSymbol[] GetMembers(string name) { return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs index f181b5f3d0..a483bceb0c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs @@ -18,8 +18,8 @@ class ReflectionGenericTypeParameterSymbolBuilder : ReflectionGenericTypeParamet /// /// /// - public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionMemberSymbolBuilder resolvingMember, GenericTypeParameterBuilder builder) : - base(context, resolvingModule, resolvingMember, builder) + public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionMemberSymbolBuilder resolvingMember) : + base(context, resolvingModule, resolvingMember,) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs index ac8e95076a..3d393a04d0 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs @@ -18,8 +18,15 @@ class ReflectionTypeSymbolBuilder : ReflectionTypeSymbolBase, IReflectionTypeSym readonly TypeBuilder _builder; Type? _type; - List? _incompleteMethods; - List? _incompleteCustomAttributes; + ITypeSymbol _parentType; + List? _genericTypeParameters; + List _interfaces; + List _fields; + List? _constructors; + List? _methods; + List? _properties; + List? _events; + List? _customAttributes; /// /// Initializes a new instance. @@ -50,16 +57,15 @@ public ReflectionTypeSymbolBuilder(ReflectionSymbolContext context, IReflectionM /// public void SetParent(ITypeSymbol? parent) { - UnderlyingTypeBuilder.SetParent(parent?.Unpack()); + _parentType = (IReflectionTypeSymbol?)parent; } /// public IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names) { - var l = UnderlyingTypeBuilder.DefineGenericParameters(names); var a = new IGenericTypeParameterSymbolBuilder[l.Length]; for (int i = 0; i < l.Length; i++) - a[i] = ResolveGenericTypeParameterSymbol(l[i]); + a[i] = new ReflectionGenericTypeParameterSymbolBuilder(Context, ResolvingModuleBuilder, this); return a; } @@ -116,8 +122,8 @@ public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, IType public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers) { var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), returnTypeRequiredCustomModifiers?.Unpack(), returnTypeOptionalCustomModifiers?.Unpack(), parameterTypes?.Unpack(), parameterTypeRequiredCustomModifiers?.Unpack(), parameterTypeOptionalCustomModifiers?.Unpack())); - _incompleteMethods ??= []; - _incompleteMethods.Add(m); + _methods ??= []; + _methods.Add(m); return m; } @@ -125,8 +131,8 @@ public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attribute public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention, returnType?.Unpack(), parameterTypes?.Unpack())); - _incompleteMethods ??= []; - _incompleteMethods.Add(m); + _methods ??= []; + _methods.Add(m); return m; } @@ -134,8 +140,8 @@ public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAt public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, System.Reflection.CallingConventions callingConvention) { var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, (CallingConventions)callingConvention)); - _incompleteMethods ??= []; - _incompleteMethods.Add(m); + _methods ??= []; + _methods.Add(m); return m; } @@ -143,8 +149,8 @@ public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAt public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes) { var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes)); - _incompleteMethods ??= []; - _incompleteMethods.Add(m); + _methods ??= []; + _methods.Add(m); return m; } @@ -152,8 +158,8 @@ public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAt public IMethodSymbolBuilder DefineMethod(string name, System.Reflection.MethodAttributes attributes, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes) { var m = ResolveMethodSymbol(UnderlyingTypeBuilder.DefineMethod(name, (MethodAttributes)attributes, returnType?.Unpack(), parameterTypes?.Unpack())); - _incompleteMethods ??= []; - _incompleteMethods.Add(m); + _methods ??= []; + _methods.Add(m); return m; } @@ -257,8 +263,8 @@ public IConstructorSymbolBuilder DefineTypeInitializer() public void SetCustomAttribute(CustomAttribute attribute) { UnderlyingTypeBuilder.SetCustomAttribute(attribute.Unpack()); - _incompleteCustomAttributes ??= []; - _incompleteCustomAttributes.Add(attribute); + _customAttributes ??= []; + _customAttributes.Add(attribute); } #endregion @@ -319,10 +325,10 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) /// IMethodSymbol[] GetIncompleteMethods(BindingFlags bindingAttr = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance) { - if (_incompleteMethods == null) + if (_methods == null) return []; else - return SymbolUtil.FilterMethods(this, _incompleteMethods, bindingAttr).Cast().ToArray(); + return SymbolUtil.SelectMethods(this, _methods, bindingAttr).Cast().ToArray(); } #endregion @@ -335,9 +341,9 @@ public override CustomAttribute[] GetCustomAttributes(bool inherit = false) if (IsComplete) return ResolveCustomAttributes(UnderlyingRuntimeMember.GetCustomAttributesData(inherit).ToArray()); else if (inherit == false || BaseType == null) - return _incompleteCustomAttributes?.ToArray() ?? []; + return _customAttributes?.ToArray() ?? []; else - return Enumerable.Concat(_incompleteCustomAttributes?.ToArray() ?? [], ResolveCustomAttributes(BaseType.Unpack().GetInheritedCustomAttributesData())).ToArray(); + return Enumerable.Concat(_customAttributes?.ToArray() ?? [], ResolveCustomAttributes(BaseType.Unpack().GetInheritedCustomAttributesData())).ToArray(); } /// @@ -363,8 +369,8 @@ public void Complete() if (_builder.IsCreated() == false) { _type = _builder.CreateType() ?? throw new InvalidOperationException(); - _incompleteMethods = null; - _incompleteCustomAttributes = null; + _methods = null; + _customAttributes = null; } // force module to reresolve diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs index d11a94fcf5..b9456e1c78 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs @@ -21,10 +21,10 @@ public ReflectionArrayTypeSymbol(ReflectionSymbolContext context, IReflectionMod } /// - public override Type UnderlyingType => ElementType.UnderlyingType.MakeArrayType(rank); + public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakeArrayType(rank); /// - public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeArrayType(rank); + public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeArrayType(rank); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs index 9e0c79d87e..0dfc4d623e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs @@ -19,10 +19,10 @@ public ReflectionByRefTypeSymbol(ReflectionSymbolContext context, IReflectionMod } /// - public override Type UnderlyingType => ElementType.UnderlyingType.MakeByRefType(); + public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakeByRefType(); /// - public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeByRefType(); + public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeByRefType(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericInstantiationTypeSymbol.cs similarity index 80% rename from src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs rename to src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericInstantiationTypeSymbol.cs index e369f1e108..457afdbde9 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericSpecTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericInstantiationTypeSymbol.cs @@ -6,7 +6,7 @@ namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionGenericSpecTypeSymbol : ReflectionTypeSpecSymbol + class ReflectionGenericInstantiationTypeSymbol : ReflectionTypeSpecSymbol { /// @@ -44,17 +44,17 @@ static bool ContainsTypeBuilder(Type type) /// /// /// - public ReflectionGenericSpecTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, IReflectionTypeSymbol[] genericTypeArguments) : + public ReflectionGenericInstantiationTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, IReflectionTypeSymbol[] genericTypeArguments) : base(context, resolvingModule, elementType) { _genericTypeArguments = genericTypeArguments ?? throw new ArgumentNullException(nameof(genericTypeArguments)); } /// - public override Type UnderlyingType => _underlyingType ??= ElementType.UnderlyingType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingType).ToArray()); + public override Type UnderlyingType => _underlyingType ??= SpecifiedType.UnderlyingType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingType).ToArray()); /// - public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingRuntimeType).ToArray()); + public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingRuntimeType).ToArray()); /// /// Returns true if the underlying type contains a type builder. @@ -67,7 +67,7 @@ public override IFieldSymbol[] GetFields() { if (UnderlyingTypeContainsTypeBuilder) { - var l = ElementType.UnderlyingType.GetFields(); + var l = SpecifiedType.UnderlyingType.GetFields(); var a = new IFieldSymbol[l.Length]; for (int i = 0; i < l.Length; i++) a[i] = ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, l[i])); @@ -83,7 +83,7 @@ public override IFieldSymbol[] GetFields(BindingFlags bindingAttr) { if (UnderlyingTypeContainsTypeBuilder) { - var l = ElementType.UnderlyingType.GetFields(bindingAttr); + var l = SpecifiedType.UnderlyingType.GetFields(bindingAttr); var a = new IFieldSymbol[l.Length]; for (int i = 0; i < l.Length; i++) a[i] = ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, l[i])); @@ -98,7 +98,7 @@ public override IFieldSymbol[] GetFields(BindingFlags bindingAttr) public override IFieldSymbol? GetField(string name) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetField(name) is { } f) + if (SpecifiedType.UnderlyingType.GetField(name) is { } f) return ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, f)); return base.GetField(name); @@ -108,7 +108,7 @@ public override IFieldSymbol[] GetFields(BindingFlags bindingAttr) public override IFieldSymbol? GetField(string name, BindingFlags bindingAttr) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetField(name, bindingAttr) is { } f) + if (SpecifiedType.UnderlyingType.GetField(name, bindingAttr) is { } f) return ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, f)); return base.GetField(name, bindingAttr); @@ -119,7 +119,7 @@ public override IConstructorSymbol[] GetConstructors() { if (UnderlyingTypeContainsTypeBuilder) { - var l = ElementType.UnderlyingType.GetConstructors(); + var l = SpecifiedType.UnderlyingType.GetConstructors(); var a = new IConstructorSymbol[l.Length]; for (int i = 0; i < l.Length; i++) a[i] = ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, l[i])); @@ -135,7 +135,7 @@ public override IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) { if (UnderlyingTypeContainsTypeBuilder) { - var l = ElementType.UnderlyingType.GetConstructors(bindingAttr); + var l = SpecifiedType.UnderlyingType.GetConstructors(bindingAttr); var a = new IConstructorSymbol[l.Length]; for (int i = 0; i < l.Length; i++) a[i] = ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, l[i])); @@ -150,7 +150,7 @@ public override IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) public override IConstructorSymbol? GetConstructor(ITypeSymbol[] types) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetConstructor(types.Unpack()) is { } m) + if (SpecifiedType.UnderlyingType.GetConstructor(types.Unpack()) is { } m) return ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, m)); return base.GetConstructor(types); @@ -160,7 +160,7 @@ public override IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) public override IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetConstructor(bindingAttr, null, types.Unpack(), null) is { } m) + if (SpecifiedType.UnderlyingType.GetConstructor(bindingAttr, null, types.Unpack(), null) is { } m) return ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, m)); return base.GetConstructor(bindingAttr, types); @@ -171,7 +171,7 @@ public override IMethodSymbol[] GetMethods() { if (UnderlyingTypeContainsTypeBuilder) { - var l = ElementType.UnderlyingType.GetMethods(); + var l = SpecifiedType.UnderlyingType.GetMethods(); var a = new IMethodSymbol[l.Length]; for (int i = 0; i < l.Length; i++) a[i] = ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, l[i])); @@ -187,7 +187,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) { if (UnderlyingTypeContainsTypeBuilder) { - var l = ElementType.UnderlyingType.GetMethods(bindingAttr); + var l = SpecifiedType.UnderlyingType.GetMethods(bindingAttr); var a = new IMethodSymbol[l.Length]; for (int i = 0; i < l.Length; i++) a[i] = ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, l[i])); @@ -202,7 +202,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) public override IMethodSymbol? GetMethod(string name) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetMethod(name) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); return base.GetMethod(name); @@ -212,7 +212,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetMethod(name, bindingAttr) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); return base.GetMethod(name, bindingAttr); @@ -222,7 +222,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) public override IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetMethod(name, types.Unpack()) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, types.Unpack()) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); return base.GetMethod(name, types); @@ -232,7 +232,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); return base.GetMethod(name, bindingAttr, types); @@ -242,7 +242,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); return base.GetMethod(name, bindingAttr, types, modifiers); @@ -252,7 +252,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) { if (UnderlyingTypeContainsTypeBuilder) - if (ElementType.UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); return base.GetMethod(name, bindingAttr, callConvention, types, modifiers); @@ -265,7 +265,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) #if NETFRAMEWORK throw new NotSupportedException(); #else - if (ElementType.UnderlyingType.GetMethod(name, genericParameterCount, types.Unpack(), modifiers) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, genericParameterCount, types.Unpack(), modifiers) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); #endif @@ -279,7 +279,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) #if NETFRAMEWORK throw new NotSupportedException(); #else - if (ElementType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); #endif @@ -293,7 +293,7 @@ public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) #if NETFRAMEWORK throw new NotSupportedException(); #else - if (ElementType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) + if (SpecifiedType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); #endif diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs index b33ae45c33..dfea498d4c 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs @@ -13,7 +13,6 @@ class ReflectionGenericTypeParameterSymbol : ReflectionMemberSymbol, IReflection { readonly IReflectionMemberSymbol _resolvingMember; - readonly Type _type; ReflectionTypeSpecTable _specTable; @@ -25,11 +24,10 @@ class ReflectionGenericTypeParameterSymbol : ReflectionMemberSymbol, IReflection /// /// /// - public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMemberSymbol resolvingMember, Type type) : + public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMemberSymbol resolvingMember) : base(context, resolvingModule, resolvingMember as IReflectionTypeSymbol) { _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); - _type = type ?? throw new ArgumentNullException(nameof(type)); _specTable = new ReflectionTypeSpecTable(); } @@ -485,19 +483,19 @@ public ITypeSymbol[] GetInterfaces(bool inherit = true) } /// - public IMemberSymbol[] GetMember(string name) + public IMemberSymbol[] GetMembers(string name) { return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); } /// - public IMemberSymbol[] GetMember(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) + public IMemberSymbol[] GetMembers(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs index 6045831608..1c9dde4304 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs @@ -34,7 +34,7 @@ public ReflectionGenericTypeParameterTable(ReflectionSymbolContext context, IRef } /// - /// Gets or creates the cached for the module by type. + /// Gets or creates the cached for the module by type. /// /// /// diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs index 195f155448..fa959d0ba3 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs @@ -19,10 +19,10 @@ public ReflectionPointerTypeSymbol(ReflectionSymbolContext context, IReflectionM } /// - public override Type UnderlyingType => ElementType.UnderlyingType.MakePointerType(); + public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakePointerType(); /// - public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakePointerType(); + public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakePointerType(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs index c50573f6c8..760074bc88 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs @@ -19,10 +19,10 @@ public ReflectionSZArrayTypeSymbol(ReflectionSymbolContext context, IReflectionM } /// - public override Type UnderlyingType => ElementType.UnderlyingType.MakeArrayType(); + public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakeArrayType(); /// - public override Type UnderlyingRuntimeType => ElementType.UnderlyingRuntimeType.MakeArrayType(); + public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeArrayType(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeDefSymbol.cs similarity index 84% rename from src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs rename to src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeDefSymbol.cs index 1f10ce4395..5f04f8c93d 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeDefSymbol.cs @@ -4,7 +4,7 @@ namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionTypeSymbol : ReflectionTypeSymbolBase + class ReflectionTypeDefSymbol : ReflectionTypeSymbolBase { readonly Type _type; @@ -15,7 +15,7 @@ class ReflectionTypeSymbol : ReflectionTypeSymbolBase /// /// /// - public ReflectionTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, Type type) : + public ReflectionTypeDefSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, Type type) : base(context, resolvingModule) { _type = type ?? throw new ArgumentNullException(nameof(type)); diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs index abea837975..71ae05a00b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs @@ -6,27 +6,27 @@ namespace IKVM.CoreLib.Symbols.Reflection abstract class ReflectionTypeSpecSymbol : ReflectionTypeSymbolBase { - readonly IReflectionTypeSymbol _elementType; + readonly IReflectionTypeSymbol _specifiedType; /// /// Initializes a new instance. /// /// /// - /// - public ReflectionTypeSpecSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : + /// + public ReflectionTypeSpecSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol specifiedType) : base(context, resolvingModule) { - _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); + _specifiedType = specifiedType ?? throw new ArgumentNullException(nameof(specifiedType)); } /// /// Gets the element type. /// - protected IReflectionTypeSymbol ElementType => _elementType; + protected IReflectionTypeSymbol SpecifiedType => _specifiedType; /// - public override bool IsComplete => ElementType.IsComplete; + public override bool IsComplete => SpecifiedType.IsComplete; } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs index b115fb485b..db46cc187b 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs @@ -20,7 +20,7 @@ struct ReflectionTypeSpecTable ReflectionSZArrayTypeSymbol? _asSZArray; ReflectionPointerTypeSymbol? _asPointer; ReflectionByRefTypeSymbol? _asByRef; - ConcurrentDictionary? _genericTypeSymbols; + ConcurrentDictionary? _genericTypeSymbols; /// /// Initializes a new instance. @@ -118,9 +118,9 @@ public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[ /// /// /// - readonly ReflectionGenericSpecTypeSymbol CreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) + readonly ReflectionGenericInstantiationTypeSymbol CreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) { - return new ReflectionGenericSpecTypeSymbol(_context, _module, _elementType, genericTypeArguments); + return new ReflectionGenericInstantiationTypeSymbol(_context, _module, _elementType, genericTypeArguments); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs index 50afe94770..2961f315a9 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs @@ -479,19 +479,19 @@ public virtual ITypeSymbol[] GetInterfaces(bool inherit = true) } /// - public virtual IMemberSymbol[] GetMember(string name) + public virtual IMemberSymbol[] GetMembers(string name) { return ResolveMemberSymbols(UnderlyingType.GetMember(name)); } /// - public virtual IMemberSymbol[] GetMember(string name, BindingFlags bindingAttr) + public virtual IMemberSymbol[] GetMembers(string name, BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, bindingAttr)); } /// - public virtual IMemberSymbol[] GetMember(string name, MemberTypes type, BindingFlags bindingAttr) + public virtual IMemberSymbol[] GetMembers(string name, MemberTypes type, BindingFlags bindingAttr) { return ResolveMemberSymbols(UnderlyingType.GetMember(name, type, bindingAttr)); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs index 37cb46aecb..f3a9f249ad 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs @@ -64,7 +64,7 @@ public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) if (type is TypeBuilder builder) return _table[row] = new ReflectionTypeSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, builder); else - return _table[row] = new ReflectionTypeSymbol(_context, _module, type); + return _table[row] = new ReflectionTypeDefSymbol(_context, _module, type); return _table[row] ?? throw new InvalidOperationException(); } diff --git a/src/IKVM.CoreLib/Symbols/SymbolUtil.cs b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs index 2d7c431420..71e68dc1b1 100644 --- a/src/IKVM.CoreLib/Symbols/SymbolUtil.cs +++ b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs @@ -1,7 +1,11 @@ -using System.Collections.Generic; -using System.ComponentModel; +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Linq; using System.Reflection; +using IKVM.CoreLib.Collections; + namespace IKVM.CoreLib.Symbols { @@ -46,49 +50,143 @@ public static bool BindingFlagsMatchInherited(IMethodSymbol method, BindingFlags } /// - /// Filters the set of methods by the binding attributes. + /// Selects the single method that corresponds to the given query. Throws an if multiple candidates are found. /// + /// + /// + /// + /// + /// /// - public static IEnumerable FilterMethods(ITypeSymbol type, IEnumerable methods, BindingFlags bindingAttr = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance) + /// + /// + public static IMethodSymbol? SelectMethod(ITypeSymbol type, BindingFlags bindingFlags, string? name, IReadOnlyList? parameterTypes, IReadOnlyList? modifiers) { - var list = new HashSet(); + var list = SelectMethods(type, bindingFlags, name, parameterTypes, modifiers); + if (list == null) + throw new InvalidOperationException(); - foreach (var mb in methods) + return list.Count switch { - var mi = mb as IMethodSymbol; - if (mi != null && BindingFlagsMatch(mi, bindingAttr)) - if (list.Add(mi)) - yield return mi; - } + 0 => null, + 1 => list[0], + _ => throw new AmbiguousMatchException(), + }; + } - if ((bindingAttr & BindingFlags.DeclaredOnly) == 0) + /// + /// Selects the methods that corresponds to the given query. + /// + /// + /// + /// + public static IImmutableList SelectMethods(ITypeSymbol type, BindingFlags bindingFlags, string? name, IReadOnlyList? parameterTypes, IReadOnlyList? modifiers) + { + // we start by copying the declared methods and either removing or adding + // optimally, if doing no work, we end up returning the same list + // but we might also be appending only, thus preserving some space thanks to the immutable collection + var list = type.GetDeclaredMethods(); + + // remove items that do not match binding flags + foreach (var declaredMethod in list) + if (BindingFlagsMatch(declaredMethod, bindingFlags) == false) + list = list.Remove(declaredMethod); + + // we do want to check inherited methods + if ((bindingFlags & BindingFlags.DeclaredOnly) == 0) { - var baseMethods = new List(); - foreach (var mi in list) - if (mi.IsVirtual) - baseMethods.Add(mi.GetBaseDefinition()); + // keep a record of those methods which have been preserved + var baseMethods = new HashSet(); + + // record base methods of already emitted virtual methods + foreach (var method in list) + if (method.IsVirtual) + baseMethods.Add(method.GetBaseDefinition()); for (var baseType = type.BaseType; baseType != null; baseType = baseType.BaseType) { - foreach (var mi in baseType.GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance)) - { - if (BindingFlagsMatchInherited(mi, bindingAttr)) - { - if (mi.IsVirtual) - { - baseMethods ??= []; - if (baseMethods.Contains(mi.GetBaseDefinition())) - continue; - - baseMethods.Add(mi.GetBaseDefinition()); - } - - if (list.Add(mi)) - yield return mi; - } - } + var baseTypeMethods = baseType.GetDeclaredMethods(); + if (baseTypeMethods == null) + throw new InvalidOperationException(); + + // remove base methods that do not match inherited binding flags + // remove base methods that are virtual and already tracked + foreach (var baseTypeMethod in baseTypeMethods) + if (BindingFlagsMatchInherited(baseTypeMethod, bindingFlags) == false || baseTypeMethod.IsVirtual && baseMethods.Contains(baseTypeMethod.GetBaseDefinition())) + baseTypeMethods = baseTypeMethods.Remove(baseTypeMethod); + + // append to emitted list + list = list.AddRange(baseTypeMethods); } } + + // remove methods that do not match filter conditions + foreach (var method in list) + if (MethodFilterPredicate(method, bindingFlags, name, parameterTypes, modifiers) == false) + list = list.Remove(method); + + // return final list + return list; + } + + /// + /// Predicate that determines if the method matches the specification. + /// + /// + /// + /// + /// + /// + static bool MethodFilterPredicate(IMethodSymbol method, BindingFlags bindingFlags, string? name, IReadOnlyList? parameterTypes, IReadOnlyList? modifiers) + { + if (name != null) + { + var nameComparison = StringComparison.Ordinal; + if ((bindingFlags & BindingFlags.IgnoreCase) != 0) + nameComparison = StringComparison.OrdinalIgnoreCase; + if (string.Equals(method.Name, name, nameComparison) == false) + return false; + } + + if (parameterTypes != null) + if (MatchParameterTypes(method, parameterTypes) == false) + return false; + + if (modifiers != null) + if (MatchModifiers(method, modifiers) == false) + return false; + + return true; + } + + /// + /// Checks that the parameters types of the method match the given parameter types. + /// + /// + /// + /// + static bool MatchParameterTypes(IMethodSymbol method, IReadOnlyList parameterTypes) + { + var methodParameters = method.GetParameters(); + if (methodParameters.Length != parameterTypes.Count) + return false; + + for (int i = 0; i < methodParameters.Length; i++) + if (methodParameters[i].ParameterType != parameterTypes[i]) + return false; + + return true; + } + + /// + /// Checks that the parameter modifiers match. For now does nothing. + /// + /// + /// + /// + static bool MatchModifiers(IMethodSymbol method, IReadOnlyList modifiers) + { + return true; } } diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs new file mode 100644 index 0000000000..bf940d8195 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs @@ -0,0 +1,393 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics; + +using IKVM.CoreLib.Text; + +namespace IKVM.CoreLib.Symbols +{ + + internal static class TypeNameParserHelpers + { + + const int maxDepth = 32; + internal const int SZArray = -1; + internal const int Pointer = -2; + internal const int ByRef = -3; + const char EscapeCharacter = '\\'; + + // Keep this in sync with GetFullTypeNameLength/NeedsEscaping + private static readonly string s_endOfFullTypeNameDelimitersSearchValues = "[]&*,+\\"; + + internal static string GetGenericTypeFullName(ReadOnlySpan fullTypeName, ReadOnlySpan genericArgs) + { + Debug.Assert(genericArgs.Length > 0); + + ValueStringBuilder result = new(stackalloc char[128]); + result.Append(fullTypeName); + + result.Append('['); + foreach (var genericArg in genericArgs) + { + result.Append('['); + result.Append(genericArg.AssemblyQualifiedName); // see recursion comments in TypeName.FullName + result.Append(']'); + result.Append(','); + } + result[result.Length - 1] = ']'; // replace ',' with ']' + + return result.ToString(); + } + + /// Positive length or negative value for invalid name + internal static int GetFullTypeNameLength(ReadOnlySpan input, out bool isNestedType) + { + isNestedType = false; + + // NET 6+ guarantees that MemoryExtensions.IndexOfAny has worst-case complexity + // O(m * i) if a match is found, or O(m * n) if a match is not found, where: + // i := index of match position + // m := number of needles + // n := length of search space (haystack) + // + // Downlevel versions of .NET do not make this guarantee, instead having a + // worst-case complexity of O(m * n) even if a match occurs at the beginning of + // the search space. Since we're running this in a loop over untrusted user + // input, that makes the total loop complexity potentially O(m * n^2), where + // 'n' is adversary-controlled. To avoid DoS issues here, we'll loop manually. + + int offset = input.IndexOfAny(s_endOfFullTypeNameDelimitersSearchValues.AsSpan()); + if (offset < 0) + { + return input.Length; // no type name end chars were found, the whole input is the type name + } + + if (input[offset] == EscapeCharacter) // this is very rare (IL Emit or pure IL) + { + offset = GetUnescapedOffset(input, startOffset: offset); // this is slower, but very rare so acceptable + } + isNestedType = offset > 0 && offset < input.Length && input[offset] == '+'; + return offset; + + static int GetUnescapedOffset(ReadOnlySpan input, int startOffset) + { + int offset = startOffset; + for (; offset < input.Length; offset++) + { + char c = input[offset]; + if (c == EscapeCharacter) + { + offset++; // skip the escaped char + + if (offset == input.Length || // invalid name that ends with escape character + !NeedsEscaping(input[offset])) // invalid name, escapes a char that does not need escaping + { + return -1; + } + } + else if (NeedsEscaping(c)) + { + break; + } + } + return offset; + } + + // Keep this in sync with s_endOfFullTypeNameDelimitersSearchValues + static bool NeedsEscaping(char c) => c is '[' or ']' or '&' or '*' or ',' or '+' or EscapeCharacter; + } + + internal static ReadOnlySpan GetName(ReadOnlySpan fullName) + { + // The two-value form of MemoryExtensions.LastIndexOfAny does not suffer + // from the behavior mentioned in the comment at the top of GetFullTypeNameLength. + // It always takes O(m * i) worst-case time and is safe to use here. + + int offset = fullName.LastIndexOfAny('.', '+'); + + if (offset > 0 && fullName[offset - 1] == EscapeCharacter) // this should be very rare (IL Emit & pure IL) + { + offset = GetUnescapedOffset(fullName, startIndex: offset); + } + + return offset < 0 ? fullName : fullName.Slice(offset + 1); + + static int GetUnescapedOffset(ReadOnlySpan fullName, int startIndex) + { + int offset = startIndex; + for (; offset >= 0; offset--) + { + if (fullName[offset] is '.' or '+') + { + if (offset == 0 || fullName[offset - 1] != EscapeCharacter) + { + break; + } + offset--; // skip the escaping character + } + } + return offset; + } + } + + // this method handles escaping of the ] just to let the AssemblyNameParser fail for the right input + internal static ReadOnlySpan GetAssemblyNameCandidate(ReadOnlySpan input) + { + // The only delimiter which can terminate an assembly name is ']'. + // Otherwise EOL serves as the terminator. + int offset = input.IndexOf(']'); + + if (offset > 0 && input[offset - 1] == EscapeCharacter) // this should be very rare (IL Emit & pure IL) + { + offset = GetUnescapedOffset(input, startIndex: offset); + } + + return offset < 0 ? input : input.Slice(0, offset); + + static int GetUnescapedOffset(ReadOnlySpan input, int startIndex) + { + int offset = startIndex; + for (; offset < input.Length; offset++) + { + if (input[offset] is ']') + { + if (input[offset - 1] != EscapeCharacter) + { + break; + } + } + } + return offset; + } + } + + internal static string GetRankOrModifierStringRepresentation(int rankOrModifier, ref ValueStringBuilder builder) + { + if (rankOrModifier == ByRef) + { + builder.Append('&'); + } + else if (rankOrModifier == Pointer) + { + builder.Append('*'); + } + else if (rankOrModifier == SZArray) + { + builder.Append("[]"); + } + else if (rankOrModifier == 1) + { + builder.Append("[*]"); + } + else + { + Debug.Assert(rankOrModifier >= 2); + + // O(rank) work, so we have to assume the rank is trusted. We don't put a hard cap on this, + // but within the TypeName parser, we do require the input string to contain the correct number + // of commas. This forces the input string to have at least O(rank) length, so there's no + // alg. complexity attack possible here. Callers can of course pass any arbitrary value to + // TypeName.MakeArrayTypeName, but per first sentence in this comment, we have to assume any + // such arbitrary value which is programmatically fed in originates from a trustworthy source. + + builder.Append('['); + builder.Append(',', rankOrModifier - 1); + builder.Append(']'); + } + + return builder.ToString(); + } + + /// + /// Are there any captured generic args? We'll look for "[[" and "[" that is not followed by "]", "*" and ",". + /// + internal static bool IsBeginningOfGenericArgs(ref ReadOnlySpan span, out bool doubleBrackets) + { + doubleBrackets = false; + + if (!span.IsEmpty && span[0] == '[') + { + // There are no spaces allowed before the first '[', but spaces are allowed after that. + ReadOnlySpan trimmed = span.Slice(1).TrimStart(); + if (!trimmed.IsEmpty) + { + if (trimmed[0] == '[') + { + doubleBrackets = true; + span = trimmed.Slice(1).TrimStart(); + return true; + } + if (!(trimmed[0] is ',' or '*' or ']')) // [] or [*] or [,] or [,,,, ...] + { + span = trimmed; + return true; + } + } + } + + return false; + } + + internal static bool TryGetTypeNameInfo(ref ReadOnlySpan input, ref List? nestedNameLengths, ref int recursiveDepth, out int totalLength) + { + bool isNestedType; + + totalLength = 0; + do + { + int length = GetFullTypeNameLength(input.Slice(totalLength), out isNestedType); + if (length <= 0) + { + // invalid type names: + // -1: invalid escaping + // 0: pair of unescaped "++" characters + return false; + } + + // Compat: Ignore leading '.' for type names without namespace. .NET Framework historically ignored leading '.' here. It is likely + // that code out there depends on this behavior. For example, type names formed by concatenating namespace and name, without checking for + // empty namespace (bug), are going to have superfluous leading '.'. + // This behavior means that types that start with '.' are not round-trippable via type name. + if (length > 1 && input[0] == '.' && input.Slice(0, length).LastIndexOf('.') == 0) + { + input = input.Slice(1); + length--; + } + + if (isNestedType) + { + if (!TryDive(ref recursiveDepth)) + { + return false; + } + + (nestedNameLengths ??= new()).Add(length); + totalLength += 1; // skip the '+' sign in next search + } + totalLength += length; + } while (isNestedType); + + return true; + } + + internal static bool TryParseNextDecorator(ref ReadOnlySpan input, out int rankOrModifier) + { + // Then try pulling a single decorator. + // Whitespace cannot precede the decorator, but it can follow the decorator. + + ReadOnlySpan originalInput = input; // so we can restore on 'false' return + + if (TryStripFirstCharAndTrailingSpaces(ref input, '*')) + { + rankOrModifier = Pointer; + return true; + } + + if (TryStripFirstCharAndTrailingSpaces(ref input, '&')) + { + rankOrModifier = ByRef; + return true; + } + + if (TryStripFirstCharAndTrailingSpaces(ref input, '[')) + { + // SZArray := [] + // MDArray := [*] or [,] or [,,,, ...] + + int rank = 1; + bool hasSeenAsterisk = false; + + ReadNextArrayToken: + + if (TryStripFirstCharAndTrailingSpaces(ref input, ']')) + { + // End of array marker + rankOrModifier = rank == 1 && !hasSeenAsterisk ? SZArray : rank; + return true; + } + + if (!hasSeenAsterisk) + { + if (rank == 1 && TryStripFirstCharAndTrailingSpaces(ref input, '*')) + { + // [*] + hasSeenAsterisk = true; + goto ReadNextArrayToken; + } + else if (TryStripFirstCharAndTrailingSpaces(ref input, ',')) + { + // [,,, ...] + // The runtime restricts arrays to rank 32, but we don't enforce that here. + // Instead, the max rank is controlled by the total number of commas present + // in the array decorator. + checked { rank++; } + goto ReadNextArrayToken; + } + } + + // Don't know what this token is. + // Fall through to 'return false' statement. + } + + input = originalInput; // ensure 'ref input' not mutated + rankOrModifier = 0; + return false; + } + + internal static bool TryStripFirstCharAndTrailingSpaces(ref ReadOnlySpan span, char value) + { + if (!span.IsEmpty && span[0] == value) + { + span = span.Slice(1).TrimStart(); + return true; + } + return false; + } + + internal static void ThrowArgumentException_InvalidTypeName(int errorIndex) + { + throw new InvalidOperationException(); + } + + internal static void ThrowInvalidOperation_MaxNodesExceeded(int limit) + { + throw new InvalidOperationException(); + } + + internal static void ThrowInvalidOperation_NotGenericType() + { + throw new InvalidOperationException(); + } + + internal static void ThrowInvalidOperation_NotNestedType() + { + throw new InvalidOperationException(); + } + + internal static void ThrowInvalidOperation_NoElement() + { + throw new InvalidOperationException(); + } + + internal static void ThrowInvalidOperation_HasToBeArrayClass() + { + throw new InvalidOperationException(); + } + + internal static bool IsMaxDepthExceeded(int depth) => depth > maxDepth; + + internal static bool TryDive(ref int depth) + { + depth++; + return !IsMaxDepthExceeded(depth); + } + + internal static void ThrowInvalidOperation_NotSimpleName(string fullName) + { + throw new InvalidOperationException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs new file mode 100644 index 0000000000..9843954195 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs @@ -0,0 +1,41 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System; +using System.Collections.Immutable; +using System.Diagnostics; + +namespace IKVM.CoreLib.Symbols +{ + + [DebuggerDisplay("{AssemblyQualifiedName}")] + struct TypeSymbolNameParserResult + { + + readonly ReadOnlyMemory _namespaceName; + readonly ReadOnlyMemory _name; + readonly AssemblyIdentity? _assembly; + readonly ImmutableArray _genericTypeArguments; + readonly int _rankOrModifier; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + internal TypeSymbolNameParserResult(ReadOnlyMemory namespaceName, ReadOnlyMemory name, AssemblyIdentity? assembly, ImmutableArray genericTypeArguments, int rankOrModifier = default) + { + _namespaceName = namespaceName; + _name = name; + _assembly = assembly; + _genericTypeArguments = genericTypeArguments; + _rankOrModifier = rankOrModifier; + } + + public string AssemblyQualifiedName { get; } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs new file mode 100644 index 0000000000..c50c7527a6 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs @@ -0,0 +1,270 @@ +using System; +using System.Buffers; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics; + +using IKVM.CoreLib.Buffers; + +namespace IKVM.CoreLib.Symbols +{ + + ref struct TypeSymbolNameReader + { + + private readonly bool _throwOnError; + private ReadOnlySpan _inputString; + + private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNameParseOptions? options) : this() + { + _inputString = name; + _throwOnError = throwOnError; + _parseOptions = options ?? s_defaults; + } + + internal static TypeName? Parse(ReadOnlySpan typeName, bool throwOnError, TypeNameParseOptions? options = default) + { + ReadOnlySpan trimmedName = typeName.TrimStart(); // whitespaces at beginning are always OK + if (trimmedName.IsEmpty) + { + if (throwOnError) + { + ThrowArgumentException_InvalidTypeName(errorIndex: 0); // whitespace input needs to report the error index as 0 + } + + return null; + } + + int recursiveDepth = 0; + TypeNameParser parser = new(trimmedName, throwOnError, options); + TypeName? parsedName = parser.ParseNextTypeName(allowFullyQualifiedName: true, ref recursiveDepth); + + if (parsedName is null || !parser._inputString.IsEmpty) // unconsumed input == error + { + if (throwOnError) + { + if (IsMaxDepthExceeded(parser._parseOptions, recursiveDepth)) + { + ThrowInvalidOperation_MaxNodesExceeded(parser._parseOptions.MaxNodes); + } + + int errorIndex = typeName.Length - parser._inputString.Length; + ThrowArgumentException_InvalidTypeName(errorIndex); + } + + return null; + } + + Debug.Assert(parsedName.GetNodeCount() == recursiveDepth, $"Node count mismatch for '{typeName.ToString()}'"); + + return parsedName; + } + + // this method should return null instead of throwing, so the caller can get errorIndex and include it in error msg + private TypeName? ParseNextTypeName(bool allowFullyQualifiedName, ref int recursiveDepth) + { + if (!TryDive(_parseOptions, ref recursiveDepth)) + { + return null; + } + + List? nestedNameLengths = null; + if (!TryGetTypeNameInfo(_parseOptions, ref _inputString, ref nestedNameLengths, ref recursiveDepth, out int fullTypeNameLength)) + { + return null; + } + + // At this point, we have performed O(fullTypeNameLength) total work. + + ReadOnlySpan fullTypeName = _inputString.Slice(0, fullTypeNameLength); + _inputString = _inputString.Slice(fullTypeNameLength); + + // Don't allocate now, as it may be an open generic type like "Name`1" +#if SYSTEM_PRIVATE_CORELIB + List? genericArgs = null; +#else + ImmutableArray.Builder? genericArgs = null; +#endif + + // Are there any captured generic args? We'll look for "[[" and "[". + // There are no spaces allowed before the first '[', but spaces are allowed + // after that. The check slices _inputString, so we'll capture it into + // a local so we can restore it later if needed. + ReadOnlySpan capturedBeforeProcessing = _inputString; + if (IsBeginningOfGenericArgs(ref _inputString, out bool doubleBrackets)) + { + ParseAnotherGenericArg: + + // Namespace.Type`2[[GenericArgument1, AssemblyName1],[GenericArgument2, AssemblyName2]] - double square bracket syntax allows for fully qualified type names + // Namespace.Type`2[GenericArgument1,GenericArgument2] - single square bracket syntax is legal only for non-fully qualified type names + // Namespace.Type`2[[GenericArgument1, AssemblyName1], GenericArgument2] - mixed mode + // Namespace.Type`2[GenericArgument1, [GenericArgument2, AssemblyName2]] - mixed mode + TypeName? genericArg = ParseNextTypeName(allowFullyQualifiedName: doubleBrackets, ref recursiveDepth); + if (genericArg is null) // parsing failed + { + return null; + } + + // For [[, there had better be a ']' after the type name. + if (doubleBrackets && !TryStripFirstCharAndTrailingSpaces(ref _inputString, ']')) + { + return null; + } + + if (genericArgs is null) + { +#if SYSTEM_PRIVATE_CORELIB + genericArgs = new List(2); +#else + genericArgs = ImmutableArray.CreateBuilder(2); +#endif + } + genericArgs.Add(genericArg); + + // Is there a ',[' indicating fully qualified generic type arg? + // Is there a ',' indicating non-fully qualified generic type arg? + if (TryStripFirstCharAndTrailingSpaces(ref _inputString, ',')) + { + doubleBrackets = TryStripFirstCharAndTrailingSpaces(ref _inputString, '['); + + goto ParseAnotherGenericArg; + } + + // The only other allowable character is ']', indicating the end of + // the generic type arg list. + if (!TryStripFirstCharAndTrailingSpaces(ref _inputString, ']')) + { + return null; + } + } + + // At this point, we may have performed O(fullTypeNameLength + _inputString.Length) total work. + // This will be the case if there was whitespace after the full type name in the original input + // string. We could end up looking at these same whitespace chars again later in this method, + // such as when parsing decorators. We rely on the TryDive routine to limit the total number + // of times we might inspect the same character. + + // If there was an error stripping the generic args, back up to + // before we started processing them, and let the decorator + // parser try handling it. + if (genericArgs is null) + { + _inputString = capturedBeforeProcessing; + } + else + { + // Every constructed generic type needs the generic type definition. + if (!TryDive(_parseOptions, ref recursiveDepth)) + { + return null; + } + // If that generic type is a nested type, we don't increase the recursiveDepth any further, + // as generic type definition uses exactly the same declaring type as the constructed generic type. + } + + int previousDecorator = default; + // capture the current state so we can reprocess it again once we know the AssemblyName + capturedBeforeProcessing = _inputString; + // iterate over the decorators to ensure there are no illegal combinations + while (TryParseNextDecorator(ref _inputString, out int parsedDecorator)) + { + if (!TryDive(_parseOptions, ref recursiveDepth)) + { + return null; + } + + // Currently it's illegal for managed reference to be followed by any other decorator, + // but this is a runtime-specific behavior and the parser is not enforcing that rule. + previousDecorator = parsedDecorator; + } + + AssemblyNameInfo? assemblyName = null; + if (allowFullyQualifiedName && !TryParseAssemblyName(ref assemblyName)) + { +#if SYSTEM_PRIVATE_CORELIB + // backward compat: throw FileLoadException for non-empty invalid strings + if (_throwOnError || !_inputString.TrimStart().StartsWith(",")) + { + throw new IO.FileLoadException(SR.InvalidAssemblyName, _inputString.ToString()); + } +#else + return null; +#endif + } + + // No matter what was parsed, the full name string is allocated only once. + // In case of generic, nested, array, pointer and byref types the full name is allocated + // when needed for the first time . + string fullName = fullTypeName.ToString(); + + TypeName? declaringType = GetDeclaringType(fullName, nestedNameLengths, assemblyName); + TypeName result = new(fullName, assemblyName, declaringType: declaringType); + if (genericArgs is not null) + { + result = new(fullName: null, assemblyName, elementOrGenericType: result, declaringType, genericArgs); + } + + // The loop below is protected by the dive check during the first decorator pass prior + // to assembly name parsing above. + + if (previousDecorator != default) // some decorators were recognized + { + while (TryParseNextDecorator(ref capturedBeforeProcessing, out int parsedModifier)) + { + result = new(fullName: null, assemblyName, elementOrGenericType: result, rankOrModifier: parsedModifier); + } + } + + return result; + } + + /// false means the input was invalid and parsing has failed. Empty input is valid and returns true. + private bool TryParseAssemblyName(ref AssemblyIdentity? assemblyName) + { + ReadOnlySpan capturedBeforeProcessing = _inputString; + if (TryStripFirstCharAndTrailingSpaces(ref _inputString, ',')) + { + if (_inputString.IsEmpty) + { + _inputString = capturedBeforeProcessing; // restore the state + return false; + } + + ReadOnlySpan candidate = GetAssemblyNameCandidate(_inputString); + if (!AssemblyIdentity.TryParse(candidate, out assemblyName)) + { + return false; + } + + _inputString = _inputString.Slice(candidate.Length); + return true; + } + + return true; + } + + private static TypeSymbolNameParserResult? GetDeclaringType(string fullTypeName, List? nestedNameLengths, AssemblyIdentity? assemblyName) + { + if (nestedNameLengths is null) + { + return null; + } + + // The loop below is protected by the dive check in GetFullTypeNameLength. + + TypeSymbolNameParserResult? declaringType = null; + int nameOffset = 0; + foreach (int nestedNameLength in nestedNameLengths) + { + Debug.Assert(nestedNameLength > 0, "TryGetTypeNameInfo should return error on zero lengths"); + int fullNameLength = nameOffset + nestedNameLength; + declaringType = new(fullTypeName, assemblyName, declaringType: declaringType, nestedNameLength: fullNameLength); + nameOffset += nestedNameLength + 1; // include the '+' that was skipped in name + } + + return declaringType; + } + + } + +} diff --git a/src/IKVM.Reflection/Type.cs b/src/IKVM.Reflection/Type.cs index 5eecf0c1ea..0db2343c0f 100644 --- a/src/IKVM.Reflection/Type.cs +++ b/src/IKVM.Reflection/Type.cs @@ -162,7 +162,7 @@ public virtual EventInfo[] __GetDeclaredEvents() { return Array.Empty(); } - + public virtual PropertyInfo[] __GetDeclaredProperties() { return Array.Empty(); @@ -935,9 +935,7 @@ public MethodInfo GetMethod(string name, Type[] types, ParameterModifier[] modif public MethodInfo GetMethod(string name, BindingFlags bindingAttr, Binder binder, Type[] types, ParameterModifier[] modifiers) { // first we try an exact match and only if that fails we fall back to using the binder - return GetMemberByName(name, bindingAttr, - delegate (MethodInfo method) { return method.MethodSignature.MatchParameterTypes(types); }) - ?? GetMethodWithBinder(name, bindingAttr, binder ?? DefaultBinder, types, modifiers); + return GetMemberByName(name, bindingAttr, (MethodInfo m) => m.MethodSignature.MatchParameterTypes(types)) ?? GetMethodWithBinder(name, bindingAttr, binder ?? DefaultBinder, types, modifiers); } private T GetMethodWithBinder(string name, BindingFlags bindingAttr, Binder binder, Type[] types, ParameterModifier[] modifiers) @@ -1809,7 +1807,7 @@ void FillInInterfaceMethods(Type interfaceType, MethodInfo[] interfaceMethods, M type.FillInImplicitInterfaceMethods(interfaceMethods, targetMethods); } - void FillInImplicitInterfaceMethods(MethodInfo[] interfaceMethods, MethodInfo[] targetMethods) + void FillInImplicitInterfaceMethods(MethodInfo[] interfaceMethods, MethodInfo[] targetMethods) { MethodBase[] methods = null; @@ -1970,7 +1968,7 @@ public MethodBase __CreateMissingMethod(string name, CallingConventions callingC return CreateMissingMethod(name, callingConvention, returnType, parameterTypes, PackedCustomModifiers.CreateFromExternal(returnTypeCustomModifiers, parameterTypeCustomModifiers, parameterTypes.Length)); } - MethodBase CreateMissingMethod(string name, CallingConventions callingConvention, Type returnType, Type[] parameterTypes, PackedCustomModifiers customModifiers) + MethodBase CreateMissingMethod(string name, CallingConventions callingConvention, Type returnType, Type[] parameterTypes, PackedCustomModifiers customModifiers) { var sig = new MethodSignature(returnType ?? Module.Universe.System_Void, Util.Copy(parameterTypes), customModifiers, callingConvention, 0); var method = new MissingMethod(this, name, sig); diff --git a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs index 94939dec1e..6363309cb2 100644 --- a/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs +++ b/src/IKVM.Runtime/RuntimeManagedByteCodeJavaType.cs @@ -23,6 +23,7 @@ Jeroen Frijters */ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.Diagnostics; using System.Linq; using System.Reflection; @@ -678,7 +679,7 @@ protected override void LazyPublishMethods() SetMethods(methods.ToArray()); } - private void AddMethods(IMethodSymbol[] add, List methods) + private void AddMethods(IReadOnlyList add, List methods) { foreach (var method in add) AddMethodOrConstructor(method, Context.AttributeHelper.GetHideFromJavaFlags(method), methods); From 6d06fdb9e6fb7323348247561c4a7aadbb87929a Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Mon, 28 Oct 2024 20:42:00 -0500 Subject: [PATCH 51/59] Hmmm --- .../AssemblyIdentityParts.cs | 489 ++++++++++ .../Buffers/SequenceReader.Search.cs | 861 ++++++++++++++++++ src/IKVM.CoreLib/Buffers/SequenceReader.cs | 431 ++++----- .../Buffers/SequenceReaderExtensions.cs | 35 - src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs | 28 + .../Symbols/Emit/TypeSymbolBuilderBase.cs | 276 ++++-- src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 8 + src/IKVM.CoreLib/Symbols/TypeSymbolName.cs | 503 ++++++++++ .../Symbols/TypeSymbolNameParserHelpers.cs | 62 +- .../Symbols/TypeSymbolNameParserResult.cs | 41 - .../Symbols/TypeSymbolNameReader.cs | 92 +- 11 files changed, 2357 insertions(+), 469 deletions(-) create mode 100644 src/IKVM.CoreLib/AssemblyIdentityParser/AssemblyIdentityParts.cs create mode 100644 src/IKVM.CoreLib/Buffers/SequenceReader.Search.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolName.cs delete mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs diff --git a/src/IKVM.CoreLib/AssemblyIdentityParser/AssemblyIdentityParts.cs b/src/IKVM.CoreLib/AssemblyIdentityParser/AssemblyIdentityParts.cs new file mode 100644 index 0000000000..73aaf0ddfa --- /dev/null +++ b/src/IKVM.CoreLib/AssemblyIdentityParser/AssemblyIdentityParts.cs @@ -0,0 +1,489 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System; +using System.Globalization; +using System.Reflection; +using System.Runtime.CompilerServices; + +using IKVM.CoreLib.Text; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Parses an assembly name. + /// + internal ref partial struct AssemblyIdentityParser + { + + public readonly struct AssemblyIdentityParts + { + + public AssemblyIdentityParts(string name, Version? version, string? cultureName, AssemblyNameFlags flags, byte[]? publicKeyOrToken) + { + _name = name; + _version = version; + _cultureName = cultureName; + _flags = flags; + _publicKeyOrToken = publicKeyOrToken; + } + + public readonly string _name; + public readonly Version? _version; + public readonly string? _cultureName; + public readonly AssemblyNameFlags _flags; + public readonly byte[]? _publicKeyOrToken; + + } + + /// + /// Token categories for the lexer. + /// + private enum Token + { + Equals = 1, + Comma = 2, + String = 3, + End = 4, + } + + private enum AttributeKind + { + Version = 1, + Culture = 2, + PublicKeyOrToken = 4, + ProcessorArchitecture = 8, + Retargetable = 16, + ContentType = 32 + } + + private readonly ReadOnlySpan _input; + private int _index; + + private AssemblyIdentityParser(ReadOnlySpan input) + { + if (input.Length == 0) + throw new ArgumentException(nameof(input)); + + _input = input; + _index = 0; + } + + internal static bool TryParse(ReadOnlySpan name, ref AssemblyIdentityParts parts) + { + AssemblyIdentityParser parser = new(name); + return parser.TryParse(ref parts); + } + + private static bool TryRecordNewSeen(scoped ref AttributeKind seenAttributes, AttributeKind newAttribute) + { + if ((seenAttributes & newAttribute) != 0) + { + return false; + } + seenAttributes |= newAttribute; + return true; + } + + private bool TryParse(ref AssemblyIdentityParts result) + { + // Name must come first. + if (!TryGetNextToken(out string name, out Token token) || token != Token.String || string.IsNullOrEmpty(name)) + return false; + + Version? version = null; + string? cultureName = null; + byte[]? pkt = null; + AssemblyNameFlags flags = 0; + + AttributeKind alreadySeen = default; + if (!TryGetNextToken(out _, out token)) + return false; + + while (token != Token.End) + { + if (token != Token.Comma) + return false; + + if (!TryGetNextToken(out string attributeName, out token) || token != Token.String) + return false; + + if (!TryGetNextToken(out _, out token) || token != Token.Equals) + return false; + + if (!TryGetNextToken(out string attributeValue, out token) || token != Token.String) + return false; + + if (attributeName == string.Empty) + return false; + + if (IsAttribute(attributeName, "Version")) + { + if (!TryRecordNewSeen(ref alreadySeen, AttributeKind.Version)) + { + return false; + } + if (!TryParseVersion(attributeValue, ref version)) + { + return false; + } + } + else if (IsAttribute(attributeName, "Culture")) + { + if (!TryRecordNewSeen(ref alreadySeen, AttributeKind.Culture)) + { + return false; + } + if (!TryParseCulture(attributeValue, out cultureName)) + { + return false; + } + } + else if (IsAttribute(attributeName, "PublicKeyToken")) + { + if (!TryRecordNewSeen(ref alreadySeen, AttributeKind.PublicKeyOrToken)) + { + return false; + } + if (!TryParsePKT(attributeValue, isToken: true, out pkt)) + { + return false; + } + } + else if (IsAttribute(attributeName, "PublicKey")) + { + if (!TryRecordNewSeen(ref alreadySeen, AttributeKind.PublicKeyOrToken)) + { + return false; + } + if (!TryParsePKT(attributeValue, isToken: false, out pkt)) + { + return false; + } + flags |= AssemblyNameFlags.PublicKey; + } + else if (IsAttribute(attributeName, "ProcessorArchitecture")) + { + if (!TryRecordNewSeen(ref alreadySeen, AttributeKind.ProcessorArchitecture)) + { + return false; + } + if (!TryParseProcessorArchitecture(attributeValue, out ProcessorArchitecture arch)) + { + return false; + } + flags |= (AssemblyNameFlags)(((int)arch) << 4); + } + else if (IsAttribute(attributeName, "Retargetable")) + { + if (!TryRecordNewSeen(ref alreadySeen, AttributeKind.Retargetable)) + { + return false; + } + + if (attributeValue.Equals("Yes", StringComparison.OrdinalIgnoreCase)) + { + flags |= AssemblyNameFlags.Retargetable; + } + else if (attributeValue.Equals("No", StringComparison.OrdinalIgnoreCase)) + { + // nothing to do + } + else + { + return false; + } + } + else if (IsAttribute(attributeName, "ContentType")) + { + if (!TryRecordNewSeen(ref alreadySeen, AttributeKind.ContentType)) + { + return false; + } + + if (attributeValue.Equals("WindowsRuntime", StringComparison.OrdinalIgnoreCase)) + { + flags |= (AssemblyNameFlags)(((int)AssemblyContentType.WindowsRuntime) << 9); + } + else + { + return false; + } + } + else + { + // Desktop compat: If we got here, the attribute name is unknown to us. Ignore it. + } + + if (!TryGetNextToken(out _, out token)) + { + return false; + } + } + + result = new AssemblyIdentityParts(name, version, cultureName, flags, pkt); + return true; + } + + private static bool IsAttribute(string candidate, string attributeKind) + => candidate.Equals(attributeKind, StringComparison.OrdinalIgnoreCase); + + private static bool TryParseVersion(string attributeValue, ref Version? version) + { +#if NET8_0_OR_GREATER + ReadOnlySpan attributeValueSpan = attributeValue; + Span parts = stackalloc Range[5]; + parts = parts.Slice(0, attributeValueSpan.Split(parts, '.')); +#else + string[] parts = attributeValue.Split('.'); +#endif + if (parts.Length is < 2 or > 4) + { + return false; + } + + Span versionNumbers = [ushort.MaxValue, ushort.MaxValue, ushort.MaxValue, ushort.MaxValue]; + for (int i = 0; i < parts.Length; i++) + { + if (!ushort.TryParse( +#if NET8_0_OR_GREATER + attributeValueSpan[parts[i]], +#else + parts[i], +#endif + NumberStyles.None, NumberFormatInfo.InvariantInfo, out versionNumbers[i])) + { + return false; + } + } + + if (versionNumbers[0] == ushort.MaxValue || + versionNumbers[1] == ushort.MaxValue) + { + return false; + } + + version = + versionNumbers[2] == ushort.MaxValue ? new Version(versionNumbers[0], versionNumbers[1]) : + versionNumbers[3] == ushort.MaxValue ? new Version(versionNumbers[0], versionNumbers[1], versionNumbers[2]) : + new Version(versionNumbers[0], versionNumbers[1], versionNumbers[2], versionNumbers[3]); + + return true; + } + + private static bool TryParseCulture(string attributeValue, out string? result) + { + if (attributeValue.Equals("Neutral", StringComparison.OrdinalIgnoreCase)) + { + result = ""; + return true; + } + + result = attributeValue; + return true; + } + + private static bool TryParsePKT(string attributeValue, bool isToken, out byte[]? result) + { + if (attributeValue.Equals("null", StringComparison.OrdinalIgnoreCase) || attributeValue == string.Empty) + { + result = Array.Empty(); + return true; + } + + if (attributeValue.Length % 2 != 0 || (isToken && attributeValue.Length != 8 * 2)) + { + result = null; + return false; + } + + byte[] pkt = new byte[attributeValue.Length / 2]; + if (!HexConverter.TryDecodeFromUtf16(attributeValue.AsSpan(), pkt, out int _)) + { + result = null; + return false; + } + + result = pkt; + return true; + } + + private static bool TryParseProcessorArchitecture(string attributeValue, out ProcessorArchitecture result) + { + result = attributeValue switch + { + _ when attributeValue.Equals("msil", StringComparison.OrdinalIgnoreCase) => ProcessorArchitecture.MSIL, + _ when attributeValue.Equals("x86", StringComparison.OrdinalIgnoreCase) => ProcessorArchitecture.X86, + _ when attributeValue.Equals("ia64", StringComparison.OrdinalIgnoreCase) => ProcessorArchitecture.IA64, + _ when attributeValue.Equals("amd64", StringComparison.OrdinalIgnoreCase) => ProcessorArchitecture.Amd64, + _ when attributeValue.Equals("arm", StringComparison.OrdinalIgnoreCase) => ProcessorArchitecture.Arm, + _ when attributeValue.Equals("msil", StringComparison.OrdinalIgnoreCase) => ProcessorArchitecture.MSIL, + _ => ProcessorArchitecture.None + }; + return result != ProcessorArchitecture.None; + } + + private static bool IsWhiteSpace(char ch) + => ch is '\n' or '\r' or ' ' or '\t'; + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + private bool TryGetNextChar(out char ch) + { + if (_index < _input.Length) + { + ch = _input[_index++]; + if (ch == '\0') + { + return false; + } + } + else + { + ch = '\0'; + } + + return true; + } + + // + // Return the next token in assembly name. If the result is Token.String, + // sets "tokenString" to the tokenized string. + // + private bool TryGetNextToken(out string tokenString, out Token token) + { + tokenString = string.Empty; + char c; + + while (true) + { + if (!TryGetNextChar(out c)) + { + token = default; + return false; + } + + switch (c) + { + case ',': + { + token = Token.Comma; + return true; + } + case '=': + { + token = Token.Equals; + return true; + } + case '\0': + { + token = Token.End; + return true; + } + } + + if (!IsWhiteSpace(c)) + { + break; + } + } + + using ValueStringBuilder sb = new ValueStringBuilder(stackalloc char[64]); + + char quoteChar = '\0'; + if (c is '\'' or '\"') + { + quoteChar = c; + if (!TryGetNextChar(out c)) + { + token = default; + return false; + } + } + + for (; ; ) + { + if (c == 0) + { + if (quoteChar != 0) + { + // EOS and unclosed quotes is an error + token = default; + return false; + } + // Reached end of input and therefore of string + break; + } + + if (quoteChar != 0 && c == quoteChar) + break; // Terminate: Found closing quote of quoted string. + + if (quoteChar == 0 && (c is ',' or '=')) + { + _index--; + break; // Terminate: Found start of a new ',' or '=' token. + } + + if (quoteChar == 0 && (c is '\'' or '\"')) + { + token = default; + return false; + } + + if (c is '\\') + { + if (!TryGetNextChar(out c)) + { + token = default; + return false; + } + + switch (c) + { + case '\\': + case ',': + case '=': + case '\'': + case '"': + sb.Append(c); + break; + case 't': + sb.Append('\t'); + break; + case 'r': + sb.Append('\r'); + break; + case 'n': + sb.Append('\n'); + break; + default: + token = default; + return false; + } + } + else + { + sb.Append(c); + } + + if (!TryGetNextChar(out c)) + { + token = default; + return false; + } + } + + + int length = sb.Length; + if (quoteChar == 0) + { + while (length > 0 && IsWhiteSpace(sb[length - 1])) + length--; + } + + tokenString = sb.AsSpan(0, length).ToString(); + token = Token.String; + return true; + } + } +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Buffers/SequenceReader.Search.cs b/src/IKVM.CoreLib/Buffers/SequenceReader.Search.cs new file mode 100644 index 0000000000..c6f68c37ad --- /dev/null +++ b/src/IKVM.CoreLib/Buffers/SequenceReader.Search.cs @@ -0,0 +1,861 @@ +#if NETFRAMEWORK + +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System; +using System.Buffers; +using System.Diagnostics; +using System.Runtime.CompilerServices; + +namespace IKVM.CoreLib.Buffers +{ + + internal ref partial struct SequenceReader + where T : unmanaged, IEquatable + { + + /// + /// Try to read everything up to the given . + /// + /// The read data, if any. + /// The delimiter to look for. + /// True to move past the if found. + /// True if the was found. + public bool TryReadTo(out ReadOnlySpan span, T delimiter, bool advancePastDelimiter = true) + { + ReadOnlySpan remaining = UnreadSpan; + int index = remaining.IndexOf(delimiter); + + if (index != -1) + { + span = index == 0 ? default : remaining.Slice(0, index); + AdvanceCurrentSpan(index + (advancePastDelimiter ? 1 : 0)); + return true; + } + + return TryReadToSlow(out span, delimiter, advancePastDelimiter); + } + + private bool TryReadToSlow(out ReadOnlySpan span, T delimiter, bool advancePastDelimiter) + { + if (!TryReadToInternal(out ReadOnlySequence sequence, delimiter, advancePastDelimiter, CurrentSpan.Length - CurrentSpanIndex)) + { + span = default; + return false; + } + + span = sequence.IsSingleSegment ? sequence.First.Span : sequence.ToArray(); + return true; + } + + /// + /// Try to read everything up to the given , ignoring delimiters that are + /// preceded by . + /// + /// The read data, if any. + /// The delimiter to look for. + /// If found prior to it will skip that occurrence. + /// True to move past the if found. + /// True if the was found. + public bool TryReadTo(out ReadOnlySpan span, T delimiter, T delimiterEscape, bool advancePastDelimiter = true) + { + ReadOnlySpan remaining = UnreadSpan; + int index = remaining.IndexOf(delimiter); + + if ((index > 0 && !remaining[index - 1].Equals(delimiterEscape)) || index == 0) + { + span = remaining.Slice(0, index); + AdvanceCurrentSpan(index + (advancePastDelimiter ? 1 : 0)); + return true; + } + + // This delimiter might be skipped, go down the slow path + return TryReadToSlow(out span, delimiter, delimiterEscape, index, advancePastDelimiter); + } + + private bool TryReadToSlow(out ReadOnlySpan span, T delimiter, T delimiterEscape, int index, bool advancePastDelimiter) + { + if (!TryReadToSlow(out ReadOnlySequence sequence, delimiter, delimiterEscape, index, advancePastDelimiter)) + { + span = default; + return false; + } + + Debug.Assert(sequence.Length > 0); + span = sequence.IsSingleSegment ? sequence.First.Span : sequence.ToArray(); + return true; + } + + private bool TryReadToSlow(out ReadOnlySequence sequence, T delimiter, T delimiterEscape, int index, bool advancePastDelimiter) + { + SequenceReader copy = this; + + ReadOnlySpan remaining = UnreadSpan; + bool priorEscape = false; + + do + { + if (index >= 0) + { + if (index == 0 && priorEscape) + { + // We were in the escaped state, so skip this delimiter + priorEscape = false; + Advance(index + 1); + remaining = UnreadSpan; + goto Continue; + } + else if (index > 0 && remaining[index - 1].Equals(delimiterEscape)) + { + // This delimiter might be skipped + + // Count our escapes + int escapeCount = 1; + int i = index - 2; + for (; i >= 0; i--) + { + if (!remaining[i].Equals(delimiterEscape)) + break; + } + if (i < 0 && priorEscape) + { + // Started and ended with escape, increment once more + escapeCount++; + } + escapeCount += index - 2 - i; + + if ((escapeCount & 1) != 0) + { + // An odd escape count means we're currently escaped, + // skip the delimiter and reset escaped state. + Advance(index + 1); + priorEscape = false; + remaining = UnreadSpan; + goto Continue; + } + } + + // Found the delimiter. Move to it, slice, then move past it. + AdvanceCurrentSpan(index); + + sequence = Sequence.Slice(copy.Position, Position); + if (advancePastDelimiter) + { + Advance(1); + } + return true; + } + else + { + // No delimiter, need to check the end of the span for odd number of escapes then advance + if (remaining.EndsWith([delimiterEscape])) + { + int escapeCount = 1; + int i = remaining.Length - 2; + for (; i >= 0; i--) + { + if (!remaining[i].Equals(delimiterEscape)) + break; + } + + escapeCount += remaining.Length - 2 - i; + if (i < 0 && priorEscape) + priorEscape = (escapeCount & 1) == 0; // equivalent to incrementing escapeCount before setting priorEscape + else + priorEscape = (escapeCount & 1) != 0; + } + else + { + priorEscape = false; + } + } + + // Nothing in the current span, move to the end, checking for the skip delimiter + AdvanceCurrentSpan(remaining.Length); + remaining = CurrentSpan; + + Continue: + index = remaining.IndexOf(delimiter); + } while (!End); + + // Didn't find anything, reset our original state. + this = copy; + sequence = default; + return false; + } + + /// + /// Try to read everything up to the given . + /// + /// The read data, if any. + /// The delimiter to look for. + /// True to move past the if found. + /// True if the was found. + public bool TryReadTo(out ReadOnlySequence sequence, T delimiter, bool advancePastDelimiter = true) + { + return TryReadToInternal(out sequence, delimiter, advancePastDelimiter); + } + + private bool TryReadToInternal(out ReadOnlySequence sequence, T delimiter, bool advancePastDelimiter, int skip = 0) + { + Debug.Assert(skip >= 0); + SequenceReader copy = this; + if (skip > 0) + Advance(skip); + ReadOnlySpan remaining = UnreadSpan; + + while (_moreData) + { + int index = remaining.IndexOf(delimiter); + if (index != -1) + { + // Found the delimiter. Move to it, slice, then move past it. + if (index > 0) + { + AdvanceCurrentSpan(index); + } + + sequence = Sequence.Slice(copy.Position, Position); + if (advancePastDelimiter) + { + Advance(1); + } + return true; + } + + AdvanceCurrentSpan(remaining.Length); + remaining = CurrentSpan; + } + + // Didn't find anything, reset our original state. + this = copy; + sequence = default; + return false; + } + + /// + /// Try to read everything up to the given , ignoring delimiters that are + /// preceded by . + /// + /// The read data, if any. + /// The delimiter to look for. + /// If found prior to it will skip that occurrence. + /// True to move past the if found. + /// True if the was found. + public bool TryReadTo(out ReadOnlySequence sequence, T delimiter, T delimiterEscape, bool advancePastDelimiter = true) + { + SequenceReader copy = this; + + ReadOnlySpan remaining = UnreadSpan; + bool priorEscape = false; + + while (_moreData) + { + int index = remaining.IndexOf(delimiter); + if (index != -1) + { + if (index == 0 && priorEscape) + { + // We were in the escaped state, so skip this delimiter + priorEscape = false; + Advance(index + 1); + remaining = UnreadSpan; + continue; + } + else if (index > 0 && remaining[index - 1].Equals(delimiterEscape)) + { + // This delimiter might be skipped + + // Count our escapes + int escapeCount = 0; + for (int i = index; i > 0 && remaining[i - 1].Equals(delimiterEscape); i--, escapeCount++) + ; + if (escapeCount == index && priorEscape) + { + // Started and ended with escape, increment once more + escapeCount++; + } + + priorEscape = false; + if ((escapeCount & 1) != 0) + { + // Odd escape count means we're in the escaped state, so skip this delimiter + Advance(index + 1); + remaining = UnreadSpan; + continue; + } + } + + // Found the delimiter. Move to it, slice, then move past it. + if (index > 0) + { + Advance(index); + } + + sequence = Sequence.Slice(copy.Position, Position); + if (advancePastDelimiter) + { + Advance(1); + } + return true; + } + + // No delimiter, need to check the end of the span for odd number of escapes then advance + { + int escapeCount = 0; + for (int i = remaining.Length; i > 0 && remaining[i - 1].Equals(delimiterEscape); i--, escapeCount++) + ; + if (priorEscape && escapeCount == remaining.Length) + { + escapeCount++; + } + priorEscape = escapeCount % 2 != 0; + } + + // Nothing in the current span, move to the end, checking for the skip delimiter + Advance(remaining.Length); + remaining = CurrentSpan; + } + + // Didn't find anything, reset our original state. + this = copy; + sequence = default; + return false; + } + + /// + /// Try to read everything up to the given . + /// + /// The read data, if any. + /// The delimiters to look for. + /// True to move past the first found instance of any of the given . + /// True if any of the were found. + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public bool TryReadToAny(out ReadOnlySpan span, scoped ReadOnlySpan delimiters, bool advancePastDelimiter = true) + { + ReadOnlySpan remaining = UnreadSpan; + int index = delimiters.Length == 2 + ? remaining.IndexOfAny(delimiters[0], delimiters[1]) + : remaining.IndexOfAny(delimiters); + + if (index != -1) + { + span = remaining.Slice(0, index); + Advance(index + (advancePastDelimiter ? 1 : 0)); + return true; + } + + return TryReadToAnySlow(out span, delimiters, advancePastDelimiter); + } + + private bool TryReadToAnySlow(out ReadOnlySpan span, scoped ReadOnlySpan delimiters, bool advancePastDelimiter) + { + if (!TryReadToAnyInternal(out ReadOnlySequence sequence, delimiters, advancePastDelimiter, CurrentSpan.Length - CurrentSpanIndex)) + { + span = default; + return false; + } + + span = sequence.IsSingleSegment ? sequence.First.Span : sequence.ToArray(); + return true; + } + + /// + /// Try to read everything up to the given . + /// + /// The read data, if any. + /// The delimiters to look for. + /// True to move past the first found instance of any of the given . + /// True if any of the were found. + public bool TryReadToAny(out ReadOnlySequence sequence, scoped ReadOnlySpan delimiters, bool advancePastDelimiter = true) + { + return TryReadToAnyInternal(out sequence, delimiters, advancePastDelimiter); + } + + private bool TryReadToAnyInternal(out ReadOnlySequence sequence, scoped ReadOnlySpan delimiters, bool advancePastDelimiter, int skip = 0) + { + SequenceReader copy = this; + if (skip > 0) + Advance(skip); + ReadOnlySpan remaining = UnreadSpan; + + while (!End) + { + int index = delimiters.Length == 2 + ? remaining.IndexOfAny(delimiters[0], delimiters[1]) + : remaining.IndexOfAny(delimiters); + + if (index != -1) + { + // Found one of the delimiters. Move to it, slice, then move past it. + if (index > 0) + { + AdvanceCurrentSpan(index); + } + + sequence = Sequence.Slice(copy.Position, Position); + if (advancePastDelimiter) + { + Advance(1); + } + return true; + } + + Advance(remaining.Length); + remaining = CurrentSpan; + } + + // Didn't find anything, reset our original state. + this = copy; + sequence = default; + return false; + } + + /// + /// Try to read everything up to the given . + /// + /// The read data, if any. + /// The delimiter to look for. + /// True to move past the if found. + /// True if the was found. + public bool TryReadTo(out ReadOnlySpan span, scoped ReadOnlySpan delimiter, bool advancePastDelimiter = true) + { + ReadOnlySpan remaining = UnreadSpan; + int index = remaining.IndexOf(delimiter); + + if (index >= 0) + { + span = remaining.Slice(0, index); + AdvanceCurrentSpan(index + (advancePastDelimiter ? delimiter.Length : 0)); + return true; + } + + // This delimiter might be skipped, go down the slow path + return TryReadToSlow(out span, delimiter, advancePastDelimiter); + } + + private bool TryReadToSlow(out ReadOnlySpan span, scoped ReadOnlySpan delimiter, bool advancePastDelimiter) + { + if (!TryReadTo(out ReadOnlySequence sequence, delimiter, advancePastDelimiter)) + { + span = default; + return false; + } + + Debug.Assert(sequence.Length > 0); + span = sequence.IsSingleSegment ? sequence.First.Span : sequence.ToArray(); + return true; + } + + /// + /// Try to read data until the entire given matches. + /// + /// The read data, if any. + /// The multi (T) delimiter. + /// True to move past the if found. + /// True if the was found. + public bool TryReadTo(out ReadOnlySequence sequence, scoped ReadOnlySpan delimiter, bool advancePastDelimiter = true) + { + if (delimiter.Length == 0) + { + sequence = default; + return true; + } + + SequenceReader copy = this; + + bool advanced = false; + while (!End) + { + if (!TryReadTo(out sequence, delimiter[0], advancePastDelimiter: false)) + { + this = copy; + return false; + } + + if (delimiter.Length == 1) + { + if (advancePastDelimiter) + { + Advance(1); + } + return true; + } + + if (IsNext(delimiter)) + { + // Probably a faster way to do this, potentially by avoiding the Advance in the previous TryReadTo call + if (advanced) + { + sequence = copy.Sequence.Slice(copy.Consumed, Consumed - copy.Consumed); + } + + if (advancePastDelimiter) + { + Advance(delimiter.Length); + } + return true; + } + else + { + Advance(1); + advanced = true; + } + } + + this = copy; + sequence = default; + return false; + } + + /// + /// Try to read data with given . + /// + /// Read count. + /// The read data, if successfully read requested data. + /// true if remaining items in current is enough for . + public bool TryReadExact(int count, out ReadOnlySequence sequence) + { + if (count < 0) + { + throw new ArgumentOutOfRangeException(nameof(count)); + } + + if (count > Remaining) + { + sequence = default; + return false; + } + + sequence = Sequence.Slice(Position, count); + if (count != 0) + { + Advance(count); + } + return true; + } + + /// + /// Advance until the given , if found. + /// + /// The delimiter to search for. + /// True to move past the if found. + /// True if the given was found. + public bool TryAdvanceTo(T delimiter, bool advancePastDelimiter = true) + { + ReadOnlySpan remaining = UnreadSpan; + int index = remaining.IndexOf(delimiter); + if (index != -1) + { + Advance(advancePastDelimiter ? index + 1 : index); + return true; + } + + return TryReadToInternal(out _, delimiter, advancePastDelimiter); + } + + /// + /// Advance until any of the given , if found. + /// + /// The delimiters to search for. + /// True to move past the first found instance of any of the given . + /// True if any of the given were found. + public bool TryAdvanceToAny(scoped ReadOnlySpan delimiters, bool advancePastDelimiter = true) + { + ReadOnlySpan remaining = UnreadSpan; + int index = remaining.IndexOfAny(delimiters); + if (index != -1) + { + AdvanceCurrentSpan(index + (advancePastDelimiter ? 1 : 0)); + return true; + } + + return TryReadToAnyInternal(out _, delimiters, advancePastDelimiter); + } + + /// + /// Advance past consecutive instances of the given . + /// + /// How many positions the reader has been advanced. + public long AdvancePast(T value) + { + long start = Consumed; + + do + { + // Advance past all matches in the current span + int i; + for (i = CurrentSpanIndex; i < CurrentSpan.Length && CurrentSpan[i].Equals(value); i++) + { + } + + int advanced = i - CurrentSpanIndex; + if (advanced == 0) + { + // Didn't advance at all in this span, exit. + break; + } + + AdvanceCurrentSpan(advanced); + + // If we're at position 0 after advancing and not at the End, + // we're in a new span and should continue the loop. + } while (CurrentSpanIndex == 0 && !End); + + return Consumed - start; + } + + /// + /// Skip consecutive instances of any of the given . + /// + /// How many positions the reader has been advanced. + public long AdvancePastAny(scoped ReadOnlySpan values) + { + long start = Consumed; + + do + { + // Advance past all matches in the current span + int i; + for (i = CurrentSpanIndex; i < CurrentSpan.Length && values.IndexOf(CurrentSpan[i]) != -1; i++) + { + } + + int advanced = i - CurrentSpanIndex; + if (advanced == 0) + { + // Didn't advance at all in this span, exit. + break; + } + + AdvanceCurrentSpan(advanced); + + // If we're at position 0 after advancing and not at the End, + // we're in a new span and should continue the loop. + } while (CurrentSpanIndex == 0 && !End); + + return Consumed - start; + } + + /// + /// Advance past consecutive instances of any of the given values. + /// + /// How many positions the reader has been advanced. + public long AdvancePastAny(T value0, T value1, T value2, T value3) + { + long start = Consumed; + + do + { + // Advance past all matches in the current span + int i; + for (i = CurrentSpanIndex; i < CurrentSpan.Length; i++) + { + T value = CurrentSpan[i]; + if (!value.Equals(value0) && !value.Equals(value1) && !value.Equals(value2) && !value.Equals(value3)) + { + break; + } + } + + int advanced = i - CurrentSpanIndex; + if (advanced == 0) + { + // Didn't advance at all in this span, exit. + break; + } + + AdvanceCurrentSpan(advanced); + + // If we're at position 0 after advancing and not at the End, + // we're in a new span and should continue the loop. + } while (CurrentSpanIndex == 0 && !End); + + return Consumed - start; + } + + /// + /// Advance past consecutive instances of any of the given values. + /// + /// How many positions the reader has been advanced. + public long AdvancePastAny(T value0, T value1, T value2) + { + long start = Consumed; + + do + { + // Advance past all matches in the current span + int i; + for (i = CurrentSpanIndex; i < CurrentSpan.Length; i++) + { + T value = CurrentSpan[i]; + if (!value.Equals(value0) && !value.Equals(value1) && !value.Equals(value2)) + { + break; + } + } + + int advanced = i - CurrentSpanIndex; + if (advanced == 0) + { + // Didn't advance at all in this span, exit. + break; + } + + AdvanceCurrentSpan(advanced); + + // If we're at position 0 after advancing and not at the End, + // we're in a new span and should continue the loop. + } while (CurrentSpanIndex == 0 && !End); + + return Consumed - start; + } + + /// + /// Advance past consecutive instances of any of the given values. + /// + /// How many positions the reader has been advanced. + public long AdvancePastAny(T value0, T value1) + { + long start = Consumed; + + do + { + // Advance past all matches in the current span + int i; + for (i = CurrentSpanIndex; i < CurrentSpan.Length; i++) + { + T value = CurrentSpan[i]; + if (!value.Equals(value0) && !value.Equals(value1)) + { + break; + } + } + + int advanced = i - CurrentSpanIndex; + if (advanced == 0) + { + // Didn't advance at all in this span, exit. + break; + } + + AdvanceCurrentSpan(advanced); + + // If we're at position 0 after advancing and not at the End, + // we're in a new span and should continue the loop. + } while (CurrentSpanIndex == 0 && !End); + + return Consumed - start; + } + + /// + /// Moves the reader to the end of the sequence. + /// + public void AdvanceToEnd() + { + if (_moreData) + { + Consumed = Length; + CurrentSpan = default; + CurrentSpanIndex = 0; + _currentPosition = Sequence.End; + _nextPosition = default; + _moreData = false; + } + } + + /// + /// Check to see if the given value is next. + /// + /// The value to compare the next items to. + /// Move past the value if found. + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public bool IsNext(T next, bool advancePast = false) + { + if (End) + return false; + + if (CurrentSpan[CurrentSpanIndex].Equals(next)) + { + if (advancePast) + { + AdvanceCurrentSpan(1); + } + return true; + } + return false; + } + + /// + /// Check to see if the given values are next. + /// + /// The span to compare the next items to. + /// Move past the values if found. + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public bool IsNext(scoped ReadOnlySpan next, bool advancePast = false) + { + ReadOnlySpan unread = UnreadSpan; + if (unread.StartsWith(next)) + { + if (advancePast) + { + AdvanceCurrentSpan(next.Length); + } + return true; + } + + // Only check the slow path if there wasn't enough to satisfy next + return unread.Length < next.Length && IsNextSlow(next, advancePast); + } + + private bool IsNextSlow(scoped ReadOnlySpan next, bool advancePast) + { + ReadOnlySpan currentSpan = UnreadSpan; + + // We should only come in here if we need more data than we have in our current span + Debug.Assert(currentSpan.Length < next.Length); + + int fullLength = next.Length; + SequencePosition nextPosition = _nextPosition; + + while (next.StartsWith(currentSpan)) + { + if (next.Length == currentSpan.Length) + { + // Fully matched + if (advancePast) + { + Advance(fullLength); + } + return true; + } + + // Need to check the next segment + while (true) + { + if (!Sequence.TryGet(ref nextPosition, out ReadOnlyMemory nextSegment, advance: true)) + { + // Nothing left + return false; + } + + if (nextSegment.Length > 0) + { + next = next.Slice(currentSpan.Length); + currentSpan = nextSegment.Span; + if (currentSpan.Length > next.Length) + { + currentSpan = currentSpan.Slice(0, next.Length); + } + break; + } + } + } + + return false; + } + } +} + +#endif diff --git a/src/IKVM.CoreLib/Buffers/SequenceReader.cs b/src/IKVM.CoreLib/Buffers/SequenceReader.cs index 853c59328d..ddca1d188f 100644 --- a/src/IKVM.CoreLib/Buffers/SequenceReader.cs +++ b/src/IKVM.CoreLib/Buffers/SequenceReader.cs @@ -1,9 +1,7 @@ -// Copyright (c) All contributors. All rights reserved. -// Licensed under the MIT license. See LICENSE file in the project root for full license information. +#if NETFRAMEWORK -/* Licensed to the .NET Foundation under one or more agreements. - * The .NET Foundation licenses this file to you under the MIT license. - * See the LICENSE file in the project root for more information. */ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. using System; using System.Buffers; @@ -13,169 +11,104 @@ namespace IKVM.CoreLib.Buffers { -#if NETFRAMEWORK - - internal ref partial struct SequenceReader - where T : unmanaged, IEquatable + ref partial struct SequenceReader where T : unmanaged, IEquatable { - /// - /// A value indicating whether we're using (as opposed to . - /// - private bool usingSequence; + private SequencePosition _currentPosition; + private SequencePosition _nextPosition; + private bool _moreData; + private readonly long _length; /// - /// Backing for the entire sequence when we're not using . - /// - private ReadOnlySequence sequence; - - /// - /// The position at the start of the . - /// - private SequencePosition currentPosition; - - /// - /// The position at the end of the . - /// - private SequencePosition nextPosition; - - /// - /// Backing for the entire sequence when we're not using . - /// - private ReadOnlyMemory memory; - - /// - /// A value indicating whether there is unread data remaining. - /// - private bool moreData; - - /// - /// The total number of elements in the sequence. - /// - private long length; - - /// - /// Initializes a new instance of the struct - /// over the given . + /// Create a over the given . /// [MethodImpl(MethodImplOptions.AggressiveInlining)] public SequenceReader(ReadOnlySequence sequence) { - this.usingSequence = true; - this.CurrentSpanIndex = 0; - this.Consumed = 0; - this.sequence = sequence; - this.memory = default; - this.currentPosition = sequence.Start; - this.length = -1; + CurrentSpanIndex = 0; + Consumed = 0; + Sequence = sequence; + _currentPosition = sequence.Start; + _length = -1; ReadOnlySpan first = sequence.First.Span; - this.nextPosition = sequence.GetPosition(first.Length); - this.CurrentSpan = first; - this.moreData = first.Length > 0; + _nextPosition = sequence.GetPosition(first.Length); + CurrentSpan = first; + _moreData = first.Length > 0; - if (!this.moreData && !sequence.IsSingleSegment) + if (!_moreData && !sequence.IsSingleSegment) { - this.moreData = true; - this.GetNextSpan(); + _moreData = true; + GetNextSpan(); } } /// - /// Initializes a new instance of the struct - /// over the given . + /// True when there is no more data in the . /// - [MethodImpl(MethodImplOptions.AggressiveInlining)] - public SequenceReader(ReadOnlyMemory memory) - { - this.usingSequence = false; - this.CurrentSpanIndex = 0; - this.Consumed = 0; - this.memory = memory; - this.CurrentSpan = memory.Span; - this.length = memory.Length; - this.moreData = memory.Length > 0; - - this.currentPosition = default; - this.nextPosition = default; - this.sequence = default; - } + public readonly bool End => !_moreData; /// - /// Gets a value indicating whether there is no more data in the . + /// The underlying for the reader. /// - public bool End => !this.moreData; + public ReadOnlySequence Sequence { get; } /// - /// Gets the underlying for the reader. + /// Gets the unread portion of the . /// - public ReadOnlySequence Sequence - { - get - { - if (this.sequence.IsEmpty && !this.memory.IsEmpty) - { - // We're in memory mode (instead of sequence mode). - // Lazily fill in the sequence data. - this.sequence = new ReadOnlySequence(this.memory); - this.currentPosition = this.sequence.Start; - this.nextPosition = this.sequence.End; - } - - return this.sequence; - } - } + /// + /// The unread portion of the . + /// + public readonly ReadOnlySequence UnreadSequence => Sequence.Slice(Position); /// - /// Gets the current position in the . + /// The current position in the . /// - public SequencePosition Position - => this.Sequence.GetPosition(this.CurrentSpanIndex, this.currentPosition); + public readonly SequencePosition Position + => Sequence.GetPosition(CurrentSpanIndex, _currentPosition); /// - /// Gets the current segment in the as a span. + /// The current segment in the as a span. /// public ReadOnlySpan CurrentSpan { get; private set; } /// - /// Gets the index in the . + /// The index in the . /// public int CurrentSpanIndex { get; private set; } /// - /// Gets the unread portion of the . + /// The unread portion of the . /// - public ReadOnlySpan UnreadSpan + public readonly ReadOnlySpan UnreadSpan { [MethodImpl(MethodImplOptions.AggressiveInlining)] - get => this.CurrentSpan.Slice(this.CurrentSpanIndex); + get => CurrentSpan.Slice(CurrentSpanIndex); } /// - /// Gets the total number of 's processed by the reader. + /// The total number of 's processed by the reader. /// public long Consumed { get; private set; } /// - /// Gets remaining 's in the reader's . + /// Remaining 's in the reader's . /// - public long Remaining => this.Length - this.Consumed; + public readonly long Remaining => Length - Consumed; /// - /// Gets count of in the reader's . + /// Count of in the reader's . /// - public long Length + public readonly long Length { - [MethodImpl(MethodImplOptions.AggressiveInlining)] get { - if (this.length < 0) + if (_length < 0) { - // Cache the length - this.length = this.Sequence.Length; + // Cast-away readonly to initialize lazy field + Unsafe.AsRef(in _length) = Sequence.Length; } - - return this.length; + return _length; } } @@ -185,11 +118,11 @@ public long Length /// The next value or default if at the end. /// False if at the end of the reader. [MethodImpl(MethodImplOptions.AggressiveInlining)] - public bool TryPeek(out T value) + public readonly bool TryPeek(out T value) { - if (this.moreData) + if (_moreData) { - value = this.CurrentSpan[this.CurrentSpanIndex]; + value = CurrentSpan[CurrentSpanIndex]; return true; } else @@ -199,6 +132,64 @@ public bool TryPeek(out T value) } } + /// + /// Peeks at the next value at specific offset without advancing the reader. + /// + /// The offset from current position. + /// The next value, or the default value if at the end of the reader. + /// true if the reader is not at its end and the peek operation succeeded; false if at the end of the reader. + public readonly bool TryPeek(long offset, out T value) + { + if (offset < 0) + throw new ArgumentOutOfRangeException(nameof(offset)); + + // If we've got data and offset is not out of bounds + if (!_moreData || Remaining <= offset) + { + value = default; + return false; + } + + // Sum CurrentSpanIndex + offset could overflow as is but the value of offset should be very large + // because we check Remaining <= offset above so to overflow we should have a ReadOnlySequence close to 8 exabytes + Debug.Assert(CurrentSpanIndex + offset >= 0); + + // If offset doesn't fall inside current segment move to next until we find correct one + if ((CurrentSpanIndex + offset) <= CurrentSpan.Length - 1) + { + Debug.Assert(offset <= int.MaxValue); + + value = CurrentSpan[CurrentSpanIndex + (int)offset]; + return true; + } + else + { + long remainingOffset = offset - (CurrentSpan.Length - CurrentSpanIndex); + SequencePosition nextPosition = _nextPosition; + ReadOnlyMemory currentMemory; + + while (Sequence.TryGet(ref nextPosition, out currentMemory, advance: true)) + { + // Skip empty segment + if (currentMemory.Length > 0) + { + if (remainingOffset >= currentMemory.Length) + { + // Subtract current non consumed data + remainingOffset -= currentMemory.Length; + } + else + { + break; + } + } + } + + value = currentMemory.Span[(int)remainingOffset]; + return true; + } + } + /// /// Read the next value and advance the reader. /// @@ -207,26 +198,19 @@ public bool TryPeek(out T value) [MethodImpl(MethodImplOptions.AggressiveInlining)] public bool TryRead(out T value) { - if (this.End) + if (End) { value = default; return false; } - value = this.CurrentSpan[this.CurrentSpanIndex]; - this.CurrentSpanIndex++; - this.Consumed++; + value = CurrentSpan[CurrentSpanIndex]; + CurrentSpanIndex++; + Consumed++; - if (this.CurrentSpanIndex >= this.CurrentSpan.Length) + if (CurrentSpanIndex >= CurrentSpan.Length) { - if (this.usingSequence) - { - this.GetNextSpan(); - } - else - { - this.moreData = false; - } + GetNextSpan(); } return true; @@ -235,69 +219,70 @@ public bool TryRead(out T value) /// /// Move the reader back the specified number of items. /// + /// + /// Thrown if trying to rewind a negative amount or more than . + /// [MethodImpl(MethodImplOptions.AggressiveInlining)] public void Rewind(long count) { - if (count < 0) + if ((ulong)count > (ulong)Consumed) { throw new ArgumentOutOfRangeException(nameof(count)); } - this.Consumed -= count; - - if (this.CurrentSpanIndex >= count) + if (count == 0) { - this.CurrentSpanIndex -= (int)count; - this.moreData = true; + return; } - else if (this.usingSequence) + + Consumed -= count; + + if (CurrentSpanIndex >= count) { - // Current segment doesn't have enough data, scan backward through segments - this.RetreatToPreviousSpan(this.Consumed); + CurrentSpanIndex -= (int)count; + _moreData = true; } else { - throw new ArgumentOutOfRangeException("Rewind went past the start of the memory."); + // Current segment doesn't have enough data, scan backward through segments + RetreatToPreviousSpan(Consumed); } } [MethodImpl(MethodImplOptions.NoInlining)] private void RetreatToPreviousSpan(long consumed) { - Debug.Assert(this.usingSequence, "usingSequence"); - this.ResetReader(); - this.Advance(consumed); + ResetReader(); + Advance(consumed); } private void ResetReader() { - Debug.Assert(this.usingSequence, "usingSequence"); - this.CurrentSpanIndex = 0; - this.Consumed = 0; - this.currentPosition = this.Sequence.Start; - this.nextPosition = this.currentPosition; + CurrentSpanIndex = 0; + Consumed = 0; + _currentPosition = Sequence.Start; + _nextPosition = _currentPosition; - if (this.Sequence.TryGet(ref this.nextPosition, out ReadOnlyMemory memory, advance: true)) + if (Sequence.TryGet(ref _nextPosition, out ReadOnlyMemory memory, advance: true)) { - this.moreData = true; + _moreData = true; if (memory.Length == 0) { - this.CurrentSpan = default; - + CurrentSpan = default; // No data in the first span, move to one with data - this.GetNextSpan(); + GetNextSpan(); } else { - this.CurrentSpan = memory.Span; + CurrentSpan = memory.Span; } } else { // No data in any spans and at end of sequence - this.moreData = false; - this.CurrentSpan = default; + _moreData = false; + CurrentSpan = default; } } @@ -306,29 +291,27 @@ private void ResetReader() /// private void GetNextSpan() { - Debug.Assert(this.usingSequence, "usingSequence"); - if (!this.Sequence.IsSingleSegment) + if (!Sequence.IsSingleSegment) { - SequencePosition previousNextPosition = this.nextPosition; - while (this.Sequence.TryGet(ref this.nextPosition, out ReadOnlyMemory memory, advance: true)) + SequencePosition previousNextPosition = _nextPosition; + while (Sequence.TryGet(ref _nextPosition, out ReadOnlyMemory memory, advance: true)) { - this.currentPosition = previousNextPosition; + _currentPosition = previousNextPosition; if (memory.Length > 0) { - this.CurrentSpan = memory.Span; - this.CurrentSpanIndex = 0; + CurrentSpan = memory.Span; + CurrentSpanIndex = 0; return; } else { - this.CurrentSpan = default; - this.CurrentSpanIndex = 0; - previousNextPosition = this.nextPosition; + CurrentSpan = default; + CurrentSpanIndex = 0; + previousNextPosition = _nextPosition; } } } - - this.moreData = false; + _moreData = false; } /// @@ -338,25 +321,15 @@ private void GetNextSpan() public void Advance(long count) { const long TooBigOrNegative = unchecked((long)0xFFFFFFFF80000000); - if ((count & TooBigOrNegative) == 0 && this.CurrentSpan.Length - this.CurrentSpanIndex > (int)count) + if ((count & TooBigOrNegative) == 0 && CurrentSpan.Length - CurrentSpanIndex > (int)count) { - this.CurrentSpanIndex += (int)count; - this.Consumed += count; - } - else if (this.usingSequence) - { - // Can't satisfy from the current span - this.AdvanceToNextSpan(count); - } - else if (this.CurrentSpan.Length - this.CurrentSpanIndex == (int)count) - { - this.CurrentSpanIndex += (int)count; - this.Consumed += count; - this.moreData = false; + CurrentSpanIndex += (int)count; + Consumed += count; } else { - throw new ArgumentOutOfRangeException(nameof(count)); + // Can't satisfy from the current span + AdvanceToNextSpan(count); } } @@ -366,14 +339,12 @@ public void Advance(long count) [MethodImpl(MethodImplOptions.AggressiveInlining)] internal void AdvanceCurrentSpan(long count) { - Debug.Assert(count >= 0, "count >= 0"); + Debug.Assert(count >= 0); - this.Consumed += count; - this.CurrentSpanIndex += (int)count; - if (this.usingSequence && this.CurrentSpanIndex >= this.CurrentSpan.Length) - { - this.GetNextSpan(); - } + Consumed += count; + CurrentSpanIndex += (int)count; + if (CurrentSpanIndex >= CurrentSpan.Length) + GetNextSpan(); } /// @@ -383,57 +354,40 @@ internal void AdvanceCurrentSpan(long count) [MethodImpl(MethodImplOptions.AggressiveInlining)] internal void AdvanceWithinSpan(long count) { - Debug.Assert(count >= 0, "count >= 0"); - - this.Consumed += count; - this.CurrentSpanIndex += (int)count; - - Debug.Assert(this.CurrentSpanIndex < this.CurrentSpan.Length, "this.CurrentSpanIndex < this.CurrentSpan.Length"); - } + Debug.Assert(count >= 0); - /// - /// Move the reader ahead the specified number of items - /// if there are enough elements remaining in the sequence. - /// - /// true if there were enough elements to advance; otherwise false. - internal bool TryAdvance(long count) - { - if (this.Remaining < count) - { - return false; - } + Consumed += count; + CurrentSpanIndex += (int)count; - this.Advance(count); - return true; + Debug.Assert(CurrentSpanIndex < CurrentSpan.Length); } private void AdvanceToNextSpan(long count) { - Debug.Assert(this.usingSequence, "usingSequence"); if (count < 0) { throw new ArgumentOutOfRangeException(nameof(count)); } - this.Consumed += count; - while (this.moreData) + Consumed += count; + while (_moreData) { - int remaining = this.CurrentSpan.Length - this.CurrentSpanIndex; + int remaining = CurrentSpan.Length - CurrentSpanIndex; if (remaining > count) { - this.CurrentSpanIndex += (int)count; + CurrentSpanIndex += (int)count; count = 0; break; } // As there may not be any further segments we need to // push the current index to the end of the span. - this.CurrentSpanIndex += remaining; + CurrentSpanIndex += remaining; count -= remaining; - Debug.Assert(count >= 0, "count >= 0"); + Debug.Assert(count >= 0); - this.GetNextSpan(); + GetNextSpan(); if (count == 0) { @@ -444,43 +398,52 @@ private void AdvanceToNextSpan(long count) if (count != 0) { // Not enough data left- adjust for where we actually ended and throw - this.Consumed -= count; + Consumed -= count; throw new ArgumentOutOfRangeException(nameof(count)); } } /// - /// Copies data from the current to the given span. + /// Copies data from the current to the given span if there + /// is enough data to fill it. /// - /// Destination to copy to. - /// True if there is enough data to copy to the . + /// + /// This API is used to copy a fixed amount of data out of the sequence if possible. It does not advance + /// the reader. To look ahead for a specific stream of data can be used. + /// + /// Destination span to copy to. + /// True if there is enough data to completely fill the span. [MethodImpl(MethodImplOptions.AggressiveInlining)] - public bool TryCopyTo(Span destination) + public readonly bool TryCopyTo(Span destination) { - ReadOnlySpan firstSpan = this.UnreadSpan; + // This API doesn't advance to facilitate conditional advancement based on the data returned. + // We don't provide an advance option to allow easier utilizing of stack allocated destination spans. + // (Because we can make this method readonly we can guarantee that we won't capture the span.) + + ReadOnlySpan firstSpan = UnreadSpan; if (firstSpan.Length >= destination.Length) { firstSpan.Slice(0, destination.Length).CopyTo(destination); return true; } - return this.TryCopyMultisegment(destination); + // Not enough in the current span to satisfy the request, fall through to the slow path + return TryCopyMultisegment(destination); } - internal bool TryCopyMultisegment(Span destination) + internal readonly bool TryCopyMultisegment(Span destination) { - if (this.Remaining < destination.Length) - { + // If we don't have enough to fill the requested buffer, return false + if (Remaining < destination.Length) return false; - } - ReadOnlySpan firstSpan = this.UnreadSpan; - Debug.Assert(firstSpan.Length < destination.Length, "firstSpan.Length < destination.Length"); + ReadOnlySpan firstSpan = UnreadSpan; + Debug.Assert(firstSpan.Length < destination.Length); firstSpan.CopyTo(destination); int copied = firstSpan.Length; - SequencePosition next = this.nextPosition; - while (this.Sequence.TryGet(ref next, out ReadOnlyMemory nextSegment, true)) + SequencePosition next = _nextPosition; + while (Sequence.TryGet(ref next, out ReadOnlyMemory nextSegment, true)) { if (nextSegment.Length > 0) { @@ -497,9 +460,7 @@ internal bool TryCopyMultisegment(Span destination) return true; } - } +} #endif - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs b/src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs index 4609baa440..c7e5f451c7 100644 --- a/src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs +++ b/src/IKVM.CoreLib/Buffers/SequenceReaderExtensions.cs @@ -352,41 +352,6 @@ static int CalculateAlignment(int position, int alignment) return result + alignment; } - /// - /// Skip consecutive instances of any of the given . - /// - /// How many positions the reader has been advanced. - public static long AdvancePastAny(this ref SequenceReader reader, scoped ReadOnlySpan values) - where T : unmanaged, IEquatable - { - var start = reader.Consumed; - - do - { - // Advance past all matches in the current span - int i; - for (i = reader.CurrentSpanIndex; i < reader.CurrentSpan.Length && values.IndexOf(reader.CurrentSpan[i]) != -1; i++) - { - continue; - } - - int advanced = i - reader.CurrentSpanIndex; - if (advanced == 0) - { - // Didn't advance at all in this span, exit. - break; - } - - reader.Advance(advanced); - - // If we're at position 0 after advancing and not at the End, - // we're in a new span and should continue the loop. - } - while (reader.CurrentSpanIndex == 0 && !reader.End); - - return reader.Consumed - start; - } - } } diff --git a/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs b/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs index 3551bd310f..e49f3612e2 100644 --- a/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs +++ b/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs @@ -2,6 +2,7 @@ using System.Collections.Generic; using System.Collections.Immutable; using System.Diagnostics; +using System.Diagnostics.CodeAnalysis; using System.Linq; using System.Reflection; using System.Security.Cryptography; @@ -133,6 +134,33 @@ static ImmutableArray CalculatePublicKeyToken(ImmutableArray publicK return result.ToImmutable(); } + /// + /// Parses a span of characters into a assembly name. + /// + /// A span containing the characters representing the assembly name to parse. + /// Parsed type name. + /// Provided assembly name was invalid. + public static AssemblyIdentity Parse(ReadOnlySpan assemblyName) => TryParse(assemblyName, out AssemblyIdentity? result) ? result! : throw new ArgumentException("Invalid assembly name.", nameof(assemblyName)); + + /// + /// Tries to parse a span of characters into an assembly name. + /// + /// A span containing the characters representing the assembly name to parse. + /// Contains the result when parsing succeeds. + /// true if assembly name was converted successfully, otherwise, false. + public static bool TryParse(ReadOnlySpan assemblyName, [NotNullWhen(true)] out AssemblyIdentity? result) + { + AssemblyIdentityParser.AssemblyIdentityParts parts = default; + if (!assemblyName.IsEmpty && AssemblyIdentityParser.TryParse(assemblyName, ref parts)) + { + result = new(parts._name, parts._version, parts._cultureName, parts._publicKeyOrToken?.ToImmutableArray() ?? [], parts._publicKeyOrToken != null); + return true; + } + + result = null; + return false; + } + readonly string _name; readonly Version _version; readonly string? _cultureName; diff --git a/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs b/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs index 5c0818432b..c8390162eb 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs @@ -11,25 +11,31 @@ namespace IKVM.CoreLib.Symbols.Emit { - abstract class TypeSymbolBuilderBase : ITypeSymbolBuilder + abstract class TypeSymbolBuilderBase : ITypeSymbolBuilder + where TContext : ISymbolContext { const BindingFlags DefaultBindingFlags = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance; - readonly ISymbolContext _context; + readonly TContext _context; readonly IModuleSymbolBuilder _module; - string _name; - TypeAttributes _attributes; + readonly TypeAttributes _attributes; + readonly string _namespace; + readonly string _name; + readonly ITypeSymbol? _declaringType; + readonly PackingSize _packingSize; + readonly int _typeSize; ITypeSymbol? _parentType; - ImmutableList _genericTypeParameters = ImmutableList.Empty; + IConstructorSymbol? _typeInitializer = null; + ImmutableList _genericTypeParameters = ImmutableList.Empty; ImmutableList _interfaces = ImmutableList.Empty; - ImmutableList _fields = ImmutableList.Empty; - ImmutableList _constructors = ImmutableList.Empty; - ImmutableList _methods = ImmutableList.Empty; + ImmutableList _fields = ImmutableList.Empty; + ImmutableList _constructors = ImmutableList.Empty; + ImmutableList _methods = ImmutableList.Empty; ImmutableList<(IMethodSymbol, IMethodSymbol)> _methodOverrides = ImmutableList<(IMethodSymbol, IMethodSymbol)>.Empty; - ImmutableList _properties = ImmutableList.Empty; - ImmutableList _events = ImmutableList.Empty; + ImmutableList _properties = ImmutableList.Empty; + ImmutableList _events = ImmutableList.Empty; ImmutableList _customAttributes = ImmutableList.Empty; /// @@ -37,11 +43,34 @@ abstract class TypeSymbolBuilderBase : ITypeSymbolBuilder /// /// /// - public TypeSymbolBuilderBase(ISymbolContext context, IModuleSymbolBuilder module, TypeAttributes attributes) + /// + /// + /// + /// + /// + /// + public TypeSymbolBuilderBase(TContext context, IModuleSymbolBuilder module, TypeAttributes attributes, string name, ITypeSymbol? declaringType, PackingSize packingSize, int typeSize) { _context = context ?? throw new ArgumentNullException(nameof(context)); _module = module ?? throw new ArgumentNullException(nameof(module)); _attributes = attributes; + _declaringType = declaringType; + _packingSize = packingSize; + _typeSize = typeSize; + + int iLast = name.LastIndexOf('.'); + if (iLast <= 0) + { + // no name space + _namespace = string.Empty; + _name = name; + } + else + { + // split the name space + _namespace = name.Substring(0, iLast); + _name = name.Substring(iLast + 1); + } } /// @@ -447,9 +476,7 @@ public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes att /// public IConstructorSymbolBuilder DefineTypeInitializer() { - var constructor = CreateTypeInitializerBuilder(); - _constructors = _constructors.Add(constructor); - return constructor; + return (IConstructorSymbolBuilder)(_typeInitializer = CreateTypeInitializerBuilder()); } protected abstract IConstructorSymbolBuilder CreateTypeInitializerBuilder(); @@ -468,234 +495,341 @@ public void SetCustomAttribute(CustomAttribute attribute) #region ITypeSymbol - public void Foo() - { - System.Reflection.Metadata.TypeName t; - } - + /// public TypeAttributes Attributes => _attributes; + /// public IAssemblySymbol Assembly => _module.Assembly; + /// public IMethodBaseSymbol? DeclaringMethod => null; + /// public string? AssemblyQualifiedName => System.Reflection.Assembly.CreateQualifiedName(Assembly.FullName, FullName); - public string? FullName => _name; + /// + public string? FullName => string.IsNullOrEmpty(_namespace) ? _name : _namespace + "." + _name; - public string? Namespace => throw new NotImplementedException(); + /// + public string? Namespace => _namespace; - public TypeCode TypeCode => throw new NotImplementedException(); + /// + public TypeCode TypeCode => TypeCode.Object; - public ITypeSymbol? BaseType => throw new NotImplementedException(); + /// + public ITypeSymbol? BaseType => _parentType; - public bool ContainsGenericParameters => throw new NotImplementedException(); + /// + public bool ContainsGenericParameters => _genericTypeParameters.IsEmpty == false; + /// public GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); + /// public int GenericParameterPosition => throw new NotImplementedException(); - public IImmutableList GenericTypeArguments => throw new NotImplementedException(); + /// + public IImmutableList GenericTypeArguments => _genericTypeParameters; - public bool IsConstructedGenericType => throw new NotImplementedException(); + /// + public bool IsConstructedGenericType => false; - public bool IsGenericType => throw new NotImplementedException(); + /// + public bool IsGenericType => _genericTypeParameters.Count > 0; - public bool IsGenericTypeDefinition => throw new NotImplementedException(); + /// + public bool IsGenericTypeDefinition => IsGenericType; - public bool IsGenericParameter => throw new NotImplementedException(); + /// + public bool IsGenericParameter => false; - public bool IsAutoLayout => throw new NotImplementedException(); + /// + public bool IsAutoLayout => (_attributes & TypeAttributes.LayoutMask) == TypeAttributes.AutoLayout; + + /// + public bool IsExplicitLayout => (_attributes & TypeAttributes.LayoutMask) == TypeAttributes.ExplicitLayout; + + /// + public bool IsLayoutSequential => (_attributes & TypeAttributes.LayoutMask) == TypeAttributes.SequentialLayout; + + /// + public bool HasElementType => false; + + /// + public bool IsClass => (_attributes & TypeAttributes.ClassSemanticsMask) == TypeAttributes.Class && !IsValueType; + + /// + public bool IsValueType => IsSubclassOf(Context.ResolveCoreType("System.ValueType")); + + /// + public bool IsInterface => (_attributes & TypeAttributes.Interface) != 0; + + /// + public bool IsPrimitive => false; - public bool IsExplicitLayout => throw new NotImplementedException(); + /// + public bool IsSZArray => false; - public bool IsLayoutSequential => throw new NotImplementedException(); + /// + public bool IsArray => false; - public bool HasElementType => throw new NotImplementedException(); + /// + public bool IsEnum => IsSubclassOf(Context.ResolveCoreType("System.Enum")); - public bool IsClass => throw new NotImplementedException(); + /// + public bool IsPointer => false; - public bool IsValueType => throw new NotImplementedException(); + /// + public bool IsFunctionPointer => false; - public bool IsInterface => throw new NotImplementedException(); + /// + public bool IsUnmanagedFunctionPointer => false; - public bool IsPrimitive => throw new NotImplementedException(); + /// + public bool IsByRef => false; - public bool IsSZArray => throw new NotImplementedException(); + /// + public bool IsAbstract => (_attributes & TypeAttributes.Abstract) != 0; - public bool IsArray => throw new NotImplementedException(); + /// + public bool IsSealed => (_attributes & TypeAttributes.Sealed) != 0; - public bool IsEnum => throw new NotImplementedException(); + /// + public bool IsVisible => GetIsVisible(); - public bool IsPointer => throw new NotImplementedException(); + bool GetIsVisible() + { + if (IsGenericParameter) + return true; - public bool IsFunctionPointer => throw new NotImplementedException(); + if (HasElementType) + return GetElementType()!.IsVisible; - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + var type = (ITypeSymbol)this; + while (type.IsNested) + { + if (!type.IsNestedPublic) + return false; - public bool IsByRef => throw new NotImplementedException(); + // this should be null for non-nested types. + type = type.DeclaringType!; + } - public bool IsAbstract => throw new NotImplementedException(); + // Now "type" should be a top level type + if (!type.IsPublic) + return false; - public bool IsSealed => throw new NotImplementedException(); + if (IsGenericType && !IsGenericTypeDefinition) + { + foreach (var t in GetGenericArguments()) + { + if (!t.IsVisible) + return false; + } + } - public bool IsVisible => throw new NotImplementedException(); + return true; + } - public bool IsPublic => throw new NotImplementedException(); + /// + public bool IsPublic => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.Public; - public bool IsNotPublic => throw new NotImplementedException(); + /// + public bool IsNotPublic => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NotPublic; - public bool IsNested => throw new NotImplementedException(); + /// + public bool IsNested => DeclaringType != null; - public bool IsNestedAssembly => throw new NotImplementedException(); + /// + public bool IsNestedAssembly => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedAssembly; - public bool IsNestedFamANDAssem => throw new NotImplementedException(); + /// + public bool IsNestedFamANDAssem => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamANDAssem; - public bool IsNestedFamily => throw new NotImplementedException(); + /// + public bool IsNestedFamily => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamily; - public bool IsNestedFamORAssem => throw new NotImplementedException(); + /// + public bool IsNestedFamORAssem => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamORAssem; - public bool IsNestedPrivate => throw new NotImplementedException(); + /// + public bool IsNestedPrivate => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPrivate; - public bool IsNestedPublic => throw new NotImplementedException(); + /// + public bool IsNestedPublic => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPublic; + /// public bool IsSerializable => throw new NotImplementedException(); - public bool IsSignatureType => throw new NotImplementedException(); + /// + public bool IsSignatureType => false; - public bool IsSpecialName => throw new NotImplementedException(); + /// + public bool IsSpecialName => (_attributes & TypeAttributes.SpecialName) != 0; + /// public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); - public IModuleSymbol Module => throw new NotImplementedException(); + /// + public IModuleSymbol Module => _module; - public ITypeSymbol? DeclaringType => throw new NotImplementedException(); + /// + public ITypeSymbol? DeclaringType => _declaringType; + /// public MemberTypes MemberType => throw new NotImplementedException(); + /// public int MetadataToken => throw new NotImplementedException(); - public string Name => throw new NotImplementedException(); + /// + public string Name => _name; - public bool IsMissing => throw new NotImplementedException(); + /// + public bool IsMissing => false; + /// public bool ContainsMissing => throw new NotImplementedException(); + /// public bool IsComplete => throw new NotImplementedException(); + /// public int GetArrayRank() { - throw new NotImplementedException(); + return 0; } + /// public IImmutableList GetDefaultMembers() { throw new NotImplementedException(); } + /// public ITypeSymbol? GetElementType() { - throw new NotImplementedException(); + return null; } + /// public string? GetEnumName(object value) { throw new NotImplementedException(); } + /// public IImmutableList GetEnumNames() { throw new NotImplementedException(); } + /// public ITypeSymbol GetEnumUnderlyingType() { throw new NotImplementedException(); } + /// public IImmutableList GetGenericArguments() { - throw new NotImplementedException(); + return _genericTypeParameters; } + /// public IImmutableList GetGenericParameterConstraints() { throw new NotImplementedException(); } + /// public ITypeSymbol GetGenericTypeDefinition() { throw new NotImplementedException(); } + /// public ITypeSymbol? GetInterface(string name) { throw new NotImplementedException(); } + /// public ITypeSymbol? GetInterface(string name, bool ignoreCase) { throw new NotImplementedException(); } + /// public IImmutableList GetInterfaces(bool inherit = true) { throw new NotImplementedException(); } + /// public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) { throw new NotImplementedException(); } + /// public IImmutableList GetDeclaredConstructors() { throw new NotImplementedException(); } + /// public IConstructorSymbol? GetConstructor(IImmutableList types) { throw new NotImplementedException(); } + /// public IConstructorSymbol? GetConstructor(BindingFlags bindingFlags, IImmutableList types) { throw new NotImplementedException(); } + /// public IImmutableList GetConstructors() { throw new NotImplementedException(); } + /// public IImmutableList GetConstructors(BindingFlags bindingFlags) { throw new NotImplementedException(); } + /// public IFieldSymbol? GetField(string name) { throw new NotImplementedException(); } + /// public IFieldSymbol? GetField(string name, BindingFlags bindingFlags) { throw new NotImplementedException(); } + /// public IImmutableList GetFields() { throw new NotImplementedException(); } + /// public IImmutableList GetFields(BindingFlags bindingFlags) { throw new NotImplementedException(); } + /// public IImmutableList GetDeclaredMethods() { - throw new NotImplementedException(); + return _methods; } /// @@ -707,27 +841,27 @@ public IImmutableList GetDeclaredMethods() /// public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList? types, IImmutableList? modifiers) { - return SymbolUtil.SelectMethod(this, DefaultBindingFlags, name, types, modifiers); + return SymbolUtil.SelectMethod(this, bindingFlags, name, types, modifiers); } public IMethodSymbol? GetMethod(string name, IImmutableList types) { - throw new NotImplementedException(); + return SymbolUtil.SelectMethod(this, DefaultBindingFlags, null, types, null); } public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags) { - throw new NotImplementedException(); + return SymbolUtil.SelectMethod(this, bindingFlags, null, null, null); } public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList types) { - throw new NotImplementedException(); + return SymbolUtil.SelectMethod(this, bindingFlags, null, types, null); } public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers) { - throw new NotImplementedException(); + return SymbolUtil.SelectMethod(this, bindingFlags, null, types, modifiers); } public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers) diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index 776a0d8623..fda80bd4f0 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -8,6 +8,13 @@ namespace IKVM.CoreLib.Symbols interface ISymbolContext { + /// + /// Resolves the named type from the core assembly. + /// + /// + /// + ITypeSymbol ResolveCoreType(string typeName); + /// /// Defines a dynamic assembly that has the specified name and access rights. /// @@ -26,6 +33,7 @@ interface ISymbolContext /// /// IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes, bool collectable = true, bool saveable = false); + } } diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolName.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolName.cs new file mode 100644 index 0000000000..8743f4b7a9 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolName.cs @@ -0,0 +1,503 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System.Collections.Generic; +using System.Diagnostics; +using System.Diagnostics.CodeAnalysis; +using System.Runtime.InteropServices; +using System.Text; +using IKVM.CoreLib.Text; +using System; + + + +#if !SYSTEM_PRIVATE_CORELIB +using System.Collections.Immutable; +#endif + +namespace IKVM.CoreLib.Symbols +{ + + [DebuggerDisplay("{AssemblyQualifiedName}")] + sealed class TypeSymbolName + { + /// + /// Positive value is array rank. + /// Negative value is modifier encoded using constants defined in . + /// + private readonly int _rankOrModifier; + /// + /// To avoid the need of allocating a string for all declaring types (example: A+B+C+D+E+F+G), + /// length of the name is stored and the fullName passed in ctor represents the full name of the nested type. + /// So when the name is needed, a substring is being performed. + /// + private readonly int _nestedNameLength; + private readonly TypeSymbolName? _elementOrGenericType; + private readonly TypeSymbolName? _declaringType; + private readonly ImmutableArray _genericArguments; + private string? _name, _fullName, _assemblyQualifiedName; + + internal TypeSymbolName(string? fullName, + AssemblyIdentity? assemblyName, + TypeSymbolName? elementOrGenericType = default, + TypeSymbolName? declaringType = default, + ImmutableArray.Builder? genericTypeArguments = default, + int rankOrModifier = default, + int nestedNameLength = -1) + { + _fullName = fullName; + AssemblyName = assemblyName; + _rankOrModifier = rankOrModifier; + _elementOrGenericType = elementOrGenericType; + _declaringType = declaringType; + _nestedNameLength = nestedNameLength; + + _genericArguments = genericTypeArguments is null + ? ImmutableArray.Empty + : genericTypeArguments.Count == genericTypeArguments.Capacity ? genericTypeArguments.MoveToImmutable() : genericTypeArguments.ToImmutableArray(); + } + + /// + /// The assembly-qualified name of the type; e.g., "System.Int32, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089". + /// + /// + /// If returns null, simply returns . + /// + public string AssemblyQualifiedName + => _assemblyQualifiedName ??= AssemblyName is null ? FullName : $"{FullName}, {AssemblyName.FullName}"; // see recursion comments in FullName + + /// + /// Returns assembly name which contains this type, or null if this was not + /// created from a fully-qualified name. + /// + public AssemblyIdentity? AssemblyName { get; } + + /// + /// If this type is a nested type (see ), gets + /// the declaring type. If this type is not a nested type, throws. + /// + /// + /// For example, given "Namespace.Declaring+Nested", unwraps the outermost type and returns "Namespace.Declaring". + /// + /// The current type is not a nested type. + public TypeSymbolName DeclaringType + { + get + { + if (_declaringType is null) + { + throw new InvalidOperationException(); + } + + return _declaringType; + } + } + + /// + /// The full name of this type, including namespace, but without the assembly name; e.g., "System.Int32". + /// Nested types are represented with a '+'; e.g., "MyNamespace.MyType+NestedType". + /// + /// + /// For constructed generic types, the type arguments will be listed using their fully qualified + /// names. For example, given "List<int>", the property will return + /// "System.Collections.Generic.List`1[[System.Int32, mscorlib, ...]]". + /// For open generic types, the convention is to use a backtick ("`") followed by + /// the arity of the generic type. For example, given "Dictionary<,>", the + /// property will return "System.Collections.Generic.Dictionary`2". Given "Dictionary<,>.Enumerator", + /// the property will return "System.Collections.Generic.Dictionary`2+Enumerator". + /// See ECMA-335, Sec. I.10.7.2 (Type names and arity encoding) for more information. + /// + public string FullName + { + get + { + // This is a recursive method over potentially hostile input. Protection against DoS is offered + // via the [Try]Parse method and TypeNameParserOptions.MaxNodes property at construction time. + // This FullName property getter and related methods assume that this TypeName instance has an + // acceptable node count. + // + // The node count controls the total amount of work performed by this method, including: + // - The max possible stack depth due to the recursive methods calls; and + // - The total number of bytes allocated by this function. For a deeply-nested TypeName + // object, the total allocation across the full object graph will be + // O(FullName.Length * GetNodeCount()). + + if (_fullName is null) + { + if (IsConstructedGenericType) + { + _fullName = TypeSymbolNameParserHelpers.GetGenericTypeFullName(GetGenericTypeDefinition().FullName.AsSpan(), _genericArguments.AsSpan()); + } + else if (IsArray || IsPointer || IsByRef) + { + ValueStringBuilder builder = new(stackalloc char[128]); + builder.Append(GetElementType().FullName); + _fullName = TypeSymbolNameParserHelpers.GetRankOrModifierStringRepresentation(_rankOrModifier, ref builder); + } + else + { + Debug.Fail("Pre-allocated full name should have been provided in the ctor"); + } + } + else if (_nestedNameLength > 0 && _fullName.Length > _nestedNameLength) // Declaring types + { + // Stored fullName represents the full name of the nested type. + // Example: Namespace.Declaring+Nested + _fullName = _fullName.Substring(0, _nestedNameLength); + } + + return _fullName!; + } + } + + /// + /// Returns true if this type represents any kind of array, regardless of the array's + /// rank or its bounds. + /// + public bool IsArray => _rankOrModifier == TypeSymbolNameParserHelpers.SZArray || _rankOrModifier > 0; + + /// + /// Returns true if this type represents a constructed generic type (e.g., "List<int>"). + /// + /// + /// Returns false for open generic types (e.g., "Dictionary<,>"). + /// + public bool IsConstructedGenericType => +#if SYSTEM_PRIVATE_CORELIB + _genericArguments is not null; +#else + _genericArguments.Length > 0; +#endif + + /// + /// Returns true if this is a "plain" type; that is, not an array, not a pointer, not a reference, and + /// not a constructed generic type. Examples of elemental types are "System.Int32", + /// "System.Uri", and "YourNamespace.YourClass". + /// + /// + /// This property returning true doesn't mean that the type is a primitive like string + /// or int; it just means that there's no underlying type. + /// This property will return true for generic type definitions (e.g., "Dictionary<,>"). + /// This is because determining whether a type truly is a generic type requires loading the type + /// and performing a runtime check. + /// + public bool IsSimple => _elementOrGenericType is null; + + /// + /// Returns true if this is a managed pointer type (e.g., "ref int"). + /// Managed pointer types are sometimes called byref types () + /// + public bool IsByRef => _rankOrModifier == TypeSymbolNameParserHelpers.ByRef; + + /// + /// Returns true if this is a nested type (e.g., "Namespace.Declaring+Nested"). + /// For nested types returns their declaring type. + /// + public bool IsNested => _declaringType is not null; + + /// + /// Returns true if this type represents a single-dimensional, zero-indexed array (e.g., "int[]"). + /// + public bool IsSZArray => _rankOrModifier == TypeSymbolNameParserHelpers.SZArray; + + /// + /// Returns true if this type represents an unmanaged pointer (e.g., "int*" or "void*"). + /// Unmanaged pointer types are often just called pointers () + /// + public bool IsPointer => _rankOrModifier == TypeSymbolNameParserHelpers.Pointer; + + /// + /// Returns true if this type represents a variable-bound array; that is, an array of rank greater + /// than 1 (e.g., "int[,]") or a single-dimensional array which isn't necessarily zero-indexed. + /// + public bool IsVariableBoundArrayType => _rankOrModifier >= 1; + + /// + /// The name of this type, without the namespace and the assembly name; e.g., "Int32". + /// Nested types are represented without a '+'; e.g., "MyNamespace.MyType+NestedType" is just "NestedType". + /// + public string Name + { + get + { + // Lookups to Name and FullName might be recursive. See comments in FullName property getter. + + if (_name is null) + { + if (IsConstructedGenericType) + { + _name = TypeSymbolNameParserHelpers.GetName(GetGenericTypeDefinition().FullName.AsSpan()).ToString(); + } + else if (IsPointer || IsByRef || IsArray) + { + ValueStringBuilder builder = new(stackalloc char[64]); + builder.Append(GetElementType().Name); + _name = TypeSymbolNameParserHelpers.GetRankOrModifierStringRepresentation(_rankOrModifier, ref builder); + } + else if (_nestedNameLength > 0 && _fullName is not null) + { + _name = TypeSymbolNameParserHelpers.GetName(_fullName.AsSpan(0, _nestedNameLength)).ToString(); + } + else + { + _name = TypeSymbolNameParserHelpers.GetName(FullName.AsSpan()).ToString(); + } + } + + return _name; + } + } + + /// + /// Represents the total number of instances that are used to describe + /// this instance, including any generic arguments or underlying types. + /// + /// + /// This value is computed every time this method gets called, it's not cached. + /// There's not really a parallel concept to this in reflection. Think of it + /// as the total number of instances that would be created if + /// you were to totally deconstruct this instance and visit each intermediate + /// that occurs as part of deconstruction. + /// "int" and "Person" each have complexities of 1 because they're standalone types. + /// "int[]" has a node count of 2 because to fully inspect it involves inspecting the + /// array type itself, plus unwrapping the underlying type ("int") and inspecting that. + /// + /// "Dictionary<string, List<int[][]>>" has node count 8 because fully visiting it + /// involves inspecting 8 instances total: + /// + /// Dictionary<string, List<int[][]>> (the original type) + /// Dictionary`2 (the generic type definition) + /// string (a type argument of Dictionary) + /// List<int[][]> (a type argument of Dictionary) + /// List`1 (the generic type definition) + /// int[][] (a type argument of List) + /// int[] (the underlying type of int[][]) + /// int (the underlying type of int[]) + /// + /// + /// + public int GetNodeCount() + { + // This method uses checked arithmetic to avoid silent overflows. + // It's impossible to parse a TypeName with NodeCount > int.MaxValue + // (TypeNameParseOptions.MaxNodes is an int), but it's possible + // to create such names with the Make* APIs. + int result = 1; + + if (IsArray || IsPointer || IsByRef) + { + result = checked(result + GetElementType().GetNodeCount()); + } + else if (IsConstructedGenericType) + { + result = checked(result + GetGenericTypeDefinition().GetNodeCount()); + + foreach (TypeSymbolName genericArgument in GetGenericArguments()) + { + result = checked(result + genericArgument.GetNodeCount()); + } + } + else if (IsNested) + { + result = checked(result + DeclaringType.GetNodeCount()); + } + + return result; + } + + /// + /// The TypeName of the object encompassed or referred to by the current array, pointer, or reference type. + /// + /// + /// For example, given "int[][]", unwraps the outermost array and returns "int[]". + /// + /// The current type is not an array, pointer or reference. + public TypeSymbolName GetElementType() + { + if (!(IsArray || IsPointer || IsByRef)) + { + TypeSymbolNameParserHelpers.ThrowInvalidOperation_NoElement(); + } + + return _elementOrGenericType!; + } + + /// + /// Returns a TypeName object that represents a generic type name definition from which the current generic type name can be constructed. + /// + /// + /// Given "Dictionary<string, int>", returns the generic type definition "Dictionary<,>". + /// + /// The current type is not a generic type. + public TypeSymbolName GetGenericTypeDefinition() + { + if (!IsConstructedGenericType) + { + TypeSymbolNameParserHelpers.ThrowInvalidOperation_NotGenericType(); + } + + return _elementOrGenericType!; + } + + /// + /// Parses a span of characters into a type name. + /// + /// A span containing the characters representing the type name to parse. + /// An object that describes optional parameters to use. + /// Parsed type name. + /// Provided type name was invalid. + /// Parsing has exceeded the limit set by . + public static TypeSymbolName Parse(ReadOnlySpan typeName) + => TypeNameParser.Parse(typeName, throwOnError: true)!; + + /// + /// Tries to parse a span of characters into a type name. + /// + /// A span containing the characters representing the type name to parse. + /// An object that describes optional parameters to use. + /// Contains the result when parsing succeeds. + /// true if type name was converted successfully, otherwise, false. + public static bool TryParse(ReadOnlySpan typeName, [NotNullWhen(true)] out TypeSymbolName? result, TypeNameParseOptions? options = default) + { + result = TypeNameParser.Parse(typeName, throwOnError: false, options); + return result is not null; + } + + /// + /// Gets the number of dimensions in an array. + /// + /// An integer that contains the number of dimensions in the current type. + /// The current type is not an array. + public int GetArrayRank() + { + if (!(_rankOrModifier == TypeNameParserHelpers.SZArray || _rankOrModifier > 0)) + { + TypeNameParserHelpers.ThrowInvalidOperation_HasToBeArrayClass(); + } + + return _rankOrModifier == TypeNameParserHelpers.SZArray ? 1 : _rankOrModifier; + } + + /// + /// If this represents a constructed generic type, returns an array + /// of all the generic arguments. Otherwise it returns an empty array. + /// + /// + /// For example, given "Dictionary<string, int>", returns a 2-element array containing + /// string and int. + /// + public +#if SYSTEM_PRIVATE_CORELIB + ReadOnlySpan GetGenericArguments() => CollectionsMarshal.AsSpan(_genericArguments); +#else + ImmutableArray GetGenericArguments() => _genericArguments; +#endif + +#if SYSTEM_REFLECTION_METADATA + /// + /// Creates a new object that represents current simple name with provided assembly name. + /// + /// Assembly name. + /// Created simple name. + /// The current type name is not simple. + public TypeName WithAssemblyName(AssemblyNameInfo? assemblyName) + { + // Recursive method. See comments in FullName property getter for more information + // on how this is protected against attack. + // + // n.b. AssemblyNameInfo could also be hostile. The typical exploit is that a single + // long AssemblyNameInfo is associated with one or more simple TypeName objects, + // leading to an alg. complexity attack (DoS). It's important that TypeName doesn't + // actually *do* anything with the provided AssemblyNameInfo rather than store it. + // For example, don't use it inside a string concat operation unless the caller + // explicitly requested that to happen. If the input is hostile, the caller should + // never perform such concats in a loop. + + if (!IsSimple) + { + TypeNameParserHelpers.ThrowInvalidOperation_NotSimpleName(FullName); + } + + TypeName? declaringType = IsNested + ? DeclaringType.WithAssemblyName(assemblyName) + : null; + + return new TypeName(fullName: _fullName, + assemblyName: assemblyName, + elementOrGenericType: null, + declaringType: declaringType, + genericTypeArguments: ImmutableArray.Empty, + nestedNameLength: _nestedNameLength); + } + + /// + /// Creates a object representing a one-dimensional array + /// of the current type, with a lower bound of zero. + /// + /// + /// A object representing a one-dimensional array + /// of the current type, with a lower bound of zero. + /// + public TypeName MakeSZArrayTypeName() => MakeElementTypeName(TypeNameParserHelpers.SZArray); + + /// + /// Creates a object representing an array of the current type, + /// with the specified number of dimensions. + /// + /// The number of dimensions for the array. This number must be more than zero and less than or equal to 32. + /// + /// A object representing an array of the current type, + /// with the specified number of dimensions. + /// + /// rank is invalid. For example, 0 or negative. + public TypeName MakeArrayTypeName(int rank) + => rank <= 0 + ? throw new ArgumentOutOfRangeException(nameof(rank)) + : MakeElementTypeName(rank); + + /// + /// Creates a object that represents a pointer to the current type. + /// + /// + /// A object that represents a pointer to the current type. + /// + public TypeName MakePointerTypeName() => MakeElementTypeName(TypeNameParserHelpers.Pointer); + + /// + /// Creates a object that represents a managed reference to the current type. + /// + /// + /// A object that represents a managed reference to the current type. + /// + public TypeName MakeByRefTypeName() => MakeElementTypeName(TypeNameParserHelpers.ByRef); + + /// + /// Creates a new constructed generic type name. + /// + /// An array of type names to be used as generic arguments of the current simple type name. + /// + /// A representing the constructed type name formed by using the elements + /// of for the generic arguments of the current simple type name. + /// + /// The current type name is not simple. + public TypeName MakeGenericTypeName(ImmutableArray typeArguments) + { + if (!IsSimple) + { + TypeNameParserHelpers.ThrowInvalidOperation_NotSimpleName(FullName); + } + + return new TypeName(fullName: null, AssemblyName, elementOrGenericType: this, declaringType: _declaringType, genericTypeArguments: typeArguments); + } + + private TypeName MakeElementTypeName(int rankOrModifier) + => new TypeName( + fullName: null, + assemblyName: AssemblyName, + elementOrGenericType: this, + declaringType: null, + genericTypeArguments: ImmutableArray.Empty, + rankOrModifier: rankOrModifier); +#endif + } +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs index bf940d8195..fe18e4a8c7 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserHelpers.cs @@ -1,26 +1,30 @@ -using System; +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System; +using System.Buffers; using System.Collections.Generic; -using System.Collections.Immutable; using System.Diagnostics; +using System.Diagnostics.CodeAnalysis; +using System.Text; +using IKVM.CoreLib.Symbols; using IKVM.CoreLib.Text; namespace IKVM.CoreLib.Symbols { - - internal static class TypeNameParserHelpers + internal static class TypeSymbolNameParserHelpers { - - const int maxDepth = 32; internal const int SZArray = -1; internal const int Pointer = -2; internal const int ByRef = -3; - const char EscapeCharacter = '\\'; - + private const char EscapeCharacter = '\\'; +#if NET8_0_OR_GREATER // Keep this in sync with GetFullTypeNameLength/NeedsEscaping - private static readonly string s_endOfFullTypeNameDelimitersSearchValues = "[]&*,+\\"; + private static readonly SearchValues s_endOfFullTypeNameDelimitersSearchValues = SearchValues.Create("[]&*,+\\"); +#endif - internal static string GetGenericTypeFullName(ReadOnlySpan fullTypeName, ReadOnlySpan genericArgs) + internal static string GetGenericTypeFullName(ReadOnlySpan fullTypeName, ReadOnlySpan genericArgs) { Debug.Assert(genericArgs.Length > 0); @@ -57,7 +61,8 @@ internal static int GetFullTypeNameLength(ReadOnlySpan input, out bool isN // input, that makes the total loop complexity potentially O(m * n^2), where // 'n' is adversary-controlled. To avoid DoS issues here, we'll loop manually. - int offset = input.IndexOfAny(s_endOfFullTypeNameDelimitersSearchValues.AsSpan()); +#if NET8_0_OR_GREATER + int offset = input.IndexOfAny(s_endOfFullTypeNameDelimitersSearchValues); if (offset < 0) { return input.Length; // no type name end chars were found, the whole input is the type name @@ -67,6 +72,9 @@ internal static int GetFullTypeNameLength(ReadOnlySpan input, out bool isN { offset = GetUnescapedOffset(input, startOffset: offset); // this is slower, but very rare so acceptable } +#else + int offset = GetUnescapedOffset(input, startOffset: 0); +#endif isNestedType = offset > 0 && offset < input.Length && input[offset] == '+'; return offset; @@ -229,10 +237,10 @@ internal static bool IsBeginningOfGenericArgs(ref ReadOnlySpan span, out b return false; } - internal static bool TryGetTypeNameInfo(ref ReadOnlySpan input, ref List? nestedNameLengths, ref int recursiveDepth, out int totalLength) + internal static bool TryGetTypeNameInfo(ref ReadOnlySpan input, + ref List? nestedNameLengths, ref int recursiveDepth, out int totalLength) { bool isNestedType; - totalLength = 0; do { @@ -245,16 +253,6 @@ internal static bool TryGetTypeNameInfo(ref ReadOnlySpan input, ref List 1 && input[0] == '.' && input.Slice(0, length).LastIndexOf('.') == 0) - { - input = input.Slice(1); - length--; - } - if (isNestedType) { if (!TryDive(ref recursiveDepth)) @@ -345,37 +343,43 @@ internal static bool TryStripFirstCharAndTrailingSpaces(ref ReadOnlySpan s return false; } + [DoesNotReturn] internal static void ThrowArgumentException_InvalidTypeName(int errorIndex) { - throw new InvalidOperationException(); + throw new ArgumentException(); } + [DoesNotReturn] internal static void ThrowInvalidOperation_MaxNodesExceeded(int limit) { throw new InvalidOperationException(); } + [DoesNotReturn] internal static void ThrowInvalidOperation_NotGenericType() { throw new InvalidOperationException(); } + [DoesNotReturn] internal static void ThrowInvalidOperation_NotNestedType() { throw new InvalidOperationException(); } + [DoesNotReturn] internal static void ThrowInvalidOperation_NoElement() { throw new InvalidOperationException(); } + [DoesNotReturn] internal static void ThrowInvalidOperation_HasToBeArrayClass() { throw new InvalidOperationException(); } - internal static bool IsMaxDepthExceeded(int depth) => depth > maxDepth; + internal static bool IsMaxDepthExceeded(int depth) => false; internal static bool TryDive(ref int depth) { @@ -383,11 +387,5 @@ internal static bool TryDive(ref int depth) return !IsMaxDepthExceeded(depth); } - internal static void ThrowInvalidOperation_NotSimpleName(string fullName) - { - throw new InvalidOperationException(); - } - } - -} +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs deleted file mode 100644 index 9843954195..0000000000 --- a/src/IKVM.CoreLib/Symbols/TypeSymbolNameParserResult.cs +++ /dev/null @@ -1,41 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. - -using System; -using System.Collections.Immutable; -using System.Diagnostics; - -namespace IKVM.CoreLib.Symbols -{ - - [DebuggerDisplay("{AssemblyQualifiedName}")] - struct TypeSymbolNameParserResult - { - - readonly ReadOnlyMemory _namespaceName; - readonly ReadOnlyMemory _name; - readonly AssemblyIdentity? _assembly; - readonly ImmutableArray _genericTypeArguments; - readonly int _rankOrModifier; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - internal TypeSymbolNameParserResult(ReadOnlyMemory namespaceName, ReadOnlyMemory name, AssemblyIdentity? assembly, ImmutableArray genericTypeArguments, int rankOrModifier = default) - { - _namespaceName = namespaceName; - _name = name; - _assembly = assembly; - _genericTypeArguments = genericTypeArguments; - _rankOrModifier = rankOrModifier; - } - - public string AssemblyQualifiedName { get; } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs index c50c7527a6..06fb74130a 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolNameReader.cs @@ -1,52 +1,38 @@ using System; -using System.Buffers; using System.Collections.Generic; using System.Collections.Immutable; using System.Diagnostics; -using IKVM.CoreLib.Buffers; +using static IKVM.CoreLib.Symbols.TypeSymbolNameParserHelpers; namespace IKVM.CoreLib.Symbols { - ref struct TypeSymbolNameReader + [DebuggerDisplay("{_inputString}")] + ref struct TypeNameParser { - private readonly bool _throwOnError; - private ReadOnlySpan _inputString; - - private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNameParseOptions? options) : this() + public static TypeSymbolName? Parse(ReadOnlySpan typeName, bool throwOnError) { - _inputString = name; - _throwOnError = throwOnError; - _parseOptions = options ?? s_defaults; - } - - internal static TypeName? Parse(ReadOnlySpan typeName, bool throwOnError, TypeNameParseOptions? options = default) - { - ReadOnlySpan trimmedName = typeName.TrimStart(); // whitespaces at beginning are always OK + var trimmedName = typeName.TrimStart(); // whitespaces at beginning are always OK if (trimmedName.IsEmpty) { if (throwOnError) - { ThrowArgumentException_InvalidTypeName(errorIndex: 0); // whitespace input needs to report the error index as 0 - } return null; } int recursiveDepth = 0; - TypeNameParser parser = new(trimmedName, throwOnError, options); - TypeName? parsedName = parser.ParseNextTypeName(allowFullyQualifiedName: true, ref recursiveDepth); + var parser = new TypeNameParser(trimmedName, throwOnError); + var parsedName = parser.ParseNextTypeName(allowFullyQualifiedName: true, ref recursiveDepth); if (parsedName is null || !parser._inputString.IsEmpty) // unconsumed input == error { if (throwOnError) { - if (IsMaxDepthExceeded(parser._parseOptions, recursiveDepth)) - { - ThrowInvalidOperation_MaxNodesExceeded(parser._parseOptions.MaxNodes); - } + if (IsMaxDepthExceeded(recursiveDepth)) + ThrowInvalidOperation_MaxNodesExceeded(32); int errorIndex = typeName.Length - parser._inputString.Length; ThrowArgumentException_InvalidTypeName(errorIndex); @@ -60,16 +46,30 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam return parsedName; } + readonly bool _throwOnError; + ReadOnlySpan _inputString; + + /// + /// Initializes a new instance. + /// + /// + /// + TypeNameParser(ReadOnlySpan name, bool throwOnError) : this() + { + _inputString = name; + _throwOnError = throwOnError; + } + // this method should return null instead of throwing, so the caller can get errorIndex and include it in error msg - private TypeName? ParseNextTypeName(bool allowFullyQualifiedName, ref int recursiveDepth) + TypeSymbolName? ParseNextTypeName(bool allowFullyQualifiedName, ref int recursiveDepth) { - if (!TryDive(_parseOptions, ref recursiveDepth)) + if (!TryDive(ref recursiveDepth)) { return null; } List? nestedNameLengths = null; - if (!TryGetTypeNameInfo(_parseOptions, ref _inputString, ref nestedNameLengths, ref recursiveDepth, out int fullTypeNameLength)) + if (!TryGetTypeNameInfo(ref _inputString, ref nestedNameLengths, ref recursiveDepth, out int fullTypeNameLength)) { return null; } @@ -80,11 +80,7 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam _inputString = _inputString.Slice(fullTypeNameLength); // Don't allocate now, as it may be an open generic type like "Name`1" -#if SYSTEM_PRIVATE_CORELIB - List? genericArgs = null; -#else - ImmutableArray.Builder? genericArgs = null; -#endif + ImmutableArray.Builder? genericArgs = null; // Are there any captured generic args? We'll look for "[[" and "[". // There are no spaces allowed before the first '[', but spaces are allowed @@ -99,7 +95,7 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam // Namespace.Type`2[GenericArgument1,GenericArgument2] - single square bracket syntax is legal only for non-fully qualified type names // Namespace.Type`2[[GenericArgument1, AssemblyName1], GenericArgument2] - mixed mode // Namespace.Type`2[GenericArgument1, [GenericArgument2, AssemblyName2]] - mixed mode - TypeName? genericArg = ParseNextTypeName(allowFullyQualifiedName: doubleBrackets, ref recursiveDepth); + TypeSymbolName? genericArg = ParseNextTypeName(allowFullyQualifiedName: doubleBrackets, ref recursiveDepth); if (genericArg is null) // parsing failed { return null; @@ -113,11 +109,7 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam if (genericArgs is null) { -#if SYSTEM_PRIVATE_CORELIB - genericArgs = new List(2); -#else - genericArgs = ImmutableArray.CreateBuilder(2); -#endif + genericArgs = ImmutableArray.CreateBuilder(2); } genericArgs.Add(genericArg); @@ -154,7 +146,7 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam else { // Every constructed generic type needs the generic type definition. - if (!TryDive(_parseOptions, ref recursiveDepth)) + if (!TryDive(ref recursiveDepth)) { return null; } @@ -168,7 +160,7 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam // iterate over the decorators to ensure there are no illegal combinations while (TryParseNextDecorator(ref _inputString, out int parsedDecorator)) { - if (!TryDive(_parseOptions, ref recursiveDepth)) + if (!TryDive(ref recursiveDepth)) { return null; } @@ -178,18 +170,10 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam previousDecorator = parsedDecorator; } - AssemblyNameInfo? assemblyName = null; + AssemblyIdentity? assemblyName = null; if (allowFullyQualifiedName && !TryParseAssemblyName(ref assemblyName)) { -#if SYSTEM_PRIVATE_CORELIB - // backward compat: throw FileLoadException for non-empty invalid strings - if (_throwOnError || !_inputString.TrimStart().StartsWith(",")) - { - throw new IO.FileLoadException(SR.InvalidAssemblyName, _inputString.ToString()); - } -#else return null; -#endif } // No matter what was parsed, the full name string is allocated only once. @@ -197,8 +181,8 @@ private TypeSymbolNameReader(ReadOnlySpan name, bool throwOnError, TypeNam // when needed for the first time . string fullName = fullTypeName.ToString(); - TypeName? declaringType = GetDeclaringType(fullName, nestedNameLengths, assemblyName); - TypeName result = new(fullName, assemblyName, declaringType: declaringType); + TypeSymbolName? declaringType = GetDeclaringType(fullName, nestedNameLengths, assemblyName); + TypeSymbolName result = new(fullName, assemblyName, declaringType: declaringType); if (genericArgs is not null) { result = new(fullName: null, assemblyName, elementOrGenericType: result, declaringType, genericArgs); @@ -243,16 +227,14 @@ private bool TryParseAssemblyName(ref AssemblyIdentity? assemblyName) return true; } - private static TypeSymbolNameParserResult? GetDeclaringType(string fullTypeName, List? nestedNameLengths, AssemblyIdentity? assemblyName) + private static TypeSymbolName? GetDeclaringType(string fullTypeName, List? nestedNameLengths, AssemblyIdentity? assemblyName) { if (nestedNameLengths is null) - { return null; - } // The loop below is protected by the dive check in GetFullTypeNameLength. - TypeSymbolNameParserResult? declaringType = null; + TypeSymbolName? declaringType = null; int nameOffset = 0; foreach (int nestedNameLength in nestedNameLengths) { @@ -267,4 +249,4 @@ private bool TryParseAssemblyName(ref AssemblyIdentity? assemblyName) } -} +} \ No newline at end of file From 2172c3daead9921da5690ca5ae46905a6b5bd0b8 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Mon, 4 Nov 2024 11:26:04 -0600 Subject: [PATCH 52/59] Hmmm --- src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs | 56 ++ src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs | 54 ++ .../ConstructedGenericConstructorSymbol.cs | 96 ++ .../Symbols/ConstructedGenericEventSymbol.cs | 131 +++ .../Symbols/ConstructedGenericFieldSymbol.cs | 123 +++ .../Symbols/ConstructedGenericMethodSymbol.cs | 161 ++++ .../ConstructedGenericParameterSymbol.cs | 88 ++ .../ConstructedGenericPropertySymbol.cs | 156 ++++ .../Symbols/ConstructedGenericTypeSymbol.cs | 394 ++++++++ src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs | 34 + .../Symbols/DefinitionConstructorSymbol.cs | 21 + .../Symbols/DefinitionEventSymbol.cs | 21 + .../Symbols/DefinitionFieldSymbol.cs | 21 + .../Symbols/DefinitionMethodSymbol.cs | 21 + .../Symbols/DefinitionParameterSymbol.cs | 22 + .../Symbols/DefinitionPropertySymbol.cs | 21 + .../Symbols/DefinitionTypeSymbol.cs | 24 + .../{IEventSymbol.cs => EventSymbol.cs} | 61 +- .../{IFieldSymbol.cs => FieldSymbol.cs} | 59 +- src/IKVM.CoreLib/Symbols/GenericContext.cs | 15 + .../GenericMethodParameterTypeSymbol.cs | 38 + .../Symbols/GenericParameterTypeSymbol.cs | 78 ++ .../Symbols/GenericTypeParameterTypeSymbol.cs | 33 + src/IKVM.CoreLib/Symbols/HasElementSymbol.cs | 176 ++++ src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs | 18 +- .../Symbols/IConstructorSymbol.cs | 14 - .../Symbols/ICustomAttributeProvider.cs | 6 +- src/IKVM.CoreLib/Symbols/IMemberSymbol.cs | 39 - src/IKVM.CoreLib/Symbols/IMethodSymbol.cs | 46 - src/IKVM.CoreLib/Symbols/IModuleSymbol.cs | 42 +- src/IKVM.CoreLib/Symbols/IParameterSymbol.cs | 93 -- src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 2 +- src/IKVM.CoreLib/Symbols/ISymbolResolver.cs | 14 +- src/IKVM.CoreLib/Symbols/ITypeSymbol.cs | 676 -------------- src/IKVM.CoreLib/Symbols/InterfaceMapping.cs | 14 +- src/IKVM.CoreLib/Symbols/MemberSymbol.cs | 82 ++ ...ethodBaseSymbol.cs => MethodBaseSymbol.cs} | 63 +- src/IKVM.CoreLib/Symbols/MethodSpecTable.cs | 68 ++ src/IKVM.CoreLib/Symbols/MethodSymbol.cs | 47 + src/IKVM.CoreLib/Symbols/NameFilter.cs | 11 + src/IKVM.CoreLib/Symbols/ParameterSymbol.cs | 123 +++ src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs | 54 ++ .../{IPropertySymbol.cs => PropertySymbol.cs} | 64 +- .../ReflectionDefinitionTypeSymbol.cs | 11 + src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs | 56 ++ src/IKVM.CoreLib/Symbols/TypeSpecTable.cs | 126 +++ src/IKVM.CoreLib/Symbols/TypeSymbol.cs | 844 ++++++++++++++++++ .../Symbols/TypeSymbolListEqualityComparer.cs | 14 +- 48 files changed, 3402 insertions(+), 1029 deletions(-) create mode 100644 src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs rename src/IKVM.CoreLib/Symbols/{IEventSymbol.cs => EventSymbol.cs} (57%) rename src/IKVM.CoreLib/Symbols/{IFieldSymbol.cs => FieldSymbol.cs} (58%) create mode 100644 src/IKVM.CoreLib/Symbols/GenericContext.cs create mode 100644 src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/HasElementSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IMemberSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IMethodSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IParameterSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/ITypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/MemberSymbol.cs rename src/IKVM.CoreLib/Symbols/{IMethodBaseSymbol.cs => MethodBaseSymbol.cs} (61%) create mode 100644 src/IKVM.CoreLib/Symbols/MethodSpecTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/MethodSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/NameFilter.cs create mode 100644 src/IKVM.CoreLib/Symbols/ParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs rename src/IKVM.CoreLib/Symbols/{IPropertySymbol.cs => PropertySymbol.cs} (66%) create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSpecTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbol.cs diff --git a/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs new file mode 100644 index 0000000000..3a21c45d10 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs @@ -0,0 +1,56 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class ArrayTypeSymbol : HasElementSymbol + { + + readonly int _rank; + + string? _nameSuffix; + + /// + /// Initializes a new instance. + /// + /// + /// + public ArrayTypeSymbol(ISymbolContext context, TypeSymbol elementType, int rank) : + base(context, elementType) + { + _rank = rank; + } + + /// + protected override string NameSuffix => _nameSuffix ??= ComputeNameSuffix(); + + /// + /// Computes the value for . + /// + /// + string ComputeNameSuffix() + { + if (_rank == 1) + return "[*]"; + else + return "[" + new string(',', _rank - 1) + "]"; + } + + /// + public sealed override TypeAttributes Attributes => TypeAttributes.AutoLayout | TypeAttributes.AnsiClass | TypeAttributes.Class | TypeAttributes.Public | TypeAttributes.Sealed | TypeAttributes.Serializable; + + /// + public sealed override bool IsArray => true; + + /// + public sealed override TypeSymbol? BaseType => Context.ResolveCoreType("System.Array"); + + /// + public sealed override int GetArrayRank() + { + return _rank; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs new file mode 100644 index 0000000000..5154ea67f6 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs @@ -0,0 +1,54 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class ByRefTypeSymbol : HasElementSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public ByRefTypeSymbol(ISymbolContext context, TypeSymbol elementType) : + base(context, elementType) + { + + } + + /// + protected override string NameSuffix => "&"; + + /// + public sealed override TypeAttributes Attributes => TypeAttributes.Public; + + /// + public override TypeSymbol? BaseType => null; + + /// + public sealed override bool IsByRef => true; + + /// + public sealed override int GetArrayRank() + { + throw new NotSupportedException(); + } + + /// + public sealed override ImmutableList GetDeclaredConstructors() + { + return ImmutableList.Empty; + } + + /// + public sealed override ImmutableList GetDeclaredMethods() + { + return ImmutableList.Empty; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs new file mode 100644 index 0000000000..bd14990c84 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs @@ -0,0 +1,96 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Describes a constructor of a . + /// + class ConstructedGenericConstructorSymbol : ConstructorSymbol + { + + readonly ConstructorSymbol _definition; + readonly GenericContext _genericContext; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ConstructedGenericConstructorSymbol(ISymbolContext context, TypeSymbol declaringType, ConstructorSymbol definition, GenericContext genericContext) : + base(context, declaringType) + { + _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _genericContext = genericContext; + } + + /// + public override MethodAttributes Attributes => _definition.Attributes; + + /// + public override CallingConventions CallingConvention => _definition.CallingConvention; + + /// + public override MethodImplAttributes MethodImplementationFlags => _definition.MethodImplementationFlags; + + /// + public override string Name => _definition.Name; + + /// + public override bool IsMissing => _definition.IsMissing; + + /// + public override bool ContainsMissing => _definition.ContainsMissing; + + /// + public override bool IsComplete => _definition.IsComplete; + + /// + public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttribute(attributeType, inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return _definition.GetCustomAttributes(inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttributes(attributeType, inherit); + } + + /// + public override ImmutableList GetGenericArguments() + { + return _definition.GetGenericArguments(); + } + + /// + public override MethodImplAttributes GetMethodImplementationFlags() + { + return _definition.GetMethodImplementationFlags(); + } + + /// + public override ImmutableList GetParameters() + { + return _definition.GetParameters(); + } + + /// + public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + { + return _definition.IsDefined(attributeType, inherit); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs new file mode 100644 index 0000000000..f6dd5ef1ec --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs @@ -0,0 +1,131 @@ +using System; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Describes an event of a . + /// + class ConstructedGenericEventSymbol : EventSymbol + { + + readonly EventSymbol _definition; + readonly GenericContext _genericContext; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ConstructedGenericEventSymbol(ISymbolContext context, TypeSymbol declaringType, EventSymbol definition, GenericContext genericContext) : + base(context, declaringType) + { + _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _genericContext = genericContext; + } + + /// + public override EventAttributes Attributes => _definition.Attributes; + + /// + public override string Name => _definition.Name; + + /// + public override TypeSymbol? EventHandlerType => _definition.EventHandlerType?.Specialize(_genericContext); + + /// + public override MethodSymbol? AddMethod => _definition.AddMethod; + + /// + public override MethodSymbol? RemoveMethod => _definition.RemoveMethod; + + /// + public override MethodSymbol? RaiseMethod => _definition.RaiseMethod; + + /// + public override bool IsMissing => _definition.IsMissing; + + /// + public override bool ContainsMissing => _definition.ContainsMissing; + + /// + public override bool IsComplete => _definition.IsComplete; + + /// + public override MethodSymbol? GetAddMethod() + { + return _definition.GetAddMethod(); + } + + /// + public override MethodSymbol? GetAddMethod(bool nonPublic) + { + return _definition.GetAddMethod(nonPublic); + } + + /// + public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttribute(attributeType, inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return _definition.GetCustomAttributes(inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttributes(attributeType, inherit); + } + + /// + public override MethodSymbol[] GetOtherMethods() + { + return _definition.GetOtherMethods(); + } + + /// + public override MethodSymbol[] GetOtherMethods(bool nonPublic) + { + return _definition.GetOtherMethods(nonPublic); + } + + /// + public override MethodSymbol? GetRaiseMethod() + { + return _definition.GetRaiseMethod(); + } + /// + + public override MethodSymbol? GetRaiseMethod(bool nonPublic) + { + return _definition.GetRaiseMethod(nonPublic); + } + + /// + public override MethodSymbol? GetRemoveMethod() + { + return _definition.GetRemoveMethod(); + } + + /// + public override MethodSymbol? GetRemoveMethod(bool nonPublic) + { + return _definition.GetRemoveMethod(nonPublic); + } + + /// + public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + { + return _definition.IsDefined(attributeType, inherit); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs new file mode 100644 index 0000000000..65cd146007 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs @@ -0,0 +1,123 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Describes a field of a . + /// + class ConstructedGenericFieldSymbol : FieldSymbol + { + + readonly FieldSymbol _definition; + readonly GenericContext _genericContext; + + TypeSymbol? _fieldType; + ImmutableList? _optionalCustomModifiers; + ImmutableList? _requiredCustomModifiers; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ConstructedGenericFieldSymbol(ISymbolContext context, TypeSymbol declaringType, FieldSymbol definition, GenericContext genericContext) : + base(context, declaringType.Module, declaringType) + { + _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _genericContext = genericContext; + } + + /// + public override FieldAttributes Attributes => _definition.Attributes; + + /// + public override TypeSymbol FieldType => _fieldType ??= _definition.FieldType.Specialize(_genericContext); + + /// + public override string Name => _definition.Name; + + /// + public override bool IsMissing => _definition.IsMissing; + + /// + public override bool ContainsMissing => _definition.ContainsMissing; + + /// + public override bool IsComplete => _definition.IsComplete; + + /// + public override object? GetRawConstantValue() + { + return _definition.GetRawConstantValue(); + } + + /// + public override IImmutableList GetOptionalCustomModifiers() + { + return _optionalCustomModifiers ??= ComputeOptionalCustomModifiers(); + } + + /// + /// Computes the value for . + /// + /// + ImmutableList ComputeOptionalCustomModifiers() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetOptionalCustomModifiers()) + b.Add(i.Specialize(_genericContext)); + + return b.ToImmutable(); + } + + /// + public override IImmutableList GetRequiredCustomModifiers() + { + return _optionalCustomModifiers ??= ComputeRequiredCustomModifiers(); + } + + /// + /// Computes the value for . + /// + /// + ImmutableList ComputeRequiredCustomModifiers() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetRequiredCustomModifiers()) + b.Add(i.Specialize(_genericContext)); + + return b.ToImmutable(); + } + + /// + public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttribute(attributeType, inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return _definition.GetCustomAttributes(inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttributes(attributeType, inherit); + } + + /// + public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + { + return _definition.IsDefined(attributeType, inherit); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs new file mode 100644 index 0000000000..50e3fed47d --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs @@ -0,0 +1,161 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; +using System.Threading; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Describes a method of a . + /// + class ConstructedGenericMethodSymbol : MethodSymbol + { + + readonly MethodSymbol _definition; + readonly GenericContext _genericContext; + + TypeSymbol? _returnType; + ConstructedGenericParameterSymbol? _returnParameter; + ImmutableList? _parameters; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public ConstructedGenericMethodSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType, MethodSymbol definition, GenericContext genericContext) : + base(context, module, declaringType) + { + _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _genericContext = genericContext; + } + + /// + public override MethodAttributes Attributes => _definition.Attributes; + + /// + public override bool IsGenericMethod => true; + + /// + public override bool IsGenericMethodDefinition => false; + + /// + public override bool ContainsGenericParameters => false; + + /// + public override ParameterSymbol ReturnParameter => GetReturnParameter(); + + /// + /// Computes the value for . + /// + /// + ConstructedGenericParameterSymbol GetReturnParameter() + { + if (_returnParameter == null) + Interlocked.CompareExchange(ref _returnParameter, new ConstructedGenericParameterSymbol(Context, this, _definition.ReturnParameter, _genericContext), null); + + return _returnParameter; + } + + /// + public override TypeSymbol ReturnType => _returnType ??= _definition.ReturnType.Specialize(_genericContext); + + /// + public override ICustomAttributeProvider ReturnTypeCustomAttributes => _definition.ReturnTypeCustomAttributes; + + /// + public override CallingConventions CallingConvention => _definition.CallingConvention; + + /// + public override MethodImplAttributes MethodImplementationFlags => _definition.MethodImplementationFlags; + + /// + public override string Name => _definition.Name; + + /// + public override bool IsMissing => _definition.IsMissing; + + /// + public override bool ContainsMissing => _definition.ContainsMissing; + + /// + public override bool IsComplete => _definition.IsComplete; + + /// + public override MethodSymbol GetBaseDefinition() + { + return _definition.GetBaseDefinition(); + } + + /// + public override ImmutableList GetGenericArguments() + { + return _definition.GetGenericArguments(); + } + + /// + public override MethodSymbol GetGenericMethodDefinition() + { + throw new InvalidOperationException(); + } + + /// + public override MethodImplAttributes GetMethodImplementationFlags() + { + return _definition.GetMethodImplementationFlags(); + } + + /// + public override ImmutableList GetParameters() + { + if (_parameters == null) + Interlocked.CompareExchange(ref _parameters, ComputeGetParameters(), null); + + return _parameters; + } + + /// + /// Computs the value for . + /// + /// + ImmutableList ComputeGetParameters() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetParameters()) + b.Add(new ConstructedGenericParameterSymbol(Context, this, i, _genericContext)); + + return b.ToImmutable(); + } + + /// + public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttribute(attributeType, inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return _definition.GetCustomAttributes(inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttributes(attributeType, inherit); + } + + /// + public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + { + return _definition.IsDefined(attributeType, inherit); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs new file mode 100644 index 0000000000..093e8e1063 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs @@ -0,0 +1,88 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class ConstructedGenericParameterSymbol : ParameterSymbol + { + + readonly ParameterSymbol _definition; + readonly GenericContext _genericContext; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public ConstructedGenericParameterSymbol(ISymbolContext context, MemberSymbol declaringMember, ParameterSymbol definition, GenericContext genericContext) : + base(context, declaringMember, definition.Position) + { + _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _genericContext = genericContext; + } + + /// + public override ParameterAttributes Attributes => _definition.Attributes; + + /// + public override TypeSymbol ParameterType => _definition.ParameterType.Specialize(_genericContext); + + /// + public override string? Name => _definition.Name; + + /// + public override object? DefaultValue => _definition.DefaultValue; + + /// + public override bool IsMissing => _definition.IsMissing; + + /// + public override bool ContainsMissing => _definition.ContainsMissing; + + /// + public override bool IsComplete => _definition.IsComplete; + + /// + public override ImmutableList GetOptionalCustomModifiers() + { + return _definition.GetOptionalCustomModifiers(); + } + + /// + public override ImmutableList GetRequiredCustomModifiers() + { + return _definition.GetRequiredCustomModifiers(); + } + + /// + public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttribute(attributeType, inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return _definition.GetCustomAttributes(inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttributes(attributeType, inherit); + } + + /// + public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + { + return _definition.IsDefined(attributeType, inherit); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs new file mode 100644 index 0000000000..62567dba88 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs @@ -0,0 +1,156 @@ +using System; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Describes a property of a . + /// + class ConstructedGenericPropertySymbol : PropertySymbol + { + + readonly PropertySymbol _definition; + readonly GenericContext _genericContext; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + public ConstructedGenericPropertySymbol(ISymbolContext context, TypeSymbol declaringType, PropertySymbol definition, GenericContext genericContext) : + base(context, declaringType) + { + _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _genericContext = genericContext; + } + + /// + public override PropertyAttributes Attributes => _definition.Attributes; + + /// + public override TypeSymbol PropertyType => _definition.PropertyType.Specialize(_genericContext); + + /// + public override bool CanRead => _definition.CanRead; + + /// + public override bool CanWrite => _definition.CanWrite; + + /// + public override MethodSymbol? GetMethod => _definition.GetMethod; + + /// + public override MethodSymbol? SetMethod => _definition.SetMethod; + + /// + public override MemberTypes MemberType => _definition.MemberType; + + /// + public override string Name => _definition.Name; + + /// + public override bool IsMissing => _definition.IsMissing; + + /// + public override bool ContainsMissing => _definition.ContainsMissing; + + /// + public override bool IsComplete => _definition.IsComplete; + + /// + public override MethodSymbol[] GetAccessors() + { + return _definition.GetAccessors(); + } + + /// + public override MethodSymbol[] GetAccessors(bool nonPublic) + { + return _definition.GetAccessors(nonPublic); + } + + /// + public override MethodSymbol? GetGetMethod() + { + return _definition.GetGetMethod(); + } + + /// + public override MethodSymbol? GetGetMethod(bool nonPublic) + { + return _definition.GetGetMethod(nonPublic); + } + + /// + public override MethodSymbol? GetSetMethod() + { + return _definition.GetSetMethod(); + } + + /// + public override MethodSymbol? GetSetMethod(bool nonPublic) + { + return _definition.GetSetMethod(nonPublic); + } + + /// + public override ParameterSymbol[] GetIndexParameters() + { + return _definition.GetIndexParameters(); + } + + /// + public override TypeSymbol GetModifiedPropertyType() + { + return _definition.GetModifiedPropertyType(); + } + + /// + public override object? GetRawConstantValue() + { + return _definition.GetRawConstantValue(); + } + + /// + public override TypeSymbol[] GetOptionalCustomModifiers() + { + return _definition.GetOptionalCustomModifiers(); + } + + /// + public override TypeSymbol[] GetRequiredCustomModifiers() + { + return _definition.GetRequiredCustomModifiers(); + } + + /// + public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttribute(attributeType, inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return _definition.GetCustomAttributes(inherit); + } + + /// + public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttributes(attributeType, inherit); + } + + /// + public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + { + return _definition.IsDefined(attributeType, inherit); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs new file mode 100644 index 0000000000..34cc3df1a8 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs @@ -0,0 +1,394 @@ +using System; +using System.Collections.Immutable; +using System.Linq; +using System.Reflection; +using System.Threading; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Describes a type that is a constructed generic type. + /// + class ConstructedGenericTypeSymbol : TypeSymbol + { + + readonly TypeSymbol _definition; + readonly ImmutableList _typeArguments; + + ImmutableList? _fields; + ImmutableList? _constructors; + ImmutableList? _methods; + ImmutableList? _properties; + ImmutableList? _events; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ConstructedGenericTypeSymbol(ISymbolContext context, TypeSymbol definition, ImmutableList typeArguments) : + base(context, definition.Module, definition) + { + _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _typeArguments = typeArguments ?? throw new ArgumentNullException(nameof(typeArguments)); + } + + /// + public sealed override TypeAttributes Attributes => _definition.Attributes; + + /// + public sealed override TypeCode TypeCode => _definition.TypeCode; + + /// + public override TypeSymbol? BaseType => _definition.BaseType?.Specialize(new GenericContext(_typeArguments, null)); + + /// + public sealed override bool IsTypeDefinition => false; + + /// + public override bool IsGenericTypeDefinition => false; + + /// + public override bool IsConstructedGenericType => true; + + /// + public override bool IsGenericParameter => false; + + /// + public sealed override bool ContainsGenericParameters => _typeArguments.Any(i => i.ContainsGenericParameters); + + /// + public override int GenericParameterPosition => throw new NotSupportedException(); + + /// + public override bool HasElementType => false; + + /// + public override bool IsArray => false; + + /// + public override bool IsSZArray => false; + + /// + public override bool IsByRef => false; + + /// + public override bool IsPointer => false; + + /// + public override bool IsFunctionPointer => false; + + /// + public override bool IsUnmanagedFunctionPointer => false; + + /// + public override MethodBaseSymbol? DeclaringMethod => _definition.DeclaringMethod; + + /// + public override string? FullName => _definition.FullName; + + /// + public override string? Namespace => _definition.Namespace; + + /// + public override GenericParameterAttributes GenericParameterAttributes => _definition.GenericParameterAttributes; + + /// + public override ImmutableList GenericTypeArguments => _definition.GenericTypeArguments; + + /// + public override bool IsPrimitive => _definition.IsPrimitive; + + /// + public override bool IsEnum => _definition.IsEnum; + + /// + public override bool IsSignatureType => _definition.IsSignatureType; + + /// + public override ConstructorSymbol? TypeInitializer => _definition.TypeInitializer; + + /// + public override string Name => _definition.Name; + + /// + public override bool IsMissing => _definition.IsMissing; + + /// + public override bool ContainsMissing => _definition.ContainsMissing; + + /// + public override bool IsComplete => _definition.IsComplete; + + /// + public override TypeSymbol GetEnumUnderlyingType() + { + return _definition.GetEnumUnderlyingType().Specialize(new GenericContext(_typeArguments, null)); + } + + /// + public sealed override TypeSymbol? GetElementType() + { + return null; + } + + /// + public override int GetArrayRank() + { + throw new InvalidOperationException(); + } + + /// + public sealed override TypeSymbol GetGenericTypeDefinition() + { + return _definition; + } + + /// + public sealed override ImmutableList GetGenericArguments() + { + return _typeArguments; + } + + /// + public override ImmutableList GetGenericParameterConstraints() + { + throw new InvalidOperationException(); + } + + /// + public override ImmutableList GetDeclaredFields() + { + if (_fields == null) + Interlocked.CompareExchange(ref _fields, ComputeDeclaredFields(), null); + + return _fields ?? throw new InvalidOperationException(); + } + + /// + /// Computes the declared fields of this type. + /// + /// + ImmutableList ComputeDeclaredFields() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetDeclaredFields()) + b.Add(new ConstructedGenericFieldSymbol(Context, this, i, new GenericContext(_typeArguments, null))); + + return b.ToImmutable(); + } + + /// + public override ImmutableList GetDeclaredConstructors() + { + if (_constructors == null) + Interlocked.CompareExchange(ref _constructors, ComputeDeclaredConstructors(), null); + + return _constructors ?? throw new InvalidOperationException(); + } + + /// + /// Computes the declared constructors of this type. + /// + /// + ImmutableList ComputeDeclaredConstructors() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetDeclaredConstructors()) + b.Add(new ConstructedGenericConstructorSymbol(Context, this, i, new GenericContext(_typeArguments, null))); + + return b.ToImmutable(); + } + + /// + public override ImmutableList GetDeclaredMethods() + { + if (_methods == null) + Interlocked.CompareExchange(ref _methods, ComputeDeclaredMethods(), null); + + return _methods ?? throw new InvalidOperationException(); + } + + /// + /// Computes the declared methods of this type. + /// + /// + ImmutableList ComputeDeclaredMethods() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetDeclaredMethods()) + b.Add(new ConstructedGenericMethodSymbol(Context, this, i, new GenericContext(_typeArguments, null))); + + return b.ToImmutable(); + } + + /// + public override ImmutableList GetDeclaredProperties() + { + if (_properties == null) + Interlocked.CompareExchange(ref _properties, ComputeDeclaredProperties(), null); + + return _properties ?? throw new InvalidOperationException(); + } + + /// + /// Computes the declared properties of this type. + /// + /// + ImmutableList ComputeDeclaredProperties() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetDeclaredProperties()) + b.Add(new ConstructedGenericPropertySymbol(Context, this, i, new GenericContext(_typeArguments, null))); + + return b.ToImmutable(); + } + + /// + public override ImmutableList GetDeclaredEvents() + { + if (_events == null) + Interlocked.CompareExchange(ref _events, ComputeDeclaredEvents(), null); + + return _events ?? throw new InvalidOperationException(); + } + + /// + /// Computes the declared events of this type. + /// + /// + ImmutableList ComputeDeclaredEvents() + { + var b = ImmutableList.CreateBuilder(); + foreach (var i in _definition.GetDeclaredEvents()) + b.Add(new ConstructedGenericEventSymbol(Context, this, i, new GenericContext(_typeArguments, null))); + + return b.ToImmutable(); + } + + public override ConstructorSymbol? GetConstructor(BindingFlags bindingFlags, ImmutableList? types) + { + return _definition.GetConstructor(bindingFlags, types); + } + + public override ImmutableList GetConstructors(BindingFlags bindingFlags) + { + return _definition.GetConstructors(bindingFlags); + } + + public override ImmutableList GetDefaultMembers() + { + return _definition.GetDefaultMembers(); + } + + public override string? GetEnumName(object value) + { + return _definition.GetEnumName(value); + } + + public override ImmutableList GetEnumNames() + { + return _definition.GetEnumNames(); + } + + public override EventSymbol? GetEvent(string name, BindingFlags bindingFlags) + { + return _definition.GetEvent(name, bindingFlags); + } + + public override ImmutableList GetEvents(BindingFlags bindingFlags) + { + return _definition.GetEvents(bindingFlags); + } + + public override FieldSymbol? GetField(string name, BindingFlags bindingFlags) + { + return _definition.GetField(name, bindingFlags); + } + + public override ImmutableList GetFields(BindingFlags bindingFlags) + { + return _definition.GetFields(bindingFlags); + } + + public override TypeSymbol? GetInterface(string name, bool ignoreCase) + { + return _definition.GetInterface(name, ignoreCase); + } + + public override ImmutableList GetInterfaces(bool inherit = true) + { + return _definition.GetInterfaces(inherit); + } + + public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + { + return _definition.GetInterfaceMap(interfaceType); + } + + public override MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableList? types, ImmutableList? modifiers) + { + return _definition.GetMethod(name, genericParameterCount, bindingFlags, callConvention, types, modifiers); + } + + public override ImmutableList GetMethods(BindingFlags bindingFlags) + { + return _definition.GetMethods(bindingFlags); + } + + public override TypeSymbol? GetNestedType(string name, BindingFlags bindingFlags) + { + return _definition.GetNestedType(name, bindingFlags); + } + + public override ImmutableList GetNestedTypes(BindingFlags bindingFlags) + { + return _definition.GetNestedTypes(bindingFlags); + } + + public override PropertySymbol? GetProperty(string name, BindingFlags bindingFlags) + { + return _definition.GetProperty(name, bindingFlags); + } + + public override PropertySymbol? GetProperty(string name, TypeSymbol? returnType, ImmutableList? types) + { + return _definition.GetProperty(name, returnType, types); + } + + public override ImmutableList GetProperties(BindingFlags bindingFlags) + { + return _definition.GetProperties(bindingFlags); + } + + public override bool IsEnumDefined(object value) + { + return _definition.IsEnumDefined(value); + } + + public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttribute(attributeType, inherit); + } + + public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + { + return _definition.GetCustomAttributes(inherit); + } + + public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + { + return _definition.GetCustomAttributes(attributeType, inherit); + } + + public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + { + return _definition.IsDefined(attributeType, inherit); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs new file mode 100644 index 0000000000..4871732c95 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs @@ -0,0 +1,34 @@ +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class ConstructorSymbol : MethodBaseSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public ConstructorSymbol(ISymbolContext context, TypeSymbol declaringType) : + base(context, declaringType.Module, declaringType) + { + + } + + /// + public override MemberTypes MemberType => MemberTypes.Constructor; + + /// + public override bool IsGenericMethod => false; + + /// + public override bool IsGenericMethodDefinition => false; + + /// + public override bool ContainsGenericParameters => false; + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs new file mode 100644 index 0000000000..05c5ce5155 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs @@ -0,0 +1,21 @@ +namespace IKVM.CoreLib.Symbols +{ + + abstract class DefinitionConstructorSymbol : ConstructorSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected DefinitionConstructorSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : + base(context, module, declaringType) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs new file mode 100644 index 0000000000..873dc36881 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs @@ -0,0 +1,21 @@ +namespace IKVM.CoreLib.Symbols +{ + + abstract class DefinitionEventSymbol : EventSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected DefinitionEventSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : + base(context, module, declaringType) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs new file mode 100644 index 0000000000..d269ce91a3 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs @@ -0,0 +1,21 @@ +namespace IKVM.CoreLib.Symbols +{ + + abstract class DefinitionFieldSymbol : FieldSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected DefinitionFieldSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : + base(context, module, declaringType) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs new file mode 100644 index 0000000000..194d665634 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs @@ -0,0 +1,21 @@ +namespace IKVM.CoreLib.Symbols +{ + + abstract class DefinitionMethodSymbol : MethodSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected DefinitionMethodSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : + base(context, module, declaringType) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs new file mode 100644 index 0000000000..ed5c686d2f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs @@ -0,0 +1,22 @@ +namespace IKVM.CoreLib.Symbols +{ + + abstract class DefinitionParameterSymbol : ParameterSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + protected DefinitionParameterSymbol(ISymbolContext context, IModuleSymbol module, MemberSymbol declaringMember, int position) : + base(context, declaringMember, position) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs new file mode 100644 index 0000000000..9e239c58a2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs @@ -0,0 +1,21 @@ +namespace IKVM.CoreLib.Symbols +{ + + abstract class DefinitionPropertySymbol : PropertySymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected DefinitionPropertySymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : + base(context, module, declaringType) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs new file mode 100644 index 0000000000..62c56e4644 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs @@ -0,0 +1,24 @@ +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Describes a type definition. + /// + abstract class DefinitionTypeSymbol : TypeSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected DefinitionTypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + base(context, module, declaringType) + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IEventSymbol.cs b/src/IKVM.CoreLib/Symbols/EventSymbol.cs similarity index 57% rename from src/IKVM.CoreLib/Symbols/IEventSymbol.cs rename to src/IKVM.CoreLib/Symbols/EventSymbol.cs index 50ee2179af..219ea207de 100644 --- a/src/IKVM.CoreLib/Symbols/IEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/EventSymbol.cs @@ -1,97 +1,106 @@ using System.Reflection; -using IKVM.CoreLib.Symbols.Emit; - namespace IKVM.CoreLib.Symbols { - /// - /// Discovers the attributes of an event and provides access to event metadata. - /// - interface IEventSymbol : IMemberSymbol + abstract class EventSymbol : MemberSymbol { + /// + /// Initializes a new instance. + /// + /// + /// + public EventSymbol(ISymbolContext context, TypeSymbol declaringType) : + base(context, declaringType.Module, declaringType) + { + + } + /// /// Gets the attributes for this event. /// - EventAttributes Attributes { get; } + public abstract EventAttributes Attributes { get; } + + /// + public sealed override MemberTypes MemberType => MemberTypes.Event; /// - /// Gets the object of the underlying event-handler delegate associated with this event. + /// Gets the object of the underlying event-handler delegate associated with this event. /// - ITypeSymbol? EventHandlerType { get; } + public abstract TypeSymbol? EventHandlerType { get; } /// - /// Gets a value indicating whether the has a name with a special meaning. + /// Gets a value indicating whether the has a name with a special meaning. /// - bool IsSpecialName { get; } + public bool IsSpecialName => (Attributes & EventAttributes.SpecialName) != 0; /// /// Returns the method used to add an event handler delegate to the event source. /// - IMethodSymbol? AddMethod { get; } + public abstract MethodSymbol? AddMethod { get; } /// /// Returns the method used to remove an event handler delegate from the event source. /// - IMethodSymbol? RemoveMethod { get; } + public abstract MethodSymbol? RemoveMethod { get; } /// /// Returns the method that is called when the event is raised. /// - IMethodSymbol? RaiseMethod { get; } + public abstract MethodSymbol? RaiseMethod { get; } /// /// Returns the method used to add an event handler delegate to the event source. /// /// - IMethodSymbol? GetAddMethod(); + public abstract MethodSymbol? GetAddMethod(); /// /// Returns the method used to add an event handler delegate to the event source, specifying whether to return non-public methods. /// /// /// - IMethodSymbol? GetAddMethod(bool nonPublic); + public abstract MethodSymbol? GetAddMethod(bool nonPublic); /// - /// Returns the method used to remove an event handler delegate from the event source. + /// Returns the public methods that have been associated with an event in metadata using the .other directive. /// /// - IMethodSymbol? GetRemoveMethod(); + public abstract MethodSymbol[] GetOtherMethods(); /// - /// When overridden in a derived class, retrieves the object for removing a method of the event, specifying whether to return non-public methods. + /// Returns the methods that have been associated with the event in metadata using the .other directive, specifying whether to include non-public methods. /// /// /// - IMethodSymbol? GetRemoveMethod(bool nonPublic); + public abstract MethodSymbol[] GetOtherMethods(bool nonPublic); /// /// Returns the method that is called when the event is raised. /// /// - IMethodSymbol? GetRaiseMethod(); + public abstract MethodSymbol? GetRaiseMethod(); /// /// When overridden in a derived class, returns the method that is called when the event is raised, specifying whether to return non-public methods. /// /// /// - IMethodSymbol? GetRaiseMethod(bool nonPublic); + public abstract MethodSymbol? GetRaiseMethod(bool nonPublic); /// - /// Returns the public methods that have been associated with an event in metadata using the .other directive. + /// Returns the method used to remove an event handler delegate from the event source. /// /// - IMethodSymbol[] GetOtherMethods(); + public abstract MethodSymbol? GetRemoveMethod(); /// - /// Returns the methods that have been associated with the event in metadata using the .other directive, specifying whether to include non-public methods. + /// When overridden in a derived class, retrieves the object for removing a method of the event, specifying whether to return non-public methods. /// /// /// - IMethodSymbol[] GetOtherMethods(bool nonPublic); + public abstract MethodSymbol? GetRemoveMethod(bool nonPublic); } diff --git a/src/IKVM.CoreLib/Symbols/IFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/FieldSymbol.cs similarity index 58% rename from src/IKVM.CoreLib/Symbols/IFieldSymbol.cs rename to src/IKVM.CoreLib/Symbols/FieldSymbol.cs index c927898a57..1fba55f625 100644 --- a/src/IKVM.CoreLib/Symbols/IFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/FieldSymbol.cs @@ -1,103 +1,114 @@ -using System.Reflection; - -using IKVM.CoreLib.Symbols.Emit; +using System.Collections.Immutable; +using System.Reflection; namespace IKVM.CoreLib.Symbols { - /// - /// Discovers the attributes of a field and provides access to field metadata. - /// - interface IFieldSymbol : IMemberSymbol + abstract class FieldSymbol : MemberSymbol { + /// + /// Initializes a new instance. + /// + /// + /// + /// + public FieldSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + base(context, module, declaringType) + { + + } + /// /// Gets the attributes associated with this field. /// - FieldAttributes Attributes { get; } + public abstract FieldAttributes Attributes { get; } /// /// Gets the type of this field object. /// - ITypeSymbol FieldType { get; } + public abstract TypeSymbol FieldType { get; } + + /// + public sealed override MemberTypes MemberType => MemberTypes.Field; /// /// Gets a value indicating whether the potential visibility of this field is described by ; that is, the field is visible at most to other types in the same assembly, and is not visible to derived types outside the assembly. /// - bool IsAssembly { get; } + public bool IsAssembly => (Attributes & FieldAttributes.FieldAccessMask) == FieldAttributes.Assembly; /// /// Gets a value indicating whether the visibility of this field is described by ; that is, the field is visible only within its class and derived classes. /// - bool IsFamily { get; } + public bool IsFamily => (Attributes & FieldAttributes.FieldAccessMask) == FieldAttributes.Family; /// /// Gets a value indicating whether the visibility of this field is described by ; that is, the field can be accessed from derived classes, but only if they are in the same assembly. /// - bool IsFamilyAndAssembly { get; } + public bool IsFamilyAndAssembly => (Attributes & FieldAttributes.FieldAccessMask) == FieldAttributes.FamANDAssem; /// /// Gets a value indicating whether the potential visibility of this field is described by ; that is, the field can be accessed by derived classes wherever they are, and by classes in the same assembly. /// - bool IsFamilyOrAssembly { get; } + public bool IsFamilyOrAssembly => (Attributes & FieldAttributes.FieldAccessMask) == FieldAttributes.FamORAssem; /// /// Gets a value indicating whether the field can only be set in the body of the constructor. /// - bool IsInitOnly { get; } + public bool IsInitOnly => (Attributes & FieldAttributes.InitOnly) != 0; /// /// Gets a value indicating whether the value is written at compile time and cannot be changed. /// - bool IsLiteral { get; } + public bool IsLiteral => (Attributes & FieldAttributes.Literal) != 0; /// /// Gets a value indicating whether this field has the NotSerialized attribute. /// - bool IsNotSerialized { get; } + public bool IsNotSerialized => (Attributes & FieldAttributes.NotSerialized) != 0; /// /// Gets a value indicating whether the corresponding PinvokeImpl attribute is set in FieldAttributes. /// - bool IsPinvokeImpl { get; } + public bool IsPinvokeImpl => (Attributes & FieldAttributes.PinvokeImpl) != 0; /// /// Gets a value indicating whether the field is private. /// - bool IsPrivate { get; } + public bool IsPrivate => (Attributes & FieldAttributes.FieldAccessMask) == FieldAttributes.Private; /// /// Gets a value indicating whether the field is public. /// - bool IsPublic { get; } + public bool IsPublic => (Attributes & FieldAttributes.FieldAccessMask) == FieldAttributes.Public; /// /// Gets a value indicating whether the corresponding SpecialName attribute is set in the FieldAttributes enumerator. /// - bool IsSpecialName { get; } + public bool IsSpecialName => (Attributes & FieldAttributes.SpecialName) != 0; /// /// Gets a value indicating whether the field is static. /// - bool IsStatic { get; } + public bool IsStatic => (Attributes & FieldAttributes.Static) != 0; /// /// Returns a literal value associated with the field by a compiler. /// /// - object? GetRawConstantValue(); + public abstract object? GetRawConstantValue(); /// /// Gets an array of types that identify the optional custom modifiers of the field. /// /// - ITypeSymbol[] GetOptionalCustomModifiers(); + public abstract IImmutableList GetOptionalCustomModifiers(); /// /// Gets an array of types that identify the required custom modifiers of the property. /// /// - ITypeSymbol[] GetRequiredCustomModifiers(); + public abstract IImmutableList GetRequiredCustomModifiers(); } diff --git a/src/IKVM.CoreLib/Symbols/GenericContext.cs b/src/IKVM.CoreLib/Symbols/GenericContext.cs new file mode 100644 index 0000000000..e10d781136 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/GenericContext.cs @@ -0,0 +1,15 @@ +using System.Collections.Immutable; + +namespace IKVM.CoreLib.Symbols +{ + + readonly struct GenericContext(ImmutableList? GenericTypeArguments, ImmutableList? GenericMethodArguments) + { + + public readonly ImmutableList? GenericTypeArguments = GenericTypeArguments; + + public readonly ImmutableList? GenericMethodArguments = GenericMethodArguments; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs new file mode 100644 index 0000000000..d28ee961a1 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs @@ -0,0 +1,38 @@ +using System; +using System.Collections.Immutable; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class GenericMethodParameterTypeSymbol : GenericParameterTypeSymbol + { + + readonly MethodBaseSymbol _declaringMethod; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected GenericMethodParameterTypeSymbol(ISymbolContext context, IModuleSymbol module, MethodBaseSymbol declaringMethod) : + base(context, module, null) + { + _declaringMethod = declaringMethod ?? throw new ArgumentNullException(nameof(declaringMethod)); + } + + /// + public override MethodBaseSymbol? DeclaringMethod => _declaringMethod; + + /// + internal override TypeSymbol Specialize(IImmutableList? genericTypeArguments, IImmutableList? genericMethodArguments) + { + if (genericMethodArguments == null) + throw new InvalidOperationException(); + + return genericMethodArguments[GenericParameterPosition]; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs new file mode 100644 index 0000000000..af1375b5a7 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs @@ -0,0 +1,78 @@ +using System; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class GenericParameterTypeSymbol : TypeSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected GenericParameterTypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + base(context, module, declaringType) + { + + } + + /// + public sealed override TypeAttributes Attributes => TypeAttributes.Public; + + /// + public override MethodBaseSymbol? DeclaringMethod => null; + + /// + public sealed override bool IsGenericTypeDefinition => false; + + /// + public sealed override bool HasElementType => false; + + /// + public sealed override bool IsArray => false; + + /// + public sealed override bool IsSZArray => false; + + /// + public sealed override bool IsByRef => false; + + /// + public sealed override bool IsPointer => false; + + /// + public sealed override bool IsFunctionPointer => false; + + /// + public sealed override bool IsUnmanagedFunctionPointer => false; + + /// + public sealed override bool IsConstructedGenericType => false; + + /// + public sealed override bool IsGenericParameter => true; + + /// + public sealed override bool ContainsGenericParameters => true; + + /// + public sealed override TypeCode TypeCode => TypeCode.Object; + + /// + public sealed override TypeSymbol? GetElementType() + { + return null; + } + + /// + public sealed override int GetArrayRank() + { + throw new NotSupportedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs new file mode 100644 index 0000000000..f53bfb9b84 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs @@ -0,0 +1,33 @@ +using System; +using System.Collections.Immutable; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class GenericTypeParameterTypeSymbol : GenericParameterTypeSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected GenericTypeParameterTypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol declaringType) : + base(context, module, declaringType) + { + + } + + /// + internal override TypeSymbol Specialize(IImmutableList? genericTypeArguments, IImmutableList? genericMethodArguments) + { + if (genericTypeArguments == null) + throw new InvalidOperationException(); + + return genericTypeArguments[GenericParameterPosition]; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/HasElementSymbol.cs b/src/IKVM.CoreLib/Symbols/HasElementSymbol.cs new file mode 100644 index 0000000000..a47ae2e122 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/HasElementSymbol.cs @@ -0,0 +1,176 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class HasElementSymbol : TypeSymbol + { + + readonly TypeSymbol _elementType; + + string? _name; + string? _fullName; + + /// + /// Initializes a new instance. + /// + /// + /// + public HasElementSymbol(ISymbolContext context, TypeSymbol elementType) : + base(context, elementType.Module, null) + { + _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); + } + + /// + public sealed override string? Namespace => _elementType.Namespace; + + /// + public sealed override string Name => _name ??= _elementType.Name + NameSuffix; + + /// + public sealed override string? FullName => _fullName ??= ComputeFullName(); + + /// + /// Computes the value of . + /// + /// + string? ComputeFullName() + { + var fullName = _elementType.FullName; + return fullName == null ? null : fullName + NameSuffix; + } + + /// + /// Gets the suffix of the type name. + /// + protected abstract string NameSuffix { get; } + + /// + public sealed override bool HasElementType => true; + + /// + public sealed override bool IsTypeDefinition => false; + + /// + public sealed override bool IsGenericTypeDefinition => false; + + /// + public sealed override bool IsConstructedGenericType => false; + + /// + public sealed override bool IsGenericParameter => false; + + /// + public sealed override ImmutableList GenericTypeArguments => throw new NotSupportedException(); + + /// + public sealed override bool ContainsGenericParameters => _elementType.ContainsGenericParameters; + + /// + public sealed override int GenericParameterPosition => throw new NotSupportedException(); + + /// + public sealed override GenericParameterAttributes GenericParameterAttributes => throw new NotSupportedException(); + + /// + public sealed override bool IsPrimitive => false; + + /// + public sealed override bool IsEnum => false; + + /// + public override bool IsArray => false; + + /// + public override bool IsSZArray => true; + + /// + public override bool IsByRef => true; + + /// + public override bool IsPointer => false; + + /// + public override bool IsFunctionPointer => false; + + /// + public override bool IsUnmanagedFunctionPointer => false; + + /// + public sealed override TypeCode TypeCode => TypeCode.Object; + + /// + public sealed override bool IsComplete => _elementType.IsComplete; + + /// + public sealed override TypeSymbol? GetElementType() + { + return _elementType; + } + + /// + public sealed override TypeSymbol GetGenericTypeDefinition() + { + throw new NotSupportedException(); + } + + /// + public sealed override ImmutableList GetGenericArguments() + { + throw new NotSupportedException(); + } + + /// + public sealed override ImmutableList GetGenericParameterConstraints() + { + throw new NotSupportedException(); + } + + /// + public sealed override ImmutableList GetDeclaredFields() + { + return ImmutableList.Empty; + } + + /// + public sealed override ImmutableList GetDeclaredProperties() + { + return ImmutableList.Empty; + } + + /// + public sealed override ImmutableList GetDeclaredEvents() + { + return ImmutableList.Empty; + } + + /// + public sealed override bool IsEnumDefined(object value) + { + throw new NotSupportedException(); + } + + /// + public sealed override string? GetEnumName(object value) + { + throw new NotSupportedException(); + } + + /// + public sealed override ImmutableList GetEnumNames() + { + throw new NotSupportedException(); + } + + /// + public sealed override TypeSymbol GetEnumUnderlyingType() + { + throw new NotSupportedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs index dbdfb9eef0..5e6f3ec7b2 100644 --- a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs @@ -13,12 +13,12 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider /// /// Gets a collection of the types defined in this assembly. /// - IEnumerable DefinedTypes { get; } + IEnumerable DefinedTypes { get; } /// /// Gets a collection of the public types defined in this assembly that are visible outside the assembly. /// - IEnumerable ExportedTypes { get; } + IEnumerable ExportedTypes { get; } /// /// Gets the display name of the assembly. @@ -65,7 +65,7 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider /// /// /// - Stream? GetManifestResourceStream(ITypeSymbol type, string name); + Stream? GetManifestResourceStream(TypeSymbol type, string name); /// /// Gets the specified module in this assembly. @@ -104,7 +104,7 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider /// /// /// - ITypeSymbol? GetType(string name); + TypeSymbol? GetType(string name); /// /// Gets the object with the specified name in the assembly instance and optionally throws an exception if the type is not found. @@ -112,7 +112,7 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider /// /// /// - ITypeSymbol? GetType(string name, bool throwOnError); + TypeSymbol? GetType(string name, bool throwOnError); /// /// Gets the object with the specified name in the assembly instance, with the options of ignoring the case, and of throwing an exception if the type is not found. @@ -121,24 +121,24 @@ interface IAssemblySymbol : ISymbol, ICustomAttributeProvider /// /// /// - ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase); + TypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase); /// /// Gets all types defined in this assembly. /// /// - ITypeSymbol[] GetTypes(); + TypeSymbol[] GetTypes(); /// /// Gets the public types defined in this assembly that are visible outside the assembly. /// /// - ITypeSymbol[] GetExportedTypes(); + TypeSymbol[] GetExportedTypes(); /// /// Gets the entry point of this assembly. /// - IMethodSymbol? EntryPoint { get; } + MethodSymbol? EntryPoint { get; } } diff --git a/src/IKVM.CoreLib/Symbols/IConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/IConstructorSymbol.cs deleted file mode 100644 index 3b5d8a4c23..0000000000 --- a/src/IKVM.CoreLib/Symbols/IConstructorSymbol.cs +++ /dev/null @@ -1,14 +0,0 @@ -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Discovers the attributes of a class constructor and provides access to constructor metadata. - /// - interface IConstructorSymbol : IMethodBaseSymbol - { - - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs index a8747edc43..16d99e27ae 100644 --- a/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs +++ b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs @@ -20,7 +20,7 @@ interface ICustomAttributeProvider : ISymbol /// /// /// - CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false); + CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false); /// /// Retrieves a custom attribute of a specified type that is applied to a specified member. @@ -28,7 +28,7 @@ interface ICustomAttributeProvider : ISymbol /// /// /// - CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false); + CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false); /// /// Indicates whether one or more instance of is defined on this member. @@ -36,7 +36,7 @@ interface ICustomAttributeProvider : ISymbol /// /// /// - bool IsDefined(ITypeSymbol attributeType, bool inherit = false); + bool IsDefined(TypeSymbol attributeType, bool inherit = false); } diff --git a/src/IKVM.CoreLib/Symbols/IMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/IMemberSymbol.cs deleted file mode 100644 index f54d6c3ffa..0000000000 --- a/src/IKVM.CoreLib/Symbols/IMemberSymbol.cs +++ /dev/null @@ -1,39 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Obtains information about the attributes of a member and provides access to member metadata. - /// - interface IMemberSymbol : ISymbol, ICustomAttributeProvider - { - - /// - /// Gets the module in which the type that declares the member represented by the current is defined. - /// - IModuleSymbol Module { get; } - - /// - /// Gets the class that declares this member. - /// - ITypeSymbol? DeclaringType { get; } - - /// - /// When overridden in a derived class, gets a value indicating the type of the member - method, constructor, event, and so on. - /// - MemberTypes MemberType { get; } - - /// - /// Gets a value that identifies a metadata element. - /// - int MetadataToken { get; } - - /// - /// Gets the name of the current member. - /// - string Name { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs deleted file mode 100644 index c3c8d5c9e0..0000000000 --- a/src/IKVM.CoreLib/Symbols/IMethodSymbol.cs +++ /dev/null @@ -1,46 +0,0 @@ -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Discovers the attributes of a method and provides access to method metadata. - /// - interface IMethodSymbol : IMethodBaseSymbol - { - - /// - /// Gets a object that contains information about the return type of the method, such as whether the return type has custom modifiers. - /// - IParameterSymbol ReturnParameter { get; } - - /// - /// Gets the return type of this method. - /// - ITypeSymbol ReturnType { get; } - - /// - /// Gets the custom attributes for the return type. - /// - ICustomAttributeProvider ReturnTypeCustomAttributes { get; } - - /// - /// When overridden in a derived class, returns the object for the method on the direct or indirect base class in which the method represented by this instance was first declared. - /// - /// - IMethodSymbol GetBaseDefinition(); - - /// - /// Returns a object that represents a generic method definition from which the current method can be constructed. - /// - /// - IMethodSymbol GetGenericMethodDefinition(); - - /// - /// Substitutes the elements of an array of types for the type parameters of the current generic method definition, and returns a MethodInfo object representing the resulting constructed method. - /// - /// - /// - IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments); - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs index bcd76ad225..819cd33d4e 100644 --- a/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs @@ -51,7 +51,7 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - IFieldSymbol? GetField(string name); + FieldSymbol? GetField(string name); /// /// Returns a field having the specified name and binding attributes. @@ -59,27 +59,27 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - IFieldSymbol? GetField(string name, BindingFlags bindingAttr); + FieldSymbol? GetField(string name, BindingFlags bindingAttr); /// /// Returns the global fields defined on the module that match the specified binding flags. /// /// /// - IFieldSymbol[] GetFields(BindingFlags bindingFlags); + FieldSymbol[] GetFields(BindingFlags bindingFlags); /// /// Returns the global fields defined on the module. /// /// - IFieldSymbol[] GetFields(); + FieldSymbol[] GetFields(); /// /// Returns a method having the specified name. /// /// /// - IMethodSymbol? GetMethod(string name); + MethodSymbol? GetMethod(string name); /// /// Returns a method having the specified name and parameter types. @@ -87,7 +87,7 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - IMethodSymbol? GetMethod(string name, ITypeSymbol[] types); + MethodSymbol? GetMethod(string name, TypeSymbol[] types); /// /// Returns a method having the specified name, binding information, calling convention, and parameter types and modifiers. @@ -98,27 +98,27 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers); + MethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, TypeSymbol[] types, ParameterModifier[]? modifiers); /// /// Returns the global methods defined on the module. /// /// - IMethodSymbol[] GetMethods(); + MethodSymbol[] GetMethods(); /// /// Returns the global methods defined on the module that match the specified binding flags. /// /// /// - IMethodSymbol[] GetMethods(BindingFlags bindingFlags); + MethodSymbol[] GetMethods(BindingFlags bindingFlags); /// /// Returns the specified type, performing a case-sensitive search. /// /// /// - ITypeSymbol? GetType(string className); + TypeSymbol? GetType(string className); /// /// Returns the specified type, searching the module with the specified case sensitivity. @@ -126,7 +126,7 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - ITypeSymbol? GetType(string className, bool ignoreCase); + TypeSymbol? GetType(string className, bool ignoreCase); /// /// Returns the specified type, specifying whether to make a case-sensitive search of the module and whether to throw an exception if the type cannot be found. @@ -135,20 +135,20 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase); + TypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase); /// /// Returns all the types defined within this module. /// /// - ITypeSymbol[] GetTypes(); + TypeSymbol[] GetTypes(); /// /// Returns the type identified by the specified metadata token. /// /// /// - ITypeSymbol ResolveType(int metadataToken); + TypeSymbol ResolveType(int metadataToken); /// /// Returns the type identified by the specified metadata token, in the context defined by the specified generic type parameters. @@ -157,14 +157,14 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments); + TypeSymbol ResolveType(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); /// /// Returns the field identified by a metadata token. /// /// /// - IFieldSymbol? ResolveField(int metadataToken); + FieldSymbol? ResolveField(int metadataToken); /// /// Returns the field identified by the specified metadata token, in the context defined by the specified generic type parameters. @@ -173,14 +173,14 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments); + FieldSymbol? ResolveField(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); /// /// Returns the type or member identified by a metadata token. /// /// /// - IMemberSymbol? ResolveMember(int metadataToken); + MemberSymbol? ResolveMember(int metadataToken); /// /// Returns the type or member identified by the specified metadata token, in the context defined by the specified generic type parameters. @@ -189,14 +189,14 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments); + MemberSymbol? ResolveMember(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); /// /// Returns the method or constructor identified by the specified metadata token. /// /// /// - IMethodBaseSymbol? ResolveMethod(int metadataToken); + MethodBaseSymbol? ResolveMethod(int metadataToken); /// /// Returns the method or constructor identified by the specified metadata token, in the context defined by the specified generic type parameters. @@ -205,7 +205,7 @@ interface IModuleSymbol : ISymbol, ICustomAttributeProvider /// /// /// - IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments); + MethodBaseSymbol? ResolveMethod(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); /// /// Returns the signature blob identified by a metadata token. diff --git a/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs deleted file mode 100644 index e1008c96c6..0000000000 --- a/src/IKVM.CoreLib/Symbols/IParameterSymbol.cs +++ /dev/null @@ -1,93 +0,0 @@ -using System.Reflection; - -using IKVM.CoreLib.Symbols.Reflection; - -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Discovers the attributes of a parameter and provides access to parameter metadata. - /// - interface IParameterSymbol : ISymbol, ICustomAttributeProvider - { - - /// - /// Gets the attributes for this parameter. - /// - ParameterAttributes Attributes { get; } - - /// - /// Gets a value indicating the member in which the parameter is implemented. - /// - IMemberSymbol Member { get; } - - /// - /// Gets the Type of this parameter. - /// - ITypeSymbol ParameterType { get; } - - /// - /// Gets the name of the parameter. - /// - string? Name { get; } - - /// - /// Gets the zero-based position of the parameter in the formal parameter list. - /// - int Position { get; } - - /// - /// Gets a value that indicates whether this parameter has a default value. - /// - bool HasDefaultValue { get; } - - /// - /// Gets a value indicating the default value if the parameter has a default value. - /// - object? DefaultValue { get; } - - /// - /// Gets a value indicating whether this is an input parameter. - /// - bool IsIn { get; } - - /// - /// Gets a value indicating whether this is an output parameter. - /// - bool IsOut { get; } - - /// - /// Gets a value indicating whether this parameter is optional. - /// - bool IsOptional { get; } - - /// - /// Gets a value indicating whether this parameter is a locale identifier (lcid). - /// - bool IsLcid { get; } - - /// - /// Gets a value indicating whether this is a Retval parameter. - /// - bool IsRetval { get; } - - /// - /// Gets a value that identifies this parameter in metadata. - /// - int MetadataToken { get; } - - /// - /// Returns an array of types representing the optional custom modifiers of the parameter. - /// - /// - ITypeSymbol[] GetOptionalCustomModifiers(); - - /// - /// Returns an array of types representing the required custom modifiers of the parameter. - /// - /// - ITypeSymbol[] GetRequiredCustomModifiers(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index fda80bd4f0..251d0496a8 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -13,7 +13,7 @@ interface ISymbolContext /// /// /// - ITypeSymbol ResolveCoreType(string typeName); + TypeSymbol ResolveCoreType(string typeName); /// /// Defines a dynamic assembly that has the specified name and access rights. diff --git a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs index b14842d29f..1505789560 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs @@ -8,25 +8,25 @@ interface ISymbolResolver { /// - /// Resolves the named type from the core assembly. + /// Resolves the named assembly from any reference source. /// - /// + /// /// - ITypeSymbol ResolveCoreType(string typeName); + IAssemblySymbol? ResolveAssembly(string assemblyName); /// - /// Resolves the named assembly from any reference source. + /// Resolves the named type from the core assembly. /// - /// + /// /// - IAssemblySymbol? ResolveAssembly(string assemblyName); + TypeSymbol ResolveCoreType(string typeName); /// /// Resolves the named type from any reference source. /// /// /// - ITypeSymbol? ResolveType(string typeName); + TypeSymbol? ResolveType(string typeName); } diff --git a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs deleted file mode 100644 index 47f1d65324..0000000000 --- a/src/IKVM.CoreLib/Symbols/ITypeSymbol.cs +++ /dev/null @@ -1,676 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Collections.Immutable; -using System.Reflection; - -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Represents type declarations: class types, interface types, array types, value types, enumeration types, type parameters, generic type definitions, and open or closed constructed generic types. - /// - interface ITypeSymbol : IMemberSymbol - { - - /// - /// Gets the attributes associated with the . - /// - TypeAttributes Attributes { get; } - - /// - /// Gets the in which the type is declared. For generic types, gets the in which the generic type is defined. - /// - IAssemblySymbol Assembly { get; } - - /// - /// Gets a that represents the declaring method, if the current represents a type parameter of a generic method. - /// - IMethodBaseSymbol? DeclaringMethod { get; } - - /// - /// Gets the assembly-qualified name of the type, which includes the name of the assembly from which this object was loaded. - /// - string? AssemblyQualifiedName { get; } - - /// - /// Gets the fully qualified name of the type, including its namespace but not its assembly. - /// - string? FullName { get; } - - /// - /// Gets the namespace of the . - /// - string? Namespace { get; } - - /// - /// Gets the underlying type code of the specified Type. - /// - TypeCode TypeCode { get; } - - /// - /// Gets the type from which the current directly inherits. - /// - ITypeSymbol? BaseType { get; } - - /// - /// Gets a value indicating whether the current object has type parameters that have not been replaced by specific types. - /// - bool ContainsGenericParameters { get; } - - /// - /// Gets a combination of flags that describe the covariance and special constraints of the current generic type parameter. - /// - GenericParameterAttributes GenericParameterAttributes { get; } - - /// - /// Gets the position of the type parameter in the type parameter list of the generic type or method that declared the parameter, when the object represents a type parameter of a generic type or a generic method. - /// - int GenericParameterPosition { get; } - - /// - /// Gets an array of the generic type arguments for this type. - /// - IImmutableList GenericTypeArguments { get; } - - /// - /// Gets a value that indicates whether this object represents a constructed generic type. You can create instances of a constructed generic type. - /// - bool IsConstructedGenericType { get; } - - /// - /// Gets a value indicating whether the current type is a generic type. - /// - bool IsGenericType { get; } - - /// - /// Gets a value indicating whether the current Type represents a generic type definition, from which other generic types can be constructed. - /// - bool IsGenericTypeDefinition { get; } - - /// - /// Gets a value indicating whether the current represents a type parameter in the definition of a generic type or method. - /// - bool IsGenericParameter { get; } - - /// - /// Gets a value indicating whether the fields of the current type are laid out automatically by the common language runtime. - /// - bool IsAutoLayout { get; } - - /// - /// Gets a value indicating whether the fields of the current type are laid out at explicitly specified offsets. - /// - bool IsExplicitLayout { get; } - - /// - /// Gets a value indicating whether the fields of the current type are laid out sequentially, in the order that they were defined or emitted to the metadata. - /// - bool IsLayoutSequential { get; } - - /// - /// Gets a value indicating whether the current encompasses or refers to another type; that is, whether the current is an array, a pointer, or is passed by reference. - /// - bool HasElementType { get; } - - /// - /// Gets a value indicating whether the is a class or a delegate; that is, not a value type or interface. - /// - bool IsClass { get; } - - /// - /// Gets a value indicating whether the is a value type. - /// - bool IsValueType { get; } - - /// - /// Gets a value indicating whether the is an interface; that is, not a class or a value type. - /// - bool IsInterface { get; } - - /// - /// Gets a value indicating whether the is one of the primitive types. - /// - bool IsPrimitive { get; } - - /// - /// Gets a value that indicates whether the type is an array type that can represent only a single-dimensional array with a zero lower bound. - /// - bool IsSZArray { get; } - - /// - /// Gets a value that indicates whether the type is an array. - /// - bool IsArray { get; } - - /// - /// Gets a value indicating whether the current represents an enumeration. - /// - bool IsEnum { get; } - - /// - /// Gets a value indicating whether the is a pointer. - /// - bool IsPointer { get; } - - /// - /// Gets a value that indicates whether the current is an unmanaged function pointer. - /// - bool IsFunctionPointer { get; } - - /// - /// Gets a value that indicates whether the current is an unmanaged function pointer. - /// - bool IsUnmanagedFunctionPointer { get; } - - /// - /// Gets a value indicating whether the is passed by reference. - /// - bool IsByRef { get; } - - /// - /// Gets a value indicating whether the is abstract and must be overridden. - /// - bool IsAbstract { get; } - - /// - /// Gets a value indicating whether the is declared sealed. - /// - bool IsSealed { get; } - - /// - /// Gets a value indicating whether the can be accessed by code outside the assembly. - /// - bool IsVisible { get; } - - /// - /// Gets a value indicating whether the is declared public. - /// - bool IsPublic { get; } - - /// - /// Gets a value indicating whether the is not declared public. - /// - bool IsNotPublic { get; } - - /// - /// Gets a value indicating whether the current object represents a type whose definition is nested inside the definition of another type. - /// - bool IsNested { get; } - - /// - /// Gets a value indicating whether the is nested and visible only within its own assembly. - /// - bool IsNestedAssembly { get; } - - /// - /// Gets a value indicating whether the is nested and visible only to classes that belong to both its own family and its own assembly. - /// - bool IsNestedFamANDAssem { get; } - - /// - /// Gets a value indicating whether the is nested and visible only within its own family. - /// - bool IsNestedFamily { get; } - - /// - /// Gets a value indicating whether the is nested and visible only to classes that belong to either its own family or to its own assembly. - /// - bool IsNestedFamORAssem { get; } - - /// - /// Gets a value indicating whether the is nested and declared private. - /// - bool IsNestedPrivate { get; } - - /// - /// Gets a value indicating whether a class is nested and declared public. - /// - bool IsNestedPublic { get; } - - /// - /// Gets a value indicating whether the is binary serializable. - /// - bool IsSerializable { get; } - - /// - /// Gets a value that indicates whether the type is a signature type. - /// - bool IsSignatureType { get; } - - /// - /// Gets a value indicating whether the type has a name that requires special handling. - /// - bool IsSpecialName { get; } - - /// - /// Gets the initializer for the type. - /// - IConstructorSymbol? TypeInitializer { get; } - - /// - /// Gets the number of dimensions in an array. - /// - /// - int GetArrayRank(); - - /// - /// Searches for the members defined for the current whose DefaultMemberAttribute is set. - /// - /// - IImmutableList GetDefaultMembers(); - - /// - /// When overridden in a derived class, returns the of the object encompassed or referred to by the current array, pointer or reference type. - /// - /// - ITypeSymbol? GetElementType(); - - /// - /// Returns the name of the constant that has the specified value, for the current enumeration type. - /// - /// - /// - string? GetEnumName(object value); - - /// - /// Returns the names of the members of the current enumeration type. - /// - /// - IImmutableList GetEnumNames(); - - /// - /// Returns the underlying type of the current enumeration type. - /// - /// - ITypeSymbol GetEnumUnderlyingType(); - - /// - /// Returns an array of objects that represent the type arguments of a closed generic type or the type parameters of a generic type definition. - /// - /// - IImmutableList GetGenericArguments(); - - /// - /// Returns an array of objects that represent the constraints on the current generic type parameter. - /// - /// - IImmutableList GetGenericParameterConstraints(); - - /// - /// Returns a object that represents a generic type definition from which the current generic type can be constructed. - /// - /// - ITypeSymbol GetGenericTypeDefinition(); - - /// - /// Searches for the interface with the specified name. - /// - /// - /// - ITypeSymbol? GetInterface(string name); - - /// - /// When overridden in a derived class, searches for the specified interface, specifying whether to do a case-insensitive search for the interface name. - /// - /// - /// - /// - ITypeSymbol? GetInterface(string name, bool ignoreCase); - - /// - /// When overridden in a derived class, gets all the interfaces implemented or if specified,inherited by the current . - /// - /// - IImmutableList GetInterfaces(bool inherit = true); - - /// - /// Returns an interface mapping for the specified interface type. - /// - /// - /// - InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType); - - /// - /// Returns all the declared constructors of the current . - /// - /// - IImmutableList GetDeclaredConstructors(); - - /// - /// Searches for a public instance constructor whose parameters match the types in the specified array. - /// - /// - /// - IConstructorSymbol? GetConstructor(IImmutableList types); - - /// - /// Searches for a constructor whose parameters match the specified argument types, using the specified binding constraints. - /// - /// - /// - /// - IConstructorSymbol? GetConstructor(BindingFlags bindingFlags, IImmutableList types); - - /// - /// Returns all the public constructors defined for the current . - /// - /// - IImmutableList GetConstructors(); - - /// - /// When overridden in a derived class, searches for the constructors defined for the current , using the specified BindingFlags. - /// - /// - /// - IImmutableList GetConstructors(BindingFlags bindingFlags); - - /// - /// Searches for the public field with the specified name. - /// - /// - /// - IFieldSymbol? GetField(string name); - - /// - /// Searches for the specified field, using the specified binding constraints. - /// - /// - /// - /// - IFieldSymbol? GetField(string name, BindingFlags bindingFlags); - - /// - /// Returns all the public fields of the current . - /// - /// - IImmutableList GetFields(); - - /// - /// When overridden in a derived class, searches for the fields defined for the current , using the specified binding constraints. - /// - /// - /// - IImmutableList GetFields(BindingFlags bindingFlags); - - /// - /// Returns all the declared methods of the current . - /// - /// - IImmutableList GetDeclaredMethods(); - - /// - /// Searches for the public method with the specified name. - /// - /// - /// - IMethodSymbol? GetMethod(string name); - - /// - /// Searches for the specified public method whose parameters match the specified argument types. - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, IImmutableList types); - - /// - /// Searches for the specified method, using the specified binding constraints. - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags); - - /// - /// Searches for the specified method whose parameters match the specified argument types, using the specified binding constraints. - /// - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList types); - - /// - /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints and the specified calling convention. - /// - /// - /// - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers); - - /// - /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints and the specified calling convention. - /// - /// - /// - /// - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers); - - /// - /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints. - /// - /// - /// - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, IImmutableList types, IImmutableList modifiers); - - /// - /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints. - /// - /// - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, IImmutableList types, IImmutableList modifiers); - - /// - /// Searches for the specified public method whose parameters match the specified generic parameter count, argument types and modifiers. - /// - /// - /// - /// - /// - /// - IMethodSymbol? GetMethod(string name, int genericParameterCount, IImmutableList types, IImmutableList modifiers); - - /// - /// Returns all the public methods of the current . - /// - /// - IImmutableList GetMethods(); - - /// - /// When overridden in a derived class, searches for the methods defined for the current , using the specified binding constraints. - /// - /// - /// - IImmutableList GetMethods(BindingFlags bindingFlags); - - /// - /// Returns all the declared properties of the current . - /// - /// - IImmutableList GetDeclaredProperties(); - - /// - /// Searches for the public property with the specified name. - /// - /// - /// - IPropertySymbol? GetProperty(string name); - - /// - /// Searches for the specified property, using the specified binding constraints. - /// - /// - /// - /// - IPropertySymbol? GetProperty(string name, BindingFlags bindingFlags); - - /// - /// Searches for the specified public property whose parameters match the specified argument types. - /// - /// - /// - /// - IPropertySymbol? GetProperty(string name, IImmutableList types); - - /// - /// Searches for the specified public property whose parameters match the specified argument types. - /// - /// - /// - /// - /// - IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, IImmutableList types); - - /// - /// Searches for the public property with the specified name and return type. - /// - /// - /// - /// - IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType); - - /// - /// Returns all the public properties of the current . - /// - /// - IImmutableList GetProperties(); - - /// - /// When overridden in a derived class, searches for the properties of the current , using the specified binding constraints. - /// - /// - /// - IImmutableList GetProperties(BindingFlags bindingFlags); - - /// - /// Returns all the declared events of the current . - /// - /// - IImmutableList GetDeclaredEvents(); - - /// - /// Returns the object representing the specified public event. - /// - /// - /// - IEventSymbol? GetEvent(string name); - - /// - /// When overridden in a derived class, returns the object representing the specified event, using the specified binding constraints. - /// - /// - /// - /// - IEventSymbol? GetEvent(string name, BindingFlags bindingFlags); - - /// - /// Returns all the public events that are declared or inherited by the current . - /// - /// - IImmutableList GetEvents(); - - /// - /// When overridden in a derived class, searches for events that are declared or inherited by the current , using the specified binding constraints. - /// - /// - /// - IImmutableList GetEvents(BindingFlags bindingFlags); - - /// - /// Searches for the public nested type with the specified name. - /// - /// - /// - ITypeSymbol? GetNestedType(string name); - - /// - /// When overridden in a derived class, searches for the specified nested type, using the specified binding constraints. - /// - /// - /// - /// - ITypeSymbol? GetNestedType(string name, BindingFlags bindingFlags); - - /// - /// Returns the public types nested in the current . - /// - /// - IImmutableList GetNestedTypes(); - - /// - /// When overridden in a derived class, searches for the types nested in the current , using the specified binding constraints. - /// - /// - /// - IImmutableList GetNestedTypes(BindingFlags bindingFlags); - - /// - /// Determines whether an instance of a specified type c can be assigned to a variable of the current type. - /// - /// - /// - bool IsAssignableFrom(ITypeSymbol? c); - - /// - /// Determines whether the current derives from the specified . - /// - /// - /// - bool IsSubclassOf(ITypeSymbol c); - - /// - /// Returns a value that indicates whether the specified value exists in the current enumeration type. - /// - /// - /// - bool IsEnumDefined(object value); - - /// - /// Returns a object representing a one-dimensional array of the current type, with a lower bound of zero. - /// - /// - ITypeSymbol MakeArrayType(); - - /// - /// Returns a object representing an array of the current type, with the specified number of dimensions. - /// - /// - /// - ITypeSymbol MakeArrayType(int rank); - - /// - /// Substitutes the elements of an array of types for the type parameters of the current generic type definition and returns a object representing the resulting constructed type. - /// - /// - /// - ITypeSymbol MakeGenericType(IImmutableList typeArguments); - - /// - /// Returns a object that represents a pointer to the current type. - /// - /// - ITypeSymbol MakePointerType(); - - /// - /// Returns a object that represents the current type when passed as a ref parameter (ByRef parameter in Visual Basic). - /// - /// - ITypeSymbol MakeByRefType(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs b/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs index ebc5c438ce..1668a8a078 100644 --- a/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs +++ b/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs @@ -1,15 +1,13 @@ -using System.Collections.Immutable; - -namespace IKVM.CoreLib.Symbols +namespace IKVM.CoreLib.Symbols { - readonly struct InterfaceMapping(IMethodSymbol[] InterfaceMethods, ITypeSymbol InterfaceType, IMethodSymbol[] TargetMethods, ITypeSymbol TargetType) + readonly struct InterfaceMapping(MethodSymbol[] InterfaceMethods, TypeSymbol InterfaceType, MethodSymbol[] TargetMethods, TypeSymbol TargetType) { - public readonly IMethodSymbol[] InterfaceMethods = InterfaceMethods; - public readonly ITypeSymbol InterfaceType = InterfaceType; - public readonly IMethodSymbol[] TargetMethods = TargetMethods; - public readonly ITypeSymbol TargetType = TargetType; + public readonly MethodSymbol[] InterfaceMethods = InterfaceMethods; + public readonly TypeSymbol InterfaceType = InterfaceType; + public readonly MethodSymbol[] TargetMethods = TargetMethods; + public readonly TypeSymbol TargetType = TargetType; } diff --git a/src/IKVM.CoreLib/Symbols/MemberSymbol.cs b/src/IKVM.CoreLib/Symbols/MemberSymbol.cs new file mode 100644 index 0000000000..fd5dd1db01 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/MemberSymbol.cs @@ -0,0 +1,82 @@ +using System; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class MemberSymbol : ICustomAttributeProvider + { + + readonly ISymbolContext _context; + readonly IModuleSymbol _module; + readonly TypeSymbol? _declaringType; + + /// + /// Initializes a new instance. + /// + /// + /// + public MemberSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _declaringType = declaringType; + } + + public ISymbolContext Context => _context; + + /// + /// Gets the module in which the type that declares the member represented by the current is defined. + /// + public IModuleSymbol Module => _module; + + /// + /// Gets the appropriate for this instance. + /// + public IAssemblySymbol Assembly => _module.Assembly; + + /// + /// Gets the class that declares this member. + /// + public TypeSymbol? DeclaringType => _declaringType; + + /// + /// When overridden in a derived class, gets a value indicating the type of the member - method, constructor, event, and so on. + /// + public abstract MemberTypes MemberType { get; } + + /// + /// Gets the name of the current member. + /// + public abstract string Name { get; } + + /// + /// Returns true if the symbol is missing. + /// + public abstract bool IsMissing { get; } + + /// + /// Returns true if the symbol contains a missing symbol. + /// + public abstract bool ContainsMissing { get; } + + /// + /// Returns true if the symbol is complete. That is, was created with a builder and completed. + /// + public abstract bool IsComplete { get; } + + /// + public abstract CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false); + + /// + public abstract CustomAttribute[] GetCustomAttributes(bool inherit = false); + + /// + public abstract CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false); + + /// + public abstract bool IsDefined(TypeSymbol attributeType, bool inherit = false); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs similarity index 61% rename from src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs rename to src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs index 99c9a74735..31b74dbb29 100644 --- a/src/IKVM.CoreLib/Symbols/IMethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs @@ -4,125 +4,134 @@ namespace IKVM.CoreLib.Symbols { - /// - /// Provides information about methods and constructors. - /// - interface IMethodBaseSymbol : IMemberSymbol + abstract class MethodBaseSymbol : MemberSymbol { + /// + /// Initializes a new instance. + /// + /// + /// + /// + public MethodBaseSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + base(context, module, declaringType) + { + + } + /// /// Gets the attributes associated with this method. /// - MethodAttributes Attributes { get; } + public abstract MethodAttributes Attributes { get; } /// /// Gets a value indicating the calling conventions for this method. /// - CallingConventions CallingConvention { get; } + public abstract CallingConventions CallingConvention { get; } /// /// Gets a value indicating whether the generic method contains unassigned generic type parameters. /// - bool ContainsGenericParameters { get; } + public abstract bool ContainsGenericParameters { get; } /// /// Gets a value indicating whether the method is abstract. /// - bool IsAbstract { get; } + public bool IsAbstract => (Attributes & MethodAttributes.Abstract) != 0; /// /// Gets a value indicating whether the potential visibility of this method or constructor is described by Assembly; that is, the method or constructor is visible at most to other types in the same assembly, and is not visible to derived types outside the assembly. /// - bool IsAssembly { get; } + public bool IsAssembly => (Attributes & MethodAttributes.MemberAccessMask) == MethodAttributes.Assembly; /// /// Gets a value indicating whether the method is a constructor. /// - bool IsConstructor { get; } + public bool IsConstructor => !IsStatic && (Attributes & MethodAttributes.RTSpecialName) == MethodAttributes.RTSpecialName; /// /// Gets a value indicating whether the visibility of this method or constructor is described by Family; that is, the method or constructor is visible only within its class and derived classes. /// - bool IsFamily { get; } + public bool IsFamily => (Attributes & MethodAttributes.MemberAccessMask) == MethodAttributes.Family; /// /// Gets a value indicating whether the visibility of this method or constructor is described by FamANDAssem; that is, the method or constructor can be called by derived classes, but only if they are in the same assembly. /// - bool IsFamilyAndAssembly { get; } + public bool IsFamilyAndAssembly => (Attributes & MethodAttributes.MemberAccessMask) == MethodAttributes.FamANDAssem; /// /// Gets a value indicating whether the potential visibility of this method or constructor is described by FamORAssem; that is, the method or constructor can be called by derived classes wherever they are, and by classes in the same assembly. /// - bool IsFamilyOrAssembly { get; } + public bool IsFamilyOrAssembly => (Attributes & MethodAttributes.MemberAccessMask) == MethodAttributes.FamORAssem; /// /// Gets a value indicating whether this method is final. /// - bool IsFinal { get; } + public bool IsFinal => (Attributes & MethodAttributes.Final) != 0; /// /// Gets a value indicating whether the method is generic. /// - bool IsGenericMethod { get; } + public abstract bool IsGenericMethod { get; } /// /// Gets a value indicating whether the method is a generic method definition. /// - bool IsGenericMethodDefinition { get; } + public abstract bool IsGenericMethodDefinition { get; } /// /// Gets a value indicating whether only a member of the same kind with exactly the same signature is hidden in the derived class. /// - bool IsHideBySig { get; } + public bool IsHideBySig => (Attributes & MethodAttributes.HideBySig) != 0; /// /// Gets a value indicating whether this member is private. /// - bool IsPrivate { get; } + public bool IsPrivate => (Attributes & MethodAttributes.MemberAccessMask) == MethodAttributes.Private; /// /// Gets a value indicating whether this is a public method. /// - bool IsPublic { get; } + public bool IsPublic => (Attributes & MethodAttributes.MemberAccessMask) == MethodAttributes.Public; /// /// Gets a value indicating whether the method is static. /// - bool IsStatic { get; } + public bool IsStatic => (Attributes & MethodAttributes.Static) != 0; /// /// Gets a value indicating whether the method is virtual. /// - bool IsVirtual { get; } + public bool IsVirtual => (Attributes & MethodAttributes.Virtual) != 0; /// /// Gets a value indicating whether this method has a special name. /// - bool IsSpecialName { get; } + public bool IsSpecialName => (Attributes & MethodAttributes.SpecialName) != 0; /// /// Gets the flags that specify the attributes of a method implementation. /// - MethodImplAttributes MethodImplementationFlags { get; } + public abstract MethodImplAttributes MethodImplementationFlags { get; } /// /// Returns an array of objects that represent the type arguments of a generic method or the type parameters of a generic method definition. /// /// - ImmutableArray GetGenericArguments(); + public abstract ImmutableList GetGenericArguments(); /// /// When overridden in a derived class, gets the parameters of the specified method or constructor. /// /// - ImmutableArray GetParameters(); + public abstract ImmutableList GetParameters(); /// /// When overridden in a derived class, returns the MethodImplAttributes flags. /// /// - MethodImplAttributes GetMethodImplementationFlags(); + public abstract MethodImplAttributes GetMethodImplementationFlags(); } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/MethodSpecTable.cs b/src/IKVM.CoreLib/Symbols/MethodSpecTable.cs new file mode 100644 index 0000000000..691d12a179 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/MethodSpecTable.cs @@ -0,0 +1,68 @@ +using System; +using System.Collections.Concurrent; +using System.Collections.Immutable; +using System.Threading; + +namespace IKVM.CoreLib.Symbols +{ + + struct MethodSpecTable + { + + readonly ISymbolContext _context; + readonly IModuleSymbol _module; + readonly TypeSymbol? _type; + readonly MethodSymbol _method; + readonly ImmutableList _typeArguments; + + ConcurrentDictionary, ConstructedGenericMethodSymbol>? _cache; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public MethodSpecTable(ISymbolContext context, IModuleSymbol module, TypeSymbol? type, MethodSymbol method, ImmutableList typeArguments) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _module = module ?? throw new ArgumentNullException(nameof(module)); + _type = type; + _method = method ?? throw new ArgumentNullException(nameof(method)); + _typeArguments = typeArguments ?? throw new ArgumentNullException(nameof(typeArguments)); + } + + /// + /// Gets or creates a representing a specialized generic of this method. + /// + /// + /// + public MethodSymbol GetOrCreateGenericMethodSymbol(ImmutableList typeArguments) + { + if (typeArguments is null) + throw new ArgumentNullException(nameof(typeArguments)); + + if (_method.IsGenericMethodDefinition == false) + throw new InvalidOperationException(); + + if (_cache == null) + Interlocked.CompareExchange(ref _cache, new(TypeSymbolListEqualityComparer.Instance), null); + + return _cache.GetOrAdd(typeArguments, CreateGenericMethodSymbol); + } + + /// + /// Creates a new representing a specialized generic of this type. + /// + /// + /// + readonly ConstructedGenericMethodSymbol CreateGenericMethodSymbol(ImmutableList typeArguments) + { + return new ConstructedGenericMethodSymbol(_context, _module, _type, _method, new GenericContext(_typeArguments, typeArguments)); + } + } + +} diff --git a/src/IKVM.CoreLib/Symbols/MethodSymbol.cs b/src/IKVM.CoreLib/Symbols/MethodSymbol.cs new file mode 100644 index 0000000000..92c532b4f4 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/MethodSymbol.cs @@ -0,0 +1,47 @@ +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class MethodSymbol : MethodBaseSymbol + { + + MethodSpecTable _specTable; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + protected MethodSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + base(context, module, declaringType) + { + _specTable = new MethodSpecTable(context, module, declaringType, this); + } + + /// + public override MemberTypes MemberType => MemberTypes.Method; + + /// + public abstract ParameterSymbol ReturnParameter { get; } + + /// + public abstract TypeSymbol ReturnType { get; } + + /// + public abstract ICustomAttributeProvider ReturnTypeCustomAttributes { get; } + + /// + public abstract MethodSymbol GetBaseDefinition(); + + /// + public abstract MethodSymbol GetGenericMethodDefinition(); + + /// + public MethodSymbol MakeGenericMethod(IImmutableList typeArguments) => _specTable.GetOrCreateGenericMethodSymbol(typeArguments); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/NameFilter.cs b/src/IKVM.CoreLib/Symbols/NameFilter.cs new file mode 100644 index 0000000000..185de6696a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/NameFilter.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols +{ + + abstract partial class NameFilter + { + + + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/ParameterSymbol.cs new file mode 100644 index 0000000000..8456595dfb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ParameterSymbol.cs @@ -0,0 +1,123 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class ParameterSymbol : ICustomAttributeProvider + { + + readonly ISymbolContext _context; + readonly MemberSymbol _member; + readonly int _position; + + /// + /// Initializes a new instance. + /// + /// + public ParameterSymbol(ISymbolContext context, MemberSymbol member, int position) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _member = member ?? throw new ArgumentNullException(nameof(member)); + _position = position; + } + + public ISymbolContext Context => _context; + + /// + /// Gets the attributes for this parameter. + /// + public abstract ParameterAttributes Attributes { get; } + + /// + /// Gets a value indicating the member in which the parameter is implemented. + /// + public MemberSymbol Member => _member; + + /// + /// Gets the Type of this parameter. + /// + public abstract TypeSymbol ParameterType { get; } + + /// + /// Gets the name of the parameter. + /// + public abstract string? Name { get; } + + /// + /// Gets the zero-based position of the parameter in the formal parameter list. + /// + public int Position => _position; + + /// + /// Gets a value that indicates whether this parameter has a default value. + /// + public bool HasDefaultValue => (Attributes & ParameterAttributes.HasDefault) == ParameterAttributes.HasDefault; + + /// + /// Gets a value indicating the default value if the parameter has a default value. + /// + public abstract object? DefaultValue { get; } + + /// + /// Gets a value indicating whether this is an input parameter. + /// + public bool IsIn => (Attributes & ParameterAttributes.In) == ParameterAttributes.In; + + /// + /// Gets a value indicating whether this is an output parameter. + /// + public bool IsOut => (Attributes & ParameterAttributes.Out) == ParameterAttributes.Out; + + /// + /// Gets a value indicating whether this parameter is optional. + /// + public bool IsOptional => (Attributes & ParameterAttributes.Optional) == ParameterAttributes.Optional; + + /// + /// Gets a value indicating whether this parameter is a locale identifier (lcid). + /// + public bool IsLcid => (Attributes & ParameterAttributes.Lcid) == ParameterAttributes.Lcid; + + /// + /// Gets a value indicating whether this is a Retval parameter. + /// + public bool IsRetval => (Attributes & ParameterAttributes.Retval) == ParameterAttributes.Retval; + + /// + /// Returns true if the symbol is missing. + /// + public abstract bool IsMissing { get; } + + /// + /// Returns true if the symbol contains a missing symbol. + /// + public abstract bool ContainsMissing { get; } + + /// + /// Returns true if the symbol is complete. That is, was created with a builder and completed. + /// + public abstract bool IsComplete { get; } + + /// + public abstract ImmutableList GetOptionalCustomModifiers(); + + /// + public abstract ImmutableList GetRequiredCustomModifiers(); + + /// + public abstract CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false); + + /// + public abstract CustomAttribute[] GetCustomAttributes(bool inherit = false); + + /// + public abstract CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false); + + /// + public abstract bool IsDefined(TypeSymbol attributeType, bool inherit = false); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs new file mode 100644 index 0000000000..eaa223bcb5 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs @@ -0,0 +1,54 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class PointerTypeSymbol : HasElementSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public PointerTypeSymbol(ISymbolContext context, TypeSymbol elementType) : + base(context, elementType) + { + + } + + /// + protected override string NameSuffix => "*"; + + /// + public sealed override TypeAttributes Attributes => TypeAttributes.Public; + + /// + public override TypeSymbol? BaseType => null; + + /// + public sealed override bool IsPointer => true; + + /// + public sealed override int GetArrayRank() + { + throw new NotSupportedException(); + } + + /// + public sealed override ImmutableList GetDeclaredConstructors() + { + return ImmutableList.Empty; + } + + /// + public sealed override ImmutableList GetDeclaredMethods() + { + return ImmutableList.Empty; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/PropertySymbol.cs similarity index 66% rename from src/IKVM.CoreLib/Symbols/IPropertySymbol.cs rename to src/IKVM.CoreLib/Symbols/PropertySymbol.cs index 5f47a277b5..bad5bb9690 100644 --- a/src/IKVM.CoreLib/Symbols/IPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/PropertySymbol.cs @@ -1,119 +1,125 @@ using System.Reflection; -using IKVM.CoreLib.Symbols.Emit; - namespace IKVM.CoreLib.Symbols { - /// - /// Discovers the attributes of a property and provides access to property metadata. - /// - interface IPropertySymbol : IMemberSymbol + abstract class PropertySymbol : MemberSymbol { + /// + /// Initializes a new instance. + /// + /// + /// + public PropertySymbol(ISymbolContext context, TypeSymbol declaringType) : + base(context, declaringType.Module, declaringType) + { + + } + /// /// Gets the attributes for this property. /// - PropertyAttributes Attributes { get; } + public abstract PropertyAttributes Attributes { get; } /// /// Gets the type of this property. /// - ITypeSymbol PropertyType { get; } + public abstract TypeSymbol PropertyType { get; } /// /// Gets a value indicating whether the property can be read. /// - bool CanRead { get; } + public abstract bool CanRead { get; } /// /// Gets a value indicating whether the property can be written to. /// - bool CanWrite { get; } + public abstract bool CanWrite { get; } /// /// Gets a value indicating whether the property is the special name. /// - bool IsSpecialName { get; } - - /// - /// Returns a literal value associated with the property by a compiler. - /// - /// - object? GetRawConstantValue(); + public bool IsSpecialName => (Attributes & PropertyAttributes.SpecialName) != 0; /// /// Gets the get accessor for this property. /// - IMethodSymbol? GetMethod { get; } + public abstract MethodSymbol? GetMethod { get; } /// /// Gets the set accessor for this property. /// - IMethodSymbol? SetMethod { get; } + public abstract MethodSymbol? SetMethod { get; } /// /// Returns an array whose elements reflect the public get and set accessors of the property reflected by the current instance. /// /// - IMethodSymbol[] GetAccessors(); + public abstract MethodSymbol[] GetAccessors(); /// /// Returns an array whose elements reflect the public and, if specified, non-public get and set accessors of the property reflected by the current instance. /// /// /// - IMethodSymbol[] GetAccessors(bool nonPublic); + public abstract MethodSymbol[] GetAccessors(bool nonPublic); /// /// Returns the public get accessor for this property. /// /// - IMethodSymbol? GetGetMethod(); + public abstract MethodSymbol? GetGetMethod(); /// /// When overridden in a derived class, returns the public or non-public get accessor for this property. /// /// /// - IMethodSymbol? GetGetMethod(bool nonPublic); + public abstract MethodSymbol? GetGetMethod(bool nonPublic); /// /// Returns the public set accessor for this property. /// /// - IMethodSymbol? GetSetMethod(); + public abstract MethodSymbol? GetSetMethod(); /// /// When overridden in a derived class, returns the set accessor for this property. /// /// /// - IMethodSymbol? GetSetMethod(bool nonPublic); + public abstract MethodSymbol? GetSetMethod(bool nonPublic); /// /// When overridden in a derived class, returns an array of all the index parameters for the property. /// /// - IParameterSymbol[] GetIndexParameters(); + public abstract ParameterSymbol[] GetIndexParameters(); /// /// Gets the modified type of this property object. /// /// - ITypeSymbol GetModifiedPropertyType(); + public abstract TypeSymbol GetModifiedPropertyType(); + + /// + /// Returns a literal value associated with the property by a compiler. + /// + /// + public abstract object? GetRawConstantValue(); /// /// Returns an array of types representing the optional custom modifiers of the property. /// /// - ITypeSymbol[] GetOptionalCustomModifiers(); + public abstract TypeSymbol[] GetOptionalCustomModifiers(); /// /// Returns an array of types representing the required custom modifiers of the property. /// /// - ITypeSymbol[] GetRequiredCustomModifiers(); + public abstract TypeSymbol[] GetRequiredCustomModifiers(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs new file mode 100644 index 0000000000..81ba5a0ad8 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs @@ -0,0 +1,11 @@ +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionDefinitionTypeSymbol : DefinitionTypeSymbol + { + + + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs new file mode 100644 index 0000000000..c06ec483cb --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs @@ -0,0 +1,56 @@ +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class SZArrayTypeSymbol : HasElementSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public SZArrayTypeSymbol(ISymbolContext context, TypeSymbol elementType) : + base(context, elementType) + { + + } + + /// + protected override string NameSuffix => "[]"; + + /// + public sealed override TypeAttributes Attributes => TypeAttributes.AutoLayout | TypeAttributes.AnsiClass | TypeAttributes.Class | TypeAttributes.Public | TypeAttributes.Sealed | TypeAttributes.Serializable; + + /// + public sealed override bool IsArray => true; + + /// + public sealed override bool IsSZArray => true; + + /// + public sealed override ITypeSymbol? BaseType => Context.ResolveCoreType("System.Array"); + + /// + public sealed override int GetArrayRank() + { + return 1; + } + + /// + public sealed override IImmutableList GetDeclaredConstructors() + { + return ImmutableList.Empty; + } + + /// + public sealed override IImmutableList GetDeclaredMethods() + { + return ImmutableList.Empty; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/TypeSpecTable.cs new file mode 100644 index 0000000000..e6a94c1a2c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSpecTable.cs @@ -0,0 +1,126 @@ +using System; +using System.Collections.Concurrent; +using System.Collections.Immutable; +using System.Threading; + +using IKVM.CoreLib.Collections; +using IKVM.CoreLib.Threading; + +namespace IKVM.CoreLib.Symbols +{ + + struct TypeSpecTable + { + + readonly ISymbolContext _context; + readonly TypeSymbol _elementType; + + IndexRangeDictionary _asArray; + ReaderWriterLockSlim? _asArrayLock; + SZArrayTypeSymbol? _asSZArray; + PointerTypeSymbol? _asPointer; + ByRefTypeSymbol? _asByRef; + ConcurrentDictionary, ConstructedGenericTypeSymbol>? _genericTypeSymbols; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public TypeSpecTable(ISymbolContext context, TypeSymbol elementType) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); + _asArray = new IndexRangeDictionary(); + } + + /// + /// Gets or creates a representing an Array of this type. + /// + /// + /// + /// + public ArrayTypeSymbol GetOrCreateArrayTypeSymbol(int rank) + { + if (_asArrayLock == null) + Interlocked.CompareExchange(ref _asArrayLock, new(), null); + + using (_asArrayLock.CreateUpgradeableReadLock()) + { + if (_asArray[rank] == null) + using (_asArrayLock.CreateWriteLock()) + _asArray[rank] = new ArrayTypeSymbol(_context, _elementType, rank); + + return _asArray[rank] ?? throw new InvalidOperationException(); + } + } + + /// + /// Gets or creates a representing a SZArray of this type. + /// + /// + public SZArrayTypeSymbol GetOrCreateSZArrayTypeSymbol() + { + if (_asSZArray == null) + Interlocked.CompareExchange(ref _asSZArray, new SZArrayTypeSymbol(_context, _elementType), null); + + return _asSZArray; + } + + /// + /// Gets or creates a representing a pointer of this type. + /// + /// + public PointerTypeSymbol GetOrCreatePointerTypeSymbol() + { + if (_asPointer == null) + Interlocked.CompareExchange(ref _asPointer, new PointerTypeSymbol(_context, _elementType), null); + + return _asPointer; + } + + /// + /// Gets or creates a representing a by-ref of this type. + /// + /// + public ByRefTypeSymbol GetOrCreateByRefTypeSymbol() + { + if (_asByRef == null) + Interlocked.CompareExchange(ref _asByRef, new ByRefTypeSymbol(_context, _elementType), null); + + return _asByRef; + } + + /// + /// Gets or creates a representing a specialized generic of this type. + /// + /// + /// + public ConstructedGenericTypeSymbol GetOrCreateGenericTypeSymbol(IImmutableList genericTypeArguments) + { + if (genericTypeArguments is null) + throw new ArgumentNullException(nameof(genericTypeArguments)); + + if (_elementType.IsGenericTypeDefinition == false) + throw new InvalidOperationException(); + + if (_genericTypeSymbols == null) + Interlocked.CompareExchange(ref _genericTypeSymbols, new(TypeSymbolListEqualityComparer.Instance), null); + + return _genericTypeSymbols.GetOrAdd(genericTypeArguments, CreateGenericTypeSymbol); + } + + /// + /// Creates a new representing a specialized generic of this type. + /// + /// + /// + readonly ConstructedGenericTypeSymbol CreateGenericTypeSymbol(IImmutableList genericTypeArguments) + { + return new ConstructedGenericTypeSymbol(_context, _elementType, genericTypeArguments); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbol.cs b/src/IKVM.CoreLib/Symbols/TypeSymbol.cs new file mode 100644 index 0000000000..ea7e51f45a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeSymbol.cs @@ -0,0 +1,844 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class TypeSymbol : MemberSymbol + { + + const BindingFlags DefaultLookup = BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public; + const BindingFlags DeclaredOnlyLookup = BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static | BindingFlags.DeclaredOnly; + + TypeSpecTable _typeSpecTable; + + string? _assemblyQualifiedName; + + /// + /// Initializes a new instance. + /// + /// + public TypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + base(context, module, declaringType) + { + _typeSpecTable = new TypeSpecTable(Context, this); + } + + /// + /// Gets the attributes associated with the . + /// + public abstract TypeAttributes Attributes { get; } + + /// + /// Gets a that represents the declaring method, if the current represents a type parameter of a generic method. + /// + public abstract MethodBaseSymbol? DeclaringMethod { get; } + + /// + /// Gets the assembly-qualified name of the type, which includes the name of the assembly from which this object was loaded. + /// + public string? AssemblyQualifiedName => _assemblyQualifiedName ??= ComputeAssemblyQualifiedName(); + + /// + /// Computes the value of . + /// + /// + string? ComputeAssemblyQualifiedName() + { + var fullName = FullName; + if (fullName == null) // open types return null for FullName by design. + return null; + + var assemblyName = Assembly.FullName; + return fullName + ", " + assemblyName; + } + + /// + /// Gets the fully qualified name of the type, including its namespace but not its assembly. + /// + public abstract string? FullName { get; } + + /// + /// Gets the namespace of the . + /// + public abstract string? Namespace { get; } + + /// + /// Gets the underlying type code of the specified Type. + /// + public abstract TypeCode TypeCode { get; } + + /// + public sealed override MemberTypes MemberType => IsPublic || IsNotPublic ? MemberTypes.TypeInfo : MemberTypes.NestedType; + + /// + /// Gets the type from which the current directly inherits. + /// + public abstract TypeSymbol? BaseType { get; } + + /// + /// Gets a value indicating whether the current object has type parameters that have not been replaced by specific types. + /// + public abstract bool ContainsGenericParameters { get; } + + /// + /// Gets a combination of flags that describe the covariance and special constraints of the current generic type parameter. + /// + public abstract GenericParameterAttributes GenericParameterAttributes { get; } + + /// + /// Gets the position of the type parameter in the type parameter list of the generic type or method that declared the parameter, when the object represents a type parameter of a generic type or a generic method. + /// + public abstract int GenericParameterPosition { get; } + + /// + /// Gets an array of the generic type arguments for this type. + /// + public abstract ImmutableList GenericTypeArguments { get; } + + /// + /// Gets a value that indicates whether the type is a type definition. + /// + public abstract bool IsTypeDefinition { get; } + + /// + /// Gets a value indicating whether the current Type represents a generic type definition, from which other generic types can be constructed. + /// + public abstract bool IsGenericTypeDefinition { get; } + + /// + /// Gets a value that indicates whether this object represents a constructed generic type. You can create instances of a constructed generic type. + /// + public abstract bool IsConstructedGenericType { get; } + + /// + /// Gets a value indicating whether the current type is a generic type. + /// + public bool IsGenericType => IsConstructedGenericType || IsGenericTypeDefinition; + + /// + /// Gets a value indicating whether the current represents a type parameter in the definition of a generic type or method. + /// + public abstract bool IsGenericParameter { get; } + + /// + /// Gets a value indicating whether the fields of the current type are laid out automatically by the common language runtime. + /// + public bool IsAutoLayout => (Attributes & TypeAttributes.LayoutMask) == TypeAttributes.AutoLayout; + + /// + /// Gets a value indicating whether the fields of the current type are laid out at explicitly specified offsets. + /// + public bool IsExplicitLayout => (Attributes & TypeAttributes.LayoutMask) == TypeAttributes.ExplicitLayout; + + /// + /// Gets a value indicating whether the fields of the current type are laid out sequentially, in the order that they were defined or emitted to the metadata. + /// + public bool IsLayoutSequential => (Attributes & TypeAttributes.LayoutMask) == TypeAttributes.SequentialLayout; + + /// + /// Gets a value indicating whether the current encompasses or refers to another type; that is, whether the current is an array, a pointer, or is passed by reference. + /// + public abstract bool HasElementType { get; } + + /// + /// Gets a value indicating whether the is a class or a delegate; that is, not a value type or interface. + /// + public bool IsClass => (Attributes & TypeAttributes.ClassSemanticsMask) == TypeAttributes.Class && !IsValueType; + + /// + /// Gets a value indicating whether the is a value type. + /// + public bool IsValueType => IsSubclassOf(Context.ResolveCoreType("System.ValueType")); + + /// + /// Gets a value indicating whether the is an interface; that is, not a class or a value type. + /// + public bool IsInterface => (Attributes & TypeAttributes.Interface) != 0; + + /// + /// Gets a value indicating whether the is one of the primitive types. + /// + public abstract bool IsPrimitive { get; } + + /// + /// Gets a value that indicates whether the type is an array type that can represent only a single-dimensional array with a zero lower bound. + /// + public abstract bool IsSZArray { get; } + + /// + /// Gets a value that indicates whether the type is an array. + /// + public abstract bool IsArray { get; } + + /// + /// Gets a value indicating whether the current represents an enumeration. + /// + public abstract bool IsEnum { get; } + + /// + /// Gets a value indicating whether the is a pointer. + /// + public abstract bool IsPointer { get; } + + /// + /// Gets a value that indicates whether the current is an unmanaged function pointer. + /// + public abstract bool IsFunctionPointer { get; } + + /// + /// Gets a value that indicates whether the current is an unmanaged function pointer. + /// + public abstract bool IsUnmanagedFunctionPointer { get; } + + /// + /// Gets a value indicating whether the is passed by reference. + /// + public abstract bool IsByRef { get; } + + /// + /// Gets a value indicating whether the is abstract and must be overridden. + /// + public bool IsAbstract => (Attributes & TypeAttributes.Abstract) == TypeAttributes.Abstract; + + /// + /// Gets a value indicating whether the is declared sealed. + /// + public bool IsSealed => (Attributes & TypeAttributes.Sealed) == TypeAttributes.Sealed; + + /// + /// Gets a value indicating whether the can be accessed by code outside the assembly. + /// + public bool IsVisible => ComputeIsVisible(); + + /// + /// Computes the value for . + /// + /// + bool ComputeIsVisible() + { + if (IsGenericParameter) + return true; + + if (HasElementType) + return GetElementType()!.IsVisible; + + var type = (TypeSymbol)this; + while (type.IsNested) + { + if (!type.IsNestedPublic) + return false; + + // this should be null for non-nested types. + type = type.DeclaringType!; + } + + // Now "type" should be a top level type + if (!type.IsPublic) + return false; + + if (IsGenericType && !IsGenericTypeDefinition) + { + foreach (var t in GetGenericArguments()) + { + if (!t.IsVisible) + return false; + } + } + + return true; + } + + /// + /// Gets a value indicating whether the is declared public. + /// + public bool IsPublic => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.Public; + + /// + /// Gets a value indicating whether the is not declared public. + /// + public bool IsNotPublic => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NotPublic; + + /// + /// Gets a value indicating whether the current object represents a type whose definition is nested inside the definition of another type. + /// + public bool IsNested => DeclaringType != null; + + /// + /// Gets a value indicating whether the is nested and visible only within its own assembly. + /// + public bool IsNestedAssembly => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedAssembly; + + /// + /// Gets a value indicating whether the is nested and visible only to classes that belong to both its own family and its own assembly. + /// + public bool IsNestedFamANDAssem => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamANDAssem; + + /// + /// Gets a value indicating whether the is nested and visible only within its own family. + /// + public bool IsNestedFamily => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamily; + + /// + /// Gets a value indicating whether the is nested and visible only to classes that belong to either its own family or to its own assembly. + /// + public bool IsNestedFamORAssem => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamORAssem; + + /// + /// Gets a value indicating whether the is nested and declared private. + /// + public bool IsNestedPrivate => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPrivate; + + /// + /// Gets a value indicating whether a class is nested and declared public. + /// + public bool IsNestedPublic => (Attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPublic; + + /// + /// Gets a value indicating whether the is binary serializable. + /// + public bool IsSerializable => (Attributes & TypeAttributes.Serializable) != 0; + + /// + /// Gets a value that indicates whether the type is a signature type. + /// + public abstract bool IsSignatureType { get; } + + /// + /// Gets a value indicating whether the type has a name that requires special handling. + /// + public bool IsSpecialName => (Attributes & TypeAttributes.SpecialName) == TypeAttributes.SpecialName; + + /// + /// Gets the initializer for the type. + /// + public abstract ConstructorSymbol? TypeInitializer { get; } + + /// + /// Gets the number of dimensions in an array. + /// + /// + public abstract int GetArrayRank(); + + /// + /// Returns all the declared constructors of the current . + /// + /// + public abstract ImmutableList GetDeclaredConstructors(); + + /// + /// Searches for a public instance constructor whose parameters match the types in the specified array. + /// + /// + /// + public ConstructorSymbol? GetConstructor(ImmutableList? types) => GetConstructor(BindingFlags.Public | BindingFlags.Instance, types); + + /// + /// Searches for a constructor whose parameters match the specified argument types, using the specified binding constraints. + /// + /// + /// + /// + public abstract ConstructorSymbol? GetConstructor(BindingFlags bindingFlags, ImmutableList? types); + + /// + /// Returns all the public constructors defined for the current . + /// + /// + public ImmutableList GetConstructors() => GetConstructors(BindingFlags.Public | BindingFlags.Instance); + + /// + /// When overridden in a derived class, searches for the constructors defined for the current , using the specified BindingFlags. + /// + /// + /// + public abstract ImmutableList GetConstructors(BindingFlags bindingFlags); + + /// + /// Searches for the members defined for the current whose DefaultMemberAttribute is set. + /// + /// + public abstract ImmutableList GetDefaultMembers(); + + /// + /// When overridden in a derived class, returns the of the object encompassed or referred to by the current array, pointer or reference type. + /// + /// + public abstract TypeSymbol? GetElementType(); + + /// + /// Returns the name of the constant that has the specified value, for the current enumeration type. + /// + /// + /// + public abstract string? GetEnumName(object value); + + /// + /// Returns the names of the members of the current enumeration type. + /// + /// + public abstract ImmutableList GetEnumNames(); + + /// + /// Returns the underlying type of the current enumeration type. + /// + /// + public abstract TypeSymbol GetEnumUnderlyingType(); + + /// + /// Returns all the declared events of the current . + /// + /// + public abstract ImmutableList GetDeclaredEvents(); + + /// + /// Returns the object representing the specified public event. + /// + /// + /// + public EventSymbol? GetEvent(string name) => GetEvent(name, DefaultLookup); + + /// + /// When overridden in a derived class, returns the object representing the specified event, using the specified binding constraints. + /// + /// + /// + /// + public abstract EventSymbol? GetEvent(string name, BindingFlags bindingFlags); + + /// + /// Returns all the public events that are declared or inherited by the current . + /// + /// + public ImmutableList GetEvents() => GetEvents(DefaultLookup); + + /// + /// When overridden in a derived class, searches for events that are declared or inherited by the current , using the specified binding constraints. + /// + /// + /// + public abstract ImmutableList GetEvents(BindingFlags bindingFlags); + + /// + /// Returns all the declared fields of the current . + /// + /// + public abstract ImmutableList GetDeclaredFields(); + + /// + /// Searches for the public field with the specified name. + /// + /// + /// + public FieldSymbol? GetField(string name) => GetField(name, DefaultLookup); + + /// + /// Searches for the specified field, using the specified binding constraints. + /// + /// + /// + /// + public abstract FieldSymbol? GetField(string name, BindingFlags bindingFlags); + + /// + /// Returns all the public fields of the current . + /// + /// + public ImmutableList GetFields() => GetFields(DefaultLookup); + + /// + /// When overridden in a derived class, searches for the fields defined for the current , using the specified binding constraints. + /// + /// + /// + public abstract ImmutableList GetFields(BindingFlags bindingFlags); + + /// + /// Returns an array of objects that represent the type arguments of a closed generic type or the type parameters of a generic type definition. + /// + /// + public abstract ImmutableList GetGenericArguments(); + + /// + /// Returns an array of objects that represent the constraints on the current generic type parameter. + /// + /// + public abstract ImmutableList GetGenericParameterConstraints(); + + /// + /// Returns a object that represents a generic type definition from which the current generic type can be constructed. + /// + /// + public abstract TypeSymbol GetGenericTypeDefinition(); + + /// + /// Searches for the interface with the specified name. + /// + /// + /// + public TypeSymbol? GetInterface(string name) => GetInterface(name, false); + + /// + /// When overridden in a derived class, searches for the specified interface, specifying whether to do a case-insensitive search for the interface name. + /// + /// + /// + /// + public abstract TypeSymbol? GetInterface(string name, bool ignoreCase); + + /// + /// When overridden in a derived class, gets all the interfaces implemented or if specified,inherited by the current . + /// + /// + public abstract ImmutableList GetInterfaces(bool inherit = true); + + /// + /// Returns an interface mapping for the specified interface type. + /// + /// + /// + public abstract InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType); + + /// + /// Returns all the declared methods of the current . + /// + /// + public abstract ImmutableList GetDeclaredMethods(); + + /// + /// Searches for the public method with the specified name. + /// + /// + /// + public MethodSymbol? GetMethod(string name) => GetMethod(name, DefaultLookup); + + /// + /// Searches for the specified public method whose parameters match the specified argument types. + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, ImmutableList? types) => GetMethod(name, DefaultLookup, types); + + /// + /// Searches for the specified method, using the specified binding constraints. + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, BindingFlags bindingFlags) => GetMethod(name, bindingFlags, null); + + /// + /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints. + /// + /// + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, bindingAttr, CallingConventions.Any, types, modifiers); + + /// + /// Searches for the specified method whose parameters match the specified argument types, using the specified binding constraints. + /// + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, BindingFlags bindingFlags, ImmutableList? types) => GetMethod(name, bindingFlags, CallingConventions.Any, types, null); + + /// + /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints and the specified calling convention. + /// + /// + /// + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, 0, bindingFlags, callConvention, types, modifiers); + + /// + /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints. + /// + /// + /// + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, genericParameterCount, bindingFlags, CallingConventions.Any, types, modifiers); + + /// + /// Searches for the specified public method whose parameters match the specified generic parameter count, argument types and modifiers. + /// + /// + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, int genericParameterCount, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, genericParameterCount, DefaultLookup, CallingConventions.Any, types, modifiers); + + /// + /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints and the specified calling convention. + /// + /// + /// + /// + /// + /// + /// + /// + public abstract MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableList? types, ImmutableList? modifiers); + + /// + /// Returns all the public methods of the current . + /// + /// + public ImmutableList GetMethods() => GetMethods(DefaultLookup); + + /// + /// When overridden in a derived class, searches for the methods defined for the current , using the specified binding constraints. + /// + /// + /// + public abstract ImmutableList GetMethods(BindingFlags bindingFlags); + + /// + /// Searches for the public nested type with the specified name. + /// + /// + /// + public TypeSymbol? GetNestedType(string name) => GetNestedType(name, DefaultLookup); + + /// + /// When overridden in a derived class, searches for the specified nested type, using the specified binding constraints. + /// + /// + /// + /// + public abstract TypeSymbol? GetNestedType(string name, BindingFlags bindingFlags); + + /// + /// Returns the public types nested in the current . + /// + /// + public ImmutableList GetNestedTypes() => GetNestedTypes(DefaultLookup); + + /// + /// When overridden in a derived class, searches for the types nested in the current , using the specified binding constraints. + /// + /// + /// + public abstract ImmutableList GetNestedTypes(BindingFlags bindingFlags); + + /// + /// Returns all the declared properties of the current . + /// + /// + public abstract ImmutableList GetDeclaredProperties(); + + /// + /// Searches for the public property with the specified name. + /// + /// + /// + public PropertySymbol? GetProperty(string name) => GetProperty(name, DefaultLookup); + + /// + /// Searches for the specified property, using the specified binding constraints. + /// + /// + /// + /// + public abstract PropertySymbol? GetProperty(string name, BindingFlags bindingFlags); + + /// + /// Searches for the specified public property whose parameters match the specified argument types. + /// + /// + /// + /// + public PropertySymbol? GetProperty(string name, ImmutableList? types) => GetProperty(name, null, types); + + /// + /// Searches for the public property with the specified name and return type. + /// + /// + /// + /// + public PropertySymbol? GetProperty(string name, TypeSymbol? returnType) => GetProperty(name, returnType, null); + + /// + /// Searches for the specified public property whose parameters match the specified argument types. + /// + /// + /// + /// + /// + public abstract PropertySymbol? GetProperty(string name, TypeSymbol? returnType, ImmutableList? types); + + /// + /// Returns all the public properties of the current . + /// + /// + public ImmutableList GetProperties() => GetProperties(DefaultLookup); + + /// + /// When overridden in a derived class, searches for the properties of the current , using the specified binding constraints. + /// + /// + /// + public abstract ImmutableList GetProperties(BindingFlags bindingFlags); + + /// + /// Determines whether an instance of a specified type c can be assigned to a variable of the current type. + /// + /// + /// + public bool IsAssignableFrom(TypeSymbol? c) + { + if (c == null) + return false; + + if (this == c) + return true; + + // If c is a subclass of this class, then c can be cast to this type. + if (c.IsSubclassOf(this)) + return true; + + if (IsInterface) + { + return c.ImplementInterface(this); + } + else if (IsGenericParameter) + { + var constraints = GetGenericParameterConstraints(); + for (int i = 0; i < constraints.Count; i++) + if (!constraints[i].IsAssignableFrom(c)) + return false; + + return true; + } + + return false; + } + + /// + /// Determines whether an instance of a specified type c is an interface implemented by the current type. + /// + /// + /// + bool ImplementInterface(TypeSymbol? interfaceType) + { + var t = this; + + while (t != null) + { + var interfaces = t.GetInterfaces(); + if (interfaces != null) + { + for (int i = 0; i < interfaces.Count; i++) + { + // Interfaces don't derive from other interfaces, they implement them. + // So instead of IsSubclassOf, we should use ImplementInterface instead. + if (interfaces[i] == interfaceType || (interfaces[i] != null && interfaces[i].ImplementInterface(interfaceType))) + return true; + } + } + + t = t.BaseType; + } + + return false; + } + + /// + /// Determines whether the current derives from the specified . + /// + /// + /// + public bool IsSubclassOf(TypeSymbol c) + { + var p = (TypeSymbol?)this; + if (p == c) + return false; + + while (p != null) + { + if (p == c) + return true; + + p = p.BaseType; + } + + return false; + } + + /// + /// Returns a value that indicates whether the specified value exists in the current enumeration type. + /// + /// + /// + public abstract bool IsEnumDefined(object value); + + /// + /// Returns a object representing a one-dimensional array of the current type, with a lower bound of zero. + /// + /// + public TypeSymbol MakeArrayType() => _typeSpecTable.GetOrCreateSZArrayTypeSymbol(); + + /// + /// Returns a object representing an array of the current type, with the specified number of dimensions. + /// + /// + /// + public TypeSymbol MakeArrayType(int rank) => _typeSpecTable.GetOrCreateArrayTypeSymbol(rank); + + /// + /// Returns a object that represents the current type when passed as a ref parameter (ByRef parameter in Visual Basic). + /// + /// + public TypeSymbol MakeByRefType() => _typeSpecTable.GetOrCreateByRefTypeSymbol(); + + /// + /// Substitutes the elements of an array of types for the type parameters of the current generic type definition and returns a object representing the resulting constructed type. + /// + /// + /// + public TypeSymbol MakeGenericType(ImmutableList typeArguments) => _typeSpecTable.GetOrCreateGenericTypeSymbol(typeArguments); + + /// + /// Returns a object that represents a pointer to the current type. + /// + /// + public TypeSymbol MakePointerType() => _typeSpecTable.GetOrCreatePointerTypeSymbol(); + + /// + /// Specializes the current given the specified generic arguments. + /// + /// + /// + internal virtual TypeSymbol Specialize(GenericContext context) + { + if (ContainsGenericParameters == false) + return this; + + var args = GetGenericArguments(); + for (int i = 0; i < args.Count; i++) + if (args[i].ContainsGenericParameters) + args = args.SetItem(i, args[i].Specialize(context)); + + return MakeGenericType(args); + } + + ImmutableList Query() where T : MemberSymbol + { + + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs index f4a39c701b..33de80afef 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs @@ -6,12 +6,13 @@ namespace IKVM.CoreLib.Symbols /// /// Compares two ReflectionTypeSymbol array instances for equality. /// - class TypeSymbolListEqualityComparer : IEqualityComparer + class TypeSymbolListEqualityComparer : IEqualityComparer> { public static readonly TypeSymbolListEqualityComparer Instance = new(); - public bool Equals(ITypeSymbol[]? x, ITypeSymbol[]? y) + /// + public bool Equals(IReadOnlyList? x, IReadOnlyList? y) { if (x == y) return true; @@ -19,21 +20,22 @@ public bool Equals(ITypeSymbol[]? x, ITypeSymbol[]? y) if (x == null || y == null) return false; - if (x.Length != y.Length) + if (x.Count != y.Count) return false; - for (int i = 0; i < x.Length; i++) + for (int i = 0; i < x.Count; i++) if (x[i] != y[i]) return false; return true; } - public int GetHashCode(ITypeSymbol[] obj) + /// + public int GetHashCode(IReadOnlyList obj) { int result = 17; - for (int i = 0; i < obj.Length; i++) + for (int i = 0; i < obj.Count; i++) { unchecked { From f0ba11df11c0580befcc03e35b54b3a029d21631 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Thu, 14 Nov 2024 17:24:42 -0600 Subject: [PATCH 53/59] New stuff. --- .../IkvmReflectionSymbolTests.cs | 501 -------- .../ReflectionAssemblySymbolTests.cs | 98 ++ .../Reflection/ReflectionModuleSymbolTests.cs | 82 ++ .../Reflection/ReflectionSymbolTests.cs | 514 -------- .../Reflection/ReflectionTypeSymbolTests.cs | 358 ++++++ src/IKVM.CoreLib/IKVM.CoreLib.csproj | 27 + .../Reflection/ReflectionExtensions.cs | 16 + src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs | 86 +- src/IKVM.CoreLib/Symbols/AssemblySymbol.cs | 209 ++++ src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs | 32 +- .../ConstructedGenericConstructorSymbol.cs | 35 +- .../Symbols/ConstructedGenericEventSymbol.cs | 116 +- .../Symbols/ConstructedGenericFieldSymbol.cs | 86 +- .../Symbols/ConstructedGenericMethodSymbol.cs | 104 +- .../ConstructedGenericParameterSymbol.cs | 53 +- .../ConstructedGenericPropertySymbol.cs | 136 +- .../Symbols/ConstructedGenericTypeSymbol.cs | 376 +++--- src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs | 2 +- src/IKVM.CoreLib/Symbols/CustomAttribute.cs | 63 +- .../Symbols/CustomAttributeImpl.cs | 143 +++ .../Symbols/CustomAttributeNamedArgument.cs | 25 +- .../Symbols/CustomAttributeTypedArgument.cs | 71 +- src/IKVM.CoreLib/Symbols/DefaultBinder.cs | 726 +++++++++++ .../Symbols/DefinitionConstructorSymbol.cs | 5 +- .../Symbols/DefinitionEventSymbol.cs | 5 +- .../Symbols/DefinitionFieldSymbol.cs | 2 +- .../Symbols/DefinitionMethodSymbol.cs | 2 +- .../Symbols/DefinitionParameterSymbol.cs | 3 +- .../Symbols/DefinitionPropertySymbol.cs | 5 +- .../Symbols/DefinitionTypeSymbol.cs | 75 +- .../Symbols/Emit/AssemblySymbolBuilder.cs | 110 ++ .../Symbols/Emit/ConstructorSymbolBuilder.cs | 69 + .../Symbols/Emit/EventSymbolBuilder.cs | 72 ++ .../Symbols/Emit/FieldSymbolBuilder.cs | 77 ++ ...GenericMethodParameterTypeSymbolBuilder.cs | 49 + .../GenericTypeParameterSymbolBuilderBase.cs | 606 --------- .../GenericTypeParameterTypeSymbolBuilder.cs | 49 + .../Symbols/Emit/IAssemblySymbolBuilder.cs | 86 -- .../Symbols/Emit/IConstructorSymbolBuilder.cs | 11 - .../Emit/ICustomAttributeProviderBuilder.cs | 15 - .../Symbols/Emit/IEventSymbolBuilder.cs | 33 - .../Symbols/Emit/IFieldSymbolBuilder.cs | 21 - .../IGenericTypeParameterSymbolBuilder.cs | 28 - src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs | 31 +- .../Symbols/Emit/ILocalBuilder.cs | 2 +- .../Symbols/Emit/IMemberSymbolBuilder.cs | 11 - .../Symbols/Emit/IMethodBaseSymbolBuilder.cs | 39 - .../Symbols/Emit/IMethodSymbolBuilder.cs | 39 - .../Symbols/Emit/IParameterSymbolBuilder.cs | 15 - .../Symbols/Emit/IPropertySymbolBuilder.cs | 33 - .../Symbols/Emit/ISignatureHelper.cs | 6 - .../Symbols/Emit/ISymbolBuilder.cs | 26 - .../Symbols/Emit/ITypeSymbolBuilder.cs | 331 ----- .../Symbols/Emit/MethodSymbolBuilder.cs | 110 ++ ...ymbolBuilder.cs => ModuleSymbolBuilder.cs} | 178 ++- .../Symbols/Emit/PropertySymbolBuilder.cs | 138 ++ .../Symbols/Emit/TypeSymbolBuilder.cs | 602 +++++++++ .../Symbols/Emit/TypeSymbolBuilderBase.cs | 1111 ----------------- src/IKVM.CoreLib/Symbols/EventSymbol.cs | 31 +- src/IKVM.CoreLib/Symbols/FieldSymbol.cs | 6 +- src/IKVM.CoreLib/Symbols/GenericContext.cs | 6 +- .../GenericMethodParameterTypeSymbol.cs | 19 +- .../Symbols/GenericParameterTypeSymbol.cs | 119 +- .../Symbols/GenericTypeParameterTypeSymbol.cs | 23 +- src/IKVM.CoreLib/Symbols/HasElementSymbol.cs | 45 +- src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs | 145 --- .../Symbols/ICustomAttributeProvider.cs | 11 +- .../ICustomAttributeProviderInternal.cs | 26 + src/IKVM.CoreLib/Symbols/IModuleSymbol.cs | 226 ---- src/IKVM.CoreLib/Symbols/ISymbol.cs | 27 - src/IKVM.CoreLib/Symbols/ISymbolContext.cs | 13 +- src/IKVM.CoreLib/Symbols/ISymbolResolver.cs | 2 +- src/IKVM.CoreLib/Symbols/InterfaceMapping.cs | 10 +- .../Symbols/ManifestResourceInfo.cs | 4 +- src/IKVM.CoreLib/Symbols/MemberQuery.cs | 201 +++ src/IKVM.CoreLib/Symbols/MemberSymbol.cs | 52 +- .../Symbols/MemberSymbolPolicy.cs | 266 ++++ src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs | 11 +- src/IKVM.CoreLib/Symbols/MethodSpecTable.cs | 18 +- src/IKVM.CoreLib/Symbols/MethodSymbol.cs | 34 +- .../Symbols/ModuleFieldSymbolPolicy.cs | 44 + .../Symbols/ModuleMethodSymbolPolicy.cs | 68 + src/IKVM.CoreLib/Symbols/ModuleSymbol.cs | 242 ++++ .../Symbols/ModuleTypeSymbolPolicy.cs | 57 + src/IKVM.CoreLib/Symbols/ParameterSymbol.cs | 48 +- src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs | 28 +- src/IKVM.CoreLib/Symbols/PropertySymbol.cs | 26 +- .../Emit/IReflectionAssemblySymbolBuilder.cs | 25 - .../IReflectionConstructorSymbolBuilder.cs | 18 - ...eflectionCustomAttributeProviderBuilder.cs | 13 - .../Emit/IReflectionEventSymbolBuilder.cs | 18 - .../Emit/IReflectionFieldSymbolBuilder.cs | 15 - ...ectionGenericTypeParameterSymbolBuilder.cs | 24 - .../Emit/IReflectionMemberSymbolBuilder.cs | 22 - .../IReflectionMethodBaseSymbolBuilder.cs | 13 - .../Emit/IReflectionMethodSymbolBuilder.cs | 18 - .../Emit/IReflectionModuleSymbolBuilder.cs | 18 - .../Emit/IReflectionParameterSymbolBuilder.cs | 24 - .../Emit/IReflectionPropertySymbolBuilder.cs | 18 - .../Emit/IReflectionSymbolBuilder.cs | 14 - .../Emit/IReflectionTypeSymbolBuilder.cs | 18 - ...ectionGenericTypeParameterSymbolBuilder.cs | 2 +- .../Reflection/IReflectionAssemblySymbol.cs | 28 - .../IReflectionConstructorSymbol.cs | 21 - .../Reflection/IReflectionEventSymbol.cs | 22 - .../Reflection/IReflectionFieldSymbol.cs | 21 - .../Reflection/IReflectionMemberSymbol.cs | 31 - .../Reflection/IReflectionMethodBaseSymbol.cs | 38 - .../Reflection/IReflectionMethodSymbol.cs | 46 - .../Reflection/IReflectionModuleSymbol.cs | 145 --- .../Reflection/IReflectionParameterSymbol.cs | 31 - .../Reflection/IReflectionPropertySymbol.cs | 38 - .../Symbols/Reflection/IReflectionSymbol.cs | 352 ------ .../Reflection/IReflectionTypeSymbol.cs | 150 --- .../Reflection/ReflectionArrayTypeSymbol.cs | 31 - .../Reflection/ReflectionAssemblySymbol.cs | 155 +-- .../Reflection/ReflectionByRefTypeSymbol.cs | 29 - .../Reflection/ReflectionConstructorSymbol.cs | 78 +- .../ReflectionDefinitionTypeSymbol.cs | 11 - .../Reflection/ReflectionEventSymbol.cs | 119 +- .../Reflection/ReflectionEventTable.cs | 95 -- .../Reflection/ReflectionFieldSymbol.cs | 115 +- .../Reflection/ReflectionFieldTable.cs | 84 -- ...eflectionGenericInstantiationTypeSymbol.cs | 305 ----- ...lectionGenericMethodParameterTypeSymbol.cs | 62 + .../ReflectionGenericTypeParameterSymbol.cs | 699 ----------- .../ReflectionGenericTypeParameterTable.cs | 78 -- ...eflectionGenericTypeParameterTypeSymbol.cs | 61 + .../Reflection/ReflectionMemberSymbol.cs | 238 ---- .../Reflection/ReflectionMethodBaseSymbol.cs | 135 -- .../Reflection/ReflectionMethodSpecTable.cs | 64 - .../Reflection/ReflectionMethodSymbol.cs | 206 ++- .../Reflection/ReflectionMethodTable.cs | 141 --- .../Reflection/ReflectionModuleSymbol.cs | 395 +----- .../Reflection/ReflectionModuleTable.cs | 20 +- .../Reflection/ReflectionParameterSpecInfo.cs | 51 - .../Reflection/ReflectionParameterSymbol.cs | 124 +- .../Reflection/ReflectionParameterTable.cs | 98 -- .../Reflection/ReflectionPointerTypeSymbol.cs | 29 - .../Reflection/ReflectionPropertySymbol.cs | 164 +-- .../Reflection/ReflectionPropertyTable.cs | 81 -- .../Reflection/ReflectionSZArrayTypeSymbol.cs | 29 - .../Symbols/Reflection/ReflectionSymbol.cs | 589 --------- .../Reflection/ReflectionSymbolContext.cs | 475 +++---- .../Reflection/ReflectionSymbolExtensions.cs | 11 - .../Reflection/ReflectionTypeDefSymbol.cs | 46 - .../Reflection/ReflectionTypeSpecSymbol.cs | 33 - .../Reflection/ReflectionTypeSpecTable.cs | 128 -- .../Reflection/ReflectionTypeSymbol.cs | 239 ++++ .../Reflection/ReflectionTypeSymbolBase.cs | 695 ----------- .../Symbols/Reflection/ReflectionTypeTable.cs | 75 -- .../Symbols/Reflection/ReflectionUtil.cs | 547 ++------ src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs | 71 +- src/IKVM.CoreLib/Symbols/Symbol.cs | 35 + src/IKVM.CoreLib/Symbols/SymbolContext.cs | 41 + src/IKVM.CoreLib/Symbols/SymbolUtil.cs | 154 +-- .../Symbols/SyntheticConstructorSymbol.cs | 109 ++ .../Symbols/SyntheticMethodSymbol.cs | 140 +++ .../Symbols/SyntheticParameterSymbol.cs | 73 ++ .../Symbols/TypeConstructorSymbolPolicy.cs | 53 + .../Symbols/TypeEventSymbolPolicy.cs | 79 ++ .../Symbols/TypeFieldSymbolPolicy.cs | 44 + .../Symbols/TypeMethodSymbolPolicy.cs | 65 + .../Symbols/TypePropertySymbolPolicy.cs | 87 ++ src/IKVM.CoreLib/Symbols/TypeSpecTable.cs | 17 +- src/IKVM.CoreLib/Symbols/TypeSymbol.cs | 386 ++++-- .../Symbols/TypeSymbolExtensions.cs | 2 +- .../Symbols/TypeSymbolListEqualityComparer.cs | 38 +- src/IKVM.CoreLib/Symbols/TypeSymbolName.cs | 25 +- .../Symbols/TypeTypeSymbolPolicy.cs | 57 + src/IKVM.Runtime/Annotation.cs | 2 - 171 files changed, 7547 insertions(+), 11311 deletions(-) delete mode 100644 src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs create mode 100644 src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionAssemblySymbolTests.cs create mode 100644 src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionModuleSymbolTests.cs delete mode 100644 src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs create mode 100644 src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionTypeSymbolTests.cs create mode 100644 src/IKVM.CoreLib/Symbols/AssemblySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs create mode 100644 src/IKVM.CoreLib/Symbols/DefaultBinder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/MethodSymbolBuilder.cs rename src/IKVM.CoreLib/Symbols/Emit/{IModuleSymbolBuilder.cs => ModuleSymbolBuilder.cs} (60%) create mode 100644 src/IKVM.CoreLib/Symbols/Emit/PropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ICustomAttributeProviderInternal.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IModuleSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/ISymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/MemberQuery.cs create mode 100644 src/IKVM.CoreLib/Symbols/MemberSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/ModuleFieldSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/ModuleMethodSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/ModuleSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/ModuleTypeSymbolPolicy.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericInstantiationTypeSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericMethodParameterTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeDefSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Symbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/SymbolContext.cs create mode 100644 src/IKVM.CoreLib/Symbols/SyntheticConstructorSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/SyntheticMethodSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/SyntheticParameterSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeConstructorSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeEventSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeFieldSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeMethodSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypePropertySymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeTypeSymbolPolicy.cs diff --git a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs deleted file mode 100644 index 792c054a3c..0000000000 --- a/src/IKVM.CoreLib.Tests/Symbols/IkvmReflection/IkvmReflectionSymbolTests.cs +++ /dev/null @@ -1,501 +0,0 @@ -using System; -using System.IO; -using System.Linq; - -using FluentAssertions; - -using IKVM.CoreLib.Symbols; -using IKVM.CoreLib.Symbols.IkvmReflection; -using IKVM.CoreLib.Symbols.IkvmReflection.Emit; -using IKVM.Reflection; -using IKVM.Reflection.Emit; - -using Microsoft.VisualStudio.TestPlatform.PlatformAbstractions; -using Microsoft.VisualStudio.TestTools.UnitTesting; - -namespace IKVM.CoreLib.Tests.Symbols.IkvmReflection -{ - - [TestClass] - public class IkvmReflectionSymbolTests - { - - class Foo - { - - T? field; - - bool Method(int p1) => true; - - } - - Universe? universe; - Assembly? coreAssembly; - Assembly? thisAssembly; - - [TestInitialize] - public void Setup() - { - universe = new Universe(typeof(object).Assembly.GetName().Name); - universe.AssemblyResolve += Universe_AssemblyResolve; - coreAssembly = universe.LoadFile(typeof(object).Assembly.GetAssemblyLocation()); - thisAssembly = universe.LoadFile(typeof(IkvmReflectionSymbolTests).Assembly.GetAssemblyLocation()); - } - - /// - /// Attempt to load assembly from system. - /// - /// - /// - /// - Assembly? Universe_AssemblyResolve(object sender, IKVM.Reflection.ResolveEventArgs args) - { - try - { - var asm = System.Reflection.Assembly.Load(args.Name); - if (asm != null && File.Exists(asm.Location)) - return universe!.LoadFile(asm.Location); - } - catch - { - - } - - return null; - } - - [TestMethod] - public void SameTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); - var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); - s1.Should().BeOfType(); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void GenericTypeDefinitionShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); - var s2 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void GenericTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); - var s2 = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void ArrayTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); - var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object").MakeArrayType(2)); - s1.IsSZArray.Should().BeFalse(); - s2.IsSZArray.Should().BeFalse(); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void SZArrayTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); - var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeArrayType()); - s1.IsSZArray.Should().BeTrue(); - s2.IsSZArray.Should().BeTrue(); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public unsafe void PointerTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakePointerType()); - var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakePointerType()); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public unsafe void ByRefTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeByRefType()); - var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32").MakeByRefType()); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void EnumTypeShouldBeSame() - { - var c = new IkvmReflectionSymbolContext(universe); - var s1 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.AttributeTargets")); - var s2 = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.AttributeTargets")); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void CanResolveType() - { - var c = new IkvmReflectionSymbolContext(universe); - var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); - s.Name.Should().Be("Object"); - s.FullName.Should().Be("System.Object"); - } - - [TestMethod] - public void CanResolveFieldOfGenericTypeDefinition() - { - var c = new IkvmReflectionSymbolContext(universe); - var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1")); - s.IsGenericType.Should().BeTrue(); - s.IsGenericTypeDefinition.Should().BeTrue(); - var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); - f.Name.Should().Be("field"); - f.FieldType.IsGenericType.Should().BeFalse(); - f.FieldType.IsGenericParameter.Should().BeTrue(); - } - - [TestMethod] - public void CanResolveFieldOfGenericType() - { - var c = new IkvmReflectionSymbolContext(universe); - var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+Foo`1").MakeGenericType(coreAssembly.GetType("System.Int32"))); - s.IsGenericType.Should().BeTrue(); - s.IsGenericTypeDefinition.Should().BeFalse(); - var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); - f.Name.Should().Be("field"); - f.FieldType.IsGenericType.Should().BeFalse(); - f.FieldType.IsGenericParameter.Should().BeFalse(); - f.FieldType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Int32"))); - } - - [TestMethod] - public void CanResolveMethod() - { - var c = new IkvmReflectionSymbolContext(universe); - var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); - var m = s.GetMethod("ToString"); - m.Name.Should().Be("ToString"); - m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.String"))); - m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.String"))); - m.IsGenericMethod.Should().BeFalse(); - m.IsGenericMethodDefinition.Should().BeFalse(); - m.IsPublic.Should().BeTrue(); - m.IsPrivate.Should().BeFalse(); - } - - [TestMethod] - public void CanResolveGenericMethod() - { - var c = new IkvmReflectionSymbolContext(universe); - var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.ValueTuple")); - var m = s.GetMethods().FirstOrDefault(i => i.Name == "Create" && i.GetGenericArguments().Length == 1); - m.Name.Should().Be("Create"); - m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.ValueTuple`1")).MakeGenericType(m.GetGenericArguments()[0])); - m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.ValueTuple`1")).MakeGenericType(m.GetGenericArguments()[0])); - m.IsGenericMethod.Should().BeTrue(); - m.IsGenericMethodDefinition.Should().BeTrue(); - m.IsPublic.Should().BeTrue(); - m.IsPrivate.Should().BeFalse(); - } - - [TestMethod] - public void CanResolveParameters() - { - var c = new IkvmReflectionSymbolContext(universe); - var s = c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object")); - var m = s.GetMethod("ReferenceEquals"); - m.Name.Should().Be("ReferenceEquals"); - m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Boolean"))); - m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Boolean"))); - m.IsGenericMethod.Should().BeFalse(); - m.IsGenericMethodDefinition.Should().BeFalse(); - m.IsPublic.Should().BeTrue(); - m.IsPrivate.Should().BeFalse(); - var p = m.GetParameters(); - p.Length.Should().Be(2); - p[0].Name.Should().Be("objA"); - p[0].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object"))); - p[1].Name.Should().Be("objB"); - p[1].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(coreAssembly.GetType("System.Object"))); - } - - [AttributeUsage(AttributeTargets.Class)] - class AttributeWithType : Attribute - { - - public AttributeWithType(System.Type type) - { - Type = type; - } - - public System.Type Type { get; } - - } - - [AttributeWithType(typeof(object))] - class ClassWithAttributeWithType - { - - - - } - - [TestMethod] - public void CanReadCustomAttributes() - { - var c = new IkvmReflectionSymbolContext(universe!); - var s = c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+ClassWithAttributeWithType")); - var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(thisAssembly.GetType("IKVM.CoreLib.Tests.Symbols.IkvmReflection.IkvmReflectionSymbolTests+AttributeWithType"))); - var v = a.Value.ConstructorArguments[0].Value; - v.Should().BeOfType(); - } - - [TestMethod] - public void CanResolveAssemblyBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var assemblySymbol = c.GetOrCreateAssemblySymbol(a); - assemblySymbol.Should().BeOfType(); - assemblySymbol.Should().BeSameAs(c.GetOrCreateAssemblySymbol(a)); - } - - [TestMethod] - public void CanResolveModuleBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var moduleSymbol = c.GetOrCreateModuleSymbol(m); - moduleSymbol.Should().BeOfType(); - moduleSymbol.Should().BeSameAs(c.GetOrCreateModuleSymbol(m)); - } - - [TestMethod] - public void CanResolveTypeBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - - var type1 = m.DefineType("DynamicType1"); - var type1Symbol = c.GetOrCreateTypeSymbol(type1); - type1Symbol.Should().BeOfType(); - type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); - } - - [TestMethod] - public void CanResolveMultipleTypeBuilders() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - - var type1 = m.DefineType("DynamicType1"); - var type1Symbol = c.GetOrCreateTypeSymbol(type1); - type1Symbol.Should().BeOfType(); - type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); - type1.CreateType(); - - var type2 = m.DefineType("DynamicType2"); - var type2Symbol = c.GetOrCreateTypeSymbol(type2); - type2Symbol.Should().BeOfType(); - type2Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type2)); - } - - [TestMethod] - public void CanResolveMethodBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - } - - [TestMethod] - public void CanResolveMultipleMethodBuilders() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - - var method2 = t.DefineMethod("DynamicMethod2", MethodAttributes.Public | MethodAttributes.Static); - var method2Symbol = c.GetOrCreateMethodSymbol(method2); - method2Symbol.Should().BeOfType(); - method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); - } - - [TestMethod] - public void CanResolveFieldBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var field = t.DefineField("dynamicField", coreAssembly.GetType("System.Object"), FieldAttributes.Public); - var fieldSymbol = c.GetOrCreateFieldSymbol(field); - fieldSymbol.Should().BeOfType(); - fieldSymbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field)); - } - - [TestMethod] - public void CanResolveMultipleFieldBuilders() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var field1 = t.DefineField("dynamicField1", coreAssembly.GetType("System.Object"), FieldAttributes.Public); - var field1Symbol = c.GetOrCreateFieldSymbol(field1); - field1Symbol.Should().BeOfType(); - field1Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field1)); - - var field2 = t.DefineField("dynamicField2", coreAssembly.GetType("System.Object"), FieldAttributes.Public); - var field2Symbol = c.GetOrCreateFieldSymbol(field2); - field2Symbol.Should().BeOfType(); - field2Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field2)); - } - - [TestMethod] - public void CanResolvePropertyBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var property = t.DefineProperty("DynamicProperty", PropertyAttributes.None, coreAssembly.GetType("System.Object"), []); - var propertySymbol = c.GetOrCreatePropertySymbol(property); - propertySymbol.Should().BeOfType(); - propertySymbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property)); - } - - [TestMethod] - public void CanResolveMultiplePropertyBuilders() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var property1 = t.DefineProperty("DynamicProperty1", PropertyAttributes.None, coreAssembly!.GetType("System.Object"), []); - var property1Symbol = c.GetOrCreatePropertySymbol(property1); - property1Symbol.Should().BeOfType(); - property1Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property1)); - - var property2 = t.DefineProperty("DynamicProperty2", PropertyAttributes.None, coreAssembly.GetType("System.Object"), []); - var property2Symbol = c.GetOrCreatePropertySymbol(property2); - property2Symbol.Should().BeOfType(); - property2Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property2)); - } - - [TestMethod] - public void CanResolveEventBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly!.GetType("System.EventHandler")); - var event1Symbol = c.GetOrCreateEventSymbol(event1); - event1Symbol.Should().BeOfType(); - event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); - } - - [TestMethod] - public void CanResolveMultipleEventBuilders() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = universe.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.Save); - var m = a.DefineDynamicModule("DynamicModule", "DynamicModule.dll"); - var t = m.DefineType("DynamicType"); - - var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly!.GetType("System.EventHandler")); - var event1Symbol = c.GetOrCreateEventSymbol(event1); - event1Symbol.Should().BeOfType(); - event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); - - var event2 = t.DefineEvent("DynamicEvent", EventAttributes.None, coreAssembly.GetType("System.EventHandler")); - var event2Symbol = c.GetOrCreateEventSymbol(event2); - event2Symbol.Should().BeOfType(); - event2Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event2)); - } - - [TestMethod] - public void CanGetMethodsFromTypeBuilder() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, true); - var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); - var type = m.DefineType("DynamicType"); - - var method = type.DefineMethod("DynamicMethod1", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); - var il = method.GetILGenerator(); - il.Emit(System.Reflection.Emit.OpCodes.Ret); - - // before complete - type.GetMethods().Should().HaveCount(5); - var incompleteMethod = type.GetMethod("DynamicMethod1"); - - // complete the type - type.Complete(); - - // after complete - type.GetMethods().Should().HaveCount(5); - var completeMethod = type.GetMethod("DynamicMethod1"); - - // all the methods should be the same - incompleteMethod.Should().BeSameAs(completeMethod); - incompleteMethod.Should().BeSameAs(method); - } - - [TestMethod] - public void CanGetGenericDelegateInvoke() - { - var c = new IkvmReflectionSymbolContext(universe!); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, true); - var m = a.DefineModule("DynamicModule", "DynamicModule.dll"); - - var tb = m.DefineType("DynamicGenericDelegate", System.Reflection.TypeAttributes.NotPublic | System.Reflection.TypeAttributes.Sealed, c.GetOrCreateTypeSymbol(coreAssembly!.GetType("System.MulticastDelegate"))); - var gtp = tb.DefineGenericParameters("T1"); - var mb = tb.DefineMethod("Invoke", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.NewSlot | System.Reflection.MethodAttributes.Virtual, null, [gtp[0]]); - mb.SetImplementationFlags(System.Reflection.MethodImplAttributes.Runtime); - - var type = m.DefineType("DynamicType2"); - var method = type.DefineMethod("CallDelegate", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); - var il = method.GetILGenerator(); - il.Emit(System.Reflection.Emit.OpCodes.Ldind_I4, 0); - il.Emit(System.Reflection.Emit.OpCodes.Ldnull); - il.Emit(System.Reflection.Emit.OpCodes.Castclass, tb); - il.EmitCall(System.Reflection.Emit.OpCodes.Callvirt, mb, null); - - tb.Complete(); - type.Complete(); - } - - } - -} diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionAssemblySymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionAssemblySymbolTests.cs new file mode 100644 index 0000000000..349435f133 --- /dev/null +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionAssemblySymbolTests.cs @@ -0,0 +1,98 @@ +using System.Linq; + +using FluentAssertions; + +using IKVM.CoreLib.Symbols.Reflection; + +using Microsoft.VisualStudio.TestTools.UnitTesting; + +namespace IKVM.CoreLib.Tests.Symbols.Reflection +{ + + [TestClass] + public class ReflectionAssemblySymbolTests + { + + [TestMethod] + public void SystemObjectShouldNotBeNull() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + c.ResolveCoreType("System.Object").Should().NotBeNull(); + } + + [TestMethod] + public void ResolvedAssemblyShouldBeSame() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var a = typeof(TestClassAttribute).Assembly; + var s = c.ResolveAssemblySymbol(a); + var s1 = c.ResolveAssemblySymbol(a); + s.Should().BeSameAs(s1); + } + + [TestMethod] + public void AssemblyPropertiesShouldMatch() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var a = typeof(TestClassAttribute).Assembly; + var s = c.ResolveAssemblySymbol(a); + s.FullName.Should().Be(a.FullName); + s.Location.Should().Be(a.Location); + s.IsMissing.Should().BeFalse(); + s.ContainsMissing.Should().BeFalse(); + s.IsComplete.Should().BeTrue(); + } + + [TestMethod] + public void AssemblyIdentityShouldMatch() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var a = typeof(TestClassAttribute).Assembly; + var s = c.ResolveAssemblySymbol(a); + s.GetIdentity().Name.Should().Be(a.GetName().Name); + s.GetIdentity().Version.Should().Be(a.GetName().Version); + s.GetIdentity().CultureName.Should().Be(a.GetName().CultureName); + s.GetIdentity().PublicKeyToken.Should().BeEquivalentTo(a.GetName().GetPublicKeyToken()); + } + + [TestMethod] + public void CanGetAssemblyModules() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var a = typeof(TestClassAttribute).Assembly; + var s = c.ResolveAssemblySymbol(a); + var l = s.GetModules(); + l.Length.Should().Be(1); + l[0].Should().NotBeNull(); + l[0].Name.Should().Be("Microsoft.VisualStudio.TestPlatform.TestFramework.dll"); + } + + [TestMethod] + public void CanGetTypes() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var a = typeof(TestClassAttribute).Assembly; + var s = c.ResolveAssemblySymbol(a); + var l = s.GetTypes(); + } + + [TestMethod] + public void CanGetCustomAttributes() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var a = typeof(TestClassAttribute).Assembly; + var s = c.ResolveAssemblySymbol(a); + var l = s.GetCustomAttributes(true); + l.Should().HaveCountGreaterThan(5); + + var companyAttributeType = c.ResolveCoreType("System.Reflection.AssemblyCompanyAttribute"); + var companyAttribute = l.Single(e => e.AttributeType == companyAttributeType); + companyAttribute.NamedArguments.Should().HaveCount(0); + companyAttribute.ConstructorArguments.Should().HaveCount(1); + companyAttribute.ConstructorArguments[0].ArgumentType.Should().Be(c.ResolveCoreType("System.String")); + ((string?)companyAttribute.ConstructorArguments[0].Value).Should().Be("Microsoft Corporation"); + } + + } + +} diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionModuleSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionModuleSymbolTests.cs new file mode 100644 index 0000000000..f72002dad9 --- /dev/null +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionModuleSymbolTests.cs @@ -0,0 +1,82 @@ +using FluentAssertions; + +using IKVM.CoreLib.Symbols.Reflection; + +using Microsoft.VisualStudio.TestTools.UnitTesting; + +namespace IKVM.CoreLib.Tests.Symbols.Reflection +{ + + [TestClass] + public class ReflectionModuleSymbolTests + { + + [TestMethod] + public void CanResolve() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var m = c.ResolveModuleSymbol(typeof(object).Module); + m.Name.Should().Be(typeof(object).Module.Name); + } + + [TestMethod] + public void ShouldBeSame() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveModuleSymbol(typeof(object).Module); + var s1 = c.ResolveModuleSymbol(typeof(object).Module); + s.Should().BeSameAs(s1); + } + + [TestMethod] + public void PropertiesShouldMatch() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var m = typeof(object).Module; + var s = c.ResolveModuleSymbol(m); + s.Name.Should().Be(m.Name); + s.IsMissing.Should().BeFalse(); + s.ContainsMissing.Should().BeFalse(); + s.IsComplete.Should().BeTrue(); + s.FullyQualifiedName.Should().Be(m.FullyQualifiedName); + } + + [TestMethod] + public void CanGetFields() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var m = typeof(object).Module; + var s = c.ResolveModuleSymbol(m); + var l = s.GetFields(); + } + + [TestMethod] + public void CanGetMethods() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var m = typeof(object).Module; + var s = c.ResolveModuleSymbol(m); + var l = s.GetMethods(); + } + + [TestMethod] + public void CanGetTypes() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var m = typeof(object).Module; + var s = c.ResolveModuleSymbol(m); + var l = s.GetTypes(); + } + + [TestMethod] + public void CanGetCustomAttributes() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var m = typeof(object).Module; + var s = c.ResolveModuleSymbol(m); + var l = s.GetCustomAttributes(true); + } + + } + +} diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs deleted file mode 100644 index f083a2a698..0000000000 --- a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionSymbolTests.cs +++ /dev/null @@ -1,514 +0,0 @@ -using System; -using System.Linq; -using System.Reflection; -using System.Reflection.Emit; - -using FluentAssertions; - -using IKVM.CoreLib.Symbols; -using IKVM.CoreLib.Symbols.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; - -using Microsoft.VisualStudio.TestTools.UnitTesting; - -namespace IKVM.CoreLib.Tests.Symbols.Reflection -{ - - [TestClass] - public class ReflectionSymbolTests - { - - class Foo - { - T? field; - } - - [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)] - class AttributeWithWithDefaultCtor : Attribute - { - - public AttributeWithWithDefaultCtor() - { - - } - - } - - [AttributeUsage(AttributeTargets.Class)] - class AttributeWithType : Attribute - { - - public AttributeWithType(Type type) - { - Type = type; - } - - public Type Type { get; } - - } - - [AttributeWithType(typeof(object))] - class ClassWithAttributeWithType - { - - - - } - - [TestMethod] - public void SameTypeShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(object)); - var s2 = c.GetOrCreateTypeSymbol(typeof(object)); - s1.Should().BeOfType(); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void GenericTypeDefinitionShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(Foo<>)); - var s2 = c.GetOrCreateTypeSymbol(typeof(Foo<>)); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void GenericTypeShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(Foo)); - var s2 = c.GetOrCreateTypeSymbol(typeof(Foo)); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void ArrayTypeShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(object[,])); - var s2 = c.GetOrCreateTypeSymbol(typeof(object[,])); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void SZArrayTypeShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(object[])); - var s2 = c.GetOrCreateTypeSymbol(typeof(object[])); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public unsafe void PointerTypeShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(int*)); - var s2 = c.GetOrCreateTypeSymbol(typeof(int*)); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public unsafe void ByRefTypeShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(int).MakeByRefType()); - var s2 = c.GetOrCreateTypeSymbol(typeof(int).MakeByRefType()); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void EnumTypeShouldBeSame() - { - var c = new ReflectionSymbolContext(); - var s1 = c.GetOrCreateTypeSymbol(typeof(AttributeTargets)); - var s2 = c.GetOrCreateTypeSymbol(typeof(AttributeTargets)); - s1.Should().BeSameAs(s2); - } - - [TestMethod] - public void CanResolveType() - { - var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(object)); - s.Name.Should().Be("Object"); - s.FullName.Should().Be("System.Object"); - } - - [TestMethod] - public void CanResolveFieldOfGenericTypeDefinition() - { - var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(Foo<>)); - s.IsGenericType.Should().BeTrue(); - s.IsGenericTypeDefinition.Should().BeTrue(); - var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); - f.Name.Should().Be("field"); - f.FieldType.IsGenericType.Should().BeFalse(); - f.FieldType.IsGenericParameter.Should().BeTrue(); - } - - [TestMethod] - public void CanResolveFieldOfGenericType() - { - var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(Foo)); - s.IsGenericType.Should().BeTrue(); - s.IsGenericTypeDefinition.Should().BeFalse(); - var f = s.GetField("field", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); - f.Name.Should().Be("field"); - f.FieldType.IsGenericType.Should().BeFalse(); - f.FieldType.IsGenericParameter.Should().BeFalse(); - f.FieldType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(int))); - } - - [TestMethod] - public void CanResolveMethod() - { - var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(object)); - var m = s.GetMethod("ToString"); - m.Name.Should().Be("ToString"); - m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(string))); - m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(string))); - m.IsGenericMethod.Should().BeFalse(); - m.IsGenericMethodDefinition.Should().BeFalse(); - m.IsPublic.Should().BeTrue(); - m.IsPrivate.Should().BeFalse(); - } - - [TestMethod] - public void CanResolveGenericMethod() - { - var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(ValueTuple)); - var m = s.GetMethods().FirstOrDefault(i => i.Name == "Create" && i.GetGenericArguments().Length == 1); - m.Name.Should().Be("Create"); - m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(ValueTuple<>)).MakeGenericType(m.GetGenericArguments()[0])); - m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(ValueTuple<>)).MakeGenericType(m.GetGenericArguments()[0])); - m.IsGenericMethod.Should().BeTrue(); - m.IsGenericMethodDefinition.Should().BeTrue(); - m.IsPublic.Should().BeTrue(); - m.IsPrivate.Should().BeFalse(); - } - - [TestMethod] - public void CanResolveParameters() - { - var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(object)); - var m = s.GetMethod("ReferenceEquals"); - m.Name.Should().Be("ReferenceEquals"); - m.ReturnType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(bool))); - m.ReturnParameter.ParameterType.Should().BeSameAs(c.GetOrCreateTypeSymbol(typeof(bool))); - m.IsGenericMethod.Should().BeFalse(); - m.IsGenericMethodDefinition.Should().BeFalse(); - m.IsPublic.Should().BeTrue(); - m.IsPrivate.Should().BeFalse(); - var p = m.GetParameters(); - p.Length.Should().Be(2); - p[0].Name.Should().Be("objA"); - p[0].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(typeof(object))); - p[1].Name.Should().Be("objB"); - p[1].ParameterType.Should().Be(c.GetOrCreateTypeSymbol(typeof(object))); - } - - [TestMethod] - public void CanReadCustomAttributes() - { - var c = new ReflectionSymbolContext(); - var s = c.GetOrCreateTypeSymbol(typeof(ClassWithAttributeWithType)); - var a = s.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithType))); - var v = a.Value.ConstructorArguments[0].Value; - v.Should().BeOfType(); - } - - [TestMethod] - public void CanReadCustomAttributesFromTypeBuilder() - { - var c = new ReflectionSymbolContext(); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); - var m = a.DefineModule("DynamicModule"); - var type = m.DefineType("DynamicType"); - - type.SetCustomAttribute(CustomAttribute.Create(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor)).GetConstructors()[0], [])); - var ca = type.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor))); - ca.Should().NotBeNull(); - } - - [TestMethod] - public void CanReadCustomAttributesFromMethodBuilder() - { - var c = new ReflectionSymbolContext(); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); - var m = a.DefineModule("DynamicModule"); - var type = m.DefineType("DynamicType"); - - var method = type.DefineMethod("DynamicMethod1", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); - var il = method.GetILGenerator(); - il.Emit(OpCodes.Ret); - - method.SetCustomAttribute(CustomAttribute.Create(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor)).GetConstructors()[0], [])); - var ca = method.GetCustomAttribute(c.GetOrCreateTypeSymbol(typeof(AttributeWithWithDefaultCtor))); - ca.Should().NotBeNull(); - } - - [TestMethod] - public void CanResolveAssemblyBuilder() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var assemblySymbol = c.GetOrCreateAssemblySymbol(a); - assemblySymbol.Should().BeOfType(); - assemblySymbol.Should().BeSameAs(c.GetOrCreateAssemblySymbol(a)); - } - - [TestMethod] - public void CanResolveModuleBuilder() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var module = a.DefineDynamicModule("Test"); - var moduleSymbol = c.GetOrCreateModuleSymbol(module); - moduleSymbol.Should().BeOfType(); - moduleSymbol.Should().BeSameAs(c.GetOrCreateModuleSymbol(module)); - } - - [TestMethod] - public void CanResolveTypeBuilder() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - - var type1 = m.DefineType("DynamicType1"); - var type1Symbol = c.GetOrCreateTypeSymbol(type1); - type1Symbol.Should().BeOfType(); - type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); - } - - [TestMethod] - public void CanResolveMultipleTypeBuilders() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - - var type1 = m.DefineType("DynamicType1"); - var type1Symbol = c.GetOrCreateTypeSymbol(type1); - type1Symbol.Should().BeOfType(); - type1Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type1)); - type1.CreateType(); - - var type2 = m.DefineType("DynamicType2"); - var type2Symbol = c.GetOrCreateTypeSymbol(type2); - type2Symbol.Should().BeOfType(); - type2Symbol.Should().BeSameAs(c.GetOrCreateTypeSymbol(type2)); - } - - [TestMethod] - public void CanResolveMethodBuilder() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - } - - [TestMethod] - public void CanResolveMultipleMethodBuilders() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var method1 = t.DefineMethod("DynamicMethod1", MethodAttributes.Public | MethodAttributes.Static); - var method1Symbol = c.GetOrCreateMethodSymbol(method1); - method1Symbol.Should().BeOfType(); - method1Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method1)); - - var method2 = t.DefineMethod("DynamicMethod2", MethodAttributes.Public | MethodAttributes.Static); - var method2Symbol = c.GetOrCreateMethodSymbol(method2); - method2Symbol.Should().BeOfType(); - method2Symbol.Should().BeSameAs(c.GetOrCreateMethodSymbol(method2)); - } - - [TestMethod] - public void CanResolveFieldBuilder() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var field = t.DefineField("dynamicField", typeof(object), FieldAttributes.Public); - var fieldSymbol = c.GetOrCreateFieldSymbol(field); - fieldSymbol.Should().BeOfType(); - fieldSymbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field)); - } - - [TestMethod] - public void CanResolveMultipleFieldBuilders() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var field1 = t.DefineField("dynamicField1", typeof(object), FieldAttributes.Public); - var field1Symbol = c.GetOrCreateFieldSymbol(field1); - field1Symbol.Should().BeOfType(); - field1Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field1)); - - var field2 = t.DefineField("dynamicField2", typeof(object), FieldAttributes.Public); - var field2Symbol = c.GetOrCreateFieldSymbol(field2); - field2Symbol.Should().BeOfType(); - field2Symbol.Should().BeSameAs(c.GetOrCreateFieldSymbol(field2)); - } - - [TestMethod] - public void CanResolvePropertyBuilder() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var property = t.DefineProperty("DynamicProperty", PropertyAttributes.None, typeof(object), []); - var propertySymbol = c.GetOrCreatePropertySymbol(property); - propertySymbol.Should().BeOfType(); - propertySymbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property)); - } - - [TestMethod] - public void CanResolveMultiplePropertyBuilders() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var property1 = t.DefineProperty("DynamicProperty1", PropertyAttributes.None, typeof(object), []); - var property1Symbol = c.GetOrCreatePropertySymbol(property1); - property1Symbol.Should().BeOfType(); - property1Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property1)); - - var property2 = t.DefineProperty("DynamicProperty2", PropertyAttributes.None, typeof(object), []); - var property2Symbol = c.GetOrCreatePropertySymbol(property2); - property2Symbol.Should().BeOfType(); - property2Symbol.Should().BeSameAs(c.GetOrCreatePropertySymbol(property2)); - } - - [TestMethod] - public void CanResolveEventBuilder() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); - var event1Symbol = c.GetOrCreateEventSymbol(event1); - event1Symbol.Should().BeOfType(); - event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); - } - - [TestMethod] - public void CanResolveMultipleEventBuilders() - { - var c = new ReflectionSymbolContext(); - var a = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect); - var m = a.DefineDynamicModule("DynamicModule"); - var t = m.DefineType("DynamicType"); - - var event1 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); - var event1Symbol = c.GetOrCreateEventSymbol(event1); - event1Symbol.Should().BeOfType(); - event1Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event1)); - - var event2 = t.DefineEvent("DynamicEvent", EventAttributes.None, typeof(EventHandler)); - var event2Symbol = c.GetOrCreateEventSymbol(event2); - event2Symbol.Should().BeOfType(); - event2Symbol.Should().BeSameAs(c.GetOrCreateEventSymbol(event2)); - } - - [TestMethod] - public void CanCompleteTypeBuilder() - { - var c = new ReflectionSymbolContext(); - var a = c.GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("DynamicAssembly"), AssemblyBuilderAccess.RunAndCollect)); - - var moduleBuilder = a.DefineModule("DynamicModule"); - var moduleSymbol = (IModuleSymbol)moduleBuilder; - - var type1Builder = moduleBuilder.DefineType("DynamicType1"); - var type1Symbol = (ITypeSymbol)type1Builder; - type1Symbol.Should().BeOfType(); - - type1Builder.Complete(); - var type1Again = moduleBuilder.GetType("DynamicType1"); - type1Again.Should().BeSameAs(type1Symbol); - type1Again.Name.Should().Be("DynamicType1"); - - // check that we can relookup type - moduleSymbol.GetType("DynamicType1").Should().BeSameAs(type1Symbol); - } - - [TestMethod] - public void CanGetMethodsFromTypeBuilder() - { - var c = new ReflectionSymbolContext(); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); - var m = a.DefineModule("DynamicModule"); - var type = m.DefineType("DynamicType"); - - var method = type.DefineMethod("DynamicMethod1", System.Reflection.MethodAttributes.Public | System.Reflection.MethodAttributes.Static); - var il = method.GetILGenerator(); - il.Emit(OpCodes.Ret); - - // before complete - type.GetMethods().Should().HaveCount(5); - var incompleteMethod = type.GetMethod("DynamicMethod1"); - - // complete the type - type.Complete(); - - // after complete - type.GetMethods().Should().HaveCount(5); - var completeMethod = type.GetMethod("DynamicMethod1"); - - // all the methods should be the same - incompleteMethod.Should().BeSameAs(completeMethod); - incompleteMethod.Should().BeSameAs(method); - } - - /// - /// Generics closed over a type builder need to be handled specially. - /// - [TestMethod] - public void CanCreateRuntimeGenericTypeOfTypeBuilder() - { - var c = new ReflectionSymbolContext(); - var a = c.DefineAssembly(new AssemblyIdentity("DynamicAssembly"), false, false); - var m = a.DefineModule("DynamicModule"); - var type = m.DefineType("DynamicType"); - var funcType = c.GetOrCreateTypeSymbol(typeof(Func<,>)); - var realFuncType = funcType.MakeGenericType(type, type); - var invokeMethod = realFuncType.GetMethod("Invoke"); - invokeMethod.Should().NotBeNull(); - invokeMethod.GetParameters().Should().HaveCount(1); - invokeMethod.GetParameters()[0].ParameterType.Should().BeSameAs(type); - invokeMethod.ReturnType.Should().BeSameAs(type); - } - - } - -} diff --git a/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionTypeSymbolTests.cs b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionTypeSymbolTests.cs new file mode 100644 index 0000000000..0103ea6f87 --- /dev/null +++ b/src/IKVM.CoreLib.Tests/Symbols/Reflection/ReflectionTypeSymbolTests.cs @@ -0,0 +1,358 @@ +using System.Collections.Generic; +using System.Reflection; + +using FluentAssertions; + +using IKVM.CoreLib.Symbols; +using IKVM.CoreLib.Symbols.Reflection; + +using Microsoft.VisualStudio.TestTools.UnitTesting; + +namespace IKVM.CoreLib.Tests.Symbols.Reflection +{ + + [TestClass] + public class ReflectionTypeSymbolTests + { + + [TestMethod] + public void SystemObjectPropertiesShouldMatch() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveCoreType("System.Object"); + s.AssemblyQualifiedName.Should().Be(typeof(object).AssemblyQualifiedName); + s.Name.Should().Be(typeof(object).Name); + s.FullName.Should().Be(typeof(object).FullName); + s.BaseType.Should().BeNull(); + s.HasElementType.Should().BeFalse(); + s.IsAbstract.Should().BeFalse(); + s.IsArray.Should().BeFalse(); + s.IsAutoLayout.Should().BeTrue(); + s.IsByRef.Should().BeFalse(); + s.IsClass.Should().BeTrue(); + s.IsComplete.Should().BeTrue(); + s.IsConstructedGenericType.Should().BeFalse(); + s.IsEnum.Should().BeFalse(); + s.IsExplicitLayout.Should().BeFalse(); + s.IsFunctionPointer.Should().BeFalse(); + s.IsGenericMethodParameter.Should().BeFalse(); + s.IsGenericParameter.Should().BeFalse(); + s.IsGenericType.Should().BeFalse(); + s.IsGenericTypeDefinition.Should().BeFalse(); + s.IsGenericTypeParameter.Should().BeFalse(); + s.IsInterface.Should().BeFalse(); + s.IsLayoutSequential.Should().BeFalse(); + s.IsMissing.Should().BeFalse(); + s.IsNested.Should().BeFalse(); + s.IsNestedAssembly.Should().BeFalse(); + s.IsNestedFamANDAssem.Should().BeFalse(); + s.IsNestedFamily.Should().BeFalse(); + s.IsNestedFamORAssem.Should().BeFalse(); + s.IsNestedPrivate.Should().BeFalse(); + s.IsNestedPublic.Should().BeFalse(); + s.IsNotPublic.Should().BeFalse(); + s.IsPointer.Should().BeFalse(); + s.IsPrimitive.Should().BeFalse(); + s.IsPublic.Should().BeTrue(); + s.IsSealed.Should().BeFalse(); + s.IsSerializable.Should().BeTrue(); + s.IsSZArray.Should().BeFalse(); + s.IsTypeDefinition.Should().BeTrue(); + s.IsUnmanagedFunctionPointer.Should().BeFalse(); + s.IsValueType.Should().BeFalse(); + s.IsVisible.Should().BeTrue(); + } + + [TestMethod] + public void ShouldInt32PropertiesShouldMatch() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveCoreType("System.Int32"); + s.AssemblyQualifiedName.Should().Be(typeof(int).AssemblyQualifiedName); + s.Name.Should().Be(typeof(int).Name); + s.FullName.Should().Be(typeof(int).FullName); + s.BaseType.Should().Be(c.ResolveCoreType("System.ValueType")); + s.HasElementType.Should().BeFalse(); + s.IsAbstract.Should().BeFalse(); + s.IsArray.Should().BeFalse(); + s.IsAutoLayout.Should().BeFalse(); + s.IsByRef.Should().BeFalse(); + s.IsClass.Should().BeFalse(); + s.IsComplete.Should().BeTrue(); + s.IsConstructedGenericType.Should().BeFalse(); + s.IsEnum.Should().BeFalse(); + s.IsExplicitLayout.Should().BeFalse(); + s.IsFunctionPointer.Should().BeFalse(); + s.IsGenericMethodParameter.Should().BeFalse(); + s.IsGenericParameter.Should().BeFalse(); + s.IsGenericType.Should().BeFalse(); + s.IsGenericTypeDefinition.Should().BeFalse(); + s.IsGenericTypeParameter.Should().BeFalse(); + s.IsInterface.Should().BeFalse(); + s.IsLayoutSequential.Should().BeTrue(); + s.IsMissing.Should().BeFalse(); + s.IsNested.Should().BeFalse(); + s.IsNestedAssembly.Should().BeFalse(); + s.IsNestedFamANDAssem.Should().BeFalse(); + s.IsNestedFamily.Should().BeFalse(); + s.IsNestedFamORAssem.Should().BeFalse(); + s.IsNestedPrivate.Should().BeFalse(); + s.IsNestedPublic.Should().BeFalse(); + s.IsNotPublic.Should().BeFalse(); + s.IsPointer.Should().BeFalse(); + s.IsPrimitive.Should().BeTrue(); + s.IsPublic.Should().BeTrue(); + s.IsSealed.Should().BeTrue(); + s.IsSerializable.Should().BeTrue(); + s.IsSZArray.Should().BeFalse(); + s.IsTypeDefinition.Should().BeTrue(); + s.IsUnmanagedFunctionPointer.Should().BeFalse(); + s.IsValueType.Should().BeTrue(); + s.IsVisible.Should().BeTrue(); + } + + [TestMethod] + public void SystemInt32ShouldReturnSameInstance() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s1 = c.ResolveCoreType("System.Int32"); + var s2 = c.ResolveCoreType("System.Int32"); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void CanMakeArrayType() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveCoreType("System.Int32"); + var p = s.MakeArrayType(); + p.AssemblyQualifiedName.Should().Be(typeof(int[]).AssemblyQualifiedName); + p.Name.Should().Be(typeof(int[]).Name); + p.FullName.Should().Be(typeof(int[]).FullName); + p.BaseType.Should().Be(c.ResolveCoreType("System.Array")); + p.HasElementType.Should().BeTrue(); + p.IsAbstract.Should().BeFalse(); + p.IsArray.Should().BeTrue(); + p.IsAutoLayout.Should().BeTrue(); + p.IsByRef.Should().BeFalse(); + p.IsClass.Should().BeTrue(); + p.IsComplete.Should().BeTrue(); + p.IsConstructedGenericType.Should().BeFalse(); + p.IsEnum.Should().BeFalse(); + p.IsExplicitLayout.Should().BeFalse(); + p.IsFunctionPointer.Should().BeFalse(); + p.IsGenericMethodParameter.Should().BeFalse(); + p.IsGenericParameter.Should().BeFalse(); + p.IsGenericType.Should().BeFalse(); + p.IsGenericTypeDefinition.Should().BeFalse(); + p.IsGenericTypeParameter.Should().BeFalse(); + p.IsInterface.Should().BeFalse(); + p.IsLayoutSequential.Should().BeFalse(); + p.IsMissing.Should().BeFalse(); + p.IsNested.Should().BeFalse(); + p.IsNestedAssembly.Should().BeFalse(); + p.IsNestedFamANDAssem.Should().BeFalse(); + p.IsNestedFamily.Should().BeFalse(); + p.IsNestedFamORAssem.Should().BeFalse(); + p.IsNestedPrivate.Should().BeFalse(); + p.IsNestedPublic.Should().BeFalse(); + p.IsNotPublic.Should().BeFalse(); + p.IsPointer.Should().BeFalse(); + p.IsPrimitive.Should().BeFalse(); + p.IsPublic.Should().BeTrue(); + p.IsSealed.Should().BeTrue(); + p.IsSerializable.Should().BeTrue(); + p.IsSZArray.Should().BeTrue(); + p.IsTypeDefinition.Should().BeFalse(); + p.IsUnmanagedFunctionPointer.Should().BeFalse(); + p.IsValueType.Should().BeFalse(); + p.IsVisible.Should().BeTrue(); + } + + [TestMethod] + public void SystemInt32ArrayShouldReturnSameInstance() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s1 = c.ResolveCoreType("System.Int32").MakeArrayType(); + var s2 = c.ResolveCoreType("System.Int32").MakeArrayType(); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void CanMakePointerType() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveCoreType("System.Int32"); + var p = s.MakePointerType(); + p.AssemblyQualifiedName.Should().Be(typeof(int*).AssemblyQualifiedName); + p.Name.Should().Be(typeof(int*).Name); + p.FullName.Should().Be(typeof(int*).FullName); + p.BaseType.Should().BeNull(); + p.HasElementType.Should().BeTrue(); + p.IsAbstract.Should().BeFalse(); + p.IsArray.Should().BeFalse(); + p.IsAutoLayout.Should().BeTrue(); + p.IsByRef.Should().BeFalse(); + p.IsClass.Should().BeTrue(); + p.IsComplete.Should().BeTrue(); + p.IsConstructedGenericType.Should().BeFalse(); + p.IsEnum.Should().BeFalse(); + p.IsExplicitLayout.Should().BeFalse(); + p.IsFunctionPointer.Should().BeFalse(); + p.IsGenericMethodParameter.Should().BeFalse(); + p.IsGenericParameter.Should().BeFalse(); + p.IsGenericType.Should().BeFalse(); + p.IsGenericTypeDefinition.Should().BeFalse(); + p.IsGenericTypeParameter.Should().BeFalse(); + p.IsInterface.Should().BeFalse(); + p.IsLayoutSequential.Should().BeFalse(); + p.IsMissing.Should().BeFalse(); + p.IsNested.Should().BeFalse(); + p.IsNestedAssembly.Should().BeFalse(); + p.IsNestedFamANDAssem.Should().BeFalse(); + p.IsNestedFamily.Should().BeFalse(); + p.IsNestedFamORAssem.Should().BeFalse(); + p.IsNestedPrivate.Should().BeFalse(); + p.IsNestedPublic.Should().BeFalse(); + p.IsNotPublic.Should().BeFalse(); + p.IsPointer.Should().BeTrue(); + p.IsPrimitive.Should().BeFalse(); + p.IsPublic.Should().BeTrue(); + p.IsSealed.Should().BeFalse(); + p.IsSerializable.Should().BeFalse(); + p.IsSZArray.Should().BeFalse(); + p.IsTypeDefinition.Should().BeFalse(); + p.IsUnmanagedFunctionPointer.Should().BeFalse(); + p.IsValueType.Should().BeFalse(); + p.IsVisible.Should().BeTrue(); + } + + [TestMethod] + public void SystemInt32PointerShouldReturnSameInstance() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s1 = c.ResolveCoreType("System.Int32").MakePointerType(); + var s2 = c.ResolveCoreType("System.Int32").MakePointerType(); + s1.Should().BeSameAs(s2); + } + + [TestMethod] + public void CanMakeGenericType() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveCoreType("System.Collections.Generic.List`1"); + var t = s.MakeGenericType([c.ResolveCoreType("System.Int32")]); + t.AssemblyQualifiedName.Should().Be(typeof(List).AssemblyQualifiedName); + t.Name.Should().Be(typeof(List).Name); + t.FullName.Should().Be(typeof(List).FullName); + t.BaseType.Should().Be(c.ResolveCoreType("System.Object")); + t.HasElementType.Should().BeFalse(); + t.IsAbstract.Should().BeFalse(); + t.IsArray.Should().BeFalse(); + t.IsAutoLayout.Should().BeTrue(); + t.IsByRef.Should().BeFalse(); + t.IsClass.Should().BeTrue(); + t.IsComplete.Should().BeTrue(); + t.IsConstructedGenericType.Should().BeTrue(); + t.IsEnum.Should().BeFalse(); + t.IsExplicitLayout.Should().BeFalse(); + t.IsFunctionPointer.Should().BeFalse(); + t.IsGenericMethodParameter.Should().BeFalse(); + t.IsGenericParameter.Should().BeFalse(); + t.IsGenericType.Should().BeTrue(); + t.IsGenericTypeDefinition.Should().BeFalse(); + t.IsGenericTypeParameter.Should().BeFalse(); + t.IsInterface.Should().BeFalse(); + t.IsLayoutSequential.Should().BeFalse(); + t.IsMissing.Should().BeFalse(); + t.IsNested.Should().BeFalse(); + t.IsNestedAssembly.Should().BeFalse(); + t.IsNestedFamANDAssem.Should().BeFalse(); + t.IsNestedFamily.Should().BeFalse(); + t.IsNestedFamORAssem.Should().BeFalse(); + t.IsNestedPrivate.Should().BeFalse(); + t.IsNestedPublic.Should().BeFalse(); + t.IsNotPublic.Should().BeFalse(); + t.IsPointer.Should().BeFalse(); + t.IsPrimitive.Should().BeFalse(); + t.IsPublic.Should().BeTrue(); + t.IsSealed.Should().BeFalse(); + t.IsSerializable.Should().BeTrue(); + t.IsSZArray.Should().BeFalse(); + t.IsTypeDefinition.Should().BeFalse(); + t.IsUnmanagedFunctionPointer.Should().BeFalse(); + t.IsValueType.Should().BeFalse(); + t.IsVisible.Should().BeTrue(); + } + + [TestMethod] + public void CanGetFieldFromConstructedType() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveCoreType("System.Nullable`1"); + var t = s.MakeGenericType([c.ResolveCoreType("System.Int32")]); + var f = t.GetField("value", BindingFlags.NonPublic | BindingFlags.Instance); + f.Should().BeOfType(typeof(ConstructedGenericFieldSymbol)); + f.DeclaringType.Should().BeSameAs(t); + f.Name.Should().Be("value"); + f.ContainsMissing.Should().BeFalse(); + f.IsAssembly.Should().BeTrue(); + f.IsComplete.Should().BeTrue(); + f.IsFamily.Should().BeFalse(); + f.IsFamilyAndAssembly.Should().BeFalse(); + f.IsFamilyOrAssembly.Should().BeFalse(); + f.IsInitOnly.Should().BeFalse(); + f.IsLiteral.Should().BeFalse(); + f.IsMissing.Should().BeFalse(); + f.IsNotSerialized.Should().BeFalse(); + f.IsPrivate.Should().BeFalse(); + f.IsPublic.Should().BeFalse(); + f.IsSpecialName.Should().BeFalse(); + f.IsStatic.Should().BeFalse(); + + var ft = f.FieldType; + ft.Should().BeSameAs(c.ResolveCoreType("System.Int32")); + } + + [TestMethod] + public void CanGetMethodFromConstructedType() + { + var c = new ReflectionSymbolContext(typeof(object).Assembly); + var s = c.ResolveCoreType("System.Collections.Generic.List`1"); + var t = s.MakeGenericType([c.ResolveCoreType("System.Int32")]); + var m = t.GetMethod("Add"); + m.Should().BeOfType(typeof(ConstructedGenericMethodSymbol)); + m.DeclaringType.Should().BeSameAs(t); + m.Name.Should().Be("Add"); + m.ContainsGenericParameters.Should().BeFalse(); + m.ContainsMissing.Should().BeFalse(); + m.IsAbstract.Should().BeFalse(); + m.IsAssembly.Should().BeFalse(); + m.IsComplete.Should().BeTrue(); + m.IsConstructor.Should().BeFalse(); + m.IsFamily.Should().BeFalse(); + m.IsFamilyAndAssembly.Should().BeFalse(); + m.IsFamilyOrAssembly.Should().BeFalse(); + m.IsFinal.Should().BeTrue(); + m.IsGenericMethod.Should().BeTrue(); + m.IsGenericMethodDefinition.Should().BeFalse(); + m.IsHideBySig.Should().BeTrue(); + m.IsMissing.Should().BeFalse(); + m.IsPrivate.Should().BeFalse(); + m.IsPublic.Should().BeTrue(); + m.IsSpecialName.Should().BeFalse(); + m.IsStatic.Should().BeFalse(); + m.IsVirtual.Should().BeTrue(); + m.MethodImplementationFlags.Should().Be(System.Reflection.MethodImplAttributes.IL); + m.MemberType.Should().Be(System.Reflection.MemberTypes.Method); + + var pl = m.GetParameters(); + pl.Should().HaveCount(1); + var p0 = pl[0]; + p0.Name.Should().Be("item"); + p0.ParameterType.Should().BeSameAs(c.ResolveCoreType("System.Int32")); + } + + } + +} diff --git a/src/IKVM.CoreLib/IKVM.CoreLib.csproj b/src/IKVM.CoreLib/IKVM.CoreLib.csproj index 65ffa062b0..18066ddc58 100644 --- a/src/IKVM.CoreLib/IKVM.CoreLib.csproj +++ b/src/IKVM.CoreLib/IKVM.CoreLib.csproj @@ -5,6 +5,29 @@ enable true + + + + + + + + + + + + + + + + + + + + + + + @@ -107,4 +130,8 @@ + + + + diff --git a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs index 1fef51a679..26552f2ecd 100644 --- a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs +++ b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.Linq.Expressions; using System.Reflection; using System.Reflection.Emit; @@ -709,6 +710,21 @@ public static bool IsSZArray(this Type type) #endif } + /// + /// Gets the parameters types of the specified method or constructor. + /// + /// + /// + public static Type[] GetParameterTypes(this MethodBase method) + { + var p = method.GetParameters(); + var a = new Type[p.Length]; + for (int i = 0; i < p.Length; i++) + a[i] = p[i].ParameterType; + + return a; + } + /// /// Implements GetcustomAttributeData with support for examining inheritence. /// diff --git a/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs index 3a21c45d10..461c6f1eec 100644 --- a/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs @@ -1,4 +1,6 @@ -using System.Reflection; +using System; +using System.Collections.Immutable; +using System.Reflection; namespace IKVM.CoreLib.Symbols { @@ -7,18 +9,28 @@ class ArrayTypeSymbol : HasElementSymbol { readonly int _rank; + readonly ImmutableArray _sizes; + readonly ImmutableArray _lowerBounds; string? _nameSuffix; + ImmutableArray _interfaces; + ImmutableArray _constructors; + ImmutableArray _methods; /// /// Initializes a new instance. /// /// /// - public ArrayTypeSymbol(ISymbolContext context, TypeSymbol elementType, int rank) : + /// + /// + /// + public ArrayTypeSymbol(SymbolContext context, TypeSymbol elementType, int rank, ImmutableArray sizes, ImmutableArray lowerBounds) : base(context, elementType) { _rank = rank; + _sizes = sizes; + _lowerBounds = lowerBounds; } /// @@ -51,6 +63,76 @@ public sealed override int GetArrayRank() return _rank; } + /// + public sealed override ImmutableArray GetInterfaces() + { + return ImmutableArray.Empty; + } + + /// + public sealed override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + { + return new InterfaceMapping(ImmutableList.Empty, interfaceType, ImmutableList.Empty, this); + } + + /// + internal override ImmutableArray GetDeclaredConstructors() + { + if (_constructors == default) + { + var int32 = Context.ResolveCoreType("System.Int32"); + var ctor1Args = ImmutableArray.CreateBuilder(); + var ctor2Args = ImmutableArray.CreateBuilder(); + for (int i = 0; i < _rank; i++) + { + ctor1Args.Add(int32); + ctor2Args.Add(int32); + ctor2Args.Add(int32); + } + + ImmutableInterlocked.InterlockedInitialize(ref _constructors, + [ + new SyntheticConstructorSymbol(Context, Module, this, MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, ctor1Args.ToImmutable()), + new SyntheticConstructorSymbol(Context, Module, this, MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, ctor2Args.ToImmutable()), + ]); + } + + return _constructors; + } + + /// + internal override ImmutableArray GetDeclaredMethods() + { + if (_methods == default) + { + var int32 = Context.ResolveCoreType("System.Int32"); + + // get and set args start at the same length + var argBuilder = ImmutableArray.CreateBuilder(); + for (int i = 0; i < _rank; i++) + argBuilder.Add(int32); + + var args = argBuilder.ToImmutable(); + var getArgs = args; + var setArgs = args.Add(GetElementType()!); // set args takes a value + + ImmutableInterlocked.InterlockedInitialize(ref _methods, + [ + new SyntheticMethodSymbol(Context, Module, this, "Set", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, null, setArgs), + new SyntheticMethodSymbol(Context, Module, this, "Address", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, GetElementType()!.MakeByRefType(), getArgs), + new SyntheticMethodSymbol(Context, Module, this, "Get", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, GetElementType(), getArgs), + ]); + } + + return _methods; + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + } } diff --git a/src/IKVM.CoreLib/Symbols/AssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/AssemblySymbol.cs new file mode 100644 index 0000000000..92596cc888 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/AssemblySymbol.cs @@ -0,0 +1,209 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.IO; +using System.Linq; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class AssemblySymbol : Symbol, ICustomAttributeProviderInternal + { + + CustomAttributeImpl _customAttributes; + + /// + /// Initializes a new instance. + /// + /// + public AssemblySymbol(SymbolContext context) : + base(context) + { + _customAttributes = new CustomAttributeImpl(context, this); + } + + /// + /// Gets the display name of the assembly. + /// + public abstract string? FullName { get; } + + /// + /// Gets a string representing the version of the common language runtime (CLR) saved in the file containing the manifest. + /// + public abstract string ImageRuntimeVersion { get; } + + /// + /// Gets the full path or UNC location of the loaded file that contains the manifest. + /// + public abstract string Location { get; } + + /// + /// Gets the module that contains the manifest for the current assembly. + /// + public abstract ModuleSymbol ManifestModule { get; } + + /// + /// Gets the entry point of this assembly. + /// + public abstract MethodSymbol? EntryPoint { get; } + + /// + /// Gets a collection of the types defined in this assembly. + /// + public abstract IEnumerable DefinedTypes { get; } + + /// + /// Gets a collection of the public types defined in this assembly that are visible outside the assembly. + /// + public abstract IEnumerable ExportedTypes { get; } + + /// + /// Gets a collection that contains the modules in this assembly. + /// + public ImmutableArray Modules => GetModules(); + + /// + /// Returns true if the symbol is missing. + /// + public abstract bool IsMissing { get; } + + /// + /// Returns true if the symbol contains a missing symbol. + /// + public abstract bool ContainsMissing { get; } + + /// + /// Returns true if the symbol is complete. That is, was created with a builder and completed. + /// + public abstract bool IsComplete { get; } + + /// + /// Gets the public types defined in this assembly that are visible outside the assembly. + /// + /// + public IEnumerable GetExportedTypes() + { + foreach (var type in GetTypes()) + if (IsVisibleOutsideAssembly(type)) + yield return type; + } + + /// + /// Returns true if the specified type is visible outside the assembly. + /// + /// + /// + bool IsVisibleOutsideAssembly(TypeSymbol type) + { + var visibility = type.Attributes & TypeAttributes.VisibilityMask; + if (visibility == TypeAttributes.Public) + return true; + + if (visibility == TypeAttributes.NestedPublic) + return IsVisibleOutsideAssembly(type.DeclaringType!); + + return false; + } + + /// + /// Gets the specified module in this assembly. + /// + /// + /// + public ModuleSymbol? GetModule(string name) + { + if (name is null) + throw new ArgumentNullException(nameof(name)); + + return GetModules().Where(i => i.Name == name).Single(); + } + + /// + /// Gets all the modules that are part of this assembly, specifying whether to include resource modules. + /// + /// + public abstract ImmutableArray GetModules(); + + /// + /// Gets an for this assembly. + /// + /// + public abstract AssemblyIdentity GetIdentity(); + + /// + /// Gets the objects for all the assemblies referenced by this assembly. + /// + /// + public abstract ImmutableArray GetReferencedAssemblies(); + + /// + /// Gets the Type object with the specified name in the assembly instance. + /// + /// + /// + public TypeSymbol? GetType(string name) => GetType(name, false); + + /// + /// Gets the object with the specified name in the assembly instance and optionally throws an exception if the type is not found. + /// + /// + /// + /// + public abstract TypeSymbol? GetType(string name, bool throwOnError); + + /// + /// Gets all types defined in this assembly. + /// + /// + public abstract ImmutableArray GetTypes(); + + /// + /// Loads the specified manifest resource from this assembly. + /// + /// + /// + public abstract ManifestResourceInfo? GetManifestResourceInfo(string resourceName); + + /// + /// Loads the specified manifest resource from this assembly. + /// + /// + /// + public abstract Stream? GetManifestResourceStream(string name); + + /// + /// Loads the specified manifest resource, scoped by the namespace of the specified type, from this assembly. + /// + /// + /// + /// + public abstract Stream? GetManifestResourceStream(TypeSymbol type, string name); + + /// + internal abstract ImmutableArray GetDeclaredCustomAttributes(); + + /// + ImmutableArray ICustomAttributeProviderInternal.GetDeclaredCustomAttributes() => GetDeclaredCustomAttributes(); + + /// + ICustomAttributeProviderInternal? ICustomAttributeProviderInternal.GetInheritedCustomAttributeProvider() => null; + + /// + public IEnumerable GetCustomAttributes(bool inherit = false) => _customAttributes.GetCustomAttributes(inherit); + + /// + public IEnumerable GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttributes(attributeType, inherit); + + /// + public CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttribute(attributeType, inherit); + + /// + public bool IsDefined(TypeSymbol attributeType, bool inherit = false) => _customAttributes.IsDefined(attributeType, inherit); + + /// + public override string ToString() => FullName ?? ""; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs index 5154ea67f6..7138371e43 100644 --- a/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs @@ -13,20 +13,20 @@ class ByRefTypeSymbol : HasElementSymbol /// /// /// - public ByRefTypeSymbol(ISymbolContext context, TypeSymbol elementType) : + public ByRefTypeSymbol(SymbolContext context, TypeSymbol elementType) : base(context, elementType) { } /// - protected override string NameSuffix => "&"; + protected sealed override string NameSuffix => "&"; /// public sealed override TypeAttributes Attributes => TypeAttributes.Public; /// - public override TypeSymbol? BaseType => null; + public sealed override TypeSymbol? BaseType => null; /// public sealed override bool IsByRef => true; @@ -38,15 +38,33 @@ public sealed override int GetArrayRank() } /// - public sealed override ImmutableList GetDeclaredConstructors() + public override ImmutableArray GetInterfaces() { - return ImmutableList.Empty; + return ImmutableArray.Empty; } /// - public sealed override ImmutableList GetDeclaredMethods() + public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) { - return ImmutableList.Empty; + return new InterfaceMapping(ImmutableList.Empty, interfaceType, ImmutableList.Empty, this); + } + + /// + internal sealed override ImmutableArray GetDeclaredConstructors() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredMethods() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs index bd14990c84..3d1afb149d 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs @@ -20,8 +20,9 @@ class ConstructedGenericConstructorSymbol : ConstructorSymbol /// /// /// + /// /// - public ConstructedGenericConstructorSymbol(ISymbolContext context, TypeSymbol declaringType, ConstructorSymbol definition, GenericContext genericContext) : + public ConstructedGenericConstructorSymbol(SymbolContext context, TypeSymbol declaringType, ConstructorSymbol definition, GenericContext genericContext) : base(context, declaringType) { _definition = definition ?? throw new ArgumentNullException(nameof(definition)); @@ -41,34 +42,16 @@ public ConstructedGenericConstructorSymbol(ISymbolContext context, TypeSymbol de public override string Name => _definition.Name; /// - public override bool IsMissing => _definition.IsMissing; + public sealed override bool IsMissing => false; /// - public override bool ContainsMissing => _definition.ContainsMissing; + public sealed override bool ContainsMissing => false; /// - public override bool IsComplete => _definition.IsComplete; + public sealed override bool IsComplete => true; /// - public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttribute(attributeType, inherit); - } - - /// - public override CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return _definition.GetCustomAttributes(inherit); - } - - /// - public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttributes(attributeType, inherit); - } - - /// - public override ImmutableList GetGenericArguments() + public override ImmutableArray GetGenericArguments() { return _definition.GetGenericArguments(); } @@ -80,15 +63,15 @@ public override MethodImplAttributes GetMethodImplementationFlags() } /// - public override ImmutableList GetParameters() + public override ImmutableArray GetParameters() { return _definition.GetParameters(); } /// - public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + internal override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.IsDefined(attributeType, inherit); + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs index f6dd5ef1ec..6718f7342f 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs @@ -1,4 +1,6 @@ using System; +using System.Collections.Immutable; +using System.Linq; using System.Reflection; namespace IKVM.CoreLib.Symbols @@ -10,7 +12,7 @@ namespace IKVM.CoreLib.Symbols class ConstructedGenericEventSymbol : EventSymbol { - readonly EventSymbol _definition; + internal readonly EventSymbol _definition; readonly GenericContext _genericContext; /// @@ -19,8 +21,9 @@ class ConstructedGenericEventSymbol : EventSymbol /// /// /// + /// /// - public ConstructedGenericEventSymbol(ISymbolContext context, TypeSymbol declaringType, EventSymbol definition, GenericContext genericContext) : + public ConstructedGenericEventSymbol(SymbolContext context, TypeSymbol declaringType, EventSymbol definition, GenericContext genericContext) : base(context, declaringType) { _definition = definition ?? throw new ArgumentNullException(nameof(definition)); @@ -28,102 +31,89 @@ public ConstructedGenericEventSymbol(ISymbolContext context, TypeSymbol declarin } /// - public override EventAttributes Attributes => _definition.Attributes; + public sealed override EventAttributes Attributes => _definition.Attributes; /// - public override string Name => _definition.Name; + public sealed override string Name => _definition.Name; /// - public override TypeSymbol? EventHandlerType => _definition.EventHandlerType?.Specialize(_genericContext); + public sealed override TypeSymbol? EventHandlerType => _definition.EventHandlerType?.Specialize(_genericContext); /// - public override MethodSymbol? AddMethod => _definition.AddMethod; + public sealed override bool IsMissing => false; /// - public override MethodSymbol? RemoveMethod => _definition.RemoveMethod; + public sealed override bool ContainsMissing => false; /// - public override MethodSymbol? RaiseMethod => _definition.RaiseMethod; + public sealed override bool IsComplete => true; /// - public override bool IsMissing => _definition.IsMissing; - - /// - public override bool ContainsMissing => _definition.ContainsMissing; - - /// - public override bool IsComplete => _definition.IsComplete; - - /// - public override MethodSymbol? GetAddMethod() - { - return _definition.GetAddMethod(); - } - - /// - public override MethodSymbol? GetAddMethod(bool nonPublic) + public sealed override MethodSymbol? GetAddMethod(bool nonPublic) { - return _definition.GetAddMethod(nonPublic); - } + var baseMethod = _definition.GetAddMethod(nonPublic); + if (baseMethod is null) + return null; - /// - public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttribute(attributeType, inherit); - } + foreach (var i in DeclaringType!.GetMethods()) + if (i is ConstructedGenericMethodSymbol m) + if (m._definition == baseMethod) + return m; - /// - public override CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return _definition.GetCustomAttributes(inherit); + return null; } /// - public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + public sealed override MethodSymbol? GetRemoveMethod(bool nonPublic) { - return _definition.GetCustomAttributes(attributeType, inherit); - } + var baseMethod = _definition.GetRemoveMethod(nonPublic); + if (baseMethod is null) + return null; - /// - public override MethodSymbol[] GetOtherMethods() - { - return _definition.GetOtherMethods(); - } + foreach (var i in DeclaringType!.GetMethods()) + if (i is ConstructedGenericMethodSymbol m) + if (m._definition == baseMethod) + return m; - /// - public override MethodSymbol[] GetOtherMethods(bool nonPublic) - { - return _definition.GetOtherMethods(nonPublic); + return null; } /// - public override MethodSymbol? GetRaiseMethod() + public sealed override MethodSymbol? GetRaiseMethod(bool nonPublic) { - return _definition.GetRaiseMethod(); - } - /// + var baseMethod = _definition.GetRaiseMethod(nonPublic); + if (baseMethod is null) + return null; - public override MethodSymbol? GetRaiseMethod(bool nonPublic) - { - return _definition.GetRaiseMethod(nonPublic); - } + foreach (var i in DeclaringType!.GetMethods()) + if (i is ConstructedGenericMethodSymbol m) + if (m._definition == baseMethod) + return m; - /// - public override MethodSymbol? GetRemoveMethod() - { - return _definition.GetRemoveMethod(); + return null; } /// - public override MethodSymbol? GetRemoveMethod(bool nonPublic) + public sealed override ImmutableArray GetOtherMethods(bool nonPublic) { - return _definition.GetRemoveMethod(nonPublic); + var b = ImmutableArray.CreateBuilder(); + + foreach (var baseMethod in _definition.GetOtherMethods(nonPublic)) + { + if (baseMethod is not null) + foreach (var i in DeclaringType!.GetMethods()) + if (i is ConstructedGenericMethodSymbol m) + if (m._definition == baseMethod) + b.Add(m); + } + + return b.ToImmutable(); } /// - public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.IsDefined(attributeType, inherit); + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs index 65cd146007..193f7a4f69 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs @@ -15,8 +15,8 @@ class ConstructedGenericFieldSymbol : FieldSymbol readonly GenericContext _genericContext; TypeSymbol? _fieldType; - ImmutableList? _optionalCustomModifiers; - ImmutableList? _requiredCustomModifiers; + ImmutableArray _optionalCustomModifiers; + ImmutableArray _requiredCustomModifiers; /// /// Initializes a new instance. @@ -25,7 +25,7 @@ class ConstructedGenericFieldSymbol : FieldSymbol /// /// /// - public ConstructedGenericFieldSymbol(ISymbolContext context, TypeSymbol declaringType, FieldSymbol definition, GenericContext genericContext) : + public ConstructedGenericFieldSymbol(SymbolContext context, TypeSymbol declaringType, FieldSymbol definition, GenericContext genericContext) : base(context, declaringType.Module, declaringType) { _definition = definition ?? throw new ArgumentNullException(nameof(definition)); @@ -33,89 +33,63 @@ public ConstructedGenericFieldSymbol(ISymbolContext context, TypeSymbol declarin } /// - public override FieldAttributes Attributes => _definition.Attributes; + public sealed override FieldAttributes Attributes => _definition.Attributes; /// - public override TypeSymbol FieldType => _fieldType ??= _definition.FieldType.Specialize(_genericContext); + public sealed override TypeSymbol FieldType => _fieldType ??= _definition.FieldType.Specialize(_genericContext); /// - public override string Name => _definition.Name; + public sealed override string Name => _definition.Name; /// - public override bool IsMissing => _definition.IsMissing; + public sealed override bool IsMissing => false; /// - public override bool ContainsMissing => _definition.ContainsMissing; + public sealed override bool ContainsMissing => false; /// - public override bool IsComplete => _definition.IsComplete; + public sealed override bool IsComplete => true; /// - public override object? GetRawConstantValue() + public sealed override object? GetRawConstantValue() { return _definition.GetRawConstantValue(); } /// - public override IImmutableList GetOptionalCustomModifiers() + public sealed override ImmutableArray GetOptionalCustomModifiers() { - return _optionalCustomModifiers ??= ComputeOptionalCustomModifiers(); - } - - /// - /// Computes the value for . - /// - /// - ImmutableList ComputeOptionalCustomModifiers() - { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetOptionalCustomModifiers()) - b.Add(i.Specialize(_genericContext)); - - return b.ToImmutable(); - } - - /// - public override IImmutableList GetRequiredCustomModifiers() - { - return _optionalCustomModifiers ??= ComputeRequiredCustomModifiers(); - } + if (_optionalCustomModifiers == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetOptionalCustomModifiers()) + b.Add(i.Specialize(_genericContext)); - /// - /// Computes the value for . - /// - /// - ImmutableList ComputeRequiredCustomModifiers() - { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetRequiredCustomModifiers()) - b.Add(i.Specialize(_genericContext)); + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.ToImmutable()); + } - return b.ToImmutable(); + return _optionalCustomModifiers; } /// - public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + public sealed override ImmutableArray GetRequiredCustomModifiers() { - return _definition.GetCustomAttribute(attributeType, inherit); - } + if (_requiredCustomModifiers == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetRequiredCustomModifiers()) + b.Add(i.Specialize(_genericContext)); - /// - public override CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return _definition.GetCustomAttributes(inherit); - } + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.ToImmutable()); + } - /// - public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttributes(attributeType, inherit); + return _requiredCustomModifiers; } /// - public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.IsDefined(attributeType, inherit); + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs index 50e3fed47d..41d935920e 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Immutable; +using System.Linq; using System.Reflection; using System.Threading; @@ -12,12 +13,13 @@ namespace IKVM.CoreLib.Symbols class ConstructedGenericMethodSymbol : MethodSymbol { - readonly MethodSymbol _definition; - readonly GenericContext _genericContext; + internal readonly MethodSymbol _definition; + internal readonly GenericContext _genericContext; + ImmutableArray _typeParameters; TypeSymbol? _returnType; ConstructedGenericParameterSymbol? _returnParameter; - ImmutableList? _parameters; + ImmutableArray _parameters; /// /// Initializes a new instance. @@ -28,7 +30,7 @@ class ConstructedGenericMethodSymbol : MethodSymbol /// /// /// - public ConstructedGenericMethodSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType, MethodSymbol definition, GenericContext genericContext) : + public ConstructedGenericMethodSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol? declaringType, MethodSymbol definition, GenericContext genericContext) : base(context, module, declaringType) { _definition = definition ?? throw new ArgumentNullException(nameof(definition)); @@ -36,19 +38,19 @@ public ConstructedGenericMethodSymbol(ISymbolContext context, IModuleSymbol modu } /// - public override MethodAttributes Attributes => _definition.Attributes; + public sealed override MethodAttributes Attributes => _definition.Attributes; /// - public override bool IsGenericMethod => true; + public sealed override bool IsGenericMethod => true; /// - public override bool IsGenericMethodDefinition => false; + public sealed override bool IsGenericMethodDefinition => false; /// - public override bool ContainsGenericParameters => false; + public sealed override bool ContainsGenericParameters => false; /// - public override ParameterSymbol ReturnParameter => GetReturnParameter(); + public sealed override ParameterSymbol ReturnParameter => GetReturnParameter(); /// /// Computes the value for . @@ -63,97 +65,79 @@ ConstructedGenericParameterSymbol GetReturnParameter() } /// - public override TypeSymbol ReturnType => _returnType ??= _definition.ReturnType.Specialize(_genericContext); + public sealed override TypeSymbol ReturnType => _returnType ??= _definition.ReturnType.Specialize(_genericContext); /// - public override ICustomAttributeProvider ReturnTypeCustomAttributes => _definition.ReturnTypeCustomAttributes; + public sealed override ICustomAttributeProvider ReturnTypeCustomAttributes => _definition.ReturnTypeCustomAttributes; /// - public override CallingConventions CallingConvention => _definition.CallingConvention; + public sealed override CallingConventions CallingConvention => _definition.CallingConvention; /// - public override MethodImplAttributes MethodImplementationFlags => _definition.MethodImplementationFlags; + public sealed override MethodImplAttributes MethodImplementationFlags => _definition.MethodImplementationFlags; /// - public override string Name => _definition.Name; + public sealed override string Name => _definition.Name; /// - public override bool IsMissing => _definition.IsMissing; + public sealed override bool IsMissing => false; /// - public override bool ContainsMissing => _definition.ContainsMissing; + public sealed override bool ContainsMissing => _genericContext.GenericMethodArguments != null && _genericContext.GenericMethodArguments.Value.Any(i => i.IsMissing || i.ContainsMissing); /// - public override bool IsComplete => _definition.IsComplete; + public sealed override bool IsComplete => true; /// - public override MethodSymbol GetBaseDefinition() + public sealed override MethodSymbol GetBaseDefinition() { - return _definition.GetBaseDefinition(); + throw new NotImplementedException(); } /// - public override ImmutableList GetGenericArguments() + public sealed override ImmutableArray GetGenericArguments() { - return _definition.GetGenericArguments(); - } + if (_typeParameters == default) + ImmutableInterlocked.InterlockedInitialize(ref _typeParameters, _definition.GetGenericArguments().Select(i => i.Specialize(_genericContext)).ToImmutableArray()); - /// - public override MethodSymbol GetGenericMethodDefinition() - { - throw new InvalidOperationException(); + return _typeParameters; } /// - public override MethodImplAttributes GetMethodImplementationFlags() - { - return _definition.GetMethodImplementationFlags(); - } - - /// - public override ImmutableList GetParameters() - { - if (_parameters == null) - Interlocked.CompareExchange(ref _parameters, ComputeGetParameters(), null); - - return _parameters; - } - - /// - /// Computs the value for . - /// - /// - ImmutableList ComputeGetParameters() + public sealed override MethodSymbol GetGenericMethodDefinition() { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetParameters()) - b.Add(new ConstructedGenericParameterSymbol(Context, this, i, _genericContext)); + // value only supported for generic method not method on generic type + if (_genericContext.GenericMethodArguments == null) + throw new InvalidOperationException(); - return b.ToImmutable(); + return _definition; } /// - public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + public sealed override MethodImplAttributes GetMethodImplementationFlags() { - return _definition.GetCustomAttribute(attributeType, inherit); + return _definition.GetMethodImplementationFlags(); } /// - public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + public sealed override ImmutableArray GetParameters() { - return _definition.GetCustomAttributes(inherit); - } + if (_parameters == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetParameters()) + b.Add(new ConstructedGenericParameterSymbol(Context, this, i, _genericContext)); - /// - public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttributes(attributeType, inherit); + ImmutableInterlocked.InterlockedInitialize(ref _parameters, b.ToImmutable()); + } + + return _parameters; } /// - public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.IsDefined(attributeType, inherit); + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs index 093e8e1063..73efab265a 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs @@ -11,6 +11,9 @@ class ConstructedGenericParameterSymbol : ParameterSymbol readonly ParameterSymbol _definition; readonly GenericContext _genericContext; + ImmutableArray _optionalCustomModifiers; + ImmutableArray _requiredCustomModifiers; + /// /// Initializes a new instance. /// @@ -19,7 +22,7 @@ class ConstructedGenericParameterSymbol : ParameterSymbol /// /// /// - public ConstructedGenericParameterSymbol(ISymbolContext context, MemberSymbol declaringMember, ParameterSymbol definition, GenericContext genericContext) : + public ConstructedGenericParameterSymbol(SymbolContext context, MemberSymbol declaringMember, ParameterSymbol definition, GenericContext genericContext) : base(context, declaringMember, definition.Position) { _definition = definition ?? throw new ArgumentNullException(nameof(definition)); @@ -39,48 +42,48 @@ public ConstructedGenericParameterSymbol(ISymbolContext context, MemberSymbol de public override object? DefaultValue => _definition.DefaultValue; /// - public override bool IsMissing => _definition.IsMissing; + public sealed override bool IsMissing => false; /// - public override bool ContainsMissing => _definition.ContainsMissing; + public sealed override bool ContainsMissing => false; /// - public override bool IsComplete => _definition.IsComplete; + public sealed override bool IsComplete => true; /// - public override ImmutableList GetOptionalCustomModifiers() + public override ImmutableArray GetOptionalCustomModifiers() { - return _definition.GetOptionalCustomModifiers(); - } + if (_optionalCustomModifiers == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetOptionalCustomModifiers()) + b.Add(i.Specialize(_genericContext)); - /// - public override ImmutableList GetRequiredCustomModifiers() - { - return _definition.GetRequiredCustomModifiers(); - } + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.ToImmutable()); + } - /// - public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttribute(attributeType, inherit); + return _optionalCustomModifiers; } /// - public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + public override ImmutableArray GetRequiredCustomModifiers() { - return _definition.GetCustomAttributes(inherit); - } + if (_requiredCustomModifiers == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetRequiredCustomModifiers()) + b.Add(i.Specialize(_genericContext)); - /// - public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttributes(attributeType, inherit); + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.ToImmutable()); + } + + return _requiredCustomModifiers; } /// - public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + internal override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.IsDefined(attributeType, inherit); + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs index 62567dba88..e2b3a472c3 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols @@ -13,6 +14,10 @@ class ConstructedGenericPropertySymbol : PropertySymbol readonly PropertySymbol _definition; readonly GenericContext _genericContext; + ImmutableArray _indexParameters; + ImmutableArray _optionalCustomModifiers; + ImmutableArray _requiredCustomModifiers; + /// /// Initializes a new instance. /// @@ -21,7 +26,7 @@ class ConstructedGenericPropertySymbol : PropertySymbol /// /// /// - public ConstructedGenericPropertySymbol(ISymbolContext context, TypeSymbol declaringType, PropertySymbol definition, GenericContext genericContext) : + public ConstructedGenericPropertySymbol(SymbolContext context, TypeSymbol declaringType, PropertySymbol definition, GenericContext genericContext) : base(context, declaringType) { _definition = definition ?? throw new ArgumentNullException(nameof(definition)); @@ -40,73 +45,86 @@ public ConstructedGenericPropertySymbol(ISymbolContext context, TypeSymbol decla /// public override bool CanWrite => _definition.CanWrite; - /// - public override MethodSymbol? GetMethod => _definition.GetMethod; - - /// - public override MethodSymbol? SetMethod => _definition.SetMethod; - - /// - public override MemberTypes MemberType => _definition.MemberType; - /// public override string Name => _definition.Name; /// - public override bool IsMissing => _definition.IsMissing; + public sealed override bool IsMissing => false; /// - public override bool ContainsMissing => _definition.ContainsMissing; + public sealed override bool ContainsMissing => false; /// - public override bool IsComplete => _definition.IsComplete; + public sealed override bool IsComplete => true; /// - public override MethodSymbol[] GetAccessors() + public override ImmutableArray GetAccessors(bool nonPublic) { - return _definition.GetAccessors(); - } + var b = ImmutableArray.CreateBuilder(); - /// - public override MethodSymbol[] GetAccessors(bool nonPublic) - { - return _definition.GetAccessors(nonPublic); - } + foreach (var baseMethod in _definition.GetAccessors(nonPublic)) + { + if (baseMethod is not null) + foreach (var i in DeclaringType!.GetMethods()) + if (i is ConstructedGenericMethodSymbol m) + if (m._definition == baseMethod) + b.Add(m); + } - /// - public override MethodSymbol? GetGetMethod() - { - return _definition.GetGetMethod(); + return b.ToImmutable(); } /// public override MethodSymbol? GetGetMethod(bool nonPublic) { - return _definition.GetGetMethod(nonPublic); - } + var baseMethod = _definition.GetGetMethod(nonPublic); + if (baseMethod is null) + return null; - /// - public override MethodSymbol? GetSetMethod() - { - return _definition.GetSetMethod(); + foreach (var i in DeclaringType!.GetMethods()) + if (i is ConstructedGenericMethodSymbol m) + if (m._definition == baseMethod) + return m; + + return null; } /// public override MethodSymbol? GetSetMethod(bool nonPublic) { - return _definition.GetSetMethod(nonPublic); + var baseMethod = _definition.GetSetMethod(nonPublic); + if (baseMethod is null) + return null; + + foreach (var i in DeclaringType!.GetMethods()) + if (i is ConstructedGenericMethodSymbol m) + if (m._definition == baseMethod) + return m; + + return null; } /// - public override ParameterSymbol[] GetIndexParameters() + public override ImmutableArray GetIndexParameters() { - return _definition.GetIndexParameters(); + if (_indexParameters == default) + { + var b = ImmutableArray.CreateBuilder(); + var l = _definition.GetIndexParameters(); + + foreach (var i in l) + b.Add(new ConstructedGenericParameterSymbol(Context, this, i, _genericContext)); + + ImmutableInterlocked.InterlockedInitialize(ref _indexParameters, b.ToImmutable()); + } + + return _indexParameters; } /// public override TypeSymbol GetModifiedPropertyType() { - return _definition.GetModifiedPropertyType(); + return _definition.GetModifiedPropertyType().Specialize(_genericContext); } /// @@ -116,39 +134,53 @@ public override TypeSymbol GetModifiedPropertyType() } /// - public override TypeSymbol[] GetOptionalCustomModifiers() + public override ImmutableArray GetOptionalCustomModifiers() { - return _definition.GetOptionalCustomModifiers(); - } + if (_optionalCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, ComputeOptionalCustomModifiers()); - /// - public override TypeSymbol[] GetRequiredCustomModifiers() - { - return _definition.GetRequiredCustomModifiers(); + return _optionalCustomModifiers; } - /// - public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) + /// + /// Computes the value for . + /// + /// + ImmutableArray ComputeOptionalCustomModifiers() { - return _definition.GetCustomAttribute(attributeType, inherit); + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetOptionalCustomModifiers()) + b.Add(i.Specialize(_genericContext)); + + return b.ToImmutable(); } /// - public override CustomAttribute[] GetCustomAttributes(bool inherit = false) + public override ImmutableArray GetRequiredCustomModifiers() { - return _definition.GetCustomAttributes(inherit); + if (_requiredCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, ComputeRequiredCustomModifiers()); + + return _requiredCustomModifiers; } - /// - public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) + /// + /// Computes the value for . + /// + /// + ImmutableArray ComputeRequiredCustomModifiers() { - return _definition.GetCustomAttributes(attributeType, inherit); + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetRequiredCustomModifiers()) + b.Add(i.Specialize(_genericContext)); + + return b.ToImmutable(); } /// - public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) + internal override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.IsDefined(attributeType, inherit); + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs index 34cc3df1a8..2188686c6e 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs @@ -2,7 +2,8 @@ using System.Collections.Immutable; using System.Linq; using System.Reflection; -using System.Threading; + +using IKVM.CoreLib.Text; namespace IKVM.CoreLib.Symbols { @@ -14,26 +15,27 @@ class ConstructedGenericTypeSymbol : TypeSymbol { readonly TypeSymbol _definition; - readonly ImmutableList _typeArguments; + readonly GenericContext _genericContext; - ImmutableList? _fields; - ImmutableList? _constructors; - ImmutableList? _methods; - ImmutableList? _properties; - ImmutableList? _events; + ImmutableArray _interfaces; + ImmutableArray _fields; + ImmutableArray _constructors; + ImmutableArray _methods; + ImmutableArray _properties; + ImmutableArray _events; /// /// Initializes a new instance. /// /// /// - /// + /// /// - public ConstructedGenericTypeSymbol(ISymbolContext context, TypeSymbol definition, ImmutableList typeArguments) : - base(context, definition.Module, definition) + public ConstructedGenericTypeSymbol(SymbolContext context, TypeSymbol definition, GenericContext genericContext) : + base(context, definition.Module) { _definition = definition ?? throw new ArgumentNullException(nameof(definition)); - _typeArguments = typeArguments ?? throw new ArgumentNullException(nameof(typeArguments)); + _genericContext = genericContext; } /// @@ -43,90 +45,115 @@ public ConstructedGenericTypeSymbol(ISymbolContext context, TypeSymbol definitio public sealed override TypeCode TypeCode => _definition.TypeCode; /// - public override TypeSymbol? BaseType => _definition.BaseType?.Specialize(new GenericContext(_typeArguments, null)); + public sealed override TypeSymbol? BaseType => _definition.BaseType?.Specialize(_genericContext); /// public sealed override bool IsTypeDefinition => false; /// - public override bool IsGenericTypeDefinition => false; + public sealed override bool IsGenericTypeDefinition => false; /// - public override bool IsConstructedGenericType => true; + public sealed override bool IsConstructedGenericType => true; /// - public override bool IsGenericParameter => false; + public sealed override bool IsGenericTypeParameter => false; /// - public sealed override bool ContainsGenericParameters => _typeArguments.Any(i => i.ContainsGenericParameters); + public sealed override bool IsGenericMethodParameter => false; /// - public override int GenericParameterPosition => throw new NotSupportedException(); + public sealed override bool ContainsGenericParameters => false; /// - public override bool HasElementType => false; + public sealed override int GenericParameterPosition => throw new NotSupportedException(); /// - public override bool IsArray => false; + public sealed override bool HasElementType => false; /// - public override bool IsSZArray => false; + public sealed override bool IsArray => false; /// - public override bool IsByRef => false; + public sealed override bool IsSZArray => false; /// - public override bool IsPointer => false; + public sealed override bool IsByRef => false; /// - public override bool IsFunctionPointer => false; + public sealed override bool IsPointer => false; /// - public override bool IsUnmanagedFunctionPointer => false; + public sealed override bool IsFunctionPointer => false; /// - public override MethodBaseSymbol? DeclaringMethod => _definition.DeclaringMethod; + public sealed override bool IsUnmanagedFunctionPointer => false; /// - public override string? FullName => _definition.FullName; + public sealed override MethodBaseSymbol? DeclaringMethod => _definition.DeclaringMethod; /// - public override string? Namespace => _definition.Namespace; + public sealed override string? FullName => ComputeFullName(); - /// - public override GenericParameterAttributes GenericParameterAttributes => _definition.GenericParameterAttributes; + /// + /// Computes the value for . + /// + /// + string? ComputeFullName() + { + if (ContainsGenericParameters) + return null; - /// - public override ImmutableList GenericTypeArguments => _definition.GenericTypeArguments; + using var fullName = new ValueStringBuilder(stackalloc char[256]); + fullName.Append(_definition.FullName); + fullName.Append('['); + + if (_genericContext.GenericTypeArguments != null) + { + for (int i = 0; i < _genericContext.GenericTypeArguments.Value.Length; i++) + { + if (i != 0) + fullName.Append(','); + + fullName.Append('['); + fullName.Append(_genericContext.GenericTypeArguments.Value[i].AssemblyQualifiedName); + fullName.Append(']'); + } + } + + + fullName.Append(']'); + return fullName.ToString(); + } /// - public override bool IsPrimitive => _definition.IsPrimitive; + public sealed override string? Namespace => _definition.Namespace; /// - public override bool IsEnum => _definition.IsEnum; + public sealed override GenericParameterAttributes GenericParameterAttributes => _definition.GenericParameterAttributes; /// - public override bool IsSignatureType => _definition.IsSignatureType; + public sealed override bool IsPrimitive => _definition.IsPrimitive; /// - public override ConstructorSymbol? TypeInitializer => _definition.TypeInitializer; + public sealed override bool IsEnum => _definition.IsEnum; /// - public override string Name => _definition.Name; + public sealed override string Name => _definition.Name; /// - public override bool IsMissing => _definition.IsMissing; + public sealed override bool IsMissing => false; /// - public override bool ContainsMissing => _definition.ContainsMissing; + public sealed override bool ContainsMissing => _genericContext.GenericTypeArguments != null && _genericContext.GenericTypeArguments.Value.Any(i => i.IsMissing || i.ContainsMissing); /// - public override bool IsComplete => _definition.IsComplete; + public sealed override bool IsComplete => true; /// - public override TypeSymbol GetEnumUnderlyingType() + public sealed override TypeSymbol GetEnumUnderlyingType() { - return _definition.GetEnumUnderlyingType().Specialize(new GenericContext(_typeArguments, null)); + return _definition.GetEnumUnderlyingType().Specialize(_genericContext); } /// @@ -136,7 +163,7 @@ public override TypeSymbol GetEnumUnderlyingType() } /// - public override int GetArrayRank() + public sealed override int GetArrayRank() { throw new InvalidOperationException(); } @@ -148,245 +175,170 @@ public sealed override TypeSymbol GetGenericTypeDefinition() } /// - public sealed override ImmutableList GetGenericArguments() + public sealed override ImmutableArray GetGenericArguments() { - return _typeArguments; + return _genericContext.GenericTypeArguments!.Value; } /// - public override ImmutableList GetGenericParameterConstraints() + public sealed override ImmutableArray GetGenericParameterConstraints() { throw new InvalidOperationException(); } /// - public override ImmutableList GetDeclaredFields() + internal override ImmutableArray GetDeclaredFields() { - if (_fields == null) - Interlocked.CompareExchange(ref _fields, ComputeDeclaredFields(), null); + if (_fields == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetFields(DeclaredOnlyLookup)) + b.Add(new ConstructedGenericFieldSymbol(Context, this, i, _genericContext)); - return _fields ?? throw new InvalidOperationException(); - } - - /// - /// Computes the declared fields of this type. - /// - /// - ImmutableList ComputeDeclaredFields() - { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetDeclaredFields()) - b.Add(new ConstructedGenericFieldSymbol(Context, this, i, new GenericContext(_typeArguments, null))); + ImmutableInterlocked.InterlockedInitialize(ref _fields, b.ToImmutable()); + } - return b.ToImmutable(); + return _fields; } /// - public override ImmutableList GetDeclaredConstructors() + internal override ImmutableArray GetDeclaredConstructors() { - if (_constructors == null) - Interlocked.CompareExchange(ref _constructors, ComputeDeclaredConstructors(), null); + if (_constructors == default) + { + var b = ImmutableArray.CreateBuilder(); - return _constructors ?? throw new InvalidOperationException(); - } + // add static initializer as a declared constructor, though it is filtered out from GetConstructors + if (_definition.TypeInitializer != null) + b.Add(new ConstructedGenericConstructorSymbol(Context, this, _definition.TypeInitializer, _genericContext)); - /// - /// Computes the declared constructors of this type. - /// - /// - ImmutableList ComputeDeclaredConstructors() - { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetDeclaredConstructors()) - b.Add(new ConstructedGenericConstructorSymbol(Context, this, i, new GenericContext(_typeArguments, null))); + foreach (var i in _definition.GetConstructors(DeclaredOnlyLookup)) + b.Add(new ConstructedGenericConstructorSymbol(Context, this, i, _genericContext)); + + ImmutableInterlocked.InterlockedInitialize(ref _constructors, b.ToImmutable()); + } - return b.ToImmutable(); + return _constructors; } /// - public override ImmutableList GetDeclaredMethods() + internal override ImmutableArray GetDeclaredMethods() { - if (_methods == null) - Interlocked.CompareExchange(ref _methods, ComputeDeclaredMethods(), null); + if (_methods == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetMethods(DeclaredOnlyLookup)) + b.Add(new ConstructedGenericMethodSymbol(Context, Module, this, i, _genericContext)); - return _methods ?? throw new InvalidOperationException(); - } - - /// - /// Computes the declared methods of this type. - /// - /// - ImmutableList ComputeDeclaredMethods() - { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetDeclaredMethods()) - b.Add(new ConstructedGenericMethodSymbol(Context, this, i, new GenericContext(_typeArguments, null))); + ImmutableInterlocked.InterlockedInitialize(ref _methods, b.ToImmutable()); + } - return b.ToImmutable(); + return _methods; } /// - public override ImmutableList GetDeclaredProperties() + internal override ImmutableArray GetDeclaredProperties() { - if (_properties == null) - Interlocked.CompareExchange(ref _properties, ComputeDeclaredProperties(), null); + if (_properties == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetProperties(DeclaredOnlyLookup)) + b.Add(new ConstructedGenericPropertySymbol(Context, this, i, _genericContext)); - return _properties ?? throw new InvalidOperationException(); - } - - /// - /// Computes the declared properties of this type. - /// - /// - ImmutableList ComputeDeclaredProperties() - { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetDeclaredProperties()) - b.Add(new ConstructedGenericPropertySymbol(Context, this, i, new GenericContext(_typeArguments, null))); + ImmutableInterlocked.InterlockedInitialize(ref _properties, b.ToImmutable()); + } - return b.ToImmutable(); + return _properties; } /// - public override ImmutableList GetDeclaredEvents() + internal override ImmutableArray GetDeclaredEvents() { - if (_events == null) - Interlocked.CompareExchange(ref _events, ComputeDeclaredEvents(), null); + if (_events == default) + { + var b = ImmutableArray.CreateBuilder(); + foreach (var i in _definition.GetEvents(DeclaredOnlyLookup)) + b.Add(new ConstructedGenericEventSymbol(Context, this, i, _genericContext)); - return _events ?? throw new InvalidOperationException(); - } - - /// - /// Computes the declared events of this type. - /// - /// - ImmutableList ComputeDeclaredEvents() - { - var b = ImmutableList.CreateBuilder(); - foreach (var i in _definition.GetDeclaredEvents()) - b.Add(new ConstructedGenericEventSymbol(Context, this, i, new GenericContext(_typeArguments, null))); - - return b.ToImmutable(); - } - - public override ConstructorSymbol? GetConstructor(BindingFlags bindingFlags, ImmutableList? types) - { - return _definition.GetConstructor(bindingFlags, types); - } + ImmutableInterlocked.InterlockedInitialize(ref _events, b.ToImmutable()); + } - public override ImmutableList GetConstructors(BindingFlags bindingFlags) - { - return _definition.GetConstructors(bindingFlags); + return _events; } - public override ImmutableList GetDefaultMembers() + /// + internal override ImmutableArray GetDeclaredNestedTypes() { - return _definition.GetDefaultMembers(); + return ImmutableArray.Empty; } - public override string? GetEnumName(object value) + /// + public sealed override string? GetEnumName(object value) { return _definition.GetEnumName(value); } - public override ImmutableList GetEnumNames() + /// + public sealed override ImmutableArray GetEnumNames() { return _definition.GetEnumNames(); } - public override EventSymbol? GetEvent(string name, BindingFlags bindingFlags) - { - return _definition.GetEvent(name, bindingFlags); - } - - public override ImmutableList GetEvents(BindingFlags bindingFlags) - { - return _definition.GetEvents(bindingFlags); - } - - public override FieldSymbol? GetField(string name, BindingFlags bindingFlags) - { - return _definition.GetField(name, bindingFlags); - } - - public override ImmutableList GetFields(BindingFlags bindingFlags) - { - return _definition.GetFields(bindingFlags); - } - - public override TypeSymbol? GetInterface(string name, bool ignoreCase) - { - return _definition.GetInterface(name, ignoreCase); - } - - public override ImmutableList GetInterfaces(bool inherit = true) - { - return _definition.GetInterfaces(inherit); - } - - public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) - { - return _definition.GetInterfaceMap(interfaceType); - } - - public override MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableList? types, ImmutableList? modifiers) - { - return _definition.GetMethod(name, genericParameterCount, bindingFlags, callConvention, types, modifiers); - } - - public override ImmutableList GetMethods(BindingFlags bindingFlags) + /// + public override ImmutableArray GetInterfaces() { - return _definition.GetMethods(bindingFlags); - } + if (_interfaces == default) + { + var l = _definition.GetInterfaces(); + var b = ImmutableArray.CreateBuilder(); + foreach (var i in l) + b.Add(i.Specialize(_genericContext)); - public override TypeSymbol? GetNestedType(string name, BindingFlags bindingFlags) - { - return _definition.GetNestedType(name, bindingFlags); - } + ImmutableInterlocked.InterlockedInitialize(ref _interfaces, b.ToImmutable()); + } - public override ImmutableList GetNestedTypes(BindingFlags bindingFlags) - { - return _definition.GetNestedTypes(bindingFlags); + return _interfaces; } - public override PropertySymbol? GetProperty(string name, BindingFlags bindingFlags) + /// + public sealed override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) { - return _definition.GetProperty(name, bindingFlags); + throw new NotImplementedException(); } - public override PropertySymbol? GetProperty(string name, TypeSymbol? returnType, ImmutableList? types) + /// + public sealed override bool IsEnumDefined(object value) { - return _definition.GetProperty(name, returnType, types); + return _definition.IsEnumDefined(value); } - public override ImmutableList GetProperties(BindingFlags bindingFlags) + /// + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.GetProperties(bindingFlags); + throw new NotImplementedException(); } - public override bool IsEnumDefined(object value) + /// + public override string ToString() { - return _definition.IsEnumDefined(value); - } + using var sb = new ValueStringBuilder(stackalloc char[256]); + sb.Append(_definition.ToString()); + sb.Append('['); - public override CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttribute(attributeType, inherit); - } + if (_genericContext.GenericTypeArguments != null) + { + for (int i = 0; i < _genericContext.GenericTypeArguments.Value.Length; i++) + { + if (i != 0) + sb.Append(','); - public override CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return _definition.GetCustomAttributes(inherit); - } + sb.Append(_genericContext.GenericTypeArguments.Value[i].ToString()); + } + } - public override CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) - { - return _definition.GetCustomAttributes(attributeType, inherit); - } + sb.Append(']'); - public override bool IsDefined(TypeSymbol attributeType, bool inherit = false) - { - return _definition.IsDefined(attributeType, inherit); + return sb.ToString(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs index 4871732c95..2fbfa100d1 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs @@ -11,7 +11,7 @@ abstract class ConstructorSymbol : MethodBaseSymbol /// /// /// - public ConstructorSymbol(ISymbolContext context, TypeSymbol declaringType) : + public ConstructorSymbol(SymbolContext context, TypeSymbol declaringType) : base(context, declaringType.Module, declaringType) { diff --git a/src/IKVM.CoreLib/Symbols/CustomAttribute.cs b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs index a910c5aa80..99188dbd62 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttribute.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs @@ -1,13 +1,16 @@ using System; +using System.Collections.Generic; using System.Collections.Immutable; using System.Linq; +using IKVM.CoreLib.Text; + namespace IKVM.CoreLib.Symbols { readonly record struct CustomAttribute( - ITypeSymbol AttributeType, - IConstructorSymbol Constructor, + TypeSymbol AttributeType, + ConstructorSymbol Constructor, ImmutableArray ConstructorArguments, ImmutableArray NamedArguments) { @@ -18,7 +21,7 @@ readonly record struct CustomAttribute( /// /// /// - public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs) + public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), @@ -34,7 +37,7 @@ public static CustomAttribute Create(IConstructorSymbol ctor, object?[] construc /// /// /// - public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs, IFieldSymbol[] namedFields, object?[] fieldValues) + public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs, FieldSymbol[] namedFields, object?[] fieldValues) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), @@ -50,7 +53,7 @@ public static CustomAttribute Create(IConstructorSymbol ctor, object?[] construc /// /// /// - public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues) + public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs, PropertySymbol[] namedProperties, object?[] propertyValues) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), @@ -68,7 +71,7 @@ public static CustomAttribute Create(IConstructorSymbol ctor, object?[] construc /// /// /// - public static CustomAttribute Create(IConstructorSymbol ctor, object?[] constructorArgs, IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) + public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs, PropertySymbol[] namedProperties, object?[] propertyValues, FieldSymbol[] namedFields, object?[] fieldValues) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), @@ -85,7 +88,7 @@ public static CustomAttribute Create(IConstructorSymbol ctor, object?[] construc /// /// /// - static ImmutableArray PackTypedArgs(ITypeSymbol[] types, object?[] values) + static ImmutableArray PackTypedArgs(TypeSymbol[] types, object?[] values) { if (types is null) throw new ArgumentNullException(nameof(types)); @@ -107,7 +110,7 @@ static ImmutableArray PackTypedArgs(ITypeSymbol[] /// /// /// - static CustomAttributeTypedArgument PackTypedArg(ITypeSymbol type, object? value) + static CustomAttributeTypedArgument PackTypedArg(TypeSymbol type, object? value) { return new CustomAttributeTypedArgument(type, value); } @@ -118,7 +121,7 @@ static CustomAttributeTypedArgument PackTypedArg(ITypeSymbol type, object? value /// /// /// - static ImmutableArray PackNamedArgs(IPropertySymbol[] namedProperties, object?[] propertyValues, IFieldSymbol[] namedFields, object?[] fieldValues) + static ImmutableArray PackNamedArgs(PropertySymbol[] namedProperties, object?[] propertyValues, FieldSymbol[] namedFields, object?[] fieldValues) { var a = ImmutableArray.CreateBuilder(namedProperties.Length + namedFields.Length); for (int i = 0; i < namedProperties.Length; i++) @@ -135,7 +138,7 @@ static ImmutableArray PackNamedArgs(IPropertySymbo /// /// /// - static CustomAttributeNamedArgument PackNamedArg(IPropertySymbol property, object? v) + static CustomAttributeNamedArgument PackNamedArg(PropertySymbol property, object? v) { return new CustomAttributeNamedArgument(false, property, property.Name, PackTypedArg(property.PropertyType, v)); } @@ -146,11 +149,49 @@ static CustomAttributeNamedArgument PackNamedArg(IPropertySymbol property, objec /// /// /// - static CustomAttributeNamedArgument PackNamedArg(IFieldSymbol field, object? v) + static CustomAttributeNamedArgument PackNamedArg(FieldSymbol field, object? v) { return new CustomAttributeNamedArgument(false, field, field.Name, PackTypedArg(field.FieldType, v)); } + /// + public override string ToString() + { + var vsb = new ValueStringBuilder(stackalloc char[256]); + + vsb.Append('['); + vsb.Append(Constructor.DeclaringType!.FullName); + vsb.Append('('); + + var first = true; + + var constructorArguments = ConstructorArguments; + var constructorArgumentsCount = constructorArguments.Length; + for (int i = 0; i < constructorArgumentsCount; i++) + { + if (!first) + vsb.Append(", "); + + vsb.Append(constructorArguments[i].ToString()); + first = false; + } + + var namedArguments = NamedArguments; + var namedArgumentsCount = namedArguments.Length; + for (int i = 0; i < namedArgumentsCount; i++) + { + if (!first) + vsb.Append(", "); + + vsb.Append(namedArguments[i].ToString()); + first = false; + } + + vsb.Append(")]"); + + return vsb.ToString(); + } + } diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs new file mode 100644 index 0000000000..8fbeb4c32f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs @@ -0,0 +1,143 @@ +using System; +using System.Collections.Immutable; +using System.Linq; +using System.Reflection; + +using IKVM.CoreLib.Collections; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Provides implementations in support of . + /// + struct CustomAttributeImpl + { + + readonly SymbolContext _context; + readonly ICustomAttributeProviderInternal _provider; + + TypeSymbol? _attributeUsageAttributeType; + ImmutableArray _declaredCustomAttributes; + ImmutableArray _declaredAndInheritedCustomAttributes; + + /// + /// Initializes a new instance. + /// + public CustomAttributeImpl(SymbolContext context, ICustomAttributeProviderInternal provider) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _provider = provider ?? throw new System.ArgumentNullException(nameof(provider)); + } + + /// + /// Returns the custom attributes applied to this member. + /// + /// + /// + public ImmutableArray GetCustomAttributes(bool inherit) + { + if (inherit == false) + { + if (_declaredCustomAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _declaredCustomAttributes, _provider.GetDeclaredCustomAttributes()); + + return _declaredCustomAttributes; + } + else + { + if (_declaredAndInheritedCustomAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _declaredAndInheritedCustomAttributes, ComputeInheritedCustomAttributes()); + + return _declaredAndInheritedCustomAttributes; + } + } + + /// + /// Computes the custom attributes that are applied to this member, including those which are inherited. + /// + /// + ImmutableArray ComputeInheritedCustomAttributes() + { + var list = _provider.GetDeclaredCustomAttributes(); + + // move through the inherited custom attribute providers + for (var provider = _provider.GetInheritedCustomAttributeProvider(); provider != null; provider = provider.GetInheritedCustomAttributeProvider()) + foreach (var customAttribute in provider.GetDeclaredCustomAttributes()) + if (IsInheritable(customAttribute)) + list = list.Add(customAttribute); + + return list; + } + + /// + /// Returns true if the specified is inherited. + /// + /// + /// + /// + bool IsInheritable(CustomAttribute customAttribute) + { + _attributeUsageAttributeType ??= _context.ResolveCoreType(typeof(AttributeUsageAttribute).FullName!); + if (_attributeUsageAttributeType == null) + throw new InvalidOperationException("Could not find core type System.AttributeUsageAttribute."); + + // find first AttributeUsageAttribute + var attributeUsageAttribute = customAttribute.AttributeType.GetCustomAttribute(_attributeUsageAttributeType, true); + if (attributeUsageAttribute.HasValue == false) + return false; + + // return whether the Inherited property is set + return GetInheritedValue(attributeUsageAttribute.Value); + } + + /// + /// Gets the boolean value of the property. + /// + /// + /// + bool GetInheritedValue(CustomAttribute attributeUsageAttribute) + { + foreach (var i in attributeUsageAttribute.NamedArguments) + if (i.IsField && i.MemberName == nameof(AttributeUsageAttribute.Inherited) && (bool?)i.TypedValue.Value == true) + return true; + + return false; + } + + /// + /// Returns the custom attributes applied to this member. + /// + /// + /// + public ImmutableArray GetCustomAttributes(TypeSymbol attributeType, bool inherit) + { + return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToImmutableArray(); + + } + + /// + /// Retrieves a custom attribute of a specified type applied to this member. + /// + /// + /// + /// + public CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit) + { + return GetCustomAttributes(attributeType, inherit).SingleOrDefaultOrThrow(() => new AmbiguousMatchException()); + } + + /// + /// Determines whether any custom attributes of a specified type are applied to an assembly, module, type member, or method parameter. + /// + /// + /// + /// + public bool IsDefined(TypeSymbol attributeType, bool inherit) + { + return GetCustomAttributes(attributeType, inherit).Any(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs index 9ba5842e8d..97a90013a6 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs @@ -1,10 +1,29 @@ -namespace IKVM.CoreLib.Symbols +using System.Runtime.InteropServices; + +namespace IKVM.CoreLib.Symbols { readonly record struct CustomAttributeNamedArgument( bool IsField, - IMemberSymbol MemberInfo, + MemberSymbol MemberInfo, string MemberName, - CustomAttributeTypedArgument TypedValue); + CustomAttributeTypedArgument TypedValue) + { + + /// + public override string ToString() + { + if (MemberInfo is null) + return base.ToString()!; + + return $"{MemberInfo.Name} = {TypedValue.ToString(ArgumentType != ArgumentType.Context.ResolveCoreType("System.Object"))}"; + } + + /// + /// Gets the type of the argument. + /// + internal TypeSymbol ArgumentType => MemberInfo is FieldSymbol fi ? fi.FieldType : ((PropertySymbol)MemberInfo).PropertyType; + + } } diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs index d19aebfddb..5f868c3f6a 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs @@ -1,8 +1,73 @@ -namespace IKVM.CoreLib.Symbols +using IKVM.CoreLib.Text; + +using System; +using System.Collections.Generic; + +namespace IKVM.CoreLib.Symbols { readonly record struct CustomAttributeTypedArgument( - ITypeSymbol ArgumentType, - object? Value); + TypeSymbol ArgumentType, + object? Value) + { + + + public override string ToString() => ToString(false); + + /// + /// Returns a string reprsentation of this typed argument. + /// + /// + /// + internal string ToString(bool typed) + { + if (ArgumentType is null) + return base.ToString()!; + + if (ArgumentType.IsEnum) + return typed ? $"{Value}" : $"({ArgumentType.FullName}){Value}"; + + if (Value is null) + return typed ? "null" : $"({ArgumentType.Name})null"; + + if (ArgumentType == ArgumentType.Context.ResolveCoreType("System.String")) + return $"\"{Value}\""; + + if (ArgumentType == ArgumentType.Context.ResolveCoreType("System.Char")) + return $"'{Value}'"; + + if (ArgumentType == ArgumentType.Context.ResolveCoreType("System.Type")) + return $"typeof({((TypeSymbol)Value!).FullName})"; + + if (ArgumentType.IsArray) + { + var array = (IReadOnlyList)Value!; + var elementType = ArgumentType.GetElementType()!; + + using var result = new ValueStringBuilder(stackalloc char[256]); + result.Append("new "); + result.Append(elementType.IsEnum ? elementType.FullName : elementType.Name); + result.Append('['); + var count = array.Count; + result.Append(count.ToString()); + result.Append("] { "); + + for (int i = 0; i < count; i++) + { + if (i != 0) + result.Append(", "); + + result.Append(array[i].ToString(elementType != ArgumentType.Context.ResolveCoreType("System.Object"))); + } + + result.Append(" }"); + + return result.ToString(); + } + + return typed ? $"{Value}" : $"({ArgumentType.Name}){Value}"; + } + + } } diff --git a/src/IKVM.CoreLib/Symbols/DefaultBinder.cs b/src/IKVM.CoreLib/Symbols/DefaultBinder.cs new file mode 100644 index 0000000000..58a58a31e6 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/DefaultBinder.cs @@ -0,0 +1,726 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Provides methods to select various symbols based on requirements. + /// + internal class DefaultBinder + { + + readonly SymbolContext _context; + + TypeSymbol? _lazyObjectType; + TypeSymbol? _lazyIntPtrType; + TypeSymbol? _lazyUIntPtrType; + + /// + /// Initializes a new instance. + /// + /// + /// + public DefaultBinder(SymbolContext context) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + } + + /// + /// Gets the symbol for . + /// + TypeSymbol ObjectType => _lazyObjectType ??= _context.ResolveCoreType("System.Object"); + + /// + /// Gets the symbol for . + /// + TypeSymbol IntPtrType => _lazyIntPtrType ??= _context.ResolveCoreType("System.IntPtr"); + + /// + /// Gets the symbol for . + /// + TypeSymbol UIntPtrType => _lazyUIntPtrType ??= _context.ResolveCoreType("System.UIntPtr"); + + /// + /// Given a set of methods that match the base criteria, select a method based upon an array of parameter types. This + /// method should return null if no method matches the criteria. + /// + public MethodBaseSymbol? SelectMethod(IReadOnlyList match, BindingFlags bindingFlags, ImmutableArray types, ImmutableArray? modifiers) + { + // we don't automatically jump out on exact match + if (match == null || match.Count == 0) + throw new ArgumentException("Unexpected empty array.", nameof(match)); + + var candidates = new List(match); + + // find all the methods that can be described by the types parameter + // remove all of them that cannot + int curIdx = 0; + for (var i = 0; i < candidates.Count; i++) + { + var par = candidates[i].GetParameters(); + if (par.Length != types.Length) + continue; + + int j; + for (j = 0; j < types.Length; j++) + { + var type = types[j]; + var parameterType = par[j].ParameterType; + + // exact parameter type match + if (type == parameterType) + continue; + + // everything is convertable to object + if (parameterType == ObjectType) + continue; + + // primitive paramter that can't be converted to parameter type + if (parameterType.IsPrimitive && CanChangePrimitive(type, parameterType) == false) + break; + + // can't otherwise assign type to parameter type + if (parameterType.IsAssignableFrom(type) == false) + break; + } + + if (j == types.Length) + candidates[curIdx++] = candidates[i]; + } + + if (curIdx == 0) + return null; + if (curIdx == 1) + return candidates[0]; + + // walk all of the methods looking the most specific method to invoke + int currentMin = 0; + var ambig = false; + + var paramOrder = types.Length > 0 ? stackalloc int[types.Length] : Array.Empty(); + for (var i = 0; i < types.Length; i++) + paramOrder[i] = i; + + for (var i = 1; i < curIdx; i++) + { + int newMin = FindMostSpecificMethod(candidates[currentMin], paramOrder, null, candidates[i], paramOrder, null, types); + if (newMin == 0) + ambig = true; + else + { + if (newMin == 2) + { + ambig = false; + currentMin = i; + } + } + } + + var bestMatch = candidates[currentMin]; + if (ambig) + throw new AmbiguousMatchException($"Ambiguous match found for '{bestMatch.DeclaringType} {bestMatch}'."); + + return bestMatch; + } + + /// + /// Selects the property that matches the base criteria. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + public PropertySymbol? SelectProperty(BindingFlags bindingAttr, IReadOnlyList match, TypeSymbol? returnType, ImmutableArray? indexes, ImmutableArray? modifiers) + { + // if indexes is present every element must be non-null + if (indexes != null) + foreach (var index in indexes) + throw new ArgumentNullException(nameof(index)); + + if (match == null || match.Count == 0) + throw new ArgumentException(nameof(match)); + + var candidates = new List(match); + + int i, j = 0; + + // Find all the properties that can be described by type indexes parameter + int curIdx = 0; + for (i = 0; i < candidates.Count; i++) + { + if (indexes != null) + { + var par = candidates[i].GetIndexParameters(); + if (par.Length != indexes.Value.Length) + continue; + + for (j = 0; j < indexes.Value.Length; j++) + { + var pCls = par[j].ParameterType; + + // If the classes exactly match continue + if (pCls == indexes.Value[j]) + continue; + + if (pCls == ObjectType) + continue; + + if (pCls.IsPrimitive) + { + if (CanChangePrimitive(indexes.Value[j], pCls) == false) + break; + } + else + { + if (pCls.IsAssignableFrom(indexes.Value[j]) == false) + break; + } + } + } + + if (indexes == null || j == indexes.Value.Length) + { + if (returnType != null) + { + if (candidates[i].PropertyType.IsPrimitive) + { + if (CanChangePrimitive(returnType, candidates[i].PropertyType) == false) + continue; + } + else + { + if (candidates[i].PropertyType.IsAssignableFrom(returnType) == false) + continue; + } + } + + candidates[curIdx++] = candidates[i]; + } + } + + if (curIdx == 0) + return null; + + if (curIdx == 1) + return candidates[0]; + + int currentMin = 0; + var ambig = false; + + var paramOrder = indexes != null && indexes.Value.Length > 0 ? stackalloc int[indexes.Value.Length] : Array.Empty(); + for (i = 0; i < paramOrder.Length; i++) + paramOrder[i] = i; + + for (i = 1; i < curIdx; i++) + { + int newMin = FindMostSpecificType(candidates[currentMin].PropertyType, candidates[i].PropertyType, returnType); + if (newMin == 0 && indexes != null) + newMin = FindMostSpecific(candidates[currentMin].GetIndexParameters(), paramOrder, null, candidates[i].GetIndexParameters(), paramOrder, null, indexes); + + if (newMin == 0) + { + newMin = FindMostSpecificProperty(candidates[currentMin], candidates[i]); + if (newMin == 0) + ambig = true; + } + + if (newMin == 2) + { + ambig = false; + currentMin = i; + } + } + + var bestMatch = candidates[currentMin]; + if (ambig) + throw new AmbiguousMatchException(bestMatch.ToString()); + + return bestMatch; + } + + /// + /// Returns any exact bindings that may exist. + /// + /// + /// + /// + /// + public MethodBaseSymbol? ExactBinding(IReadOnlyList match, ImmutableArray types) + { + if (match is null) + throw new ArgumentNullException(nameof(match)); + + var aExactMatches = new MethodBaseSymbol[match.Count]; + int cExactMatches = 0; + + for (int i = 0; i < match.Count; i++) + { + var par = match[i].GetParameters(); + if (par.Length == 0) + continue; + + int j; + for (j = 0; j < types.Length; j++) + { + var pCls = par[j].ParameterType; + + // If the classes exactly match continue + if (!pCls.Equals(types[j])) + break; + } + + if (j < types.Length) + continue; + + // Add the exact match to the array of exact matches. + aExactMatches[cExactMatches] = match[i]; + cExactMatches++; + } + + if (cExactMatches == 0) + return null; + + if (cExactMatches == 1) + return aExactMatches[0]; + + return FindMostDerivedNewSlotMeth(aExactMatches, cExactMatches); + } + + /// + /// Returns any exact bindings that may exist. + /// + /// + /// + /// + /// + /// + /// + public PropertySymbol? ExactPropertyBinding(IReadOnlyList match, TypeSymbol? returnType, ImmutableArray types) + { + if (match == null) + throw new ArgumentNullException(nameof(match)); + + PropertySymbol? bestMatch = null; + + for (int i = 0; i < match.Count; i++) + { + var parameter = match[i].GetIndexParameters(); + + int j; + for (j = 0; j < types.Length; j++) + { + var parameterType = parameter[j].ParameterType; + + // If the classes exactly match continue + if (parameterType != types![j]) + break; + } + + if (j < types.Length) + continue; + + if (returnType != null && returnType != match[i].PropertyType) + continue; + + if (bestMatch != null) + throw new AmbiguousMatchException(bestMatch.ToString()); + + bestMatch = match[i]; + } + + return bestMatch; + } + + int FindMostSpecific(ImmutableArray p1, ReadOnlySpan paramOrder1, TypeSymbol? paramArrayType1, + ImmutableArray p2, ReadOnlySpan paramOrder2, TypeSymbol? paramArrayType2, + IReadOnlyList types) + { + // a method using params is always less specific than one not using params + if (paramArrayType1 != null && paramArrayType2 == null) return 2; + if (paramArrayType2 != null && paramArrayType1 == null) return 1; + + // now either p1 and p2 both use params or neither does. + var p1Less = false; + var p2Less = false; + + for (int i = 0; i < types.Count; i++) + { + TypeSymbol c1, c2; + + // If a param array is present, then either + // the user re-ordered the parameters in which case + // the argument to the param array is either an array + // in which case the params is conceptually ignored and so paramArrayType1 == null + // or the argument to the param array is a single element + // in which case paramOrder[i] == p1.Length - 1 for that element + // or the user did not re-order the parameters in which case + // the paramOrder array could contain indexes larger than p.Length - 1 (see VSW 577286) + // so any index >= p.Length - 1 is being put in the param array + + if (paramArrayType1 != null && paramOrder1[i] >= p1.Length - 1) + c1 = paramArrayType1; + else + c1 = p1[paramOrder1[i]].ParameterType; + + if (paramArrayType2 != null && paramOrder2[i] >= p2.Length - 1) + c2 = paramArrayType2; + else + c2 = p2[paramOrder2[i]].ParameterType; + + if (c1 == c2) continue; + + switch (FindMostSpecificType(c1, c2, types[i])) + { + case 0: return 0; + case 1: p1Less = true; break; + case 2: p2Less = true; break; + } + } + + // Two way p1Less and p2Less can be equal. All the arguments are the + // same they both equal false, otherwise there were things that both + // were the most specific type on.... + if (p1Less == p2Less) + { + return 0; + } + else + { + return p1Less ? 1 : 2; + } + } + + /// + /// Finds which type is the most specific. + /// + /// + /// + /// + /// + int FindMostSpecificType(TypeSymbol c1, TypeSymbol c2, TypeSymbol? t) + { + // if the two types are exact, move on + if (c1 == c2) + return 0; + + if (c1 == t) + return 1; + + if (c2 == t) + return 2; + + bool c1FromC2; + bool c2FromC1; + + if (c1.IsByRef || c2.IsByRef) + { + if (c1.IsByRef && c2.IsByRef) + { + c1 = c1.GetElementType()!; + c2 = c2.GetElementType()!; + } + else if (c1.IsByRef) + { + if (c1.GetElementType() == c2) + return 2; + + c1 = c1.GetElementType()!; + } + else // if (c2.IsByRef) + { + if (c2.GetElementType() == c1) + return 1; + + c2 = c2.GetElementType()!; + } + } + + if (c1.IsPrimitive && c2.IsPrimitive) + { + c1FromC2 = CanChangePrimitive(c2, c1); + c2FromC1 = CanChangePrimitive(c1, c2); + } + else + { + c1FromC2 = c1.IsAssignableFrom(c2); + c2FromC1 = c2.IsAssignableFrom(c1); + } + + if (c1FromC2 == c2FromC1) + return 0; + + if (c1FromC2) + { + return 2; + } + else + { + return 1; + } + } + + int FindMostSpecificMethod(MethodBaseSymbol m1, ReadOnlySpan paramOrder1, TypeSymbol? paramArrayType1, + MethodBaseSymbol m2, ReadOnlySpan paramOrder2, TypeSymbol? paramArrayType2, + ImmutableArray types) + { + // Find the most specific method based on the parameters. + int res = FindMostSpecific(m1.GetParameters(), paramOrder1, paramArrayType1, + m2.GetParameters(), paramOrder2, paramArrayType2, types); + + // If the match was not ambiguous then return the result. + if (res != 0) + return res; + + // Check to see if the methods have the exact same name and signature. + if (CompareMethodSig(m1, m2)) + { + // Determine the depth of the declaring types for both methods. + var hierarchyDepth1 = GetHierarchyDepth(m1.DeclaringType!); + var hierarchyDepth2 = GetHierarchyDepth(m2.DeclaringType!); + + // the most derived method is the most specific one + if (hierarchyDepth1 == hierarchyDepth2) + return 0; + + if (hierarchyDepth1 < hierarchyDepth2) + return 2; + + return 1; + } + + // The match is ambiguous. + return 0; + } + + int FindMostSpecificField(FieldSymbol cur1, FieldSymbol cur2) + { + // Check to see if the fields have the same name. + if (cur1.Name == cur2.Name) + { + int hierarchyDepth1 = GetHierarchyDepth(cur1.DeclaringType!); + int hierarchyDepth2 = GetHierarchyDepth(cur2.DeclaringType!); + + if (hierarchyDepth1 == hierarchyDepth2) + { + Debug.Assert(cur1.IsStatic != cur2.IsStatic, "hierarchyDepth1 == hierarchyDepth2"); + return 0; + } + else if (hierarchyDepth1 < hierarchyDepth2) + return 2; + else + return 1; + } + + // The match is ambiguous. + return 0; + } + + int FindMostSpecificProperty(PropertySymbol cur1, PropertySymbol cur2) + { + // Check to see if the fields have the same name. + if (cur1.Name == cur2.Name) + { + int hierarchyDepth1 = GetHierarchyDepth(cur1.DeclaringType!); + int hierarchyDepth2 = GetHierarchyDepth(cur2.DeclaringType!); + + if (hierarchyDepth1 == hierarchyDepth2) + { + return 0; + } + else if (hierarchyDepth1 < hierarchyDepth2) + return 2; + else + return 1; + } + + // The match is ambiguous. + return 0; + } + + /// + /// Returns true if the two methods have the exact same signature. + /// + /// + /// + /// + public static bool CompareMethodSig(MethodBaseSymbol m1, MethodBaseSymbol m2) + { + var params1 = m1.GetParameters(); + var params2 = m2.GetParameters(); + + if (params1.Length != params2.Length) + return false; + + for (int i = 0; i < params1.Length; i++) + if (params1[i].ParameterType != params2[i].ParameterType) + return false; + + return true; + } + + /// + /// Gets the depth of the type within the type hierarchy. + /// + /// + /// + int GetHierarchyDepth(TypeSymbol type) + { + int depth = 0; + + for (var cType = (TypeSymbol?)type; cType != null; cType = cType.BaseType) + depth++; + + return depth; + } + + internal MethodBaseSymbol? FindMostDerivedNewSlotMeth(ReadOnlySpan match, int cMatches) + { + int deepestHierarchy = 0; + MethodBaseSymbol? methWithDeepestHierarchy = null; + + for (int i = 0; i < cMatches; i++) + { + // Calculate the depth of the hierarchy of the declaring type of the current method. + int currentHierarchyDepth = GetHierarchyDepth(match[i].DeclaringType!); + + // The two methods have the same name, signature, and hierarchy depth. + // This can only happen if at least one is vararg or generic. + if (currentHierarchyDepth == deepestHierarchy) + throw new AmbiguousMatchException(methWithDeepestHierarchy!.ToString()); + + // Check to see if this method is on the most derived class. + if (currentHierarchyDepth > deepestHierarchy) + { + deepestHierarchy = currentHierarchyDepth; + methWithDeepestHierarchy = match[i]; + } + } + + return methWithDeepestHierarchy; + } + + // This method will create the mapping between the Parameters and the underlying + // data based upon the names array. The names array is stored in the same order + // as the values and maps to the parameters of the method. We store the mapping + // from the parameters to the names in the paramOrder array. All parameters that + // don't have matching names are then stored in the array in order. + bool CreateParamOrder(int[] paramOrder, ImmutableArray pars, string[] names) + { + var used = new bool[pars.Length]; + + // Mark which parameters have not been found in the names list + for (var i = 0; i < pars.Length; i++) + paramOrder[i] = -1; + + // Find the parameters with names. + for (var i = 0; i < names.Length; i++) + { + int j; + for (j = 0; j < pars.Length; j++) + { + if (names[i].Equals(pars[j].Name)) + { + paramOrder[j] = i; + used[i] = true; + break; + } + } + + // This is an error condition. The name was not found. This method must not match what we sent. + if (j == pars.Length) + return false; + } + + // Now we fill in the holes with the parameters that are unused. + int pos = 0; + for (int i = 0; i < pars.Length; i++) + { + if (paramOrder[i] == -1) + { + for (; pos < pars.Length; pos++) + { + if (!used[pos]) + { + paramOrder[i] = pos; + pos++; + break; + } + } + } + } + + return true; + } + + /// + /// Returns true if the given source primitive type can be converted to the given target primitive type. + /// + /// + /// + /// + internal bool CanChangePrimitive(TypeSymbol source, TypeSymbol target) + { + if ((source == IntPtrType && target == IntPtrType) || (source == UIntPtrType && target == UIntPtrType)) + return true; + + var widerCodes = PrimitiveConversions[(int)source.TypeCode]; + var targetCode = (Primitives)(1 << (int)target.TypeCode); + + return (widerCodes & targetCode) != 0; + } + + static ReadOnlySpan PrimitiveConversions => + [ + /* Empty */ 0, // not primitive + /* Object */ 0, // not primitive + /* DBNull */ 0, // not primitive + /* Boolean */ Primitives.Boolean, + /* Char */ Primitives.Char | Primitives.UInt16 | Primitives.UInt32 | Primitives.Int32 | Primitives.UInt64 | Primitives.Int64 | Primitives.Single | Primitives.Double, + /* SByte */ Primitives.SByte | Primitives.Int16 | Primitives.Int32 | Primitives.Int64 | Primitives.Single | Primitives.Double, + /* Byte */ Primitives.Byte | Primitives.Char | Primitives.UInt16 | Primitives.Int16 | Primitives.UInt32 | Primitives.Int32 | Primitives.UInt64 | Primitives.Int64 | Primitives.Single | Primitives.Double, + /* Int16 */ Primitives.Int16 | Primitives.Int32 | Primitives.Int64 | Primitives.Single | Primitives.Double, + /* UInt16 */ Primitives.UInt16 | Primitives.UInt32 | Primitives.Int32 | Primitives.UInt64 | Primitives.Int64 | Primitives.Single | Primitives.Double, + /* Int32 */ Primitives.Int32 | Primitives.Int64 | Primitives.Single | Primitives.Double, + /* UInt32 */ Primitives.UInt32 | Primitives.UInt64 | Primitives.Int64 | Primitives.Single | Primitives.Double, + /* Int64 */ Primitives.Int64 | Primitives.Single | Primitives.Double, + /* UInt64 */ Primitives.UInt64 | Primitives.Single | Primitives.Double, + /* Single */ Primitives.Single | Primitives.Double, + /* Double */ Primitives.Double, + /* Decimal */ Primitives.Decimal, + /* DateTime */ Primitives.DateTime, + /* [Unused] */ 0, + /* String */ Primitives.String, + ]; + + [Flags] + enum Primitives + { + Boolean = 1 << TypeCode.Boolean, + Char = 1 << TypeCode.Char, + SByte = 1 << TypeCode.SByte, + Byte = 1 << TypeCode.Byte, + Int16 = 1 << TypeCode.Int16, + UInt16 = 1 << TypeCode.UInt16, + Int32 = 1 << TypeCode.Int32, + UInt32 = 1 << TypeCode.UInt32, + Int64 = 1 << TypeCode.Int64, + UInt64 = 1 << TypeCode.UInt64, + Single = 1 << TypeCode.Single, + Double = 1 << TypeCode.Double, + Decimal = 1 << TypeCode.Decimal, + DateTime = 1 << TypeCode.DateTime, + String = 1 << TypeCode.String, + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs index 05c5ce5155..887319c0e6 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs @@ -8,10 +8,9 @@ abstract class DefinitionConstructorSymbol : ConstructorSymbol /// Initializes a new instance. /// /// - /// /// - protected DefinitionConstructorSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : - base(context, module, declaringType) + protected DefinitionConstructorSymbol(SymbolContext context, DefinitionTypeSymbol declaringType) : + base(context, declaringType) { } diff --git a/src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs index 873dc36881..cffd762c08 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionEventSymbol.cs @@ -8,10 +8,9 @@ abstract class DefinitionEventSymbol : EventSymbol /// Initializes a new instance. /// /// - /// /// - protected DefinitionEventSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : - base(context, module, declaringType) + protected DefinitionEventSymbol(SymbolContext context, DefinitionTypeSymbol declaringType) : + base(context, declaringType) { } diff --git a/src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs index d269ce91a3..80e916149a 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionFieldSymbol.cs @@ -10,7 +10,7 @@ abstract class DefinitionFieldSymbol : FieldSymbol /// /// /// - protected DefinitionFieldSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : + protected DefinitionFieldSymbol(SymbolContext context, ModuleSymbol module, DefinitionTypeSymbol declaringType) : base(context, module, declaringType) { diff --git a/src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs index 194d665634..163c508dcf 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionMethodSymbol.cs @@ -10,7 +10,7 @@ abstract class DefinitionMethodSymbol : MethodSymbol /// /// /// - protected DefinitionMethodSymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : + protected DefinitionMethodSymbol(SymbolContext context, ModuleSymbol module, DefinitionTypeSymbol? declaringType) : base(context, module, declaringType) { diff --git a/src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs index ed5c686d2f..688d604e97 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionParameterSymbol.cs @@ -8,10 +8,9 @@ abstract class DefinitionParameterSymbol : ParameterSymbol /// Initializes a new instance. /// /// - /// /// /// - protected DefinitionParameterSymbol(ISymbolContext context, IModuleSymbol module, MemberSymbol declaringMember, int position) : + protected DefinitionParameterSymbol(SymbolContext context, MemberSymbol declaringMember, int position) : base(context, declaringMember, position) { diff --git a/src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs index 9e239c58a2..7d8f4e3d98 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionPropertySymbol.cs @@ -8,10 +8,9 @@ abstract class DefinitionPropertySymbol : PropertySymbol /// Initializes a new instance. /// /// - /// /// - protected DefinitionPropertySymbol(ISymbolContext context, IModuleSymbol module, DefinitionTypeSymbol declaringType) : - base(context, module, declaringType) + protected DefinitionPropertySymbol(SymbolContext context, DefinitionTypeSymbol declaringType) : + base(context, declaringType) { } diff --git a/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs index 62c56e4644..97cc7d37a5 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs @@ -1,4 +1,6 @@ -namespace IKVM.CoreLib.Symbols +using System; + +namespace IKVM.CoreLib.Symbols { /// @@ -12,11 +14,76 @@ abstract class DefinitionTypeSymbol : TypeSymbol /// /// /// - /// - protected DefinitionTypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : - base(context, module, declaringType) + protected DefinitionTypeSymbol(SymbolContext context, ModuleSymbol module) : + base(context, module) + { + + } + + /// + public sealed override MethodBaseSymbol? DeclaringMethod => null; + + /// + public sealed override bool IsTypeDefinition => true; + + /// + public sealed override bool IsArray => false; + + /// + public sealed override bool IsByRef => false; + + /// + public sealed override bool IsConstructedGenericType => false; + + /// + public sealed override bool IsFunctionPointer => false; + + /// + public sealed override bool ContainsMissing => false; + + /// + public sealed override int GenericParameterPosition => throw new InvalidOperationException(); + + /// + public sealed override bool HasElementType => false; + + /// + public sealed override bool IsGenericTypeParameter => false; + + /// + public sealed override bool IsGenericMethodParameter => false; + + /// + public sealed override bool IsMissing => false; + + /// + public sealed override bool IsPointer => false; + + /// + public sealed override bool IsSZArray => false; + + /// + public sealed override bool IsUnmanagedFunctionPointer => false; + + /// + public sealed override bool IsComplete => true; + + /// + public sealed override TypeSymbol? GetElementType() + { + return null; + } + + /// + public sealed override TypeSymbol GetGenericTypeDefinition() { + throw new InvalidOperationException(); + } + /// + public sealed override int GetArrayRank() + { + throw new InvalidOperationException(); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs new file mode 100644 index 0000000000..b3da39193f --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs @@ -0,0 +1,110 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.IO; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class AssemblySymbolBuilder : AssemblySymbol + { + + readonly AssemblyIdentity _identity; + + /// + /// Initializes a new instance. + /// + /// + public AssemblySymbolBuilder(SymbolContext context, AssemblyIdentity identity) : + base(context) + { + _identity = identity ?? throw new ArgumentNullException(nameof(identity)); + } + + /// + public override string? FullName => throw new NotImplementedException(); + + /// + public override string ImageRuntimeVersion => throw new NotImplementedException(); + + /// + public override string Location => throw new NotImplementedException(); + + /// + public override ModuleSymbol ManifestModule => throw new NotImplementedException(); + + /// + public override IEnumerable DefinedTypes => throw new NotImplementedException(); + + /// + public override IEnumerable ExportedTypes => throw new NotImplementedException(); + + /// + public override MethodSymbol? EntryPoint => throw new NotImplementedException(); + + /// + public override bool IsMissing => false; + + /// + public override bool ContainsMissing => false; + + /// + public override bool IsComplete => false; + + /// + public override AssemblyIdentity GetIdentity() + { + return _identity; + } + + /// + public override ManifestResourceInfo? GetManifestResourceInfo(string resourceName) + { + throw new NotImplementedException(); + } + + /// + public override Stream? GetManifestResourceStream(string name) + { + throw new NotImplementedException(); + } + + /// + public override Stream? GetManifestResourceStream(TypeSymbol type, string name) + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetModules() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetReferencedAssemblies() + { + throw new NotImplementedException(); + } + + /// + public override TypeSymbol? GetType(string name, bool throwOnError) + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetTypes() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs new file mode 100644 index 0000000000..da8da14a7a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs @@ -0,0 +1,69 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class ConstructorSymbolBuilder : ConstructorSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public ConstructorSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : + base(context, declaringType) + { + + } + + /// + public override MethodAttributes Attributes => throw new NotImplementedException(); + + /// + public override CallingConventions CallingConvention => throw new NotImplementedException(); + + /// + public override MethodImplAttributes MethodImplementationFlags => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsMissing => throw new NotImplementedException(); + + /// + public override bool ContainsMissing => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + public override ImmutableArray GetGenericArguments() + { + throw new NotImplementedException(); + } + + /// + public override MethodImplAttributes GetMethodImplementationFlags() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetParameters() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs new file mode 100644 index 0000000000..fbabc5c356 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs @@ -0,0 +1,72 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class EventSymbolBuilder : EventSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public EventSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : + base(context, declaringType) + { + + } + + /// + public override EventAttributes Attributes => throw new NotImplementedException(); + + /// + public override TypeSymbol? EventHandlerType => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsMissing => throw new NotImplementedException(); + + /// + public override bool ContainsMissing => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + public override MethodSymbol? GetAddMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetOtherMethods(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override MethodSymbol? GetRaiseMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override MethodSymbol? GetRemoveMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs new file mode 100644 index 0000000000..4d35f4cffd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs @@ -0,0 +1,77 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class FieldSymbolBuilder : FieldSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public FieldSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : + base(context, declaringType.Module, declaringType) + { + + } + + /// + /// Initializes a new instance. + /// + /// + /// + public FieldSymbolBuilder(SymbolContext context, ModuleSymbolBuilder declaringModule) : + base(context, declaringModule, null) + { + + } + + /// + public override FieldAttributes Attributes => throw new NotImplementedException(); + + /// + public override TypeSymbol FieldType => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsMissing => throw new NotImplementedException(); + + /// + public override bool ContainsMissing => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + public override object? GetRawConstantValue() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetOptionalCustomModifiers() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetRequiredCustomModifiers() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs new file mode 100644 index 0000000000..9a8b1a8423 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs @@ -0,0 +1,49 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class GenericMethodParameterTypeSymbolBuilder : GenericMethodParameterTypeSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public GenericMethodParameterTypeSymbolBuilder(SymbolContext context, MethodSymbolBuilder declaringMethod) : + base(context, declaringMethod) + { + + } + + /// + public override string? FullName => throw new NotImplementedException(); + + /// + public override string? Namespace => throw new NotImplementedException(); + + /// + public override GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); + + /// + public override int GenericParameterPosition => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + public override ImmutableArray GetInterfaces() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs b/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs deleted file mode 100644 index b7fa430396..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterSymbolBuilderBase.cs +++ /dev/null @@ -1,606 +0,0 @@ -using System; -using System.Collections.Immutable; -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Emit -{ - - class GenericTypeParameterSymbolBuilderBase : IGenericTypeParameterSymbolBuilder - { - - readonly ISymbolContext _context; - readonly IModuleSymbolBuilder _module; - readonly IMemberSymbolBuilder _member; - readonly string _name; - - GenericParameterAttributes _attributes; - ITypeSymbol? _baseTypeConstraint; - ImmutableArray _interfaceConstraints = ImmutableArray.Empty; - ImmutableList _customAttributes = ImmutableList.Empty; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - /// - public GenericTypeParameterSymbolBuilderBase(ISymbolContext context, IModuleSymbolBuilder module, IMemberSymbolBuilder member, string name) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _member = member ?? throw new ArgumentNullException(nameof(member)); - _name = name ?? throw new ArgumentNullException(nameof(name)); - } - - /// - public ISymbolContext Context => _context; - - /// - public IModuleSymbolBuilder ResolvingModuleBuilder => _module; - - /// - public IMemberSymbolBuilder ResolvingMemberBuilder => _member; - - #region IGenericTypeParameterSymbolBuilder - - /// - public void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint) - { - _baseTypeConstraint = baseTypeConstraint; - } - - /// - public void SetGenericParameterAttributes(GenericParameterAttributes attributes) - { - _attributes = attributes; - } - - /// - public void SetInterfaceConstraints(params ITypeSymbol[] interfaceConstraints) - { - _interfaceConstraints = interfaceConstraints.ToImmutableArray(); - } - - #endregion - - #region ICustomAttributeProviderBuilder - - /// - public void SetCustomAttribute(CustomAttribute attribute) - { - _customAttributes = _customAttributes.Add(attribute); - } - - #endregion - - #region ITypeSymbol - - /// - public virtual IAssemblySymbol Assembly => ResolvingModuleBuilder.Assembly; - - /// - public virtual string? AssemblyQualifiedName => System.Reflection.Assembly.CreateQualifiedName(Assembly.FullName, FullName); - - /// - public virtual TypeAttributes Attributes => _attributes; - - /// - public virtual ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); - - /// - public virtual bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; - - /// - public virtual IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); - - /// - public virtual string? FullName => UnderlyingType.FullName; - - /// - public virtual string? Namespace => UnderlyingType.Namespace; - - /// - public virtual GenericParameterAttributes GenericParameterAttributes => UnderlyingType.GenericParameterAttributes; - - /// - public virtual int GenericParameterPosition => UnderlyingType.GenericParameterPosition; - - /// - public virtual ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); - - /// - public virtual bool HasElementType => UnderlyingType.HasElementType; - - /// - public virtual TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); - - /// - public virtual bool IsAbstract => UnderlyingType.IsAbstract; - - /// - public virtual bool IsSZArray => UnderlyingType.IsSZArray(); - - /// - public virtual bool IsArray => UnderlyingType.IsArray; - - /// - public virtual bool IsAutoLayout => UnderlyingType.IsAutoLayout; - - /// - public virtual bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; - - /// - public virtual bool IsByRef => UnderlyingType.IsByRef; - - /// - public virtual bool IsClass => UnderlyingType.IsClass; - - /// - public virtual bool IsEnum => UnderlyingType.IsEnum; - - /// - public virtual bool IsInterface => UnderlyingType.IsInterface; - - /// - public virtual bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; - - /// - public virtual bool IsGenericParameter => UnderlyingType.IsGenericParameter; - - /// - public virtual bool IsGenericType => UnderlyingType.IsGenericType; - - /// - public virtual bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; - - /// - public virtual bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; - - /// - public virtual bool IsNested => UnderlyingType.IsNested; - - /// - public virtual bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; - - /// - public virtual bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; - - /// - public virtual bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; - - /// - public virtual bool IsNestedFamily => UnderlyingType.IsNestedFamily; - - /// - public virtual bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; - - /// - public virtual bool IsNestedPublic => UnderlyingType.IsNestedPublic; - - /// - public virtual bool IsNotPublic => UnderlyingType.IsNotPublic; - - /// - public virtual bool IsPointer => UnderlyingType.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public virtual bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; - - /// - public virtual bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; - -#else - - /// - public virtual bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public virtual bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public virtual bool IsPrimitive => UnderlyingType.IsPrimitive; - - /// - public virtual bool IsPublic => UnderlyingType.IsPublic; - - /// - public virtual bool IsSealed => UnderlyingType.IsSealed; - - /// - public virtual bool IsSerializable => UnderlyingType.IsSerializable; - - /// - public virtual bool IsValueType => UnderlyingType.IsValueType; - - /// - public virtual bool IsVisible => UnderlyingType.IsVisible; - - /// - public virtual bool IsSignatureType => throw new NotImplementedException(); - - /// - public virtual bool IsSpecialName => UnderlyingType.IsSpecialName; - - /// - public virtual IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); - - /// - public virtual int GetArrayRank() - { - return UnderlyingType.GetArrayRank(); - } - - /// - public virtual IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public virtual IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public virtual IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); - } - - /// - public virtual IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors(bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetDefaultMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); - } - - /// - public virtual ITypeSymbol? GetElementType() - { - return ResolveTypeSymbol(UnderlyingType.GetElementType()); - } - - /// - public virtual string? GetEnumName(object value) - { - return UnderlyingType.GetEnumName(value); - } - - /// - public virtual string[] GetEnumNames() - { - return UnderlyingType.GetEnumNames(); - } - - /// - public virtual ITypeSymbol GetEnumUnderlyingType() - { - return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public virtual Array GetEnumValues() - { - return UnderlyingType.GetEnumValues(); - } - - /// - public virtual IEventSymbol? GetEvent(string name) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name)); - } - - /// - public virtual IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name, bindingAttr)); - } - - /// - public virtual IEventSymbol[] GetEvents() - { - return ResolveEventSymbols(UnderlyingType.GetEvents()); - } - - /// - public virtual IEventSymbol[] GetEvents(BindingFlags bindingAttr) - { - return ResolveEventSymbols(UnderlyingType.GetEvents(bindingAttr)); - } - - /// - public virtual IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name)); - } - - /// - public virtual IFieldSymbol? GetField(string name, BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name, bindingAttr)); - } - - /// - public virtual IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingType.GetFields()); - } - - /// - public virtual IFieldSymbol[] GetFields(BindingFlags bindingAttr) - { - return ResolveFieldSymbols(UnderlyingType.GetFields(bindingAttr)); - } - - /// - public virtual ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); - } - - /// - public virtual ITypeSymbol[] GetGenericParameterConstraints() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public virtual ITypeSymbol GetGenericTypeDefinition() - { - return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public virtual ITypeSymbol? GetInterface(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); - } - - /// - public virtual ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public virtual InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); - } - - /// - public virtual ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public virtual IMemberSymbol[] GetMembers(string name) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name)); - } - - /// - public virtual IMemberSymbol[] GetMembers(string name, BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetMembers(string name, MemberTypes type, BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, type, bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetMembers(BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMembers(bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetMembers()); - } - - /// - public virtual IMethodSymbol? GetMethod(string name) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr)); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers?.Unpack())); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public virtual IMethodSymbol[] GetMethods(BindingFlags bindingAttr) - { - return ResolveMethodSymbols(UnderlyingType.GetMethods(bindingAttr)); - } - - /// - public virtual IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(UnderlyingType.GetMethods()); - } - - /// - public virtual ITypeSymbol? GetNestedType(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); - } - - /// - public virtual ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, bindingAttr)); - } - - /// - public virtual ITypeSymbol[] GetNestedTypes() - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); - } - - /// - public virtual ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public virtual IPropertySymbol[] GetProperties() - { - return ResolvePropertySymbols(UnderlyingType.GetProperties()); - } - - /// - public virtual IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); - } - - /// - public virtual IPropertySymbol? GetProperty(string name) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public virtual bool IsAssignableFrom(ITypeSymbol? c) - { - return UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public virtual bool IsEnumDefined(object value) - { - return UnderlyingType.IsEnumDefined(value); - } - - /// - public virtual bool IsSubclassOf(ITypeSymbol c) - { - return UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public virtual ITypeSymbol MakeArrayType() - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); - } - - /// - public virtual ITypeSymbol MakeArrayType(int rank) - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); - } - - /// - public virtual ITypeSymbol MakeByRefType() - { - return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); - } - - /// - public virtual ITypeSymbol MakePointerType() - { - return ResolveTypeSymbol(UnderlyingType.MakePointerType()); - } - - /// - public virtual ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); - } - -#endregion - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs new file mode 100644 index 0000000000..8da8419572 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs @@ -0,0 +1,49 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class GenericTypeParameterTypeSymbolBuilder : GenericTypeParameterTypeSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public GenericTypeParameterTypeSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : + base(context, declaringType) + { + + } + + /// + public override string? FullName => throw new NotImplementedException(); + + /// + public override string? Namespace => throw new NotImplementedException(); + + /// + public override GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); + + /// + public override int GenericParameterPosition => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + public override ImmutableArray GetInterfaces() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs deleted file mode 100644 index bda4b9a53a..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IAssemblySymbolBuilder.cs +++ /dev/null @@ -1,86 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IAssemblySymbolBuilder : ISymbolBuilder, IAssemblySymbol, ICustomAttributeProviderBuilder - { - - /// - /// Defines a named module in this assembly. - /// - /// - /// - IModuleSymbolBuilder DefineModule(string name); - - /// - /// Defines a named module in this assembly. - /// - /// - /// - /// - IModuleSymbolBuilder DefineModule(string name, string fileName); - - /// - /// Defines a named module in this assembly. - /// - /// - /// - /// - /// - IModuleSymbolBuilder DefineModule(string name, string fileName, bool emitSymbolInfo); - - /// - /// Sets a Win32 icon on the generated assembly. - /// - /// - void DefineIconResource(byte[] bytes); - - /// - /// Sets a manifest resource on the generated assembly. - /// - /// - void DefineManifestResource(byte[] bytes); - - /// - /// Sets a Win32 version info resource on the generated assembly. - /// - void DefineVersionInfoResource(); - - /// - /// Sets the entry point for this assembly, assuming that a console application is being built. - /// - /// - void SetEntryPoint(IMethodSymbol entryMethod); - - /// - /// Sets the entry point for this assembly and defines the type of the portable executable (PE file) being built. - /// - /// - /// - void SetEntryPoint(IMethodSymbol entryMethod, PEFileKinds fileKind); - - /// - /// Adds a forwarded type to this assembly. - /// - /// - void AddTypeForwarder(ITypeSymbol type); - - /// - /// Adds an external resource file to the assembly. - /// - /// - /// - void AddResourceFile(string name, string fileName); - - /// - /// Saves this assembly to disk. - /// - /// - /// - /// - void Save(string assemblyFileName, PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs deleted file mode 100644 index a099d7d060..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IConstructorSymbolBuilder.cs +++ /dev/null @@ -1,11 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IConstructorSymbolBuilder : ISymbolBuilder, IMethodBaseSymbolBuilder, IConstructorSymbol - { - - - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs deleted file mode 100644 index d07fbc431f..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeProviderBuilder.cs +++ /dev/null @@ -1,15 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface ICustomAttributeProviderBuilder - { - - /// - /// Set a custom attribute on this object. - /// - /// - public void SetCustomAttribute(CustomAttribute attribute); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs deleted file mode 100644 index 719f270b57..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IEventSymbolBuilder.cs +++ /dev/null @@ -1,33 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IEventSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IEventSymbol - { - - /// - /// Sets the method used to subscribe to this event. - /// - /// - void SetAddOnMethod(IMethodSymbolBuilder mdBuilder); - - /// - /// Sets the method used to unsubscribe to this event. - /// - /// - void SetRemoveOnMethod(IMethodSymbolBuilder mdBuilder); - - /// - /// Sets the method used to raise this event. - /// - /// - void SetRaiseMethod(IMethodSymbolBuilder mdBuilder); - - /// - /// Adds one of the "other" methods associated with this event. "Other" methods are methods other than the "on" and "raise" methods associated with an event. This function can be called many times to add as many "other" methods. - /// - /// - void AddOtherMethod(IMethodSymbolBuilder mdBuilder); - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs deleted file mode 100644 index 9cd676798b..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IFieldSymbolBuilder.cs +++ /dev/null @@ -1,21 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IFieldSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IFieldSymbol - { - - /// - /// Sets the default value of this field. - /// - /// - void SetConstant(object? defaultValue); - - /// - /// Specifies the field layout. - /// - /// - void SetOffset(int iOffset); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs deleted file mode 100644 index 575c05d768..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IGenericTypeParameterSymbolBuilder.cs +++ /dev/null @@ -1,28 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IGenericTypeParameterSymbolBuilder : ISymbolBuilder, ITypeSymbol - { - - /// - /// Sets the base type that a type must inherit in order to be substituted for the type parameter. - /// - /// - void SetBaseTypeConstraint(ITypeSymbol? baseTypeConstraint); - - /// - /// Sets the variance characteristics and special constraints of the generic parameter, such as the parameterless constructor constraint. - /// - /// - void SetGenericParameterAttributes(System.Reflection.GenericParameterAttributes genericParameterAttributes); - - /// - /// Sets the interfaces a type must implement in order to be substituted for the type parameter. - /// - /// - void SetInterfaceConstraints(params ITypeSymbol[] interfaceConstraints); - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs index bc74233ab5..a9c04150aa 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/IILGenerator.cs @@ -1,4 +1,7 @@ -namespace IKVM.CoreLib.Symbols.Emit +using System.Collections.Immutable; +using System.Reflection.Emit; + +namespace IKVM.CoreLib.Symbols.Emit { interface IILGenerator @@ -41,14 +44,14 @@ interface IILGenerator /// /// /// - ILocalBuilder DeclareLocal(ITypeSymbol localType, bool pinned); + ILocalBuilder DeclareLocal(TypeSymbol localType, bool pinned); /// /// Declares a local variable of the specified type. /// /// /// - ILocalBuilder DeclareLocal(ITypeSymbol localType); + ILocalBuilder DeclareLocal(TypeSymbol localType); /// /// Declares a new label. @@ -77,7 +80,7 @@ interface IILGenerator /// Begins a catch block. /// /// - void BeginCatchBlock(ITypeSymbol? exceptionType); + void BeginCatchBlock(TypeSymbol? exceptionType); /// /// Begins an exception fault block in the Microsoft intermediate language (MSIL) stream. @@ -98,7 +101,7 @@ interface IILGenerator /// Emits an instruction to throw an exception. /// /// - void ThrowException(ITypeSymbol excType); + void ThrowException(TypeSymbol excType); /// /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the index of the given local variable. @@ -112,7 +115,7 @@ interface IILGenerator /// /// /// - void Emit(System.Reflection.Emit.OpCode opcode, ITypeSymbol cls); + void Emit(System.Reflection.Emit.OpCode opcode, TypeSymbol cls); /// /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the metadata token for the given string. @@ -140,14 +143,14 @@ interface IILGenerator /// /// /// - void Emit(System.Reflection.Emit.OpCode opcode, IMethodSymbol meth); + void Emit(System.Reflection.Emit.OpCode opcode, MethodSymbol meth); /// /// Puts the specified instruction and a signature token onto the Microsoft intermediate language (MSIL) stream of instructions. /// /// /// - void Emit(System.Reflection.Emit.OpCode opcode, ISignatureHelper signature); + void Emit(System.Reflection.Emit.OpCode opcode, SignatureHelper signature); /// /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream and leaves space to include a label when fixes are done. @@ -161,14 +164,14 @@ interface IILGenerator /// /// /// - void Emit(System.Reflection.Emit.OpCode opcode, IFieldSymbol field); + void Emit(System.Reflection.Emit.OpCode opcode, FieldSymbol field); /// /// Puts the specified instruction and metadata token for the specified constructor onto the Microsoft intermediate language (MSIL) stream of instructions. /// /// /// - void Emit(System.Reflection.Emit.OpCode opcode, IConstructorSymbol con); + void Emit(System.Reflection.Emit.OpCode opcode, ConstructorSymbol con); /// /// Puts the specified instruction and numerical argument onto the Microsoft intermediate language (MSIL) stream of instructions. @@ -224,7 +227,7 @@ interface IILGenerator /// /// /// - void EmitCall(System.Reflection.Emit.OpCode opcode, IMethodSymbol methodInfo, ITypeSymbol[]? optionalParameterTypes); + void EmitCall(System.Reflection.Emit.OpCode opcode, MethodSymbol methodInfo, ImmutableList? optionalParameterTypes); /// /// Puts a Calli instruction onto the Microsoft intermediate language (MSIL) stream, specifying an unmanaged calling convention for the indirect call. @@ -233,7 +236,7 @@ interface IILGenerator /// /// /// - void EmitCalli(System.Reflection.Emit.OpCode opcode, System.Runtime.InteropServices.CallingConvention unmanagedCallConv, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes); + void EmitCalli(System.Reflection.Emit.OpCode opcode, System.Runtime.InteropServices.CallingConvention unmanagedCallConv, TypeSymbol? returnType, ImmutableList? parameterTypes); /// /// Puts a Calli instruction onto the Microsoft intermediate language (MSIL) stream, specifying a managed calling convention for the indirect call. @@ -243,7 +246,7 @@ interface IILGenerator /// /// /// - void EmitCalli(System.Reflection.Emit.OpCode opcode, System.Reflection.CallingConventions callingConvention, ITypeSymbol? returnType, ITypeSymbol[]? parameterTypes, ITypeSymbol[]? optionalParameterTypes); + void EmitCalli(System.Reflection.Emit.OpCode opcode, System.Reflection.CallingConventions callingConvention, TypeSymbol? returnType, ImmutableList? parameterTypes, ImmutableList? optionalParameterTypes); /// /// Emits the Microsoft intermediate language (MSIL) to call with a string. @@ -255,7 +258,7 @@ interface IILGenerator /// Emits the Microsoft intermediate language (MSIL) necessary to call with the given field. /// /// - void EmitWriteLine(IFieldSymbol fld); + void EmitWriteLine(FieldSymbol fld); /// /// Emits the Microsoft intermediate language (MSIL) necessary to call with the given local variable. diff --git a/src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs index 650edcb8dd..9faf874942 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs @@ -20,7 +20,7 @@ interface ILocalBuilder /// /// Gets the type of the local variable. /// - ITypeSymbol LocalType { get; } + TypeSymbol LocalType { get; } /// /// Sets the name of this local variable. diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs deleted file mode 100644 index a2d87e08e7..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IMemberSymbolBuilder.cs +++ /dev/null @@ -1,11 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IMemberSymbolBuilder : ISymbolBuilder, IMemberSymbol, ICustomAttributeProviderBuilder - { - - - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs deleted file mode 100644 index 162146f11a..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IMethodBaseSymbolBuilder.cs +++ /dev/null @@ -1,39 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IMethodBaseSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IMethodBaseSymbol - { - - /// - /// Sets the implementation flags for this method. - /// - /// - void SetImplementationFlags(MethodImplAttributes attributes); - - /// - /// Defines a parameter of this method. - /// - /// - /// - /// - /// - IParameterSymbolBuilder DefineParameter(int iSequence, ParameterAttributes attributes, string? strParamName); - - /// - /// Gets an ILGenerator object, with the specified MSIL stream size, that can be used to build a method body for this method. - /// - /// - /// - IILGenerator GetILGenerator(int streamSize); - - /// - /// Gets an ILGenerator for this method. - /// - /// - IILGenerator GetILGenerator(); - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs deleted file mode 100644 index 8ae9770eb6..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IMethodSymbolBuilder.cs +++ /dev/null @@ -1,39 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IMethodSymbolBuilder : ISymbolBuilder, IMethodBaseSymbolBuilder, IMethodSymbol - { - - /// - /// Sets the number and types of parameters for a method. - /// - /// - void SetParameters(params ITypeSymbol[] parameterTypes); - - /// - /// Sets the return type of the method. - /// - /// - void SetReturnType(ITypeSymbol? returnType); - - /// - /// Sets the method signature, including the return type, the parameter types, and the required and optional custom modifiers of the return type and parameter types. - /// - /// - /// - /// - /// - /// - /// - void SetSignature(ITypeSymbol? returnType, ITypeSymbol[]? returnTypeRequiredCustomModifiers, ITypeSymbol[]? returnTypeOptionalCustomModifiers, ITypeSymbol[]? parameterTypes, ITypeSymbol[][]? parameterTypeRequiredCustomModifiers, ITypeSymbol[][]? parameterTypeOptionalCustomModifiers); - - /// - /// Sets the number of generic type parameters for the current method, specifies their names, and returns an array of GenericTypeParameterBuilder objects that can be used to define their constraints. - /// - /// - /// - IGenericTypeParameterSymbolBuilder[] DefineGenericParameters(params string[] names); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs deleted file mode 100644 index ec2148e7bf..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IParameterSymbolBuilder.cs +++ /dev/null @@ -1,15 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IParameterSymbolBuilder : ISymbolBuilder, IParameterSymbol, ICustomAttributeProviderBuilder - { - - /// - /// Sets the default value of the parameter. - /// - /// - void SetConstant(object? defaultValue); - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs deleted file mode 100644 index 29dd90ed45..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/IPropertySymbolBuilder.cs +++ /dev/null @@ -1,33 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface IPropertySymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, IPropertySymbol - { - - /// - /// Sets the default value of this property. - /// - /// - void SetConstant(object? defaultValue); - - /// - /// Sets the method that gets the property value. - /// - /// - void SetGetMethod(IMethodSymbolBuilder mdBuilder); - - /// - /// Sets the method that sets the property value. - /// - /// - void SetSetMethod(IMethodSymbolBuilder mdBuilder); - - /// - /// Adds one of the other methods associated with this property. - /// - /// - void AddOtherMethod(IMethodSymbolBuilder mdBuilder); - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs b/src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs deleted file mode 100644 index f7be27ef9b..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/ISignatureHelper.cs +++ /dev/null @@ -1,6 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - public interface ISignatureHelper - { - } -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs deleted file mode 100644 index 3e952aae98..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/ISymbolBuilder.cs +++ /dev/null @@ -1,26 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Emit -{ - - /// - /// Base interface for a builder of symbols. - /// - interface ISymbolBuilder - { - - - - } - - /// - /// Base interface for a builder of symbols. - /// - /// - interface ISymbolBuilder : ISymbolBuilder - where TSymbol : ISymbol - { - - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs deleted file mode 100644 index 5a05624bb5..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/ITypeSymbolBuilder.cs +++ /dev/null @@ -1,331 +0,0 @@ -using System.Collections.Immutable; -using System.Reflection; -using System.Reflection.Emit; -using System.Runtime.InteropServices; - -namespace IKVM.CoreLib.Symbols.Emit -{ - - interface ITypeSymbolBuilder : ISymbolBuilder, IMemberSymbolBuilder, ITypeSymbol - { - - /// - /// Sets the base type of the type currently under construction. - /// - /// - void SetParent(ITypeSymbol? parent); - - /// - /// Defines the generic type parameters for the current type, specifying their number and their names, and returns an array of GenericTypeParameterBuilder objects that can be used to set their constraints. - /// - /// - /// - IImmutableList DefineGenericParameters(IImmutableList names); - - /// - /// Defines the initializer for this type. - /// - /// - IConstructorSymbolBuilder DefineTypeInitializer(); - - /// - /// Adds an interface that this type implements. - /// - /// - void AddInterfaceImplementation(ITypeSymbol interfaceType); - - /// - /// Adds a new constructor to the type, with the given attributes and signature and the standard calling convention. - /// - /// - /// - /// - IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, IImmutableList parameterTypes); - - /// - /// Adds a new constructor to the type, with the given attributes and signature. - /// - /// - /// - /// - /// - IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes); - - /// - /// Adds a new constructor to the type, with the given attributes, signature, and custom modifiers. - /// - /// - /// - /// - /// - /// - /// - IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, IImmutableList> optionalCustomModifiers); - - /// - /// Defines the parameterless constructor. The constructor defined here will simply call the parameterless constructor of the parent. - /// - /// - /// - IConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes); - - /// - /// Adds a new event to the type, with the given name, attributes and event type. - /// - /// - /// - /// - /// - IEventSymbolBuilder DefineEvent(string name, EventAttributes attributes, ITypeSymbol eventtype); - - /// - /// Adds a new field to the type, with the given name, attributes, and field type. - /// - /// - /// - /// - /// - IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, FieldAttributes attributes); - - /// - /// Adds a new field to the type, with the given name, attributes, field type, and custom modifiers. - /// - /// - /// - /// - /// - /// - /// - IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, IImmutableList requiredCustomModifiers, IImmutableList optionalCustomModifiers, FieldAttributes attributes); - - /// - /// Adds a new method to the type, with the specified name, method attributes, calling convention, method signature, and custom modifiers. - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); - - /// - /// Adds a new method to the type, with the specified name, method attributes, calling convention, and method signature. - /// - /// - /// - /// - /// - /// - /// - IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes); - - /// - /// Adds a new method to the type, with the specified name, method attributes, and calling convention. - /// - /// - /// - /// - /// - IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention); - - /// - /// Adds a new method to the type, with the specified name and method attributes. - /// - /// - /// - /// - IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes); - - /// - /// Adds a new method to the type, with the specified name, method attributes, and method signature. - /// - /// - /// - /// - /// - /// - IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes); - - /// - /// Specifies a given method body that implements a given method declaration, potentially with a different name. - /// - /// - /// - void DefineMethodOverride(IMethodSymbol methodInfoBody, IMethodSymbol methodInfoDeclaration); - - /// - /// Defines a nested type, given its name, attributes, the type that it extends, and the interfaces that it implements. - /// - /// - /// - /// - /// - /// - ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces); - - /// - /// Defines a nested type, given its name, attributes, size, and the type that it extends. - /// - /// - /// - /// - /// - /// - /// - ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize); - - /// - /// Defines a nested type, given its name, attributes, the type that it extends, and the packing size. - /// - /// - /// - /// - /// - /// - ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize); - - /// - /// Defines a nested type, given its name. - /// - /// - /// - ITypeSymbolBuilder DefineNestedType(string name); - - /// - /// Defines a nested type, given its name, attributes, and the type that it extends. - /// - /// - /// - /// - /// - ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent); - - /// - /// Defines a nested type, given its name and attributes. - /// - /// - /// - /// - ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr); - - /// - /// Defines a nested type, given its name, attributes, the total size of the type, and the type that it extends. - /// - /// - /// - /// - /// - /// - ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize); - - /// - /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); - - /// - /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet); - - /// - /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, the PInvoke flags, and custom modifiers for the parameters and return type. - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet); - - /// - /// Adds a new property to the type, with the given name and property signature. - /// - /// - /// - /// - /// - /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList parameterTypes); - - /// - /// Adds a new property to the type, with the given name, attributes, calling convention, and property signature. - /// - /// - /// - /// - /// - /// - /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList parameterTypes); - - /// - /// Adds a new property to the type, with the given name, property signature, and custom modifiers. - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); - - /// - /// Adds a new property to the type, with the given name, calling convention, property signature, and custom modifiers. - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); - - /// - /// Finishes the type, updating the associated symbol. - /// - void Complete(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Emit/MethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/MethodSymbolBuilder.cs new file mode 100644 index 0000000000..341474d2c1 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/MethodSymbolBuilder.cs @@ -0,0 +1,110 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class MethodSymbolBuilder : MethodSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public MethodSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : + base(context, declaringType.Module, declaringType) + { + + } + + /// + /// Initializes a new instance. + /// + /// + /// + public MethodSymbolBuilder(SymbolContext context, ModuleSymbolBuilder declaringModule) : + base(context, declaringModule, null) + { + + } + + /// + public override ParameterSymbol ReturnParameter => throw new NotImplementedException(); + + /// + public override TypeSymbol ReturnType => throw new NotImplementedException(); + + /// + public override ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + + /// + public override MethodAttributes Attributes => throw new NotImplementedException(); + + /// + public override CallingConventions CallingConvention => throw new NotImplementedException(); + + /// + public override bool ContainsGenericParameters => throw new NotImplementedException(); + + /// + public override bool IsGenericMethod => throw new NotImplementedException(); + + /// + public override bool IsGenericMethodDefinition => throw new NotImplementedException(); + + /// + public override MethodImplAttributes MethodImplementationFlags => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsMissing => throw new NotImplementedException(); + + /// + public override bool ContainsMissing => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + public override MethodSymbol GetBaseDefinition() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetGenericArguments() + { + throw new NotImplementedException(); + } + + /// + public override MethodSymbol GetGenericMethodDefinition() + { + throw new NotImplementedException(); + } + + /// + public override MethodImplAttributes GetMethodImplementationFlags() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetParameters() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ModuleSymbolBuilder.cs similarity index 60% rename from src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs rename to src/IKVM.CoreLib/Symbols/Emit/ModuleSymbolBuilder.cs index 7413e2fad1..fef8885466 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/IModuleSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/ModuleSymbolBuilder.cs @@ -10,9 +10,20 @@ namespace IKVM.CoreLib.Symbols.Emit { - interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, ICustomAttributeProviderBuilder + class ModuleSymbolBuilder : ModuleSymbol { + /// + /// Initializes a new instance. + /// + /// + /// + public ModuleSymbolBuilder(SymbolContext context, AssemblySymbolBuilder assembly) : + base(context, assembly) + { + + } + /// /// Gets or sets the preferred address of the first byte of the image when it is loaded into memory. /// @@ -28,6 +39,21 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// DllCharacteristics DllCharacteristics { get; set; } + /// + public override string FullyQualifiedName => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsMissing => throw new NotImplementedException(); + + /// + public override bool ContainsMissing => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + /// /// Defines a document for source. /// @@ -36,7 +62,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ISymbolDocumentWriter? DefineDocument(string url, Guid language, Guid languageVendor, Guid documentType); + ISymbolDocumentWriter? DefineDocument(string url, Guid language, Guid languageVendor, Guid documentType) + { + throw new NotImplementedException(); + } /// /// Defines a binary large object (BLOB) that represents a manifest resource to be embedded in the dynamic assembly. @@ -44,7 +73,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - void DefineManifestResource(string name, Stream stream, ResourceAttributes attribute); + void DefineManifestResource(string name, Stream stream, ResourceAttributes attribute) + { + throw new NotImplementedException(); + } /// /// Defines the named managed embedded resource to be stored in this module. @@ -52,7 +84,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IResourceWriter DefineResource(string name, string description); + IResourceWriter DefineResource(string name, string description) + { + throw new NotImplementedException(); + } /// /// Defines the named managed embedded resource with the given attributes that is to be stored in this module. @@ -61,7 +96,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IResourceWriter DefineResource(string name, string description, ResourceAttributes attribute); + IResourceWriter DefineResource(string name, string description, ResourceAttributes attribute) + { + throw new NotImplementedException(); + } /// /// Defines a global method with the specified name, attributes, calling convention, return type, and parameter types. @@ -72,7 +110,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes); + MethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, TypeSymbol? returnType, IImmutableList parameterTypes) + { + throw new NotImplementedException(); + } /// /// Defines a global method with the specified name, attributes, calling convention, return type, custom modifiers for the return type, parameter types, and custom modifiers for the parameter types. @@ -87,7 +128,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList requiredReturnTypeCustomModifiers, IImmutableList optionalReturnTypeCustomModifiers, IImmutableList parameterTypes, IImmutableList> requiredParameterTypeCustomModifiers, IImmutableList> optionalParameterTypeCustomModifiers); + MethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, TypeSymbol? returnType, IImmutableList requiredReturnTypeCustomModifiers, IImmutableList optionalReturnTypeCustomModifiers, IImmutableList parameterTypes, IImmutableList> requiredParameterTypeCustomModifiers, IImmutableList> optionalParameterTypeCustomModifiers) + { + throw new NotImplementedException(); + } /// /// Defines a global method with the specified name, attributes, return type, and parameter types. @@ -97,14 +141,20 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - IMethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes); + MethodSymbolBuilder DefineGlobalMethod(string name, MethodAttributes attributes, TypeSymbol? returnType, IImmutableList parameterTypes) + { + throw new NotImplementedException(); + } /// /// Constructs a TypeBuilder for a private type with the specified name in this module. /// /// /// - ITypeSymbolBuilder DefineType(string name); + TypeSymbolBuilder DefineType(string name) + { + throw new NotImplementedException(); + } /// /// Constructs a TypeBuilder given the type name, the attributes, the type that the defined type extends, and the total size of the type. @@ -114,7 +164,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, int typesize); + TypeSymbolBuilder DefineType(string name, TypeAttributes attr, TypeSymbol? parent, int typesize) + { + throw new NotImplementedException(); + } /// /// Constructs a TypeBuilder given type name, its attributes, and the type that the defined type extends. @@ -123,7 +176,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent); + TypeSymbolBuilder DefineType(string name, TypeAttributes attr, TypeSymbol? parent) + { + throw new NotImplementedException(); + } /// /// Constructs a TypeBuilder given the type name and the type attributes. @@ -131,7 +187,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineType(string name, TypeAttributes attr); + TypeSymbolBuilder DefineType(string name, TypeAttributes attr) + { + throw new NotImplementedException(); + } /// /// Constructs a TypeBuilder given the type name, the attributes, the type that the defined type extends, and the packing size of the type. @@ -141,7 +200,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packsize); + TypeSymbolBuilder DefineType(string name, TypeAttributes attr, TypeSymbol? parent, PackingSize packsize) + { + throw new NotImplementedException(); + } /// /// Constructs a TypeBuilder given the type name, attributes, the type that the defined type extends, the packing size of the defined type, and the total size of the defined type. @@ -152,7 +214,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packingSize, int typesize); + TypeSymbolBuilder DefineType(string name, TypeAttributes attr, TypeSymbol? parent, PackingSize packingSize, int typesize) + { + throw new NotImplementedException(); + } /// /// Constructs a TypeBuilder given the type name, attributes, the type that the defined type extends, and the interfaces that the defined type implements. @@ -162,7 +227,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineType(string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces); + TypeSymbolBuilder DefineType(string name, TypeAttributes attr, TypeSymbol? parent, ImmutableList interfaces) + { + throw new NotImplementedException(); + } /// /// Defines a nested type, given its name. @@ -170,7 +238,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name); + TypeSymbolBuilder DefineNestedType(TypeSymbolBuilder enclosingType, string name) + { + throw new NotImplementedException(); + } /// /// Defines a nested type, given its name and attributes. @@ -179,7 +250,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr); + TypeSymbolBuilder DefineNestedType(TypeSymbolBuilder enclosingType, string name, TypeAttributes attr) + { + throw new NotImplementedException(); + } /// /// Defines a nested type, given its name, attributes, and the type that it extends. @@ -189,7 +263,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent); + TypeSymbolBuilder DefineNestedType(TypeSymbolBuilder enclosingType, string name, TypeAttributes attr, TypeSymbol? parent) + { + throw new NotImplementedException(); + } /// /// Defines a nested type, given its name, attributes, the type that it extends, and the interfaces that it implements. @@ -200,7 +277,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces); + TypeSymbolBuilder DefineNestedType(TypeSymbolBuilder enclosingType, string name, TypeAttributes attr, TypeSymbol? parent, IImmutableList interfaces) + { + throw new NotImplementedException(); + } /// /// Defines a nested type, given its name, attributes, size, and the type that it extends. @@ -211,7 +291,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize); + TypeSymbolBuilder DefineNestedType(TypeSymbolBuilder enclosingType, string name, TypeAttributes attr, TypeSymbol? parent, int typeSize) + { + throw new NotImplementedException(); + } /// /// Defines a nested type, given its name, attributes, the type that it extends, and the packing size. @@ -222,7 +305,10 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize); + TypeSymbolBuilder DefineNestedType(TypeSymbolBuilder enclosingType, string name, TypeAttributes attr, TypeSymbol? parent, PackingSize packSize) + { + throw new NotImplementedException(); + } /// /// Defines a nested type, given its name, attributes, size, and the type that it extends. @@ -234,25 +320,67 @@ interface IModuleSymbolBuilder : ISymbolBuilder, IModuleSymbol, I /// /// /// - ITypeSymbolBuilder DefineNestedType(ITypeSymbolBuilder enclosingType, string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize); + TypeSymbolBuilder DefineNestedType(TypeSymbolBuilder enclosingType, string name, TypeAttributes attr, TypeSymbol? parent, PackingSize packSize, int typeSize) + { + throw new NotImplementedException(); + } /// /// Explicitely adds a reference to the specified assembly. /// /// - void AddReference(IAssemblySymbol assembly); + void AddReference(AssemblySymbol assembly) + { + throw new NotImplementedException(); + } /// /// Finishes the module and all types. Required before save. /// - void Complete(); + void Complete() + { + throw new NotImplementedException(); + } /// /// Saves this module assembly to disk. Module must first be completed. /// /// /// - void Save(PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine); + void Save(PortableExecutableKinds portableExecutableKind, ImageFileMachine imageFileMachine) + { + throw new NotImplementedException(); + } + + /// + public override bool IsResource() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredFields() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredMethods() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredTypes() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/PropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/PropertySymbolBuilder.cs new file mode 100644 index 0000000000..615a0a36ad --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/PropertySymbolBuilder.cs @@ -0,0 +1,138 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class PropertySymbolBuilder : PropertySymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public PropertySymbolBuilder(SymbolContext context, TypeSymbol declaringType) : + base(context, declaringType) + { + + } + + /// + public override PropertyAttributes Attributes => throw new NotImplementedException(); + + /// + public override TypeSymbol PropertyType => throw new NotImplementedException(); + + /// + public override bool CanRead => throw new NotImplementedException(); + + /// + public override bool CanWrite => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsMissing => throw new NotImplementedException(); + + /// + public override bool ContainsMissing => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + public override MethodSymbol? GetGetMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override MethodSymbol? GetSetMethod(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override TypeSymbol GetModifiedPropertyType() + { + throw new NotImplementedException(); + } + + /// + public override object? GetRawConstantValue() + { + throw new NotImplementedException(); + } + + /// + /// Sets the default value of this property. + /// + /// + public void SetConstant(object? defaultValue) + { + throw new NotImplementedException(); + } + + /// + /// Sets the method that gets the property value. + /// + /// + public void SetGetMethod(MethodSymbolBuilder mdBuilder) + { + throw new NotImplementedException(); + } + + /// + /// Sets the method that sets the property value. + /// + /// + public void SetSetMethod(MethodSymbolBuilder mdBuilder) + { + throw new NotImplementedException(); + } + + /// + /// Adds one of the other methods associated with this property. + /// + /// + public void AddOtherMethod(MethodSymbolBuilder mdBuilder) + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetAccessors(bool nonPublic) + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetIndexParameters() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetOptionalCustomModifiers() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetRequiredCustomModifiers() + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilder.cs new file mode 100644 index 0000000000..dd65ee203b --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilder.cs @@ -0,0 +1,602 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; +using System.Reflection.Emit; +using System.Runtime.InteropServices; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + class TypeSymbolBuilder : TypeSymbol + { + + /// + /// Initializes a new instance. + /// + /// + /// + public TypeSymbolBuilder(SymbolContext context, ModuleSymbol declaringModule) : + base(context, declaringModule) + { + + } + + /// + public override TypeAttributes Attributes => throw new NotImplementedException(); + + /// + public override MethodBaseSymbol? DeclaringMethod => throw new NotImplementedException(); + + /// + public override string? FullName => throw new NotImplementedException(); + + /// + public override string? Namespace => throw new NotImplementedException(); + + /// + public override TypeCode TypeCode => throw new NotImplementedException(); + + /// + public override TypeSymbol? BaseType => throw new NotImplementedException(); + + /// + public override bool ContainsGenericParameters => throw new NotImplementedException(); + + /// + public override GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); + + /// + public override int GenericParameterPosition => throw new NotImplementedException(); + + /// + public override bool IsTypeDefinition => true; + + /// + public override bool IsGenericTypeDefinition => throw new NotImplementedException(); + + /// + public override bool IsConstructedGenericType => false; + + /// + public override bool IsGenericTypeParameter => false; + + /// + public override bool IsGenericMethodParameter => false; + + /// + public override bool HasElementType => throw new NotImplementedException(); + + /// + public override bool IsPrimitive => throw new NotImplementedException(); + + /// + public override bool IsSZArray => throw new NotImplementedException(); + + /// + public override bool IsArray => throw new NotImplementedException(); + + /// + public override bool IsEnum => throw new NotImplementedException(); + + /// + public override bool IsPointer => throw new NotImplementedException(); + + /// + public override bool IsFunctionPointer => throw new NotImplementedException(); + + /// + public override bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); + + /// + public override bool IsByRef => throw new NotImplementedException(); + + /// + public override string Name => throw new NotImplementedException(); + + /// + public override bool IsMissing => throw new NotImplementedException(); + + /// + public override bool ContainsMissing => throw new NotImplementedException(); + + /// + public override bool IsComplete => throw new NotImplementedException(); + + /// + /// Sets the base type of the type currently under construction. + /// + /// + void SetParent(TypeSymbol? parent) + { + throw new NotImplementedException(); + } + + /// + /// Defines the generic type parameters for the current type, specifying their number and their names, and returns an array of GenericTypeParameterBuilder objects that can be used to set their constraints. + /// + /// + /// + ImmutableList DefineGenericParameters(ImmutableList names) + { + throw new NotImplementedException(); + } + + /// + /// Defines the initializer for this type. + /// + /// + ConstructorSymbolBuilder DefineTypeInitializer() + { + throw new NotImplementedException(); + } + + /// + /// Adds an interface that this type implements. + /// + /// + void AddInterfaceImplementation(TypeSymbol interfaceType) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new constructor to the type, with the given attributes and signature and the standard calling convention. + /// + /// + /// + /// + ConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, ImmutableList parameterTypes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new constructor to the type, with the given attributes and signature. + /// + /// + /// + /// + /// + ConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ImmutableList parameterTypes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new constructor to the type, with the given attributes, signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + ConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, ImmutableList parameterTypes, ImmutableList> requiredCustomModifiers, ImmutableList> optionalCustomModifiers) + { + throw new NotImplementedException(); + } + + /// + /// Defines the parameterless constructor. The constructor defined here will simply call the parameterless constructor of the parent. + /// + /// + /// + ConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new event to the type, with the given name, attributes and event type. + /// + /// + /// + /// + /// + EventSymbolBuilder DefineEvent(string name, EventAttributes attributes, TypeSymbol eventtype) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new field to the type, with the given name, attributes, and field type. + /// + /// + /// + /// + /// + FieldSymbolBuilder DefineField(string fieldName, TypeSymbol type, FieldAttributes attributes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new field to the type, with the given name, attributes, field type, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + FieldSymbolBuilder DefineField(string fieldName, TypeSymbol type, ImmutableList requiredCustomModifiers, ImmutableList optionalCustomModifiers, FieldAttributes attributes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new method to the type, with the specified name, method attributes, calling convention, method signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + MethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, TypeSymbol? returnType, ImmutableList returnTypeRequiredCustomModifiers, ImmutableList returnTypeOptionalCustomModifiers, ImmutableList parameterTypes, ImmutableList> parameterTypeRequiredCustomModifiers, ImmutableList> parameterTypeOptionalCustomModifiers) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new method to the type, with the specified name, method attributes, calling convention, and method signature. + /// + /// + /// + /// + /// + /// + /// + MethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, TypeSymbol? returnType, ImmutableList parameterTypes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new method to the type, with the specified name, method attributes, and calling convention. + /// + /// + /// + /// + /// + MethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new method to the type, with the specified name and method attributes. + /// + /// + /// + /// + MethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new method to the type, with the specified name, method attributes, and method signature. + /// + /// + /// + /// + /// + /// + MethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, TypeSymbol? returnType, ImmutableList parameterTypes) + { + throw new NotImplementedException(); + } + + /// + /// Specifies a given method body that implements a given method declaration, potentially with a different name. + /// + /// + /// + void DefineMethodOverride(MethodSymbol methodInfoBody, MethodSymbol methodInfoDeclaration) + { + throw new NotImplementedException(); + } + + /// + /// Defines a nested type, given its name, attributes, the type that it extends, and the interfaces that it implements. + /// + /// + /// + /// + /// + /// + TypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, TypeSymbol? parent, ImmutableList interfaces) + { + throw new NotImplementedException(); + } + + /// + /// Defines a nested type, given its name, attributes, size, and the type that it extends. + /// + /// + /// + /// + /// + /// + /// + TypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, TypeSymbol? parent, PackingSize packSize, int typeSize) + { + throw new NotImplementedException(); + } + + /// + /// Defines a nested type, given its name, attributes, the type that it extends, and the packing size. + /// + /// + /// + /// + /// + /// + TypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, TypeSymbol? parent, PackingSize packSize) + { + throw new NotImplementedException(); + } + + /// + /// Defines a nested type, given its name. + /// + /// + /// + TypeSymbolBuilder DefineNestedType(string name) + { + throw new NotImplementedException(); + } + + /// + /// Defines a nested type, given its name, attributes, and the type that it extends. + /// + /// + /// + /// + /// + TypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, TypeSymbol? parent) + { + throw new NotImplementedException(); + } + + /// + /// Defines a nested type, given its name and attributes. + /// + /// + /// + /// + TypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr) + { + throw new NotImplementedException(); + } + + /// + /// Defines a nested type, given its name, attributes, the total size of the type, and the type that it extends. + /// + /// + /// + /// + /// + /// + TypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, TypeSymbol? parent, int typeSize) + { + throw new NotImplementedException(); + } + + /// + /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + MethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, TypeSymbol? returnType, ImmutableList parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet) + { + throw new NotImplementedException(); + } + + /// + /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, and the PInvoke flags. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + MethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, TypeSymbol? returnType, ImmutableList parameterTypes, System.Runtime.InteropServices.CallingConvention nativeCallConv, System.Runtime.InteropServices.CharSet nativeCharSet) + { + throw new NotImplementedException(); + } + + /// + /// Defines a PInvoke method given its name, the name of the DLL in which the method is defined, the name of the entry point, the attributes of the method, the calling convention of the method, the return type of the method, the types of the parameters of the method, the PInvoke flags, and custom modifiers for the parameters and return type. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + MethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, TypeSymbol? returnType, ImmutableList returnTypeRequiredCustomModifiers, ImmutableList returnTypeOptionalCustomModifiers, ImmutableList parameterTypes, ImmutableList> parameterTypeRequiredCustomModifiers, ImmutableList> parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new property to the type, with the given name and property signature. + /// + /// + /// + /// + /// + /// + PropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, TypeSymbol returnType, ImmutableList parameterTypes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new property to the type, with the given name, attributes, calling convention, and property signature. + /// + /// + /// + /// + /// + /// + /// + PropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, TypeSymbol returnType, ImmutableList parameterTypes) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new property to the type, with the given name, property signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + PropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, TypeSymbol returnType, ImmutableList returnTypeRequiredCustomModifiers, ImmutableList returnTypeOptionalCustomModifiers, ImmutableList parameterTypes, ImmutableList> parameterTypeRequiredCustomModifiers, ImmutableList> parameterTypeOptionalCustomModifiers) + { + throw new NotImplementedException(); + } + + /// + /// Adds a new property to the type, with the given name, calling convention, property signature, and custom modifiers. + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + PropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, TypeSymbol returnType, ImmutableList returnTypeRequiredCustomModifiers, ImmutableList returnTypeOptionalCustomModifiers, ImmutableList parameterTypes, ImmutableList> parameterTypeRequiredCustomModifiers, ImmutableList> parameterTypeOptionalCustomModifiers) + { + throw new NotImplementedException(); + } + + public override int GetArrayRank() + { + throw new NotImplementedException(); + } + + internal override ImmutableArray GetDeclaredConstructors() + { + throw new NotImplementedException(); + } + + public override TypeSymbol? GetElementType() + { + throw new NotImplementedException(); + } + + public override bool IsEnumDefined(object value) + { + throw new NotImplementedException(); + } + + public override string? GetEnumName(object value) + { + throw new NotImplementedException(); + } + + public override ImmutableArray GetEnumNames() + { + throw new NotImplementedException(); + } + + public override TypeSymbol GetEnumUnderlyingType() + { + throw new NotImplementedException(); + } + + internal override ImmutableArray GetDeclaredEvents() + { + throw new NotImplementedException(); + } + + internal override ImmutableArray GetDeclaredFields() + { + throw new NotImplementedException(); + } + + public override ImmutableArray GetGenericArguments() + { + throw new NotImplementedException(); + } + + public override ImmutableArray GetGenericParameterConstraints() + { + throw new NotImplementedException(); + } + + public override TypeSymbol GetGenericTypeDefinition() + { + throw new NotImplementedException(); + } + + public override ImmutableArray GetInterfaces() + { + throw new NotImplementedException(); + } + + public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + { + throw new NotImplementedException(); + } + + internal override ImmutableArray GetDeclaredMethods() + { + throw new NotImplementedException(); + } + + internal override ImmutableArray GetDeclaredNestedTypes() + { + throw new NotImplementedException(); + } + + internal override ImmutableArray GetDeclaredProperties() + { + throw new NotImplementedException(); + } + + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs b/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs deleted file mode 100644 index c8390162eb..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/TypeSymbolBuilderBase.cs +++ /dev/null @@ -1,1111 +0,0 @@ -using System; -using System.Collections.Immutable; -using System.Diagnostics; -using System.Linq; -using System.Reflection; -using System.Reflection.Emit; -using System.Runtime.InteropServices; - -using IKVM.CoreLib.Reflection; - -namespace IKVM.CoreLib.Symbols.Emit -{ - - abstract class TypeSymbolBuilderBase : ITypeSymbolBuilder - where TContext : ISymbolContext - { - - const BindingFlags DefaultBindingFlags = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance; - - readonly TContext _context; - readonly IModuleSymbolBuilder _module; - - readonly TypeAttributes _attributes; - readonly string _namespace; - readonly string _name; - readonly ITypeSymbol? _declaringType; - readonly PackingSize _packingSize; - readonly int _typeSize; - ITypeSymbol? _parentType; - IConstructorSymbol? _typeInitializer = null; - ImmutableList _genericTypeParameters = ImmutableList.Empty; - ImmutableList _interfaces = ImmutableList.Empty; - ImmutableList _fields = ImmutableList.Empty; - ImmutableList _constructors = ImmutableList.Empty; - ImmutableList _methods = ImmutableList.Empty; - ImmutableList<(IMethodSymbol, IMethodSymbol)> _methodOverrides = ImmutableList<(IMethodSymbol, IMethodSymbol)>.Empty; - ImmutableList _properties = ImmutableList.Empty; - ImmutableList _events = ImmutableList.Empty; - ImmutableList _customAttributes = ImmutableList.Empty; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - /// - /// - /// - /// - public TypeSymbolBuilderBase(TContext context, IModuleSymbolBuilder module, TypeAttributes attributes, string name, ITypeSymbol? declaringType, PackingSize packingSize, int typeSize) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _attributes = attributes; - _declaringType = declaringType; - _packingSize = packingSize; - _typeSize = typeSize; - - int iLast = name.LastIndexOf('.'); - if (iLast <= 0) - { - // no name space - _namespace = string.Empty; - _name = name; - } - else - { - // split the name space - _namespace = name.Substring(0, iLast); - _name = name.Substring(iLast + 1); - } - } - - /// - public ISymbolContext Context => _context; - - /// - public IModuleSymbolBuilder ResolvingModuleBuilder => _module; - - #region ITypeSymbolBuilder - - /// - public void SetParent(ITypeSymbol? parent) - { - _parentType = parent; - } - - /// - public IImmutableList DefineGenericParameters(IImmutableList names) - { - if (names.Count >= 1 && _genericTypeParameters.IsEmpty == false) - throw new InvalidOperationException("Generic parameters already defined."); - - var a = ImmutableList.Create(); - for (int i = 0; i < names.Count; i++) - a = a.Add(CreateGenericParameter(names[i])); - - return _genericTypeParameters = a; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - protected abstract IGenericTypeParameterSymbolBuilder CreateGenericParameter(string name); - - /// - public void AddInterfaceImplementation(ITypeSymbol interfaceType) - { - _interfaces = _interfaces.Add(interfaceType); - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - /// - /// - /// - public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, IImmutableList> optionalCustomModifiers) - { - var constructor = CreateConstructorBuilder(attributes, callingConvention, parameterTypes, requiredCustomModifiers, optionalCustomModifiers); - _constructors = _constructors.Add(constructor); - return constructor; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - /// - /// - protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, IImmutableList> optionalCustomModifiers); - - /// - public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, IImmutableList parameterTypes) - { - var constructor = CreateConstructorBuilder(attributes, parameterTypes); - _constructors = _constructors.Add(constructor); - return constructor; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, IImmutableList parameterTypes); - - /// - public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes) - { - var constructor = CreateConstructorBuilder(attributes, callingConvention, parameterTypes); - _constructors = _constructors.Add(constructor); - return constructor; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes); - - /// - public IConstructorSymbolBuilder DefineConstructor(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, ImmutableArray> optionalCustomModifiers) - { - var constructor = CreateConstructorBuilder(attributes, callingConvention, parameterTypes, requiredCustomModifiers, optionalCustomModifiers); - _constructors = _constructors.Add(constructor); - return constructor; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - /// - /// - protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes, CallingConventions callingConvention, IImmutableList parameterTypes, IImmutableList> requiredCustomModifiers, ImmutableArray> optionalCustomModifiers); - - /// - public IConstructorSymbolBuilder DefineDefaultConstructor(MethodAttributes attributes) - { - var constructor = CreateConstructorBuilder(attributes); - _constructors = _constructors.Add(constructor); - return constructor; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - protected abstract IConstructorSymbolBuilder CreateConstructorBuilder(MethodAttributes attributes); - - /// - public IEventSymbolBuilder DefineEvent(string name, EventAttributes attributes, ITypeSymbol eventtype) - { - var @event = CreateEventBuilder(name, attributes, eventtype); - _events = _events.Add(@event); - return @event; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - protected abstract IEventSymbolBuilder CreateEventBuilder(string name, EventAttributes attributes, ITypeSymbol eventtype); - - /// - public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, FieldAttributes attributes) - { - var field = CreateFieldBuilder(fieldName, type, attributes); - _fields = _fields.Add(field); - return field; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - protected abstract IFieldSymbolBuilder CreateFieldBuilder(string fieldName, ITypeSymbol type, FieldAttributes attributes); - - /// - public IFieldSymbolBuilder DefineField(string fieldName, ITypeSymbol type, IImmutableList requiredCustomModifiers, IImmutableList optionalCustomModifiers, FieldAttributes attributes) - { - var field = CreateFieldBuilder(fieldName, type, requiredCustomModifiers, optionalCustomModifiers, attributes); - _fields = _fields.Add(field); - return field; - } - - /// - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - /// - /// - protected abstract IFieldSymbolBuilder CreateFieldBuilder(string fieldName, ITypeSymbol type, IImmutableList requiredCustomModifiers, IImmutableList optionalCustomModifiers, FieldAttributes attributes); - - /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers) - { - var method = CreateMethodBuilder(name, attributes, callingConvention, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers); - _methods = _methods.Add(method); - return method; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); - - /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes) - { - var method = CreateMethodBuilder(name, attributes, callingConvention, returnType, parameterTypes); - _methods = _methods.Add(method); - return method; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - /// - /// - protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes); - - /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, CallingConventions callingConvention) - { - var method = CreateMethodBuilder(name, attributes, callingConvention); - _methods = _methods.Add(method); - return method; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, CallingConventions callingConvention); - - /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes) - { - var method = CreateMethodBuilder(name, attributes); - _methods = _methods.Add(method); - return method; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes); - - /// - public IMethodSymbolBuilder DefineMethod(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes) - { - var method = CreateMethodBuilder(name, attributes, returnType, parameterTypes); - _methods = _methods.Add(method); - return method; - } - - /// - /// Override this method to implement the creation of a . - /// - /// - /// - /// - /// - /// - protected abstract IMethodSymbolBuilder CreateMethodBuilder(string name, MethodAttributes attributes, ITypeSymbol? returnType, IImmutableList parameterTypes); - - /// - public void DefineMethodOverride(IMethodSymbol methodInfoBody, IMethodSymbol methodInfoDeclaration) - { - _methodOverrides = _methodOverrides.Add((methodInfoBody, methodInfoDeclaration)); - } - - /// - public ITypeSymbolBuilder DefineNestedType(string name) - { - return _module.DefineNestedType(this, name); - } - - /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr) - { - return _module.DefineNestedType(this, name, attr); - } - - /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent) - { - return _module.DefineNestedType(this, name, attr, parent); - } - - /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, IImmutableList interfaces) - { - return _module.DefineNestedType(this, name, attr, parent, interfaces); - } - - /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, int typeSize) - { - return _module.DefineNestedType(this, name, attr, parent, typeSize); - } - - /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize) - { - return _module.DefineNestedType(this, name, attr, parent, packSize); - } - - /// - public ITypeSymbolBuilder DefineNestedType(string name, TypeAttributes attr, ITypeSymbol? parent, PackingSize packSize, int typeSize) - { - return _module.DefineNestedType(this, name, attr, parent, packSize, typeSize); - } - - /// - public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) - { - var method = CreatePInvokeMethodBuilder(name, dllName, attributes, callingConvention, returnType, parameterTypes, nativeCallConv, nativeCharSet); - _methods = _methods.Add(method); - return method; - } - - protected abstract IMethodSymbolBuilder CreatePInvokeMethodBuilder(string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet); - - /// - public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) - { - var method = CreatePInvokeMethodBuilder(name, dllName, entryName, attributes, callingConvention, returnType, parameterTypes, nativeCallConv, nativeCharSet); - _methods = _methods.Add(method); - return method; - } - - protected abstract IMethodSymbolBuilder CreatePInvokeMethodBuilder(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet); - - /// - public IMethodSymbolBuilder DefinePInvokeMethod(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet) - { - var method = CreatePInvokeMethodBuilder(name, dllName, entryName, attributes, callingConvention, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers, nativeCallConv, nativeCharSet); - _methods = _methods.Add(method); - return method; - } - - protected abstract IMethodSymbolBuilder CreatePInvokeMethodBuilder(string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, ITypeSymbol? returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers, CallingConvention nativeCallConv, CharSet nativeCharSet); - - /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList parameterTypes) - { - var property = CreatePropertyBuilder(name, attributes, returnType, parameterTypes); - _properties = _properties.Add(property); - return property; - } - - protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList parameterTypes); - - /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList parameterTypes) - { - var property = CreatePropertyBuilder(name, attributes, callingConvention, returnType, parameterTypes); - _properties = _properties.Add(property); - return property; - } - - protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList parameterTypes); - - /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers) - { - var property = CreatePropertyBuilder(name, attributes, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers); - _properties = _properties.Add(property); - return property; - } - - protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); - - /// - public IPropertySymbolBuilder DefineProperty(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers) - { - var property = CreatePropertyBuilder(name, attributes, callingConvention, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers); - _properties = _properties.Add(property); - return property; - } - - protected abstract IPropertySymbolBuilder CreatePropertyBuilder(string name, PropertyAttributes attributes, CallingConventions callingConvention, ITypeSymbol returnType, IImmutableList returnTypeRequiredCustomModifiers, IImmutableList returnTypeOptionalCustomModifiers, IImmutableList parameterTypes, IImmutableList> parameterTypeRequiredCustomModifiers, IImmutableList> parameterTypeOptionalCustomModifiers); - - /// - public IConstructorSymbolBuilder DefineTypeInitializer() - { - return (IConstructorSymbolBuilder)(_typeInitializer = CreateTypeInitializerBuilder()); - } - - protected abstract IConstructorSymbolBuilder CreateTypeInitializerBuilder(); - - #endregion - - #region ICustomAttributeProviderBuilder - - /// - public void SetCustomAttribute(CustomAttribute attribute) - { - _customAttributes = _customAttributes.Add(attribute); - } - - #endregion - - #region ITypeSymbol - - /// - public TypeAttributes Attributes => _attributes; - - /// - public IAssemblySymbol Assembly => _module.Assembly; - - /// - public IMethodBaseSymbol? DeclaringMethod => null; - - /// - public string? AssemblyQualifiedName => System.Reflection.Assembly.CreateQualifiedName(Assembly.FullName, FullName); - - /// - public string? FullName => string.IsNullOrEmpty(_namespace) ? _name : _namespace + "." + _name; - - /// - public string? Namespace => _namespace; - - /// - public TypeCode TypeCode => TypeCode.Object; - - /// - public ITypeSymbol? BaseType => _parentType; - - /// - public bool ContainsGenericParameters => _genericTypeParameters.IsEmpty == false; - - /// - public GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); - - /// - public int GenericParameterPosition => throw new NotImplementedException(); - - /// - public IImmutableList GenericTypeArguments => _genericTypeParameters; - - /// - public bool IsConstructedGenericType => false; - - /// - public bool IsGenericType => _genericTypeParameters.Count > 0; - - /// - public bool IsGenericTypeDefinition => IsGenericType; - - /// - public bool IsGenericParameter => false; - - /// - public bool IsAutoLayout => (_attributes & TypeAttributes.LayoutMask) == TypeAttributes.AutoLayout; - - /// - public bool IsExplicitLayout => (_attributes & TypeAttributes.LayoutMask) == TypeAttributes.ExplicitLayout; - - /// - public bool IsLayoutSequential => (_attributes & TypeAttributes.LayoutMask) == TypeAttributes.SequentialLayout; - - /// - public bool HasElementType => false; - - /// - public bool IsClass => (_attributes & TypeAttributes.ClassSemanticsMask) == TypeAttributes.Class && !IsValueType; - - /// - public bool IsValueType => IsSubclassOf(Context.ResolveCoreType("System.ValueType")); - - /// - public bool IsInterface => (_attributes & TypeAttributes.Interface) != 0; - - /// - public bool IsPrimitive => false; - - /// - public bool IsSZArray => false; - - /// - public bool IsArray => false; - - /// - public bool IsEnum => IsSubclassOf(Context.ResolveCoreType("System.Enum")); - - /// - public bool IsPointer => false; - - /// - public bool IsFunctionPointer => false; - - /// - public bool IsUnmanagedFunctionPointer => false; - - /// - public bool IsByRef => false; - - /// - public bool IsAbstract => (_attributes & TypeAttributes.Abstract) != 0; - - /// - public bool IsSealed => (_attributes & TypeAttributes.Sealed) != 0; - - /// - public bool IsVisible => GetIsVisible(); - - bool GetIsVisible() - { - if (IsGenericParameter) - return true; - - if (HasElementType) - return GetElementType()!.IsVisible; - - var type = (ITypeSymbol)this; - while (type.IsNested) - { - if (!type.IsNestedPublic) - return false; - - // this should be null for non-nested types. - type = type.DeclaringType!; - } - - // Now "type" should be a top level type - if (!type.IsPublic) - return false; - - if (IsGenericType && !IsGenericTypeDefinition) - { - foreach (var t in GetGenericArguments()) - { - if (!t.IsVisible) - return false; - } - } - - return true; - } - - /// - public bool IsPublic => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.Public; - - /// - public bool IsNotPublic => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NotPublic; - - /// - public bool IsNested => DeclaringType != null; - - /// - public bool IsNestedAssembly => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedAssembly; - - /// - public bool IsNestedFamANDAssem => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamANDAssem; - - /// - public bool IsNestedFamily => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamily; - - /// - public bool IsNestedFamORAssem => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedFamORAssem; - - /// - public bool IsNestedPrivate => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPrivate; - - /// - public bool IsNestedPublic => (_attributes & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPublic; - - /// - public bool IsSerializable => throw new NotImplementedException(); - - /// - public bool IsSignatureType => false; - - /// - public bool IsSpecialName => (_attributes & TypeAttributes.SpecialName) != 0; - - /// - public IConstructorSymbol? TypeInitializer => throw new NotImplementedException(); - - /// - public IModuleSymbol Module => _module; - - /// - public ITypeSymbol? DeclaringType => _declaringType; - - /// - public MemberTypes MemberType => throw new NotImplementedException(); - - /// - public int MetadataToken => throw new NotImplementedException(); - - /// - public string Name => _name; - - /// - public bool IsMissing => false; - - /// - public bool ContainsMissing => throw new NotImplementedException(); - - /// - public bool IsComplete => throw new NotImplementedException(); - - /// - public int GetArrayRank() - { - return 0; - } - - /// - public IImmutableList GetDefaultMembers() - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol? GetElementType() - { - return null; - } - - /// - public string? GetEnumName(object value) - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetEnumNames() - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol GetEnumUnderlyingType() - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetGenericArguments() - { - return _genericTypeParameters; - } - - /// - public IImmutableList GetGenericParameterConstraints() - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol GetGenericTypeDefinition() - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol? GetInterface(string name) - { - throw new NotImplementedException(); - } - - /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetInterfaces(bool inherit = true) - { - throw new NotImplementedException(); - } - - /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetDeclaredConstructors() - { - throw new NotImplementedException(); - } - - /// - public IConstructorSymbol? GetConstructor(IImmutableList types) - { - throw new NotImplementedException(); - } - - /// - public IConstructorSymbol? GetConstructor(BindingFlags bindingFlags, IImmutableList types) - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetConstructors() - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetConstructors(BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - /// - public IFieldSymbol? GetField(string name) - { - throw new NotImplementedException(); - } - - /// - public IFieldSymbol? GetField(string name, BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetFields() - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetFields(BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetDeclaredMethods() - { - return _methods; - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return SymbolUtil.SelectMethod(this, DefaultBindingFlags, name, null, null); - } - - /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList? types, IImmutableList? modifiers) - { - return SymbolUtil.SelectMethod(this, bindingFlags, name, types, modifiers); - } - - public IMethodSymbol? GetMethod(string name, IImmutableList types) - { - return SymbolUtil.SelectMethod(this, DefaultBindingFlags, null, types, null); - } - - public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags) - { - return SymbolUtil.SelectMethod(this, bindingFlags, null, null, null); - } - - public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, IImmutableList types) - { - return SymbolUtil.SelectMethod(this, bindingFlags, null, types, null); - } - - public IMethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers) - { - return SymbolUtil.SelectMethod(this, bindingFlags, null, types, modifiers); - } - - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, IImmutableList types, IImmutableList modifiers) - { - throw new NotImplementedException(); - } - - public IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, IImmutableList types, IImmutableList modifiers) - { - throw new NotImplementedException(); - } - - public IMethodSymbol? GetMethod(string name, int genericParameterCount, IImmutableList types, IImmutableList modifiers) - { - throw new NotImplementedException(); - } - - /// - public IImmutableList GetMethods() - { - return SymbolUtil.SelectMethods(this, DefaultBindingFlags, null, null, null); - } - - /// - public IImmutableList GetMethods(BindingFlags bindingFlags) - { - return SymbolUtil.SelectMethods(this, bindingFlags, null, null, null); - } - - public IImmutableList GetDeclaredProperties() - { - throw new NotImplementedException(); - } - - public IPropertySymbol? GetProperty(string name) - { - throw new NotImplementedException(); - } - - public IPropertySymbol? GetProperty(string name, BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - public IPropertySymbol? GetProperty(string name, IImmutableList types) - { - throw new NotImplementedException(); - } - - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, IImmutableList types) - { - throw new NotImplementedException(); - } - - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - throw new NotImplementedException(); - } - - public IImmutableList GetProperties() - { - throw new NotImplementedException(); - } - - public IImmutableList GetProperties(BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - public IImmutableList GetDeclaredEvents() - { - throw new NotImplementedException(); - } - - public IEventSymbol? GetEvent(string name) - { - throw new NotImplementedException(); - } - - public IEventSymbol? GetEvent(string name, BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - public IImmutableList GetEvents() - { - throw new NotImplementedException(); - } - - public IImmutableList GetEvents(BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - public ITypeSymbol? GetNestedType(string name) - { - throw new NotImplementedException(); - } - - public ITypeSymbol? GetNestedType(string name, BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - public IImmutableList GetNestedTypes() - { - throw new NotImplementedException(); - } - - public IImmutableList GetNestedTypes(BindingFlags bindingFlags) - { - throw new NotImplementedException(); - } - - public bool IsAssignableFrom(ITypeSymbol? c) - { - throw new NotImplementedException(); - } - - public bool IsSubclassOf(ITypeSymbol c) - { - throw new NotImplementedException(); - } - - public bool IsEnumDefined(object value) - { - throw new NotImplementedException(); - } - - public ITypeSymbol MakeArrayType() - { - throw new NotImplementedException(); - } - - public ITypeSymbol MakeArrayType(int rank) - { - throw new NotImplementedException(); - } - - public ITypeSymbol MakeGenericType(IImmutableList typeArguments) - { - throw new NotImplementedException(); - } - - public ITypeSymbol MakePointerType() - { - throw new NotImplementedException(); - } - - public ITypeSymbol MakeByRefType() - { - throw new NotImplementedException(); - } - - CustomAttribute[] ICustomAttributeProvider.GetCustomAttributes(bool inherit) - { - throw new NotImplementedException(); - } - - public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - throw new NotImplementedException(); - } - - #endregion - - #region ICustomAttributeProvider - - /// - public override IImmutableList GetCustomAttributes(bool inherit = false) - { - if (inherit == false || BaseType == null) - return _customAttributes?.ToArray() ?? []; - else - return Enumerable.Concat(_customAttributes?.ToArray() ?? [], ResolveCustomAttributes(BaseType.Unpack().GetInheritedCustomAttributesData())).ToArray(); - } - - /// - public override CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(inherit).FirstOrDefault(i => i.AttributeType == attributeType); - } - - /// - public override CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - return GetCustomAttributes(inherit).Where(i => i.AttributeType == attributeType).ToArray(); - } - - #endregion - - /// - public void Complete() - { - if (_builder != null) - { - // complete type - if (_builder.IsCreated() == false) - { - _type = _builder.CreateType() ?? throw new InvalidOperationException(); - _methods = null; - _customAttributes = null; - } - - // force module to reresolve - Context.GetOrCreateModuleSymbol(ResolvingModule.UnderlyingModule); - OnComplete(); - } - } - - /// - public void OnComplete() - { - const BindingFlags DefaultBindingFlags = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static; - - // apply the runtime generic type parameters and pass them to the symbols for completion - var srcGenericArgs = UnderlyingRuntimeType.GetGenericArguments() ?? []; - var dstGenericArgs = GetGenericArguments() ?? []; - Debug.Assert(srcGenericArgs.Length == dstGenericArgs.Length); - for (int i = 0; i < srcGenericArgs.Length; i++) - if (dstGenericArgs[i] is IReflectionGenericTypeParameterSymbolBuilder b) - b.OnComplete(srcGenericArgs[i]); - - foreach (var i in GetConstructors(DefaultBindingFlags) ?? []) - if (i is IReflectionConstructorSymbolBuilder b) - b.OnComplete(); - - foreach (var i in GetMethods(DefaultBindingFlags) ?? []) - if (i is IReflectionMethodSymbolBuilder b) - b.OnComplete(); - - foreach (var i in GetFields(DefaultBindingFlags) ?? []) - if (i is IReflectionFieldSymbolBuilder b) - b.OnComplete(); - - foreach (var i in GetProperties(DefaultBindingFlags) ?? []) - if (i is IReflectionPropertySymbolBuilder b) - b.OnComplete(); - - foreach (var m in GetEvents(DefaultBindingFlags) ?? []) - if (m is IReflectionPropertySymbolBuilder b) - b.OnComplete(); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/EventSymbol.cs b/src/IKVM.CoreLib/Symbols/EventSymbol.cs index 219ea207de..e303e44ef2 100644 --- a/src/IKVM.CoreLib/Symbols/EventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/EventSymbol.cs @@ -1,4 +1,5 @@ -using System.Reflection; +using System.Collections.Immutable; +using System.Reflection; namespace IKVM.CoreLib.Symbols { @@ -11,7 +12,7 @@ abstract class EventSymbol : MemberSymbol /// /// /// - public EventSymbol(ISymbolContext context, TypeSymbol declaringType) : + public EventSymbol(SymbolContext context, TypeSymbol declaringType) : base(context, declaringType.Module, declaringType) { @@ -38,23 +39,23 @@ public EventSymbol(ISymbolContext context, TypeSymbol declaringType) : /// /// Returns the method used to add an event handler delegate to the event source. /// - public abstract MethodSymbol? AddMethod { get; } + public MethodSymbol? AddMethod => GetAddMethod(true); /// /// Returns the method used to remove an event handler delegate from the event source. /// - public abstract MethodSymbol? RemoveMethod { get; } + public MethodSymbol? RemoveMethod => GetRemoveMethod(true); /// /// Returns the method that is called when the event is raised. /// - public abstract MethodSymbol? RaiseMethod { get; } + public MethodSymbol? RaiseMethod => GetRaiseMethod(true); /// /// Returns the method used to add an event handler delegate to the event source. /// /// - public abstract MethodSymbol? GetAddMethod(); + public MethodSymbol? GetAddMethod() => GetAddMethod(false); /// /// Returns the method used to add an event handler delegate to the event source, specifying whether to return non-public methods. @@ -64,23 +65,23 @@ public EventSymbol(ISymbolContext context, TypeSymbol declaringType) : public abstract MethodSymbol? GetAddMethod(bool nonPublic); /// - /// Returns the public methods that have been associated with an event in metadata using the .other directive. + /// Returns the method used to remove an event handler delegate from the event source. /// /// - public abstract MethodSymbol[] GetOtherMethods(); + public MethodSymbol? GetRemoveMethod() => GetRemoveMethod(false); /// - /// Returns the methods that have been associated with the event in metadata using the .other directive, specifying whether to include non-public methods. + /// When overridden in a derived class, retrieves the object for removing a method of the event, specifying whether to return non-public methods. /// /// /// - public abstract MethodSymbol[] GetOtherMethods(bool nonPublic); + public abstract MethodSymbol? GetRemoveMethod(bool nonPublic); /// /// Returns the method that is called when the event is raised. /// /// - public abstract MethodSymbol? GetRaiseMethod(); + public MethodSymbol? GetRaiseMethod() => GetRaiseMethod(false); /// /// When overridden in a derived class, returns the method that is called when the event is raised, specifying whether to return non-public methods. @@ -90,17 +91,17 @@ public EventSymbol(ISymbolContext context, TypeSymbol declaringType) : public abstract MethodSymbol? GetRaiseMethod(bool nonPublic); /// - /// Returns the method used to remove an event handler delegate from the event source. + /// Returns the public methods that have been associated with an event in metadata using the .other directive. /// /// - public abstract MethodSymbol? GetRemoveMethod(); + public ImmutableArray GetOtherMethods() => GetOtherMethods(false); /// - /// When overridden in a derived class, retrieves the object for removing a method of the event, specifying whether to return non-public methods. + /// Returns the methods that have been associated with the event in metadata using the .other directive, specifying whether to include non-public methods. /// /// /// - public abstract MethodSymbol? GetRemoveMethod(bool nonPublic); + public abstract ImmutableArray GetOtherMethods(bool nonPublic); } diff --git a/src/IKVM.CoreLib/Symbols/FieldSymbol.cs b/src/IKVM.CoreLib/Symbols/FieldSymbol.cs index 1fba55f625..7fc9cff870 100644 --- a/src/IKVM.CoreLib/Symbols/FieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/FieldSymbol.cs @@ -13,7 +13,7 @@ abstract class FieldSymbol : MemberSymbol /// /// /// - public FieldSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + public FieldSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol? declaringType) : base(context, module, declaringType) { @@ -102,13 +102,13 @@ public FieldSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? dec /// Gets an array of types that identify the optional custom modifiers of the field. /// /// - public abstract IImmutableList GetOptionalCustomModifiers(); + public abstract ImmutableArray GetOptionalCustomModifiers(); /// /// Gets an array of types that identify the required custom modifiers of the property. /// /// - public abstract IImmutableList GetRequiredCustomModifiers(); + public abstract ImmutableArray GetRequiredCustomModifiers(); } diff --git a/src/IKVM.CoreLib/Symbols/GenericContext.cs b/src/IKVM.CoreLib/Symbols/GenericContext.cs index e10d781136..d1db2d82ba 100644 --- a/src/IKVM.CoreLib/Symbols/GenericContext.cs +++ b/src/IKVM.CoreLib/Symbols/GenericContext.cs @@ -3,12 +3,12 @@ namespace IKVM.CoreLib.Symbols { - readonly struct GenericContext(ImmutableList? GenericTypeArguments, ImmutableList? GenericMethodArguments) + readonly struct GenericContext(ImmutableArray? GenericTypeArguments, ImmutableArray? GenericMethodArguments) { - public readonly ImmutableList? GenericTypeArguments = GenericTypeArguments; + public readonly ImmutableArray? GenericTypeArguments = GenericTypeArguments; - public readonly ImmutableList? GenericMethodArguments = GenericMethodArguments; + public readonly ImmutableArray? GenericMethodArguments = GenericMethodArguments; } diff --git a/src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs index d28ee961a1..15f165447d 100644 --- a/src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/GenericMethodParameterTypeSymbol.cs @@ -1,5 +1,4 @@ using System; -using System.Collections.Immutable; namespace IKVM.CoreLib.Symbols { @@ -13,10 +12,9 @@ abstract class GenericMethodParameterTypeSymbol : GenericParameterTypeSymbol /// Initializes a new instance. /// /// - /// /// - protected GenericMethodParameterTypeSymbol(ISymbolContext context, IModuleSymbol module, MethodBaseSymbol declaringMethod) : - base(context, module, null) + protected GenericMethodParameterTypeSymbol(SymbolContext context, MethodSymbol declaringMethod) : + base(context, declaringMethod.Module) { _declaringMethod = declaringMethod ?? throw new ArgumentNullException(nameof(declaringMethod)); } @@ -25,12 +23,15 @@ protected GenericMethodParameterTypeSymbol(ISymbolContext context, IModuleSymbol public override MethodBaseSymbol? DeclaringMethod => _declaringMethod; /// - internal override TypeSymbol Specialize(IImmutableList? genericTypeArguments, IImmutableList? genericMethodArguments) - { - if (genericMethodArguments == null) - throw new InvalidOperationException(); + public override bool IsGenericTypeParameter => false; + + /// + public override bool IsGenericMethodParameter => true; - return genericMethodArguments[GenericParameterPosition]; + /// + internal override TypeSymbol Specialize(GenericContext genericContext) + { + return genericContext.GenericMethodArguments?[GenericParameterPosition] ?? this; } } diff --git a/src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs index af1375b5a7..4e0731bcf7 100644 --- a/src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/GenericParameterTypeSymbol.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols @@ -12,9 +13,8 @@ abstract class GenericParameterTypeSymbol : TypeSymbol /// /// /// - /// - protected GenericParameterTypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : - base(context, module, declaringType) + protected GenericParameterTypeSymbol(SymbolContext context, ModuleSymbol module) : + base(context, module) { } @@ -52,15 +52,30 @@ protected GenericParameterTypeSymbol(ISymbolContext context, IModuleSymbol modul /// public sealed override bool IsConstructedGenericType => false; - /// - public sealed override bool IsGenericParameter => true; - /// public sealed override bool ContainsGenericParameters => true; /// public sealed override TypeCode TypeCode => TypeCode.Object; + /// + public sealed override TypeSymbol? BaseType => null; + + /// + public sealed override bool IsTypeDefinition => false; + + /// + public sealed override bool IsPrimitive => false; + + /// + public sealed override bool IsEnum => false; + + /// + public sealed override bool IsMissing => false; + + /// + public sealed override bool ContainsMissing => false; + /// public sealed override TypeSymbol? GetElementType() { @@ -70,7 +85,97 @@ protected GenericParameterTypeSymbol(ISymbolContext context, IModuleSymbol modul /// public sealed override int GetArrayRank() { - throw new NotSupportedException(); + throw new InvalidOperationException(); + } + + /// + public sealed override string? GetEnumName(object value) + { + throw new InvalidOperationException(); + } + + /// + public sealed override ImmutableArray GetEnumNames() + { + throw new InvalidOperationException(); + } + + /// + public sealed override TypeSymbol GetEnumUnderlyingType() + { + throw new InvalidOperationException(); + } + + /// + internal sealed override ImmutableArray GetDeclaredConstructors() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredFields() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredMethods() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredProperties() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredEvents() + { + return ImmutableArray.Empty; + } + + /// + public sealed override ImmutableArray GetGenericArguments() + { + return ImmutableArray.Empty; + } + + /// + public sealed override ImmutableArray GetGenericParameterConstraints() + { + return ImmutableArray.Empty; + } + + /// + public sealed override TypeSymbol GetGenericTypeDefinition() + { + throw new InvalidOperationException(); + } + + /// + public sealed override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + { + throw new InvalidOperationException(); + } + + /// + internal override ImmutableArray GetDeclaredNestedTypes() + { + return ImmutableArray.Empty; + } + + /// + public sealed override bool IsEnumDefined(object value) + { + throw new InvalidOperationException(); + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + return ImmutableArray.Empty; } } diff --git a/src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs index f53bfb9b84..4232f014f9 100644 --- a/src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/GenericTypeParameterTypeSymbol.cs @@ -1,7 +1,4 @@ -using System; -using System.Collections.Immutable; - -namespace IKVM.CoreLib.Symbols +namespace IKVM.CoreLib.Symbols { abstract class GenericTypeParameterTypeSymbol : GenericParameterTypeSymbol @@ -11,21 +8,23 @@ abstract class GenericTypeParameterTypeSymbol : GenericParameterTypeSymbol /// Initializes a new instance. /// /// - /// /// - protected GenericTypeParameterTypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol declaringType) : - base(context, module, declaringType) + protected GenericTypeParameterTypeSymbol(SymbolContext context, TypeSymbol declaringType) : + base(context, declaringType.Module) { } /// - internal override TypeSymbol Specialize(IImmutableList? genericTypeArguments, IImmutableList? genericMethodArguments) - { - if (genericTypeArguments == null) - throw new InvalidOperationException(); + public override bool IsGenericTypeParameter => true; + + /// + public override bool IsGenericMethodParameter => false; - return genericTypeArguments[GenericParameterPosition]; + /// + internal override TypeSymbol Specialize(GenericContext genericContext) + { + return genericContext.GenericTypeArguments?[GenericParameterPosition] ?? this; } } diff --git a/src/IKVM.CoreLib/Symbols/HasElementSymbol.cs b/src/IKVM.CoreLib/Symbols/HasElementSymbol.cs index a47ae2e122..b7245d9d28 100644 --- a/src/IKVM.CoreLib/Symbols/HasElementSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/HasElementSymbol.cs @@ -18,12 +18,15 @@ abstract class HasElementSymbol : TypeSymbol /// /// /// - public HasElementSymbol(ISymbolContext context, TypeSymbol elementType) : - base(context, elementType.Module, null) + public HasElementSymbol(SymbolContext context, TypeSymbol elementType) : + base(context, elementType.Module) { _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); } + /// + public override MethodBaseSymbol? DeclaringMethod => null; + /// public sealed override string? Namespace => _elementType.Namespace; @@ -61,10 +64,10 @@ public HasElementSymbol(ISymbolContext context, TypeSymbol elementType) : public sealed override bool IsConstructedGenericType => false; /// - public sealed override bool IsGenericParameter => false; + public sealed override bool IsGenericTypeParameter => false; /// - public sealed override ImmutableList GenericTypeArguments => throw new NotSupportedException(); + public sealed override bool IsGenericMethodParameter => false; /// public sealed override bool ContainsGenericParameters => _elementType.ContainsGenericParameters; @@ -85,10 +88,10 @@ public HasElementSymbol(ISymbolContext context, TypeSymbol elementType) : public override bool IsArray => false; /// - public override bool IsSZArray => true; + public override bool IsSZArray => false; /// - public override bool IsByRef => true; + public override bool IsByRef => false; /// public override bool IsPointer => false; @@ -102,6 +105,12 @@ public HasElementSymbol(ISymbolContext context, TypeSymbol elementType) : /// public sealed override TypeCode TypeCode => TypeCode.Object; + /// + public sealed override bool IsMissing => false; + + /// + public sealed override bool ContainsMissing => _elementType.IsMissing; + /// public sealed override bool IsComplete => _elementType.IsComplete; @@ -118,33 +127,39 @@ public sealed override TypeSymbol GetGenericTypeDefinition() } /// - public sealed override ImmutableList GetGenericArguments() + public sealed override ImmutableArray GetGenericArguments() { throw new NotSupportedException(); } /// - public sealed override ImmutableList GetGenericParameterConstraints() + public sealed override ImmutableArray GetGenericParameterConstraints() { throw new NotSupportedException(); } /// - public sealed override ImmutableList GetDeclaredFields() + internal sealed override ImmutableArray GetDeclaredFields() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredProperties() { - return ImmutableList.Empty; + return ImmutableArray.Empty; } /// - public sealed override ImmutableList GetDeclaredProperties() + internal sealed override ImmutableArray GetDeclaredEvents() { - return ImmutableList.Empty; + return ImmutableArray.Empty; } /// - public sealed override ImmutableList GetDeclaredEvents() + internal override ImmutableArray GetDeclaredNestedTypes() { - return ImmutableList.Empty; + return ImmutableArray.Empty; } /// @@ -160,7 +175,7 @@ public sealed override bool IsEnumDefined(object value) } /// - public sealed override ImmutableList GetEnumNames() + public sealed override ImmutableArray GetEnumNames() { throw new NotSupportedException(); } diff --git a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs deleted file mode 100644 index 5e6f3ec7b2..0000000000 --- a/src/IKVM.CoreLib/Symbols/IAssemblySymbol.cs +++ /dev/null @@ -1,145 +0,0 @@ -using System.Collections.Generic; -using System.IO; - -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Represents an assembly, which is a reusable, versionable, and self-describing building block of a common language runtime application. - /// - interface IAssemblySymbol : ISymbol, ICustomAttributeProvider - { - - /// - /// Gets a collection of the types defined in this assembly. - /// - IEnumerable DefinedTypes { get; } - - /// - /// Gets a collection of the public types defined in this assembly that are visible outside the assembly. - /// - IEnumerable ExportedTypes { get; } - - /// - /// Gets the display name of the assembly. - /// - string? FullName { get; } - - /// - /// Gets a string representing the version of the common language runtime (CLR) saved in the file containing the manifest. - /// - string ImageRuntimeVersion { get; } - - /// - /// Gets the full path or UNC location of the loaded file that contains the manifest. - /// - string Location { get; } - - /// - /// Gets the module that contains the manifest for the current assembly. - /// - IModuleSymbol ManifestModule { get; } - - /// - /// Gets a collection that contains the modules in this assembly. - /// - IEnumerable Modules { get; } - - /// - /// Loads the specified manifest resource from this assembly. - /// - /// - /// - ManifestResourceInfo? GetManifestResourceInfo(string resourceName); - - /// - /// Loads the specified manifest resource from this assembly. - /// - /// - /// - Stream? GetManifestResourceStream(string name); - - /// - /// Loads the specified manifest resource, scoped by the namespace of the specified type, from this assembly. - /// - /// - /// - /// - Stream? GetManifestResourceStream(TypeSymbol type, string name); - - /// - /// Gets the specified module in this assembly. - /// - /// - /// - IModuleSymbol? GetModule(string name); - - /// - /// Gets all the modules that are part of this assembly. - /// - /// - IModuleSymbol[] GetModules(); - - /// - /// Gets all the modules that are part of this assembly, specifying whether to include resource modules. - /// - /// - /// - IModuleSymbol[] GetModules(bool getResourceModules); - - /// - /// Gets an for this assembly. - /// - /// - AssemblyIdentity GetIdentity(); - - /// - /// Gets the objects for all the assemblies referenced by this assembly. - /// - /// - AssemblyIdentity[] GetReferencedAssemblies(); - - /// - /// Gets the Type object with the specified name in the assembly instance. - /// - /// - /// - TypeSymbol? GetType(string name); - - /// - /// Gets the object with the specified name in the assembly instance and optionally throws an exception if the type is not found. - /// - /// - /// - /// - TypeSymbol? GetType(string name, bool throwOnError); - - /// - /// Gets the object with the specified name in the assembly instance, with the options of ignoring the case, and of throwing an exception if the type is not found. - /// - /// - /// - /// - /// - TypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase); - - /// - /// Gets all types defined in this assembly. - /// - /// - TypeSymbol[] GetTypes(); - - /// - /// Gets the public types defined in this assembly that are visible outside the assembly. - /// - /// - TypeSymbol[] GetExportedTypes(); - - /// - /// Gets the entry point of this assembly. - /// - MethodSymbol? EntryPoint { get; } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs index 16d99e27ae..5ce4a20080 100644 --- a/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs +++ b/src/IKVM.CoreLib/Symbols/ICustomAttributeProvider.cs @@ -1,10 +1,13 @@ -namespace IKVM.CoreLib.Symbols +using System.Collections.Generic; +using System.Collections.Immutable; + +namespace IKVM.CoreLib.Symbols { /// /// Provides custom attributes for reflection objects that support them. /// - interface ICustomAttributeProvider : ISymbol + interface ICustomAttributeProvider { /// @@ -12,7 +15,7 @@ interface ICustomAttributeProvider : ISymbol /// /// /// - CustomAttribute[] GetCustomAttributes(bool inherit = false); + IEnumerable GetCustomAttributes(bool inherit = false); /// /// Returns an array of custom attributes defined on this member, identified by type, or an empty array if there are no custom attributes of that type. @@ -20,7 +23,7 @@ interface ICustomAttributeProvider : ISymbol /// /// /// - CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false); + IEnumerable GetCustomAttributes(TypeSymbol attributeType, bool inherit = false); /// /// Retrieves a custom attribute of a specified type that is applied to a specified member. diff --git a/src/IKVM.CoreLib/Symbols/ICustomAttributeProviderInternal.cs b/src/IKVM.CoreLib/Symbols/ICustomAttributeProviderInternal.cs new file mode 100644 index 0000000000..f1bf5b2c42 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ICustomAttributeProviderInternal.cs @@ -0,0 +1,26 @@ +using System.Collections.Immutable; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Internal implementation support for . + /// + interface ICustomAttributeProviderInternal : ICustomAttributeProvider + { + + /// + /// Gets the custom attributes on this provider. + /// + /// + ImmutableArray GetDeclaredCustomAttributes(); + + /// + /// Gets the further provider that may declare inherited custom attributes. + /// + /// + ICustomAttributeProviderInternal? GetInheritedCustomAttributeProvider(); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs deleted file mode 100644 index 819cd33d4e..0000000000 --- a/src/IKVM.CoreLib/Symbols/IModuleSymbol.cs +++ /dev/null @@ -1,226 +0,0 @@ -using System; -using System.Reflection; - -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Performs reflection on a module. - /// - interface IModuleSymbol : ISymbol, ICustomAttributeProvider - { - - /// - /// Gets the appropriate for this instance of Module. - /// - IAssemblySymbol Assembly { get; } - - /// - /// Gets a string representing the fully qualified name and path to this module. - /// - string FullyQualifiedName { get; } - - /// - /// Gets a token that identifies the module in metadata. - /// - int MetadataToken { get; } - - /// - /// Gets a universally unique identifier (UUID) that can be used to distinguish between two versions of a module. - /// - Guid ModuleVersionId { get; } - - /// - /// Gets a representing the name of the module with the path removed. - /// - string Name { get; } - - /// - /// Gets a string representing the name of the module. - /// - string ScopeName { get; } - - /// - /// Gets a value indicating whether the object is a resource. - /// - /// - bool IsResource(); - - /// - /// Returns a field having the specified name. - /// - /// - /// - FieldSymbol? GetField(string name); - - /// - /// Returns a field having the specified name and binding attributes. - /// - /// - /// - /// - FieldSymbol? GetField(string name, BindingFlags bindingAttr); - - /// - /// Returns the global fields defined on the module that match the specified binding flags. - /// - /// - /// - FieldSymbol[] GetFields(BindingFlags bindingFlags); - - /// - /// Returns the global fields defined on the module. - /// - /// - FieldSymbol[] GetFields(); - - /// - /// Returns a method having the specified name. - /// - /// - /// - MethodSymbol? GetMethod(string name); - - /// - /// Returns a method having the specified name and parameter types. - /// - /// - /// - /// - MethodSymbol? GetMethod(string name, TypeSymbol[] types); - - /// - /// Returns a method having the specified name, binding information, calling convention, and parameter types and modifiers. - /// - /// - /// - /// - /// - /// - /// - MethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, TypeSymbol[] types, ParameterModifier[]? modifiers); - - /// - /// Returns the global methods defined on the module. - /// - /// - MethodSymbol[] GetMethods(); - - /// - /// Returns the global methods defined on the module that match the specified binding flags. - /// - /// - /// - MethodSymbol[] GetMethods(BindingFlags bindingFlags); - - /// - /// Returns the specified type, performing a case-sensitive search. - /// - /// - /// - TypeSymbol? GetType(string className); - - /// - /// Returns the specified type, searching the module with the specified case sensitivity. - /// - /// - /// - /// - TypeSymbol? GetType(string className, bool ignoreCase); - - /// - /// Returns the specified type, specifying whether to make a case-sensitive search of the module and whether to throw an exception if the type cannot be found. - /// - /// - /// - /// - /// - TypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase); - - /// - /// Returns all the types defined within this module. - /// - /// - TypeSymbol[] GetTypes(); - - /// - /// Returns the type identified by the specified metadata token. - /// - /// - /// - TypeSymbol ResolveType(int metadataToken); - - /// - /// Returns the type identified by the specified metadata token, in the context defined by the specified generic type parameters. - /// - /// - /// - /// - /// - TypeSymbol ResolveType(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); - - /// - /// Returns the field identified by a metadata token. - /// - /// - /// - FieldSymbol? ResolveField(int metadataToken); - - /// - /// Returns the field identified by the specified metadata token, in the context defined by the specified generic type parameters. - /// - /// - /// - /// - /// - FieldSymbol? ResolveField(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); - - /// - /// Returns the type or member identified by a metadata token. - /// - /// - /// - MemberSymbol? ResolveMember(int metadataToken); - - /// - /// Returns the type or member identified by the specified metadata token, in the context defined by the specified generic type parameters. - /// - /// - /// - /// - /// - MemberSymbol? ResolveMember(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); - - /// - /// Returns the method or constructor identified by the specified metadata token. - /// - /// - /// - MethodBaseSymbol? ResolveMethod(int metadataToken); - - /// - /// Returns the method or constructor identified by the specified metadata token, in the context defined by the specified generic type parameters. - /// - /// - /// - /// - /// - MethodBaseSymbol? ResolveMethod(int metadataToken, TypeSymbol[]? genericTypeArguments, TypeSymbol[]? genericMethodArguments); - - /// - /// Returns the signature blob identified by a metadata token. - /// - /// - /// - byte[] ResolveSignature(int metadataToken); - - /// - /// Returns the string identified by the specified metadata token. - /// - /// - /// - string ResolveString(int metadataToken); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/ISymbol.cs b/src/IKVM.CoreLib/Symbols/ISymbol.cs deleted file mode 100644 index 33f2a500d7..0000000000 --- a/src/IKVM.CoreLib/Symbols/ISymbol.cs +++ /dev/null @@ -1,27 +0,0 @@ -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Provides common properties and methods for managed symbols. - /// - interface ISymbol - { - - /// - /// Returns true if the symbol is missing. - /// - bool IsMissing { get; } - - /// - /// Returns true if the symbol contains a missing symbol. - /// - bool ContainsMissing { get; } - - /// - /// Returns true if the symbol is complete. That is, was created with a builder and completed. - /// - bool IsComplete { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs index 251d0496a8..531b624f1b 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolContext.cs @@ -15,24 +15,13 @@ interface ISymbolContext /// TypeSymbol ResolveCoreType(string typeName); - /// - /// Defines a dynamic assembly that has the specified name and access rights. - /// - /// - /// - /// - /// - IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, bool collectable = true, bool saveable = false); - /// /// Defines a dynamic assembly that has the specified name and access rights. /// /// /// - /// - /// /// - IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes, bool collectable = true, bool saveable = false); + AssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes); } diff --git a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs index 1505789560..29b48fd29a 100644 --- a/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs +++ b/src/IKVM.CoreLib/Symbols/ISymbolResolver.cs @@ -12,7 +12,7 @@ interface ISymbolResolver /// /// /// - IAssemblySymbol? ResolveAssembly(string assemblyName); + AssemblySymbol? ResolveAssembly(string assemblyName); /// /// Resolves the named type from the core assembly. diff --git a/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs b/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs index 1668a8a078..d7c53ce5de 100644 --- a/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs +++ b/src/IKVM.CoreLib/Symbols/InterfaceMapping.cs @@ -1,12 +1,14 @@ -namespace IKVM.CoreLib.Symbols +using System.Collections.Immutable; + +namespace IKVM.CoreLib.Symbols { - readonly struct InterfaceMapping(MethodSymbol[] InterfaceMethods, TypeSymbol InterfaceType, MethodSymbol[] TargetMethods, TypeSymbol TargetType) + readonly struct InterfaceMapping(ImmutableList InterfaceMethods, TypeSymbol InterfaceType, ImmutableList TargetMethods, TypeSymbol TargetType) { - public readonly MethodSymbol[] InterfaceMethods = InterfaceMethods; + public readonly ImmutableList InterfaceMethods = InterfaceMethods; public readonly TypeSymbol InterfaceType = InterfaceType; - public readonly MethodSymbol[] TargetMethods = TargetMethods; + public readonly ImmutableList TargetMethods = TargetMethods; public readonly TypeSymbol TargetType = TargetType; } diff --git a/src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs b/src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs index df44e1eea9..e88973308f 100644 --- a/src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs +++ b/src/IKVM.CoreLib/Symbols/ManifestResourceInfo.cs @@ -6,7 +6,7 @@ namespace IKVM.CoreLib.Symbols /// /// Provides access to manifest resources, which are XML files that describe application dependencies. /// - readonly struct ManifestResourceInfo(ResourceLocation ResourceLocation, string? FileName, IAssemblySymbol? ReferencedAssembly) + readonly struct ManifestResourceInfo(ResourceLocation ResourceLocation, string? FileName, AssemblySymbol? ReferencedAssembly) { /// @@ -22,7 +22,7 @@ readonly struct ManifestResourceInfo(ResourceLocation ResourceLocation, string? /// /// Gets the containing assembly for the manifest resource. /// - public readonly IAssemblySymbol? ReferencedAssembly = ReferencedAssembly; + public readonly AssemblySymbol? ReferencedAssembly = ReferencedAssembly; } diff --git a/src/IKVM.CoreLib/Symbols/MemberQuery.cs b/src/IKVM.CoreLib/Symbols/MemberQuery.cs new file mode 100644 index 0000000000..bc7a192aa2 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/MemberQuery.cs @@ -0,0 +1,201 @@ +using System; +using System.Collections; +using System.Collections.Generic; +using System.Reflection; +using System.Runtime.CompilerServices; + + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Stores the result of a member filtering that's filtered by name and visibility from base class (as defined by the Type.Get*() family of apis). + /// + /// The results are as if you'd passed in a bindingFlags value of "Public | NonPublic | Instance | Static | FlattenHierarchy" + /// + /// Results are sorted by declaring type. The members declared by the most derived type appear first, then those declared by its base class, and so on. + /// The Disambiguation logic takes advantage of this. + /// + /// This object is a good candidate for long term caching. + /// + /// MemberQuery's come in two flavors: ImmediateTypeOnly and full. The immediateTypeOnly only holds the results for one type, not any of its + /// base types. This is used when the binding flags passed to a Get() API limit the search to the immediate type only in order to avoid triggering + /// unnecessary assembly resolving and a lot of unnecessary ParameterInfo creation and comparison checks. + /// + struct MemberQuery : IEnumerable + where TParentSymbol : Symbol + where TMemberSymbol : MemberSymbol + { + + static readonly MemberSymbolPolicy _policy = MemberSymbolPolicy.Default; + + /// + /// Returns whether, for the specified , the query logic needs only to search the the immediate type. + /// + /// + /// + static bool NeedToSearchImmediateTypeOnly(BindingFlags bindingFlags) + { + if ((bindingFlags & (BindingFlags.Static | BindingFlags.FlattenHierarchy)) == (BindingFlags.Static | BindingFlags.FlattenHierarchy)) + return false; + + if ((bindingFlags & (BindingFlags.Instance | BindingFlags.DeclaredOnly)) == BindingFlags.Instance) + return false; + + return true; + } + + readonly TParentSymbol _parent; + readonly string? _name; + readonly BindingFlags _bindingFlags; + readonly bool _immediateParentOnly; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + internal MemberQuery(TParentSymbol parent, string? name, BindingFlags bindingFlags) + { + _parent = parent ?? throw new ArgumentNullException(nameof(parent)); + _name = name; + _bindingFlags = _policy.ModifyBindingFlags(bindingFlags); + _immediateParentOnly = NeedToSearchImmediateTypeOnly(_bindingFlags); + } + + /// + public readonly IEnumerator GetEnumerator() + { + return Query().GetEnumerator(); + } + + /// + /// Returns a single member, null or throws , for the TypeSymbol.Get*(string name,...) family of apis. + /// + /// + public readonly TMemberSymbol? Disambiguate() + { + TMemberSymbol? match = null; + + foreach (var challenger in Query()) + { + if (match != null) + { + // Assuming the policy says it's ok to ignore the ambiguity, we're to resolve in favor of the member + // declared by the most derived type. Since QueriedMemberLists are sorted in order of decreasing derivation, + // that means we let the first match win - unless, of course, they're both the "most derived member". + if (match.DeclaringType!.Equals(challenger.DeclaringType)) + throw new AmbiguousMatchException($"Ambiguous match found for '{match.DeclaringType} {match}'."); + + if (!_policy.OkToIgnoreAmbiguity(match, challenger)) + throw new AmbiguousMatchException($"Ambiguous match found for '{match.DeclaringType} {match}'."); + } + else + { + match = challenger; + } + } + + return match; + } + + /// + /// Check that are all set on . + /// + /// + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + readonly bool BindingFlagsMatch(BindingFlags mask) + { + return (_bindingFlags & mask) == mask; + } + + /// + readonly IEnumerable Query() + { + // query immediate + var priorMembers = new List(); + foreach (var i in QueryImmediate(priorMembers)) + yield return i; + + // query inheritable + if (_immediateParentOnly == false && _policy.AlwaysTreatAsDeclaredOnly == false) + for (var currentParent = _policy.GetInheritedParent(_parent); currentParent != null; currentParent = _policy.GetInheritedParent(currentParent)) + foreach (var i in QueryInherited(currentParent, priorMembers)) + yield return i; + } + + /// + /// Enumerates the results of the query against the immediate parent. + /// + /// + /// + readonly IEnumerable QueryImmediate(List priorMembers) + { + foreach (var member in _policy.GetDeclaredMembers(_parent)) + { + // skip unmatched name + if (_name != null && _name != member.Name) + continue; + + _policy.GetMemberAttributes(member, out MethodAttributes visibility, out bool isStatic, out _, out _); + + // member might exclude future members + priorMembers.Add(member); + + // check that query includes flags required by member + var matchFlags = default(BindingFlags); + matchFlags |= isStatic ? BindingFlags.Static : BindingFlags.Instance; + matchFlags |= visibility == MethodAttributes.Public ? BindingFlags.Public : BindingFlags.NonPublic; + if (BindingFlagsMatch(matchFlags) == false) + continue; + + yield return member; + } + } + + /// + /// Enumerates the results of the query against the inherited parent(s). + /// + /// + /// + /// + readonly IEnumerable QueryInherited(TParentSymbol parent, List priorMembers) + { + foreach (var member in _policy.GetDeclaredMembers(parent)) + { + // skip unmatched name + if (_name != null && _name != member.Name) + continue; + + _policy.GetMemberAttributes(member, out MethodAttributes visibility, out bool isStatic, out _, out _); + + // skip private members in inherited query + if (visibility == MethodAttributes.Private) + continue; + + // skip members that are excluded by prior members + if (priorMembers.Count != 0 && _policy.IsSuppressedByMoreDerivedMember(member, priorMembers)) + continue; + + // member might exclude future members + priorMembers.Add(member); + + // check that query includes flags required by member + var matchFlags = default(BindingFlags); + matchFlags |= isStatic ? BindingFlags.Static | BindingFlags.FlattenHierarchy : BindingFlags.Instance; + matchFlags |= visibility == MethodAttributes.Public ? BindingFlags.Public : BindingFlags.NonPublic; + if (BindingFlagsMatch(matchFlags) == false) + continue; + + yield return member; + } + } + + /// + readonly IEnumerator IEnumerable.GetEnumerator() => GetEnumerator(); + + } + +} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/MemberSymbol.cs b/src/IKVM.CoreLib/Symbols/MemberSymbol.cs index fd5dd1db01..33606a21b6 100644 --- a/src/IKVM.CoreLib/Symbols/MemberSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/MemberSymbol.cs @@ -1,39 +1,43 @@ using System; +using System.Collections; +using System.Collections.Generic; +using System.Collections.Immutable; using System.Reflection; +using System.Runtime.InteropServices.ComTypes; namespace IKVM.CoreLib.Symbols { - abstract class MemberSymbol : ICustomAttributeProvider + abstract class MemberSymbol : Symbol, ICustomAttributeProviderInternal { - readonly ISymbolContext _context; - readonly IModuleSymbol _module; + readonly ModuleSymbol _module; readonly TypeSymbol? _declaringType; + CustomAttributeImpl _customAttributes; + /// /// Initializes a new instance. /// /// /// - public MemberSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) + public MemberSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol? declaringType) : + base(context) { - _context = context ?? throw new ArgumentNullException(nameof(context)); _module = module ?? throw new ArgumentNullException(nameof(module)); _declaringType = declaringType; + _customAttributes = new CustomAttributeImpl(context, this); } - public ISymbolContext Context => _context; - /// - /// Gets the module in which the type that declares the member represented by the current is defined. + /// Gets the module in which the type that declares the member represented by the current is defined. /// - public IModuleSymbol Module => _module; + public ModuleSymbol Module => _module; /// - /// Gets the appropriate for this instance. + /// Gets the appropriate for this instance. /// - public IAssemblySymbol Assembly => _module.Assembly; + public AssemblySymbol Assembly => _module.Assembly; /// /// Gets the class that declares this member. @@ -66,16 +70,34 @@ public MemberSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? de public abstract bool IsComplete { get; } /// - public abstract CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false); + ImmutableArray ICustomAttributeProviderInternal.GetDeclaredCustomAttributes() => GetDeclaredCustomAttributes(); + + /// + internal abstract ImmutableArray GetDeclaredCustomAttributes(); + + /// + ICustomAttributeProviderInternal? ICustomAttributeProviderInternal.GetInheritedCustomAttributeProvider() => GetInheritedCustomAttributeProvider(); + + /// + /// Override to return a inherited custom attribute provider. + /// + /// + internal virtual ICustomAttributeProviderInternal? GetInheritedCustomAttributeProvider() => null; + + /// + public IEnumerable GetCustomAttributes(bool inherit = false) => _customAttributes.GetCustomAttributes(inherit); + + /// + public IEnumerable GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttributes(attributeType, inherit); /// - public abstract CustomAttribute[] GetCustomAttributes(bool inherit = false); + public CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttribute(attributeType, inherit); /// - public abstract CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false); + public bool IsDefined(TypeSymbol attributeType, bool inherit = false) => _customAttributes.IsDefined(attributeType, inherit); /// - public abstract bool IsDefined(TypeSymbol attributeType, bool inherit = false); + public override string ToString() => Name; } diff --git a/src/IKVM.CoreLib/Symbols/MemberSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/MemberSymbolPolicy.cs new file mode 100644 index 0000000000..452d287c20 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/MemberSymbolPolicy.cs @@ -0,0 +1,266 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class MemberSymbolPolicy + where TMemberSymbol : MemberSymbol + { + + /// + /// Gets the policy for the member symbol type. + /// + public static readonly MemberSymbolPolicy Default; + + /// + /// Computes the default policy for the given member symbol type. + /// + /// + static MemberSymbolPolicy() + { + var parent = typeof(TParentSymbol); + var member = typeof(TMemberSymbol); + + if (parent == typeof(ModuleSymbol)) + { + if (member.Equals(typeof(FieldSymbol))) + { + Default = (MemberSymbolPolicy)(object)new ModuleFieldSymbolPolicy(); + return; + } + else if (member.Equals(typeof(MethodSymbol))) + { + Default = (MemberSymbolPolicy)(object)new ModuleMethodSymbolPolicy(); + return; + } + else if (member.Equals(typeof(TypeSymbol))) + { + Default = (MemberSymbolPolicy)(object)new ModuleTypeSymbolPolicy(); + return; + } + else + { + throw new InvalidOperationException("Unknown member type."); + } + } + + if (parent == typeof(TypeSymbol)) + { + if (member.Equals(typeof(FieldSymbol))) + { + Default = (MemberSymbolPolicy)(object)new TypeFieldSymbolPolicy(); + return; + } + else if (member.Equals(typeof(ConstructorSymbol))) + { + Default = (MemberSymbolPolicy)(object)new TypeConstructorSymbolPolicy(); + return; + } + else if (member.Equals(typeof(MethodSymbol))) + { + Default = (MemberSymbolPolicy)(object)new TypeMethodSymbolPolicy(); + return; + } + else if (member.Equals(typeof(PropertySymbol))) + { + Default = (MemberSymbolPolicy)(object)new TypePropertySymbolPolicy(); + return; + } + else if (member.Equals(typeof(EventSymbol))) + { + Default = (MemberSymbolPolicy)(object)new TypeEventSymbolPolicy(); + return; + } + else if (member.Equals(typeof(TypeSymbol))) + { + Default = (MemberSymbolPolicy)(object)new TypeTypeSymbolPolicy(); + return; + } + else + { + throw new InvalidOperationException("Unknown member type."); + } + } + + throw new InvalidOperationException("Unknown parent type."); + } + + /// + /// Returns all of the directly declared members on the given . + /// + /// + /// + public abstract ImmutableArray GetDeclaredMembers(TParentSymbol parent); + + /// + /// Returns the base parent symbol that this parent is inherited from. Used for Type.BaseType. + /// + /// + /// + public abstract TParentSymbol? GetInheritedParent(TParentSymbol parent); + + /// + /// Policy to decide whether a member is considered "virtual", "virtual new" and what its member visibility is. + /// (For "visibility", we reuse the MethodAttributes enum since Reflection lacks an element-agnostic enum for this. + /// Only the MemberAccessMask bits are set.) + /// + public abstract void GetMemberAttributes(TMemberSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot); + + /// + /// Policy to decide whether "derivedMember" is a virtual override of "baseMember." Used to implement MethodInfo.GetBaseDefinition(), + /// parent chain traversal for discovering inherited custom attributes, and suppressing lookup results in the Type.Get*() api family. + /// + /// Does not consider explicit overrides (methodimpls.) Does not consider "overrides" of interface methods. + /// + public abstract bool ImplicitlyOverrides(TMemberSymbol? baseMember, TMemberSymbol? derivedMember); + + /// + /// Policy to decide how BindingFlags should be reinterpreted for a given member type. + /// This is overridden for nested types which all match on any combination Instance | Static and are never inherited. + /// It is also overridden for constructors which are never inherited. + /// + public virtual BindingFlags ModifyBindingFlags(BindingFlags bindingFlags) + { + return bindingFlags; + } + + /// + /// Policy to decide if BindingFlags is always interpreted as having set DeclaredOnly. + /// + public abstract bool AlwaysTreatAsDeclaredOnly { get; } + + /// + /// Policy to decide how or if members in more derived types hide same-named members in base types. + /// Due to .NET Framework compat concerns, the definitions are a bit more arbitrary than we'd like. + /// + public abstract bool IsSuppressedByMoreDerivedMember(TMemberSymbol member, List priorMembers); + + /// + /// Policy to decide whether to throw an AmbiguousMatchException on an ambiguous Type.Get*() call. + /// Does not apply to GetConstructor/GetMethod/GetProperty calls that have a non-null Type[] array passed to it. + /// + /// If method returns true, the Get() api will pick the member that's in the most derived type. + /// If method returns false, the Get() api throws AmbiguousMatchException. + /// + public abstract bool OkToIgnoreAmbiguity(TMemberSymbol m1, TMemberSymbol m2); + + /// + // Helper method for determining whether two methods are signature-compatible. + /// + /// + /// + /// + protected static bool AreNamesAndSignaturesEqual(MethodSymbol method1, MethodSymbol method2) + { + if (method1.Name != method2.Name) + return false; + + var p1 = method1.GetParameters(); + var p2 = method2.GetParameters(); + if (p1.Length != p2.Length) + return false; + + bool isGenericMethod1 = method1.IsGenericMethodDefinition; + bool isGenericMethod2 = method2.IsGenericMethodDefinition; + if (isGenericMethod1 != isGenericMethod2) + return false; + + if (!isGenericMethod1) + { + for (int i = 0; i < p1.Length; i++) + { + var parameterType1 = p1[i].ParameterType; + var parameterType2 = p2[i].ParameterType; + if (!(parameterType1.Equals(parameterType2))) + { + return false; + } + } + } + else + { + if (method1.GetGenericArguments().Length != method2.GetGenericArguments().Length) + return false; + + for (int i = 0; i < p1.Length; i++) + { + var parameterType1 = p1[i].ParameterType; + var parameterType2 = p2[i].ParameterType; + if (!GenericMethodAwareAreParameterTypesEqual(parameterType1, parameterType2)) + { + return false; + } + } + } + return true; + } + + /// + /// This helper compares the types of the corresponding parameters of two methods to see if one method is signature equivalent to the other. + /// This is needed when comparing the signatures of two generic methods as Type.Equals() is not up to that job. + /// + static bool GenericMethodAwareAreParameterTypesEqual(TypeSymbol t1, TypeSymbol t2) + { + // Fast-path - if Reflection has already deemed them equivalent, we can trust its result. + if (t1.Equals(t2)) + return true; + + // If we got here, Reflection determined the types not equivalent. Most of the time, that's the result we want. + // There is however, one wrinkle. If the type is or embeds a generic method parameter type, Reflection will always report them + // non-equivalent, since generic parameter type comparison always compares both the position and the declaring method. For our purposes, though, + // we only want to consider the position. + + // Fast-path: if the types don't embed any generic parameters, we can go ahead and use Reflection's result. + if (!(t1.ContainsGenericParameters && t2.ContainsGenericParameters)) + return false; + + if ((t1.IsArray && t2.IsArray) || (t1.IsByRef && t2.IsByRef) || (t1.IsPointer && t2.IsPointer)) + { + if (t1.IsSZArray != t2.IsSZArray) + return false; + + if (t1.IsArray && (t1.GetArrayRank() != t2.GetArrayRank())) + return false; + + return GenericMethodAwareAreParameterTypesEqual(t1.GetElementType()!, t2.GetElementType()!); + } + + if (t1.IsConstructedGenericType) + { + // We can use regular old Equals() rather than recursing into GenericMethodAwareAreParameterTypesEqual() since the + // generic type definition will always be a plain old named type and won't embed any generic method parameters. + if (!(t1.GetGenericTypeDefinition().Equals(t2.GetGenericTypeDefinition()))) + return false; + + var ga1 = t1.GenericTypeArguments; + var ga2 = t2.GenericTypeArguments; + if (ga1.Length != ga2.Length) + return false; + + for (int i = 0; i < ga1.Length; i++) + { + if (!GenericMethodAwareAreParameterTypesEqual(ga1[i], ga2[i])) + return false; + } + return true; + } + + if (t1.IsGenericMethodParameter && t2.IsGenericMethodParameter) + { + // A generic method parameter. The DeclaringMethods will be different but we don't care about that - we can assume that + // the declaring method will be the method that declared the parameter's whose type we're testing. We only need to + // compare the positions. + return t1.GenericParameterPosition == t2.GenericParameterPosition; + } + + // If we got here, either t1 and t2 are different flavors of types or they are both simple named types or both generic type parameters. + // Either way, we can trust Reflection's result here. + return false; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs index 31b74dbb29..412c743338 100644 --- a/src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs @@ -13,7 +13,7 @@ abstract class MethodBaseSymbol : MemberSymbol /// /// /// - public MethodBaseSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + public MethodBaseSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol? declaringType) : base(context, module, declaringType) { @@ -115,16 +115,16 @@ public MethodBaseSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol public abstract MethodImplAttributes MethodImplementationFlags { get; } /// - /// Returns an array of objects that represent the type arguments of a generic method or the type parameters of a generic method definition. + /// Returns an array of objects that represent the type arguments of a generic method or the type parameters of a generic method definition. /// /// - public abstract ImmutableList GetGenericArguments(); + public abstract ImmutableArray GetGenericArguments(); /// /// When overridden in a derived class, gets the parameters of the specified method or constructor. /// /// - public abstract ImmutableList GetParameters(); + public abstract ImmutableArray GetParameters(); /// /// When overridden in a derived class, returns the MethodImplAttributes flags. @@ -132,6 +132,9 @@ public MethodBaseSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol /// public abstract MethodImplAttributes GetMethodImplementationFlags(); + /// + public override string ToString() => base.ToString(); + } } diff --git a/src/IKVM.CoreLib/Symbols/MethodSpecTable.cs b/src/IKVM.CoreLib/Symbols/MethodSpecTable.cs index 691d12a179..1cba073caa 100644 --- a/src/IKVM.CoreLib/Symbols/MethodSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/MethodSpecTable.cs @@ -9,13 +9,13 @@ namespace IKVM.CoreLib.Symbols struct MethodSpecTable { - readonly ISymbolContext _context; - readonly IModuleSymbol _module; + readonly SymbolContext _context; + readonly ModuleSymbol _module; readonly TypeSymbol? _type; readonly MethodSymbol _method; - readonly ImmutableList _typeArguments; + readonly ImmutableArray _typeArguments; - ConcurrentDictionary, ConstructedGenericMethodSymbol>? _cache; + ConcurrentDictionary, ConstructedGenericMethodSymbol>? _cache; /// /// Initializes a new instance. @@ -26,13 +26,13 @@ struct MethodSpecTable /// /// /// - public MethodSpecTable(ISymbolContext context, IModuleSymbol module, TypeSymbol? type, MethodSymbol method, ImmutableList typeArguments) + public MethodSpecTable(SymbolContext context, ModuleSymbol module, TypeSymbol? type, MethodSymbol method, ImmutableArray typeArguments) { _context = context ?? throw new ArgumentNullException(nameof(context)); _module = module ?? throw new ArgumentNullException(nameof(module)); _type = type; _method = method ?? throw new ArgumentNullException(nameof(method)); - _typeArguments = typeArguments ?? throw new ArgumentNullException(nameof(typeArguments)); + _typeArguments = typeArguments; } /// @@ -40,9 +40,9 @@ public MethodSpecTable(ISymbolContext context, IModuleSymbol module, TypeSymbol? /// /// /// - public MethodSymbol GetOrCreateGenericMethodSymbol(ImmutableList typeArguments) + public MethodSymbol GetOrCreateGenericMethodSymbol(ImmutableArray typeArguments) { - if (typeArguments is null) + if (typeArguments == default) throw new ArgumentNullException(nameof(typeArguments)); if (_method.IsGenericMethodDefinition == false) @@ -59,7 +59,7 @@ public MethodSymbol GetOrCreateGenericMethodSymbol(ImmutableList typ /// /// /// - readonly ConstructedGenericMethodSymbol CreateGenericMethodSymbol(ImmutableList typeArguments) + readonly ConstructedGenericMethodSymbol CreateGenericMethodSymbol(ImmutableArray typeArguments) { return new ConstructedGenericMethodSymbol(_context, _module, _type, _method, new GenericContext(_typeArguments, typeArguments)); } diff --git a/src/IKVM.CoreLib/Symbols/MethodSymbol.cs b/src/IKVM.CoreLib/Symbols/MethodSymbol.cs index 92c532b4f4..0cc8b6c2f1 100644 --- a/src/IKVM.CoreLib/Symbols/MethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/MethodSymbol.cs @@ -15,32 +15,48 @@ abstract class MethodSymbol : MethodBaseSymbol /// /// /// - protected MethodSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : + protected MethodSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol? declaringType) : base(context, module, declaringType) { - _specTable = new MethodSpecTable(context, module, declaringType, this); + _specTable = new MethodSpecTable(context, module, declaringType, this, []); } /// public override MemberTypes MemberType => MemberTypes.Method; - /// + /// + /// Gets a object that contains information about the return type of the method, such as whether the return type has custom modifiers. + /// public abstract ParameterSymbol ReturnParameter { get; } - /// + /// + /// Gets the return type of this method. + /// public abstract TypeSymbol ReturnType { get; } - /// + /// + /// Gets the custom attributes for the return type. + /// public abstract ICustomAttributeProvider ReturnTypeCustomAttributes { get; } - /// + /// + /// When overridden in a derived class, returns the object for the method on the direct or indirect base class in which the method represented by this instance was first declared. + /// + /// public abstract MethodSymbol GetBaseDefinition(); - /// + /// + /// Returns a object that represents a generic method definition from which the current method can be constructed. + /// + /// public abstract MethodSymbol GetGenericMethodDefinition(); - /// - public MethodSymbol MakeGenericMethod(IImmutableList typeArguments) => _specTable.GetOrCreateGenericMethodSymbol(typeArguments); + /// + /// Substitutes the elements of an array of types for the type parameters of the current generic method definition, and returns a MethodInfo object representing the resulting constructed method. + /// + /// + /// + public MethodSymbol MakeGenericMethod(ImmutableArray typeArguments) => _specTable.GetOrCreateGenericMethodSymbol(typeArguments); } diff --git a/src/IKVM.CoreLib/Symbols/ModuleFieldSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/ModuleFieldSymbolPolicy.cs new file mode 100644 index 0000000000..065a74de98 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ModuleFieldSymbolPolicy.cs @@ -0,0 +1,44 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for field symbols. + /// + class ModuleFieldSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(ModuleSymbol module) => module.GetDeclaredFields(); + + /// + public override ModuleSymbol? GetInheritedParent(ModuleSymbol parent) => null; + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => false; + + /// + public sealed override void GetMemberAttributes(FieldSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + var fieldAttributes = member.Attributes; + visibility = (MethodAttributes)(fieldAttributes & FieldAttributes.FieldAccessMask); + isStatic = (0 != (fieldAttributes & FieldAttributes.Static)); + isVirtual = false; + isNewSlot = false; + } + + /// + public sealed override bool ImplicitlyOverrides(FieldSymbol? baseMember, FieldSymbol? derivedMember) => false; + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(FieldSymbol member, List priorMembers) => false; + + /// + public sealed override bool OkToIgnoreAmbiguity(FieldSymbol m1, FieldSymbol m2) => true; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ModuleMethodSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/ModuleMethodSymbolPolicy.cs new file mode 100644 index 0000000000..f7a0fdd6bd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ModuleMethodSymbolPolicy.cs @@ -0,0 +1,68 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for constructor symbols. + /// + class ModuleMethodSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(ModuleSymbol module) => module.GetDeclaredMethods(); + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => false; + + /// + public sealed override void GetMemberAttributes(MethodSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + var methodAttributes = member.Attributes; + visibility = methodAttributes & MethodAttributes.MemberAccessMask; + isStatic = (0 != (methodAttributes & MethodAttributes.Static)); + isVirtual = (0 != (methodAttributes & MethodAttributes.Virtual)); + isNewSlot = (0 != (methodAttributes & MethodAttributes.NewSlot)); + } + + /// + public override ModuleSymbol? GetInheritedParent(ModuleSymbol parent) + { + return null; + } + + /// + public sealed override bool ImplicitlyOverrides(MethodSymbol? baseMember, MethodSymbol? derivedMember) + { + return AreNamesAndSignaturesEqual(baseMember!, derivedMember!); + } + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(MethodSymbol member, List priorMembers) + { + if (!member.IsVirtual) + return false; + + foreach (var prior in priorMembers) + { + var attributes = prior.Attributes & (MethodAttributes.Virtual | MethodAttributes.VtableLayoutMask); + if (attributes != (MethodAttributes.Virtual | MethodAttributes.ReuseSlot)) + continue; + if (!ImplicitlyOverrides(member, prior)) + continue; + + return true; + } + return false; + } + + public sealed override bool OkToIgnoreAmbiguity(MethodSymbol m1, MethodSymbol m2) + { + return DefaultBinder.CompareMethodSig(m1, m2); // If all candidates have the same signature, pick the most derived one without throwing an AmbiguousMatchException. + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/ModuleSymbol.cs new file mode 100644 index 0000000000..0199e854ff --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ModuleSymbol.cs @@ -0,0 +1,242 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Performs reflection on a module. + /// + abstract class ModuleSymbol : Symbol, ICustomAttributeProviderInternal + { + + readonly SymbolContext _context; + readonly AssemblySymbol _assembly; + + ImmutableList? _types; + CustomAttributeImpl _customAttributes; + + /// + /// Initializes a new instance. + /// + /// + /// + protected ModuleSymbol(SymbolContext context, AssemblySymbol assembly) : + base(context) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); + _customAttributes = new CustomAttributeImpl(context, this); + } + + /// + /// Gets the appropriate for this instance of Module. + /// + public AssemblySymbol Assembly => _assembly; + + /// + /// Gets a string representing the fully qualified name and path to this module. + /// + public abstract string FullyQualifiedName { get; } + + /// + /// Gets a representing the name of the module with the path removed. + /// + public abstract string Name { get; } + + /// + /// Returns true if the symbol is missing. + /// + public abstract bool IsMissing { get; } + + /// + /// Returns true if the symbol contains a missing symbol. + /// + public abstract bool ContainsMissing { get; } + + /// + /// Returns true if the symbol is complete. That is, was created with a builder and completed. + /// + public abstract bool IsComplete { get; } + + /// + /// Gets a value indicating whether the object is a resource. + /// + /// + public abstract bool IsResource(); + + /// + /// Returns the fields declared on the module. + /// + /// + internal abstract ImmutableArray GetDeclaredFields(); + + /// + /// Returns a field having the specified name. + /// + /// + /// + public FieldSymbol? GetField(string name) + { + throw new NotImplementedException(); + } + + /// + /// Returns a field having the specified name and binding attributes. + /// + /// + /// + /// + public FieldSymbol? GetField(string name, BindingFlags bindingAttr) + { + throw new NotImplementedException(); + } + + /// + /// Returns the global fields defined on the module. + /// + /// + public IEnumerable GetFields() => GetFields(DefaultLookup); + + /// + /// Returns the global fields defined on the module that match the specified binding flags. + /// + /// + /// + public IEnumerable GetFields(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } + + /// + /// Returns the methods declared on the module. + /// + /// + internal abstract ImmutableArray GetDeclaredMethods(); + + /// + /// Returns a method having the specified name. + /// + /// + /// + public MethodSymbol? GetMethod(string name) + { + throw new NotImplementedException(); + } + + /// + /// Returns a method having the specified name and parameter types. + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, ImmutableArray types) + { + throw new NotImplementedException(); + } + + /// + /// Returns a method having the specified name, binding information, calling convention, and parameter types and modifiers. + /// + /// + /// + /// + /// + /// + /// + public MethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ImmutableArray? types, ImmutableArray? modifiers) + { + throw new NotImplementedException(); + } + + /// + /// Returns the global methods defined on the module. + /// + /// + public IEnumerable GetMethods() => GetMethods(DefaultLookup); + + /// + /// Returns the global methods defined on the module that match the specified binding flags. + /// + /// + /// + public IEnumerable GetMethods(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } + + /// + /// Returns the types declared on the module. + /// + /// + internal abstract ImmutableArray GetDeclaredTypes(); + + /// + /// Returns the specified type, performing a case-sensitive search. + /// + /// + /// + public TypeSymbol? GetType(string className) + { + return GetType(className, true); + } + + /// + /// Returns the specified type, specifying whether to make a case-sensitive search of the module and whether to throw an exception if the type cannot be found. + /// + /// + /// + /// + public TypeSymbol? GetType(string className, bool throwOnError) + { + foreach (var type in GetDeclaredTypes()) + if (type.IsNested == false && type.FullName == className) + return type; + + if (throwOnError) + throw new TypeLoadException(); + + return null; + } + + /// + /// Returns all the types defined within this module. + /// + /// + public ImmutableArray GetTypes() + { + var b = GetDeclaredTypes(); + + foreach (var type in b) + if (type.IsNested) + b = b.Remove(type); + + return b; + } + + /// + internal abstract ImmutableArray GetDeclaredCustomAttributes(); + + /// + ImmutableArray ICustomAttributeProviderInternal.GetDeclaredCustomAttributes() => GetDeclaredCustomAttributes(); + + /// + ICustomAttributeProviderInternal? ICustomAttributeProviderInternal.GetInheritedCustomAttributeProvider() => null; + + /// + public IEnumerable GetCustomAttributes(bool inherit = false) => _customAttributes.GetCustomAttributes(inherit); + + /// + public IEnumerable GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttributes(attributeType, inherit); + + /// + public CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttribute(attributeType, inherit); + + /// + public bool IsDefined(TypeSymbol attributeType, bool inherit = false) => _customAttributes.IsDefined(attributeType, inherit); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ModuleTypeSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/ModuleTypeSymbolPolicy.cs new file mode 100644 index 0000000000..ab31e9c0f1 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/ModuleTypeSymbolPolicy.cs @@ -0,0 +1,57 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for type symbols. + /// + class ModuleTypeSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(ModuleSymbol module) => module.GetDeclaredTypes(); + + /// + public sealed override ModuleSymbol? GetInheritedParent(ModuleSymbol parent) => null; + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => true; + + /// + public sealed override void GetMemberAttributes(TypeSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + isStatic = true; + isVirtual = false; + isNewSlot = false; + + // Since we never search base types for nested types, we don't need to map every visibility value one to one. + // We just need to distinguish between "public" and "everything else." + visibility = member.IsNestedPublic ? MethodAttributes.Public : MethodAttributes.Private; + } + + /// + public sealed override bool ImplicitlyOverrides(TypeSymbol? baseMember, TypeSymbol? derivedMember) => false; + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(TypeSymbol member, List priorMembers) => false; + + /// + public sealed override BindingFlags ModifyBindingFlags(BindingFlags bindingFlags) + { + bindingFlags &= BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.IgnoreCase; + bindingFlags |= BindingFlags.Static | BindingFlags.DeclaredOnly; + return bindingFlags; + } + + /// + public sealed override bool OkToIgnoreAmbiguity(TypeSymbol m1, TypeSymbol m2) + { + return false; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/ParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/ParameterSymbol.cs index 8456595dfb..1a5f208e6b 100644 --- a/src/IKVM.CoreLib/Symbols/ParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ParameterSymbol.cs @@ -1,29 +1,36 @@ using System; +using System.Collections.Generic; using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols { - abstract class ParameterSymbol : ICustomAttributeProvider + abstract class ParameterSymbol : ICustomAttributeProviderInternal { - readonly ISymbolContext _context; - readonly MemberSymbol _member; + readonly SymbolContext _context; + readonly MemberSymbol _declaringMember; readonly int _position; + CustomAttributeImpl _customAttributes; + /// /// Initializes a new instance. /// /// - public ParameterSymbol(ISymbolContext context, MemberSymbol member, int position) + public ParameterSymbol(SymbolContext context, MemberSymbol declaringMember, int position) { _context = context ?? throw new ArgumentNullException(nameof(context)); - _member = member ?? throw new ArgumentNullException(nameof(member)); + _declaringMember = declaringMember ?? throw new ArgumentNullException(nameof(declaringMember)); _position = position; + _customAttributes = new CustomAttributeImpl(context, this); } - public ISymbolContext Context => _context; + /// + /// Gets the context which owns this parameter. + /// + public SymbolContext Context => _context; /// /// Gets the attributes for this parameter. @@ -33,7 +40,7 @@ public ParameterSymbol(ISymbolContext context, MemberSymbol member, int position /// /// Gets a value indicating the member in which the parameter is implemented. /// - public MemberSymbol Member => _member; + public MemberSymbol Member => _declaringMember; /// /// Gets the Type of this parameter. @@ -101,22 +108,37 @@ public ParameterSymbol(ISymbolContext context, MemberSymbol member, int position public abstract bool IsComplete { get; } /// - public abstract ImmutableList GetOptionalCustomModifiers(); + public abstract ImmutableArray GetOptionalCustomModifiers(); + + /// + public abstract ImmutableArray GetRequiredCustomModifiers(); + + /// + ImmutableArray ICustomAttributeProviderInternal.GetDeclaredCustomAttributes() => GetDeclaredCustomAttributes(); + + /// + internal abstract ImmutableArray GetDeclaredCustomAttributes(); /// - public abstract ImmutableList GetRequiredCustomModifiers(); + ICustomAttributeProviderInternal? ICustomAttributeProviderInternal.GetInheritedCustomAttributeProvider() => GetInheritedCustomAttributeProvider(); + + /// + /// Override to return a inherited custom attribute provider. + /// + /// + protected virtual ICustomAttributeProviderInternal? GetInheritedCustomAttributeProvider() => null; /// - public abstract CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false); + public IEnumerable GetCustomAttributes(bool inherit = false) => _customAttributes.GetCustomAttributes(inherit); /// - public abstract CustomAttribute[] GetCustomAttributes(bool inherit = false); + public IEnumerable GetCustomAttributes(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttributes(attributeType, inherit); /// - public abstract CustomAttribute[] GetCustomAttributes(TypeSymbol attributeType, bool inherit = false); + public CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit = false) => _customAttributes.GetCustomAttribute(attributeType, inherit); /// - public abstract bool IsDefined(TypeSymbol attributeType, bool inherit = false); + public bool IsDefined(TypeSymbol attributeType, bool inherit = false) => _customAttributes.IsDefined(attributeType, inherit); } diff --git a/src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs index eaa223bcb5..dd04d056aa 100644 --- a/src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs @@ -13,7 +13,7 @@ class PointerTypeSymbol : HasElementSymbol /// /// /// - public PointerTypeSymbol(ISymbolContext context, TypeSymbol elementType) : + public PointerTypeSymbol(SymbolContext context, TypeSymbol elementType) : base(context, elementType) { @@ -38,15 +38,33 @@ public sealed override int GetArrayRank() } /// - public sealed override ImmutableList GetDeclaredConstructors() + public override ImmutableArray GetInterfaces() { - return ImmutableList.Empty; + return ImmutableArray.Empty; } /// - public sealed override ImmutableList GetDeclaredMethods() + public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) { - return ImmutableList.Empty; + return new InterfaceMapping(ImmutableList.Empty, interfaceType, ImmutableList.Empty, this); + } + + /// + internal sealed override ImmutableArray GetDeclaredConstructors() + { + return ImmutableArray.Empty; + } + + /// + internal sealed override ImmutableArray GetDeclaredMethods() + { + return ImmutableArray.Empty; + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/PropertySymbol.cs b/src/IKVM.CoreLib/Symbols/PropertySymbol.cs index bad5bb9690..2ff817e29d 100644 --- a/src/IKVM.CoreLib/Symbols/PropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/PropertySymbol.cs @@ -1,4 +1,5 @@ -using System.Reflection; +using System.Collections.Immutable; +using System.Reflection; namespace IKVM.CoreLib.Symbols { @@ -11,7 +12,7 @@ abstract class PropertySymbol : MemberSymbol /// /// /// - public PropertySymbol(ISymbolContext context, TypeSymbol declaringType) : + public PropertySymbol(SymbolContext context, TypeSymbol declaringType) : base(context, declaringType.Module, declaringType) { @@ -22,6 +23,9 @@ public PropertySymbol(ISymbolContext context, TypeSymbol declaringType) : /// public abstract PropertyAttributes Attributes { get; } + /// + public sealed override MemberTypes MemberType => MemberTypes.Property; + /// /// Gets the type of this property. /// @@ -45,31 +49,31 @@ public PropertySymbol(ISymbolContext context, TypeSymbol declaringType) : /// /// Gets the get accessor for this property. /// - public abstract MethodSymbol? GetMethod { get; } + public MethodSymbol? GetMethod => GetGetMethod(true); /// /// Gets the set accessor for this property. /// - public abstract MethodSymbol? SetMethod { get; } + public MethodSymbol? SetMethod => GetSetMethod(true); /// /// Returns an array whose elements reflect the public get and set accessors of the property reflected by the current instance. /// /// - public abstract MethodSymbol[] GetAccessors(); + public ImmutableArray GetAccessors() => GetAccessors(false); /// /// Returns an array whose elements reflect the public and, if specified, non-public get and set accessors of the property reflected by the current instance. /// /// /// - public abstract MethodSymbol[] GetAccessors(bool nonPublic); + public abstract ImmutableArray GetAccessors(bool nonPublic); /// /// Returns the public get accessor for this property. /// /// - public abstract MethodSymbol? GetGetMethod(); + public MethodSymbol? GetGetMethod() => GetGetMethod(false); /// /// When overridden in a derived class, returns the public or non-public get accessor for this property. @@ -82,7 +86,7 @@ public PropertySymbol(ISymbolContext context, TypeSymbol declaringType) : /// Returns the public set accessor for this property. /// /// - public abstract MethodSymbol? GetSetMethod(); + public MethodSymbol? GetSetMethod() => GetSetMethod(false); /// /// When overridden in a derived class, returns the set accessor for this property. @@ -95,7 +99,7 @@ public PropertySymbol(ISymbolContext context, TypeSymbol declaringType) : /// When overridden in a derived class, returns an array of all the index parameters for the property. /// /// - public abstract ParameterSymbol[] GetIndexParameters(); + public abstract ImmutableArray GetIndexParameters(); /// /// Gets the modified type of this property object. @@ -113,13 +117,13 @@ public PropertySymbol(ISymbolContext context, TypeSymbol declaringType) : /// Returns an array of types representing the optional custom modifiers of the property. /// /// - public abstract TypeSymbol[] GetOptionalCustomModifiers(); + public abstract ImmutableArray GetOptionalCustomModifiers(); /// /// Returns an array of types representing the required custom modifiers of the property. /// /// - public abstract TypeSymbol[] GetRequiredCustomModifiers(); + public abstract ImmutableArray GetRequiredCustomModifiers(); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs deleted file mode 100644 index af8639e043..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionAssemblySymbolBuilder.cs +++ /dev/null @@ -1,25 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionAssemblySymbolBuilder : IReflectionSymbolBuilder, IAssemblySymbolBuilder, IReflectionAssemblySymbol - { - - /// - /// Gets the underlying . - /// - AssemblyBuilder UnderlyingAssemblyBuilder { get; } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs deleted file mode 100644 index d9a2a02655..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionConstructorSymbolBuilder.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionConstructorSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IConstructorSymbolBuilder, IReflectionConstructorSymbol - { - - /// - /// Gets the underlying . - /// - ConstructorBuilder UnderlyingConstructorBuilder { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs deleted file mode 100644 index 8f78217a97..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionCustomAttributeProviderBuilder.cs +++ /dev/null @@ -1,13 +0,0 @@ -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionCustomAttributeProviderBuilder : ICustomAttributeProviderBuilder - { - - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs deleted file mode 100644 index d90955a8cf..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionEventSymbolBuilder.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionEventSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IEventSymbolBuilder, IReflectionEventSymbol - { - - /// - /// Gets the underlying . - /// - EventBuilder UnderlyingEventBuilder { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs deleted file mode 100644 index 6463e87167..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionFieldSymbolBuilder.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionFieldSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IFieldSymbolBuilder, IReflectionFieldSymbol - { - - FieldBuilder UnderlyingFieldBuilder { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs deleted file mode 100644 index 8e5789c04b..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionGenericTypeParameterSymbolBuilder.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionGenericTypeParameterSymbolBuilder : IReflectionSymbolBuilder, IGenericTypeParameterSymbolBuilder, IReflectionTypeSymbol - { - - /// - /// Gets the underlying . - /// - GenericTypeParameterBuilder UnderlyingGenericTypeParameterBuilder { get; } - - /// - /// Invoked when the type containing this generic type parameter is completed. Passed the completed type. - /// - void OnComplete(Type type); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs deleted file mode 100644 index f324730eb0..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMemberSymbolBuilder.cs +++ /dev/null @@ -1,22 +0,0 @@ -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionMemberSymbolBuilder : IReflectionSymbolBuilder, IMemberSymbolBuilder, IReflectionMemberSymbol - { - - /// - /// Gets the resolving . - /// - public IReflectionModuleSymbolBuilder ResolvingModuleBuilder { get; } - - /// - /// Invoked when the type responsible for this builder is completed. Implementations should update their - /// underlying type, and optionally dispatch the OnComplete invocation to downstream elements. - /// - void OnComplete(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs deleted file mode 100644 index cf15d47d49..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodBaseSymbolBuilder.cs +++ /dev/null @@ -1,13 +0,0 @@ -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionMethodBaseSymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IMethodBaseSymbolBuilder, IReflectionMethodBaseSymbol - { - - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs deleted file mode 100644 index 87d35faebb..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionMethodSymbolBuilder.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionMethodSymbolBuilder : IReflectionSymbolBuilder, IReflectionMethodBaseSymbolBuilder, IMethodSymbolBuilder, IReflectionMethodSymbol - { - - /// - /// Gets the underlying . - /// - MethodBuilder UnderlyingMethodBuilder { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs deleted file mode 100644 index 8affb7ef25..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionModuleSymbolBuilder.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionModuleSymbolBuilder : IReflectionSymbolBuilder, IModuleSymbolBuilder, IReflectionModuleSymbol - { - - /// - /// Gets the underlying . - /// - ModuleBuilder UnderlyingModuleBuilder { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs deleted file mode 100644 index 212f8a24fc..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionParameterSymbolBuilder.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionParameterSymbolBuilder : IReflectionSymbolBuilder, IParameterSymbolBuilder, IReflectionParameterSymbol - { - - /// - /// Gets the underlying . - /// - ParameterBuilder UnderlyingParameterBuilder { get; } - - /// - /// Invoked when the owning method of this parameter is completed. - /// - void OnComplete(ParameterInfo parameter); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs deleted file mode 100644 index 6028d6de6f..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionPropertySymbolBuilder.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionPropertySymbolBuilder : IReflectionSymbolBuilder, IReflectionMemberSymbolBuilder, IPropertySymbolBuilder, IReflectionPropertySymbol - { - - /// - /// Gets the underlying . - /// - PropertyBuilder UnderlyingPropertyBuilder { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs deleted file mode 100644 index 1f88cf8c8e..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionSymbolBuilder.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System.Diagnostics.CodeAnalysis; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionSymbolBuilder : ISymbolBuilder - { - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs deleted file mode 100644 index 835835b8ec..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/IReflectionTypeSymbolBuilder.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection.Emit -{ - - interface IReflectionTypeSymbolBuilder : IReflectionMemberSymbolBuilder, ITypeSymbolBuilder, IReflectionTypeSymbol - { - - /// - /// Gets the underlying . - /// - TypeBuilder UnderlyingTypeBuilder { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs index a483bceb0c..4a93a61794 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs @@ -19,7 +19,7 @@ class ReflectionGenericTypeParameterSymbolBuilder : ReflectionGenericTypeParamet /// /// public ReflectionGenericTypeParameterSymbolBuilder(ReflectionSymbolContext context, IReflectionModuleSymbolBuilder resolvingModule, IReflectionMemberSymbolBuilder resolvingMember) : - base(context, resolvingModule, resolvingMember,) + base(context, resolvingModule, resolvingMember) { _builder = builder ?? throw new ArgumentNullException(nameof(builder)); } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs deleted file mode 100644 index 73a6c9c3cd..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionAssemblySymbol.cs +++ /dev/null @@ -1,28 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionAssemblySymbol : IReflectionSymbol, IAssemblySymbol - { - - /// - /// Gets a reference to the underlying . - /// - Assembly UnderlyingAssembly { get; } - - /// - /// Gets a reference to the underlying . - /// - Assembly UnderlyingRuntimeAssembly { get; } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs deleted file mode 100644 index f477b99df7..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionConstructorSymbol.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionConstructorSymbol : IReflectionMethodBaseSymbol, IConstructorSymbol - { - - /// - /// Gets the underlying . - /// - ConstructorInfo UnderlyingConstructor { get; } - - /// - /// Gets the underlying used for IL emit operations. - /// - ConstructorInfo UnderlyingRuntimeConstructor { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs deleted file mode 100644 index 2f0374c380..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionEventSymbol.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionEventSymbol : IReflectionMemberSymbol, IEventSymbol - { - - /// - /// Gets the underlying . - /// - EventInfo UnderlyingEvent { get; } - - /// - /// Gets the underlying . - /// - EventInfo UnderlyingRuntimeEvent { get; } - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs deleted file mode 100644 index e21b606ba1..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionFieldSymbol.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionFieldSymbol : IReflectionMemberSymbol, IFieldSymbol - { - - /// - /// Gets the underlying . - /// - FieldInfo UnderlyingField { get; } - - /// - /// Gets the underlying . - /// - FieldInfo UnderlyingRuntimeField { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs deleted file mode 100644 index b309b0ee07..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMemberSymbol.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionMemberSymbol : IReflectionSymbol, IMemberSymbol - { - - /// - /// Gets the resolving module. - /// - IReflectionModuleSymbol ResolvingModule { get; } - - /// - /// Gets the resolving type. - /// - IReflectionTypeSymbol? ResolvingType { get; } - - /// - /// Gets the underlying . - /// - MemberInfo UnderlyingMember { get; } - - /// - /// Gets the underlying used when the runtime information is required. - /// - MemberInfo UnderlyingRuntimeMember { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs deleted file mode 100644 index f3e89783f7..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodBaseSymbol.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionMethodBaseSymbol : IReflectionMemberSymbol, IMethodBaseSymbol - { - - /// - /// Gets the underlying . - /// - MethodBase UnderlyingMethodBase { get; } - - /// - /// Gets the underlying . - /// - MethodBase UnderlyingRuntimeMethodBase { get; } - - /// - /// Gets or creates a for the given . - /// - /// - /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); - - /// - /// Gets or creates a for the given . - /// - /// - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs deleted file mode 100644 index 21dfd7dcfe..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionMethodSymbol.cs +++ /dev/null @@ -1,46 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionMethodSymbol : IReflectionMethodBaseSymbol, IMethodSymbol - { - - /// - /// Gets the underlying . - /// - MethodInfo UnderlyingMethod { get; } - - /// - /// Gets the underlying . - /// - MethodInfo UnderlyingRuntimeMethod { get; } - - /// - /// Gets or creates a for the given generic type parameter. - /// - /// - /// - IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); - - /// - /// Gets or creates a for the given generic version of this method definition. - /// - /// - /// - IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs deleted file mode 100644 index 7d679be5cf..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionModuleSymbol.cs +++ /dev/null @@ -1,145 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionModuleSymbol : IReflectionSymbol, IModuleSymbol - { - - /// - /// Gets the which contains this . - /// - IReflectionAssemblySymbol ResolvingAssembly { get; } - - /// - /// Gets the underlying . - /// - Module UnderlyingModule { get; } - - /// - /// Gets the underlying . - /// - Module UnderlyingRuntimeModule { get; } - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - /// - /// - IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? optionalCustomModifiers, ITypeSymbol[]? requiredCustomModifiers); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - /// - IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter); - - /// - /// Gets or creates a for the specified . - /// - /// - /// - IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs deleted file mode 100644 index 3c02883549..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionParameterSymbol.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionParameterSymbol : IReflectionSymbol, IParameterSymbol - { - - /// - /// Gets the module that resolved the parameter. - /// - IReflectionModuleSymbol ResolvingModule { get; } - - /// - /// Gets the member that resolved the parameter. - /// - IReflectionMemberSymbol ResolvingMember { get; } - - /// - /// Gets the underlying . - /// - ParameterInfo UnderlyingParameter { get; } - - /// - /// Gets the underlying . - /// - ParameterInfo UnderlyingRuntimeParameter { get; } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs deleted file mode 100644 index 12da5d1a98..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionPropertySymbol.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionPropertySymbol : IReflectionMemberSymbol, IPropertySymbol - { - - /// - /// Gets the underlying . - /// - PropertyInfo UnderlyingProperty { get; } - - /// - /// Gets the underlying . - /// - PropertyInfo UnderlyingRuntimeProperty { get; } - - /// - /// Gets or creates a for the given . - /// - /// - /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter); - - /// - /// Gets or creates a for the given . - /// - /// - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs deleted file mode 100644 index 490fe4da80..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionSymbol.cs +++ /dev/null @@ -1,352 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Collections.Immutable; -using System.Diagnostics.CodeAnalysis; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionSymbol : ISymbol - { - - /// - /// Gets the that contains this symbol. - /// - ReflectionSymbolContext Context { get; } - - /// - /// Resolves the symbol for the specified assembly. - /// - /// - /// - [return: NotNullIfNotNull(nameof(assembly))] - IReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly); - - /// - /// Resolves the symbols for the specified assemblies. - /// - /// - /// - [return: NotNullIfNotNull(nameof(assemblies))] - IReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies); - - /// - /// Resolves the symbol for the specified assembly builder. - /// - /// - /// - [return: NotNullIfNotNull(nameof(assembly))] - IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly); - - /// - /// Resolves the symbol for the specified module. - /// - /// - /// - [return: NotNullIfNotNull(nameof(module))] - IReflectionModuleSymbol? ResolveModuleSymbol(Module? module); - - /// - /// Resolves the symbols for the specified modules. - /// - /// - /// - [return: NotNullIfNotNull(nameof(modules))] - IReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules); - - /// - /// Resolves the symbols for the specified modules. - /// - /// - /// - IEnumerable ResolveModuleSymbols(IEnumerable modules); - - /// - /// Resolves the symbol for the specified module. - /// - /// - /// - [return: NotNullIfNotNull(nameof(module))] - IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module); - - /// - /// Resolves the symbol for the specified member. - /// - /// - /// - [return: NotNullIfNotNull(nameof(member))] - IReflectionMemberSymbol? ResolveMemberSymbol(MemberInfo? member); - - /// - /// Resolves the symbols for the specified members. - /// - /// - /// - [return: NotNullIfNotNull(nameof(types))] - IReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? types); - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - [return: NotNullIfNotNull(nameof(type))] - IReflectionTypeSymbol? ResolveTypeSymbol(Type? type); - - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - [return: NotNullIfNotNull(nameof(types))] - IReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types); - - /// - /// Resolves the symbols for the specified types. - /// - /// - /// - IEnumerable ResolveTypeSymbols(IEnumerable types); - - /// - /// Resolves the symbol for the specified type. - /// - /// - /// - [return: NotNullIfNotNull(nameof(type))] - IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type); - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - [return: NotNullIfNotNull(nameof(method))] - IReflectionMethodBaseSymbol? ResolveMethodBaseSymbol(MethodBase? method); - - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - [return: NotNullIfNotNull(nameof(ctor))] - IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor); - - /// - /// Resolves the symbols for the specified constructors. - /// - /// - /// - [return: NotNullIfNotNull(nameof(ctors))] - IReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors); - - /// - /// Resolves the symbol for the specified constructor. - /// - /// - /// - [return: NotNullIfNotNull(nameof(ctor))] - IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor); - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - [return: NotNullIfNotNull(nameof(method))] - IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method); - - /// - /// Resolves the symbols for the specified methods. - /// - /// - /// - [return: NotNullIfNotNull(nameof(methods))] - IReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods); - - /// - /// Resolves the symbol for the specified method. - /// - /// - /// - [return: NotNullIfNotNull(nameof(method))] - IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method); - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - [return: NotNullIfNotNull(nameof(field))] - IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field); - - /// - /// Resolves the symbols for the specified fields. - /// - /// - /// - [return: NotNullIfNotNull(nameof(fields))] - IReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields); - - /// - /// Resolves the symbol for the specified field. - /// - /// - /// - /// - /// - [return: NotNullIfNotNull(nameof(field))] - IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field, ITypeSymbol[] requiredCustomModifiers, ITypeSymbol[] optionalCustomModifiers); - - /// - /// Resolves the symbol for the specified property. - /// - /// - /// - [return: NotNullIfNotNull(nameof(property))] - IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property); - - /// - /// Resolves the symbols for the specified properties. - /// - /// - /// - [return: NotNullIfNotNull(nameof(properties))] - IReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties); - - /// - /// Resolves the symbol for the specified property. - /// - /// - /// - [return: NotNullIfNotNull(nameof(property))] - IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property); - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - [return: NotNullIfNotNull(nameof(@event))] - IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event); - - /// - /// Resolves the symbols for the specified events. - /// - /// - /// - [return: NotNullIfNotNull(nameof(events))] - IReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events); - - /// - /// Resolves the symbol for the specified event. - /// - /// - /// - [return: NotNullIfNotNull(nameof(@event))] - IReflectionEventSymbolBuilder ResolveEventSymbol(EventBuilder @event); - - /// - /// Resolves the symbol for the specified parameter. - /// - /// - /// - [return: NotNullIfNotNull(nameof(parameter))] - IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter); - - /// - /// Resolves the symbols for the specified parameters. - /// - /// - /// - [return: NotNullIfNotNull(nameof(parameters))] - IReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters); - - /// - /// Resolves the symbol for the specified generic type parameter. - /// - /// - /// - [return: NotNullIfNotNull(nameof(genericTypeParameter))] - IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder? genericTypeParameter); - - /// - /// Resolves the symbol for the specified generic type parameters. - /// - /// - /// - [return: NotNullIfNotNull(nameof(genericTypeParameters))] - IReflectionGenericTypeParameterSymbolBuilder[]? ResolveGenericTypeParameterSymbols(GenericTypeParameterBuilder[]? genericTypeParameters); - - /// - /// Transforms a custom set of custom attribute data records to a symbol record. - /// - /// - /// - [return: NotNullIfNotNull(nameof(attributes))] - CustomAttribute[]? ResolveCustomAttributes(IList? attributes); - - /// - /// Transforms a custom set of custom attribute data records to a symbol record. - /// - /// - /// - IEnumerable ResolveCustomAttributes(IEnumerable attributes); - - /// - /// Transforms a custom attribute data record to a symbol record. - /// - /// - /// - [return: NotNullIfNotNull(nameof(customAttributeData))] - CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData); - - /// - /// Transforms a list of values into symbols. - /// - /// - /// - ImmutableArray ResolveCustomAttributeTypedArguments(IList args); - - /// - /// Transforms a values into a symbol. - /// - /// - /// - CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg); - - /// - /// Transforms the type as appropriate. - /// - /// - /// - object? ResolveCustomAttributeTypedValue(object? value); - - /// - /// Transforms a list of values into symbols. - /// - /// - /// - ImmutableArray ResolveCustomAttributeNamedArguments(IList args); - - /// - /// Transforms a values into a symbol. - /// - /// - /// - CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg); - - /// - /// Transforms a into a symbol type. - /// - /// - /// - InterfaceMapping ResolveInterfaceMapping(System.Reflection.InterfaceMapping arg); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs deleted file mode 100644 index f8daebcebf..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/IReflectionTypeSymbol.cs +++ /dev/null @@ -1,150 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - interface IReflectionTypeSymbol : IReflectionMemberSymbol, ITypeSymbol - { - - /// - /// Gets the underlying . - /// - Type UnderlyingType { get; } - - /// - /// Gets the underlying used for IL emit operations for dynamic methods. - /// - Type UnderlyingRuntimeType { get; } - - /// - /// Gets or creates a for the given element type. - /// - /// - /// - IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field); - - /// - /// Gets or creates a for the given . - /// - /// - /// - /// - /// - IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event); - - /// - /// Gets or creates a for the given generic type parameter type. - /// - /// - /// - IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter); - - /// - /// Gets or creates a for the given . - /// - /// - /// - IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter); - - /// - /// Gets or creates a for the given element type. - /// - /// - IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol(); - - /// - /// Gets or creates a for the given element type. - /// - /// - /// - IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank); - - /// - /// Gets or creates a for the given element type. - /// - /// - IReflectionTypeSymbol GetOrCreatePointerTypeSymbol(); - - /// - /// Gets or creates a for the given element type. - /// - /// - IReflectionTypeSymbol GetOrCreateByRefTypeSymbol(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs deleted file mode 100644 index b9456e1c78..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionArrayTypeSymbol.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionArrayTypeSymbol : ReflectionTypeSpecSymbol - { - - readonly int rank; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionArrayTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, int rank) : - base(context, resolvingModule, elementType) - { - this.rank = rank; - } - - /// - public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakeArrayType(rank); - - /// - public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeArrayType(rank); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs index c5dffa008d..187ae9fe16 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionAssemblySymbol.cs @@ -1,190 +1,135 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.IO; -using System.Linq; using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionAssemblySymbol : ReflectionSymbol, IReflectionAssemblySymbol + class ReflectionAssemblySymbol : AssemblySymbol { - readonly Assembly _assembly; + readonly Assembly _underlyingAssembly; - ReflectionModuleTable _moduleTable; + ImmutableArray _references; + ImmutableArray _modules; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// - /// - public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly assembly) : + /// + public ReflectionAssemblySymbol(ReflectionSymbolContext context, Assembly underlyingAssembly) : base(context) { - _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); - _moduleTable = new ReflectionModuleTable(context, this); + _underlyingAssembly = underlyingAssembly ?? throw new ArgumentNullException(nameof(underlyingAssembly)); } - /// - /// Gets the underlying instance. - /// - public virtual Assembly UnderlyingAssembly => _assembly; - - /// - /// Gets the underlying instance. - /// - public virtual Assembly UnderlyingRuntimeAssembly => _assembly; - - #region IReflectionAssemblySymbol - /// - public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) - { - return _moduleTable.GetOrCreateModuleSymbol(module); - } - - #endregion - - #region IAssemblySymbol + new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; /// - public IEnumerable DefinedTypes => ResolveTypeSymbols(UnderlyingAssembly.DefinedTypes); + public sealed override IEnumerable DefinedTypes => Context.ResolveTypeSymbols(_underlyingAssembly.DefinedTypes); /// - public IMethodSymbol? EntryPoint => ResolveMethodSymbol(UnderlyingAssembly.EntryPoint); + public sealed override IEnumerable ExportedTypes => Context.ResolveTypeSymbols(_underlyingAssembly.ExportedTypes); /// - public IEnumerable ExportedTypes => ResolveTypeSymbols(UnderlyingAssembly.ExportedTypes); + public sealed override MethodSymbol? EntryPoint => Context.ResolveMethodSymbol(_underlyingAssembly.EntryPoint); /// - public string? FullName => UnderlyingAssembly.FullName; + public sealed override string? FullName => _underlyingAssembly.FullName; /// - public string ImageRuntimeVersion => UnderlyingAssembly.ImageRuntimeVersion; + public sealed override string ImageRuntimeVersion => _underlyingAssembly.ImageRuntimeVersion; /// - public string Location => UnderlyingAssembly.Location; + public sealed override string Location => _underlyingAssembly.Location; /// - public IModuleSymbol ManifestModule => ResolveModuleSymbol(UnderlyingAssembly.ManifestModule); + public sealed override ModuleSymbol ManifestModule => Context.ResolveModuleSymbol(_underlyingAssembly.ManifestModule); /// - public IEnumerable Modules => ResolveModuleSymbols(UnderlyingAssembly.Modules); + public sealed override bool IsMissing => false; /// - public ITypeSymbol[] GetExportedTypes() - { - return ResolveTypeSymbols(UnderlyingAssembly.GetExportedTypes()); - } + public sealed override bool ContainsMissing => false; /// - public IModuleSymbol? GetModule(string name) - { - return ResolveModuleSymbol(UnderlyingAssembly.GetModule(name)); - } + public sealed override bool IsComplete => true; /// - public IModuleSymbol[] GetModules() + public sealed override ImmutableArray GetModules() { - return ResolveModuleSymbols(UnderlyingAssembly.GetModules()); - } + if (_modules == default) + { + var b = ImmutableArray.CreateBuilder(); + var l = _underlyingAssembly.GetModules(); + foreach (var module in l) + b.Add(new ReflectionModuleSymbol(Context, this, module)); - /// - public IModuleSymbol[] GetModules(bool getResourceModules) - { - return ResolveModuleSymbols(UnderlyingAssembly.GetModules(getResourceModules)); - } + ImmutableInterlocked.InterlockedInitialize(ref _modules, b.ToImmutable()); + } - /// - public AssemblyIdentity GetIdentity() - { - return UnderlyingAssembly.GetName().Pack(); + return _modules; } /// - public AssemblyIdentity[] GetReferencedAssemblies() + public sealed override AssemblyIdentity GetIdentity() { - return UnderlyingAssembly.GetReferencedAssemblies().Pack(); + return _underlyingAssembly.GetName().Pack(); } /// - public ITypeSymbol? GetType(string name, bool throwOnError) + public sealed override ImmutableArray GetReferencedAssemblies() { - return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError)); - } + if (_references == default) + ImmutableInterlocked.InterlockedInitialize(ref _references, _underlyingAssembly.GetReferencedAssemblies().Pack()); - /// - public ITypeSymbol? GetType(string name, bool throwOnError, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingAssembly.GetType(name, throwOnError, ignoreCase)); + return _references; } /// - public ITypeSymbol? GetType(string name) + public sealed override TypeSymbol? GetType(string name, bool throwOnError) { - return ResolveTypeSymbol(UnderlyingAssembly.GetType(name)); + return Context.ResolveTypeSymbol(_underlyingAssembly.GetType(name, throwOnError, false)); } /// - public ITypeSymbol[] GetTypes() + public sealed override ImmutableArray GetTypes() { - return ResolveTypeSymbols(UnderlyingAssembly.GetTypes()); + return Context.ResolveTypeSymbols(_underlyingAssembly.GetTypes()); } /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) + public sealed override ManifestResourceInfo? GetManifestResourceInfo(string resourceName) { - return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData()); + throw new NotImplementedException(); } /// - public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public sealed override Stream? GetManifestResourceStream(string name) { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttributes(UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); + return _underlyingAssembly.GetManifestResourceStream(name); } /// - public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + public sealed override Stream? GetManifestResourceStream(TypeSymbol type, string name) { - var _attributeType = attributeType.Unpack(); - var a = UnderlyingAssembly.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToList(); - if (a.Count > 0) - return ResolveCustomAttribute(a[0]); - - return null; + throw new NotImplementedException(); } /// - public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return UnderlyingAssembly.IsDefined(attributeType.Unpack(), inherit); - } + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingAssembly.GetCustomAttributesData())); - /// - public ManifestResourceInfo? GetManifestResourceInfo(string resourceName) - { - return ResolveManifestResourceInfo(UnderlyingAssembly.GetManifestResourceInfo(resourceName)); + return _customAttributes; } - /// - public Stream? GetManifestResourceStream(string name) - { - return UnderlyingAssembly.GetManifestResourceStream(name); - } - - /// - public Stream? GetManifestResourceStream(ITypeSymbol type, string name) - { - return UnderlyingAssembly.GetManifestResourceStream(type.Unpack(), name); - } - - #endregion - - /// - public override string? ToString() => UnderlyingAssembly.ToString(); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs deleted file mode 100644 index 0dfc4d623e..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionByRefTypeSymbol.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionByRefTypeSymbol : ReflectionTypeSpecSymbol - { - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionByRefTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : - base(context, resolvingModule, elementType) - { - - } - - /// - public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakeByRefType(); - - /// - public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeByRefType(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs index 6049e8f842..b89e7f37db 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs @@ -1,38 +1,92 @@ using System; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionConstructorSymbol : ReflectionMethodBaseSymbol, IReflectionConstructorSymbol + class ReflectionConstructorSymbol : ConstructorSymbol { - readonly ConstructorInfo _ctor; + readonly ConstructorInfo _underlyingConstructor; + + ImmutableArray _parameters; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// - /// - /// - /// - public ReflectionConstructorSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, ConstructorInfo ctor) : - base(context, resolvingModule, resolvingType) + /// + /// + public ReflectionConstructorSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol declaringType, ConstructorInfo underlyingConstructor) : + base(context, declaringType) { - _ctor = ctor ?? throw new ArgumentNullException(nameof(ctor)); + _underlyingConstructor = underlyingConstructor ?? throw new ArgumentNullException(nameof(underlyingConstructor)); } + /// + /// Gets the associated symbol context. + /// + protected new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; + + /// + public override MethodAttributes Attributes => _underlyingConstructor.Attributes; + + /// + public override CallingConventions CallingConvention => _underlyingConstructor.CallingConvention; + /// - public virtual ConstructorInfo UnderlyingConstructor => _ctor; + public override MethodImplAttributes MethodImplementationFlags => _underlyingConstructor.MethodImplementationFlags; /// - public virtual ConstructorInfo UnderlyingRuntimeConstructor => UnderlyingConstructor; + public override string Name => _underlyingConstructor.Name; /// - public override MethodBase UnderlyingMethodBase => UnderlyingConstructor; + public override bool IsMissing => false; /// - public override MethodBase UnderlyingRuntimeMethodBase => UnderlyingRuntimeConstructor; + public override bool ContainsMissing => false; + + /// + public override bool IsComplete => false; + + /// + public override ImmutableArray GetGenericArguments() + { + return ImmutableArray.Empty; + } + + /// + public override MethodImplAttributes GetMethodImplementationFlags() + { + return _underlyingConstructor.GetMethodImplementationFlags(); + } + + /// + public override ImmutableArray GetParameters() + { + if (_parameters == default) + { + var l = _underlyingConstructor.GetParameters(); + var b = ImmutableArray.CreateBuilder(); + for (int i = 0; i < l.Length; i++) + b.Add(new ReflectionParameterSymbol(Context, this, l[i])); + + ImmutableInterlocked.InterlockedInitialize(ref _parameters, b.ToImmutable()); + } + + return _parameters; + } + + /// + internal sealed override ImmutableArray GetDeclaredCustomAttributes() + { + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingConstructor.GetCustomAttributesData())); + + return _customAttributes; + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs deleted file mode 100644 index 81ba5a0ad8..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionDefinitionTypeSymbol.cs +++ /dev/null @@ -1,11 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionDefinitionTypeSymbol : DefinitionTypeSymbol - { - - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs index b62385d455..76117cf1d6 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventSymbol.cs @@ -1,109 +1,116 @@ using System; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionEventSymbol : ReflectionMemberSymbol, IReflectionEventSymbol + class ReflectionEventSymbol : EventSymbol { - readonly EventInfo _event; + readonly EventInfo _underlyingEvent; + + TypeSymbol? _eventHandlerType; + MethodSymbol? _addMethod; + MethodSymbol? _nonPublicAddMethod; + MethodSymbol? _removeMethod; + MethodSymbol? _nonPublicRemoveMethod; + MethodSymbol? _raiseMethod; + MethodSymbol? _nonPublicRaiseMethod; + ImmutableArray _otherMethods; + ImmutableArray _nonPublicOtherMethods; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// - /// - /// - /// - public ReflectionEventSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol resolvingType, EventInfo @event) : - base(context, resolvingModule, resolvingType) + /// + /// + public ReflectionEventSymbol(ReflectionSymbolContext context, ReflectionTypeSymbol declaringType, EventInfo underlyingEvent) : + base(context, declaringType) { - _event = @event ?? throw new ArgumentNullException(nameof(@event)); + _underlyingEvent = underlyingEvent ?? throw new ArgumentNullException(nameof(underlyingEvent)); } - /// - public virtual EventInfo UnderlyingEvent => _event; - - /// - public virtual EventInfo UnderlyingRuntimeEvent => _event; - - /// - public override MemberInfo UnderlyingMember => UnderlyingEvent; - - /// - public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeEvent; - - #region IEventSymbol - - /// - public System.Reflection.EventAttributes Attributes => (System.Reflection.EventAttributes)UnderlyingEvent.Attributes; - - /// - public ITypeSymbol? EventHandlerType => ResolveTypeSymbol(UnderlyingEvent.EventHandlerType); + /// + /// Gets the associated symbol context. + /// + protected new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; /// - public bool IsSpecialName => UnderlyingEvent.IsSpecialName; + public sealed override EventAttributes Attributes => _underlyingEvent.Attributes; /// - public IMethodSymbol? AddMethod => ResolveMethodSymbol(UnderlyingEvent.AddMethod); + public sealed override TypeSymbol? EventHandlerType => _eventHandlerType ??= Context.ResolveTypeSymbol(_underlyingEvent.EventHandlerType); /// - public IMethodSymbol? RemoveMethod => ResolveMethodSymbol(UnderlyingEvent.RemoveMethod); + public sealed override string Name => _underlyingEvent.Name; /// - public IMethodSymbol? RaiseMethod => ResolveMethodSymbol(UnderlyingEvent.RaiseMethod); + public sealed override bool IsMissing => false; /// - public IMethodSymbol? GetAddMethod() - { - return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod()); - } + public sealed override bool ContainsMissing => false; /// - public IMethodSymbol? GetAddMethod(bool nonPublic) - { - return ResolveMethodSymbol(UnderlyingEvent.GetAddMethod(nonPublic)); - } + public sealed override bool IsComplete => true; /// - public IMethodSymbol? GetRemoveMethod() + public sealed override MethodSymbol? GetAddMethod(bool nonPublic) { - return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod()); + if (nonPublic) + return _nonPublicAddMethod ??= Context.ResolveMethodSymbol(_underlyingEvent.GetAddMethod(true)); + else + return _addMethod ??= Context.ResolveMethodSymbol(_underlyingEvent.GetAddMethod(false)); } /// - public IMethodSymbol? GetRemoveMethod(bool nonPublic) + public sealed override MethodSymbol? GetRemoveMethod(bool nonPublic) { - return ResolveMethodSymbol(UnderlyingEvent.GetRemoveMethod(nonPublic)); + if (nonPublic) + return _nonPublicRemoveMethod ??= Context.ResolveMethodSymbol(_underlyingEvent.GetRemoveMethod(true)); + else + return _removeMethod ??= Context.ResolveMethodSymbol(_underlyingEvent.GetRemoveMethod(false)); } /// - public IMethodSymbol? GetRaiseMethod() + public sealed override MethodSymbol? GetRaiseMethod(bool nonPublic) { - return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod()); + if (nonPublic) + return _nonPublicRaiseMethod ??= Context.ResolveMethodSymbol(_underlyingEvent.GetRaiseMethod(true)); + else + return _raiseMethod ??= Context.ResolveMethodSymbol(_underlyingEvent.GetRaiseMethod(false)); } /// - public IMethodSymbol? GetRaiseMethod(bool nonPublic) + public sealed override ImmutableArray GetOtherMethods(bool nonPublic) { - return ResolveMethodSymbol(UnderlyingEvent.GetRaiseMethod(nonPublic)); + if (nonPublic) + { + if (_nonPublicOtherMethods == default) + ImmutableInterlocked.InterlockedInitialize(ref _nonPublicOtherMethods, Context.ResolveMethodSymbols(_underlyingEvent.GetOtherMethods(true))); + + return _nonPublicOtherMethods; + } + else + { + if (_otherMethods == default) + ImmutableInterlocked.InterlockedInitialize(ref _otherMethods, Context.ResolveMethodSymbols(_underlyingEvent.GetOtherMethods(false))); + + return _otherMethods; + } } /// - public IMethodSymbol[] GetOtherMethods() + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods()); - } + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingEvent.GetCustomAttributesData())); - /// - public IMethodSymbol[] GetOtherMethods(bool nonPublic) - { - return ResolveMethodSymbols(UnderlyingEvent.GetOtherMethods(nonPublic)); + return _customAttributes; } - #endregion - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs deleted file mode 100644 index dcd4f11ebe..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionEventTable.cs +++ /dev/null @@ -1,95 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionEventTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol _type; - - IndexRangeDictionary _table = new(); - ReaderWriterLockSlim? _lock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionEventTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol type) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type ?? throw new ArgumentNullException(nameof(type)); - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - if (@event.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(@event)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var row = @event.GetMetadataTokenRowNumberSafe(); - if (_table[row] == null) - using (_lock.CreateWriteLock()) - return _table[row] ??= new ReflectionEventSymbol(_context, _module, _type, @event); - - return _table[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by event. - /// - /// - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - if (@event.GetModuleBuilder() != _module.UnderlyingModule) - throw new ArgumentException(nameof(@event)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var row = @event.GetMetadataTokenRowNumberSafe(); - if (_table[row] == null) - using (_lock.CreateWriteLock()) - return (IReflectionEventSymbolBuilder)(_table[row] ??= new ReflectionEventSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder)_type, @event)); - - return (IReflectionEventSymbolBuilder?)_table[row] ?? throw new InvalidOperationException(); - } - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs index a9d760e500..4dc22703fc 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldSymbol.cs @@ -1,103 +1,88 @@ using System; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionFieldSymbol : ReflectionMemberSymbol, IReflectionFieldSymbol + class ReflectionFieldSymbol : FieldSymbol { - readonly FieldInfo _field; + readonly FieldInfo _underlyingField; + + TypeSymbol? _fieldType; + ImmutableArray _optionalCustomModifiers; + ImmutableArray _requiredCustomModifiers; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// - /// - /// - /// - public ReflectionFieldSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType, FieldInfo field) : - base(context, resolvingModule, resolvingType) + /// + /// + public ReflectionFieldSymbol(ReflectionSymbolContext context, ModuleSymbol module, ReflectionTypeSymbol? declaringType, FieldInfo underlyingField) : + base(context, module, declaringType) { - _field = field ?? throw new ArgumentNullException(nameof(field)); + _underlyingField = underlyingField ?? throw new ArgumentNullException(nameof(underlyingField)); } - /// - public virtual FieldInfo UnderlyingField => _field; + /// + /// Gets the associated symbol context. + /// + protected new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; /// - public virtual FieldInfo UnderlyingRuntimeField => _field; + public override FieldAttributes Attributes => _underlyingField.Attributes; /// - public override MemberInfo UnderlyingMember => UnderlyingField; + public override TypeSymbol FieldType => _fieldType ??= Context.ResolveTypeSymbol(_underlyingField.FieldType); /// - public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeField; - - #region IFieldSymbol - - /// - public FieldAttributes Attributes => UnderlyingField.Attributes; - - /// - public ITypeSymbol FieldType => ResolveTypeSymbol(UnderlyingField.FieldType); - - /// - public bool IsSpecialName => UnderlyingField.IsSpecialName; - - /// - public bool IsAssembly => UnderlyingField.IsAssembly; - - /// - public bool IsFamily => UnderlyingField.IsFamily; - - /// - public bool IsFamilyAndAssembly => UnderlyingField.IsFamilyAndAssembly; - - /// - public bool IsFamilyOrAssembly => UnderlyingField.IsFamilyOrAssembly; - - /// - public bool IsInitOnly => UnderlyingField.IsInitOnly; - - /// - public bool IsLiteral => UnderlyingField.IsLiteral; + public override string Name => _underlyingField.Name; - /// - public bool IsNotSerialized => UnderlyingField.IsNotSerialized; - - /// - public bool IsPinvokeImpl => UnderlyingField.IsPinvokeImpl; - - /// - public bool IsPrivate => UnderlyingField.IsPrivate; + /// + public override bool IsMissing => false; - /// - public bool IsPublic => UnderlyingField.IsPublic; + /// + public override bool ContainsMissing => false; - /// - public bool IsStatic => UnderlyingField.IsStatic; + /// + public override bool IsComplete => false; - /// - public virtual ITypeSymbol[] GetOptionalCustomModifiers() + /// + public override object? GetRawConstantValue() { - return ResolveTypeSymbols(UnderlyingField.GetOptionalCustomModifiers()); + return _underlyingField.GetRawConstantValue(); } - /// - public virtual ITypeSymbol[] GetRequiredCustomModifiers() + /// + public override ImmutableArray GetOptionalCustomModifiers() { - return ResolveTypeSymbols(UnderlyingField.GetRequiredCustomModifiers()); + if (_optionalCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, Context.ResolveTypeSymbols(_underlyingField.GetOptionalCustomModifiers())); + + return _optionalCustomModifiers; } - /// - public object? GetRawConstantValue() + /// + public override ImmutableArray GetRequiredCustomModifiers() { - return UnderlyingField.GetRawConstantValue(); + if (_requiredCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, Context.ResolveTypeSymbols(_underlyingField.GetRequiredCustomModifiers())); + + return _requiredCustomModifiers; } - #endregion + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingField.GetCustomAttributesData())); + + return _customAttributes; + } } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs deleted file mode 100644 index 984f167a89..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionFieldTable.cs +++ /dev/null @@ -1,84 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionFieldTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol? _type; - - IndexRangeDictionary _table = new(); - ReaderWriterLockSlim? _lock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionFieldTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type; - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - /// - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - if (field.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(field)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var row = field.GetMetadataTokenRowNumberSafe(); - if (_table[row] == null) - using (_lock.CreateWriteLock()) - if (field is FieldBuilder builder) - return _table[row] ??= new ReflectionFieldSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder?)_type, builder, requiredCustomModifiers, optionalCustomModifiers); - else - return _table[row] ??= new ReflectionFieldSymbol(_context, _module, _type, field); - - return _table[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by field. - /// - /// - /// - /// - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) - { - return (IReflectionFieldSymbolBuilder)GetOrCreateFieldSymbol((FieldInfo)field, requiredCustomModifiers, optionalCustomModifiers); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericInstantiationTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericInstantiationTypeSymbol.cs deleted file mode 100644 index 457afdbde9..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericInstantiationTypeSymbol.cs +++ /dev/null @@ -1,305 +0,0 @@ -using System; -using System.Linq; -using System.Reflection; -using System.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionGenericInstantiationTypeSymbol : ReflectionTypeSpecSymbol - { - - /// - /// Returns true if the type or any generic type definition or generic arguments are type builders. That is, is this a TypeBuilderInstantiation instance. - /// - /// - /// - static bool ContainsTypeBuilder(Type type) - { - // find deepest element type - while (type.HasElementType) - type = type.GetElementType() ?? throw new InvalidOperationException(); - - // type definition, or generic type definition, result is whether it is itself a type builder - if (type.IsGenericType == false || type.IsGenericTypeDefinition) - return type is TypeBuilder; - - // are arguments of closed generic themselves type builder instantiations? - foreach (var arg in type.GetGenericArguments()) - if (ContainsTypeBuilder(arg)) - return true; - - // are we a type builder? - return type.GetGenericTypeDefinition() is TypeBuilder; - } - - readonly IReflectionTypeSymbol[] _genericTypeArguments; - Type? _underlyingType; - bool? _underlyingTypeContainsTypeBuilder; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionGenericInstantiationTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType, IReflectionTypeSymbol[] genericTypeArguments) : - base(context, resolvingModule, elementType) - { - _genericTypeArguments = genericTypeArguments ?? throw new ArgumentNullException(nameof(genericTypeArguments)); - } - - /// - public override Type UnderlyingType => _underlyingType ??= SpecifiedType.UnderlyingType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingType).ToArray()); - - /// - public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeGenericType(_genericTypeArguments.Select(i => i.UnderlyingRuntimeType).ToArray()); - - /// - /// Returns true if the underlying type contains a type builder. - /// - /// - bool UnderlyingTypeContainsTypeBuilder => _underlyingTypeContainsTypeBuilder ??= ContainsTypeBuilder(UnderlyingType); - - /// - public override IFieldSymbol[] GetFields() - { - if (UnderlyingTypeContainsTypeBuilder) - { - var l = SpecifiedType.UnderlyingType.GetFields(); - var a = new IFieldSymbol[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, l[i])); - - return a; - } - - return base.GetFields(); - } - - /// - public override IFieldSymbol[] GetFields(BindingFlags bindingAttr) - { - if (UnderlyingTypeContainsTypeBuilder) - { - var l = SpecifiedType.UnderlyingType.GetFields(bindingAttr); - var a = new IFieldSymbol[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, l[i])); - - return a; - } - - return base.GetFields(bindingAttr); - } - - /// - public override IFieldSymbol? GetField(string name) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetField(name) is { } f) - return ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, f)); - - return base.GetField(name); - } - - /// - public override IFieldSymbol? GetField(string name, BindingFlags bindingAttr) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetField(name, bindingAttr) is { } f) - return ResolveFieldSymbol(TypeBuilder.GetField(UnderlyingType, f)); - - return base.GetField(name, bindingAttr); - } - - /// - public override IConstructorSymbol[] GetConstructors() - { - if (UnderlyingTypeContainsTypeBuilder) - { - var l = SpecifiedType.UnderlyingType.GetConstructors(); - var a = new IConstructorSymbol[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, l[i])); - - return a; - } - - return base.GetConstructors(); - } - - /// - public override IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) - { - if (UnderlyingTypeContainsTypeBuilder) - { - var l = SpecifiedType.UnderlyingType.GetConstructors(bindingAttr); - var a = new IConstructorSymbol[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, l[i])); - - return a; - } - - return base.GetConstructors(bindingAttr); - } - - /// - public override IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetConstructor(types.Unpack()) is { } m) - return ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, m)); - - return base.GetConstructor(types); - } - - /// - public override IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetConstructor(bindingAttr, null, types.Unpack(), null) is { } m) - return ResolveConstructorSymbol(TypeBuilder.GetConstructor(UnderlyingType, m)); - - return base.GetConstructor(bindingAttr, types); - } - - /// - public override IMethodSymbol[] GetMethods() - { - if (UnderlyingTypeContainsTypeBuilder) - { - var l = SpecifiedType.UnderlyingType.GetMethods(); - var a = new IMethodSymbol[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, l[i])); - - return a; - } - - return base.GetMethods(); - } - - /// - public override IMethodSymbol[] GetMethods(BindingFlags bindingAttr) - { - if (UnderlyingTypeContainsTypeBuilder) - { - var l = SpecifiedType.UnderlyingType.GetMethods(bindingAttr); - var a = new IMethodSymbol[l.Length]; - for (int i = 0; i < l.Length; i++) - a[i] = ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, l[i])); - - return a; - } - - return base.GetMethods(bindingAttr); - } - - /// - public override IMethodSymbol? GetMethod(string name) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetMethod(name) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); - - return base.GetMethod(name); - } - - /// - public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); - - return base.GetMethod(name, bindingAttr); - } - - /// - public override IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetMethod(name, types.Unpack()) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); - - return base.GetMethod(name, types); - } - - /// - public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); - - return base.GetMethod(name, bindingAttr, types); - } - - /// - public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); - - return base.GetMethod(name, bindingAttr, types, modifiers); - } - - /// - public override IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - if (UnderlyingTypeContainsTypeBuilder) - if (SpecifiedType.UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); - - return base.GetMethod(name, bindingAttr, callConvention, types, modifiers); - } - - /// - public override IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - if (UnderlyingTypeContainsTypeBuilder) -#if NETFRAMEWORK - throw new NotSupportedException(); -#else - if (SpecifiedType.UnderlyingType.GetMethod(name, genericParameterCount, types.Unpack(), modifiers) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); -#endif - - return base.GetMethod(name, genericParameterCount, types, modifiers); - } - - /// - public override IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - if (UnderlyingTypeContainsTypeBuilder) -#if NETFRAMEWORK - throw new NotSupportedException(); -#else - if (SpecifiedType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, types.Unpack(), modifiers) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); -#endif - - return base.GetMethod(name, genericParameterCount, bindingAttr, types, modifiers); - } - - /// - public override IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - if (UnderlyingTypeContainsTypeBuilder) -#if NETFRAMEWORK - throw new NotSupportedException(); -#else - if (SpecifiedType.UnderlyingType.GetMethod(name, genericParameterCount, bindingAttr, null, callConvention, types.Unpack(), modifiers) is { } m) - return ResolveMethodSymbol(TypeBuilder.GetMethod(UnderlyingType, m)); -#endif - - return base.GetMethod(name, genericParameterCount, bindingAttr, callConvention, types, modifiers); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericMethodParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericMethodParameterTypeSymbol.cs new file mode 100644 index 0000000000..08e00ca933 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericMethodParameterTypeSymbol.cs @@ -0,0 +1,62 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionGenericMethodParameterTypeSymbol : GenericMethodParameterTypeSymbol + { + + readonly Type _underlyingType; + + ImmutableArray _interfaces; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionGenericMethodParameterTypeSymbol(ReflectionSymbolContext context, MethodSymbol declaringMethod, Type underlyingType) : + base(context, declaringMethod) + { + _underlyingType = underlyingType ?? throw new ArgumentNullException(nameof(underlyingType)); + } + + /// + /// Gets the context that owns this symbol. + /// + new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; + + /// + public override string? FullName => _underlyingType.FullName; + + /// + public override string? Namespace => _underlyingType.Namespace; + + /// + public override GenericParameterAttributes GenericParameterAttributes => _underlyingType.GenericParameterAttributes; + + /// + public override int GenericParameterPosition => _underlyingType.GenericParameterPosition; + + /// + public override string Name => _underlyingType.Name; + + /// + public override bool IsComplete => true; + + /// + public override ImmutableArray GetInterfaces() + { + if (_interfaces == null) + ImmutableInterlocked.InterlockedInitialize(ref _interfaces, Context.ResolveTypeSymbols(_underlyingType.GetInterfaces())); + + return _interfaces; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs deleted file mode 100644 index dfea498d4c..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterSymbol.cs +++ /dev/null @@ -1,699 +0,0 @@ -using System; -using System.Diagnostics.CodeAnalysis; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionGenericTypeParameterSymbol : ReflectionMemberSymbol, IReflectionTypeSymbol - { - - readonly IReflectionMemberSymbol _resolvingMember; - - ReflectionTypeSpecTable _specTable; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - /// - public ReflectionGenericTypeParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMemberSymbol resolvingMember) : - base(context, resolvingModule, resolvingMember as IReflectionTypeSymbol) - { - _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); - _specTable = new ReflectionTypeSpecTable(); - } - - /// - public virtual Type UnderlyingType => _type; - - /// - public virtual Type UnderlyingRuntimeType => _type; - - /// - public override MemberInfo UnderlyingMember => UnderlyingType; - - /// - public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeType; - - /// - /// Gets the method base that declares this type parameter. - /// - public IReflectionMemberSymbol? ResolvingMemberSymbol => _resolvingMember; - - #region IReflectionSymbol - - /// - [return: NotNullIfNotNull(nameof(type))] - public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) - { - if (type == _type) - return this; - else - return base.ResolveTypeSymbol(type); - } - - #endregion - - #region IReflectionTypeSymbol - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) - { - return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); - } - - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - throw new NotSupportedException(); - } - - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - throw new NotSupportedException(); - } - - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - throw new NotImplementedException(); - } - - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - throw new NotSupportedException(); - } - - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - throw new NotImplementedException(); - } - - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - throw new NotSupportedException(); - } - - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) - { - throw new NotImplementedException(); - } - - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - throw new NotSupportedException(); - } - - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - throw new NotImplementedException(); - } - - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - throw new NotSupportedException(); - } - - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - throw new NotImplementedException(); - } - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type type) - { - throw new NotSupportedException(); - } - - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - throw new NotImplementedException(); - } - - /// - public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() - { - return _specTable.GetOrCreateSZArrayTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) - { - return _specTable.GetOrCreateArrayTypeSymbol(rank); - } - - /// - public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() - { - return _specTable.GetOrCreatePointerTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() - { - return _specTable.GetOrCreateByRefTypeSymbol(); - } - - #endregion - - #region ITypeSymbol - - /// - public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); - - /// - public string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; - - /// - public System.Reflection.TypeAttributes Attributes => (System.Reflection.TypeAttributes)UnderlyingType.Attributes; - - /// - public ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); - - /// - public bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; - - /// - public IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); - - /// - public string? FullName => UnderlyingType.FullName; - - /// - public string? Namespace => UnderlyingType.Namespace; - - /// - public System.Reflection.GenericParameterAttributes GenericParameterAttributes => (System.Reflection.GenericParameterAttributes)UnderlyingType.GenericParameterAttributes; - - /// - public int GenericParameterPosition => UnderlyingType.GenericParameterPosition; - - /// - public ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); - - /// - public bool HasElementType => UnderlyingType.HasElementType; - - /// - public TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); - - /// - public bool IsAbstract => UnderlyingType.IsAbstract; - - /// - public bool IsSZArray => UnderlyingType.IsSZArray(); - - /// - public bool IsArray => UnderlyingType.IsArray; - - /// - public bool IsAutoLayout => UnderlyingType.IsAutoLayout; - - /// - public bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; - - /// - public bool IsByRef => UnderlyingType.IsByRef; - - /// - public bool IsClass => UnderlyingType.IsClass; - - /// - public bool IsEnum => UnderlyingType.IsEnum; - - /// - public bool IsInterface => UnderlyingType.IsInterface; - - /// - public bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; - - /// - public bool IsGenericParameter => UnderlyingType.IsGenericParameter; - - /// - public bool IsGenericType => UnderlyingType.IsGenericType; - - /// - public bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; - - /// - public bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; - - /// - public bool IsNested => UnderlyingType.IsNested; - - /// - public bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; - - /// - public bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; - - /// - public bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; - - /// - public bool IsNestedFamily => UnderlyingType.IsNestedFamily; - - /// - public bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; - - /// - public bool IsNestedPublic => UnderlyingType.IsNestedPublic; - - /// - public bool IsNotPublic => UnderlyingType.IsNotPublic; - - /// - public bool IsPointer => UnderlyingType.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; - - /// - public bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; - -#else - - /// - public bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public bool IsPrimitive => UnderlyingType.IsPrimitive; - - /// - public bool IsPublic => UnderlyingType.IsPublic; - - /// - public bool IsSealed => UnderlyingType.IsSealed; - - /// - public bool IsSerializable => UnderlyingType.IsSerializable; - - /// - public bool IsValueType => UnderlyingType.IsValueType; - - /// - public bool IsVisible => UnderlyingType.IsVisible; - - /// - public bool IsSignatureType => throw new NotImplementedException(); - - /// - public bool IsSpecialName => UnderlyingType.IsSpecialName; - - /// - public IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); - - /// - public int GetArrayRank() - { - return UnderlyingType.GetArrayRank(); - } - - /// - public IConstructorSymbol? GetConstructor(System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor((BindingFlags)bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); - } - - /// - public IConstructorSymbol[] GetConstructors(System.Reflection.BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetDefaultMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); - } - - /// - public ITypeSymbol? GetElementType() - { - return ResolveTypeSymbol(UnderlyingType.GetElementType()); - } - - /// - public string? GetEnumName(object value) - { - return UnderlyingType.GetEnumName(value); - } - - /// - public string[] GetEnumNames() - { - return UnderlyingType.GetEnumNames(); - } - - /// - public ITypeSymbol GetEnumUnderlyingType() - { - return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public Array GetEnumValues() - { - return UnderlyingType.GetEnumValues(); - } - - /// - public IEventSymbol? GetEvent(string name) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name)); - } - - /// - public IEventSymbol? GetEvent(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name, (BindingFlags)bindingAttr)); - } - - /// - public IEventSymbol[] GetEvents() - { - return ResolveEventSymbols(UnderlyingType.GetEvents()); - } - - /// - public IEventSymbol[] GetEvents(System.Reflection.BindingFlags bindingAttr) - { - return ResolveEventSymbols(UnderlyingType.GetEvents((BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name)); - } - - /// - public IFieldSymbol? GetField(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name, (BindingFlags)bindingAttr)); - } - - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingType.GetFields()); - } - - /// - public IFieldSymbol[] GetFields(System.Reflection.BindingFlags bindingAttr) - { - return ResolveFieldSymbols(UnderlyingType.GetFields((BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); - } - - /// - public ITypeSymbol[] GetGenericParameterConstraints() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public ITypeSymbol GetGenericTypeDefinition() - { - return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public ITypeSymbol? GetInterface(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); - } - - /// - public ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); - } - - /// - public ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public IMemberSymbol[] GetMembers(string name) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name)); - } - - /// - public IMemberSymbol[] GetMembers(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers(string name, System.Reflection.MemberTypes type, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, (MemberTypes)type, (BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMembers((BindingFlags)bindingAttr)); - } - - /// - public IMemberSymbol[] GetMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetMembers()); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr)); - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), null)); - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, (CallingConventions)callConvention, types.Unpack(), modifiers?.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConvention, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol? GetMethod(string name, System.Reflection.BindingFlags bindingAttr, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, (BindingFlags)bindingAttr, null, types.Unpack(), modifiers?.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, System.Reflection.ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public IMethodSymbol[] GetMethods(System.Reflection.BindingFlags bindingAttr) - { - return ResolveMethodSymbols(UnderlyingType.GetMethods((BindingFlags)bindingAttr)); - } - - /// - public IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(UnderlyingType.GetMethods()); - } - - /// - public ITypeSymbol? GetNestedType(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); - } - - /// - public ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, (BindingFlags)bindingAttr)); - } - - /// - public ITypeSymbol[] GetNestedTypes() - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); - } - - /// - public ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol[] GetProperties() - { - return ResolvePropertySymbols(UnderlyingType.GetProperties()); - } - - /// - public IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); - } - - /// - public IPropertySymbol? GetProperty(string name) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); - } - - /// - public IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public bool IsAssignableFrom(ITypeSymbol? c) - { - return UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public bool IsEnumDefined(object value) - { - return UnderlyingType.IsEnumDefined(value); - } - - /// - public bool IsSubclassOf(ITypeSymbol c) - { - return UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public ITypeSymbol MakeArrayType() - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); - } - - /// - public ITypeSymbol MakeArrayType(int rank) - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); - } - - /// - public ITypeSymbol MakeByRefType() - { - return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); - } - - /// - public ITypeSymbol MakePointerType() - { - return ResolveTypeSymbol(UnderlyingType.MakePointerType()); - } - - /// - public ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); - } - - #endregion - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs deleted file mode 100644 index 1c9dde4304..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTable.cs +++ /dev/null @@ -1,78 +0,0 @@ -using System; -using System.Reflection.Emit; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionGenericTypeParameterTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionMemberSymbol _member; - - IndexRangeDictionary _table = new(); - ReaderWriterLockSlim? _lock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionGenericTypeParameterTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionMemberSymbol member) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _member = member; - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) - { - if (genericTypeParameter is null) - throw new ArgumentNullException(nameof(genericTypeParameter)); - if (genericTypeParameter.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(genericTypeParameter)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var pos = genericTypeParameter.GenericParameterPosition; - if (_table[pos] == null) - using (_lock.CreateWriteLock()) - if (genericTypeParameter is GenericTypeParameterBuilder builder) - return _table[pos] ??= new ReflectionGenericTypeParameterSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionMemberSymbolBuilder)_member, builder); - else - return _table[pos] ??= new ReflectionGenericTypeParameterSymbol(_context, _module, _member, genericTypeParameter); - - return _table[pos] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the module. - /// - /// - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return (IReflectionGenericTypeParameterSymbolBuilder)GetOrCreateGenericTypeParameterSymbol((Type)genericTypeParameter); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTypeSymbol.cs new file mode 100644 index 0000000000..8da6146a6a --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionGenericTypeParameterTypeSymbol.cs @@ -0,0 +1,61 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionGenericTypeParameterTypeSymbol : GenericTypeParameterTypeSymbol + { + + readonly Type _underlyingType; + + ImmutableArray _interfaces; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + public ReflectionGenericTypeParameterTypeSymbol(ReflectionSymbolContext context, TypeSymbol declaringType, Type underlyingType) : + base(context, declaringType) + { + _underlyingType = underlyingType ?? throw new ArgumentNullException(nameof(underlyingType)); + } + + /// + /// Gets the context that owns this symbol. + /// + new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; + + /// + public override string? FullName => _underlyingType.FullName; + + /// + public override string? Namespace => _underlyingType.Namespace; + + /// + public override GenericParameterAttributes GenericParameterAttributes => _underlyingType.GenericParameterAttributes; + + /// + public override int GenericParameterPosition => _underlyingType.GenericParameterPosition; + + /// + public override string Name => _underlyingType.Name; + + /// + public override bool IsComplete => true; + + /// + public override ImmutableArray GetInterfaces() + { + if (_interfaces == null) + ImmutableInterlocked.InterlockedInitialize(ref _interfaces, Context.ResolveTypeSymbols(_underlyingType.GetInterfaces())); + + return _interfaces; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs deleted file mode 100644 index c57bc860ba..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMemberSymbol.cs +++ /dev/null @@ -1,238 +0,0 @@ -using System; -using System.Diagnostics.CodeAnalysis; -using System.Linq; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - /// - /// Obtains information about the attributes of a member and provides access to member metadata. - /// - abstract class ReflectionMemberSymbol : ReflectionSymbol, IReflectionMemberSymbol - { - - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol? _type; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionMemberSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : - base(context) - { - _module = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _type = resolvingType; - } - - /// - public abstract MemberInfo UnderlyingMember { get; } - - /// - public abstract MemberInfo UnderlyingRuntimeMember { get; } - - /// - /// Gets the which contains the metadata of this member. - /// - public IReflectionModuleSymbol ResolvingModule => _module; - - /// - /// Gets the which contains the metadata of this member, or null if the member is not a member of a type. - /// - public IReflectionTypeSymbol? ResolvingType => _type; - - /// - [return: NotNullIfNotNull(nameof(type))] - public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) - { - if (type is null) - return null; - - if (type == UnderlyingMember) - return (IReflectionTypeSymbol)this; - - if (_type != null && type == _type.UnderlyingType) - return _type; - - if (type.Module == _module.UnderlyingModule) - return _module.GetOrCreateTypeSymbol(type); - - return base.ResolveTypeSymbol(type); - } - - /// - [return: NotNullIfNotNull(nameof(ctor))] - public override IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) - { - if (ctor is null) - return null; - - if (ctor == UnderlyingMember) - return (IReflectionConstructorSymbol)this; - - if (ctor.Module == _module.UnderlyingModule) - return _module.GetOrCreateConstructorSymbol(ctor); - - return base.ResolveConstructorSymbol(ctor); - } - - /// - [return: NotNullIfNotNull(nameof(method))] - public override IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) - { - if (method is null) - return null; - - if (method == UnderlyingMember) - return (IReflectionMethodSymbol)this; - - if (method.Module == _module.UnderlyingModule) - return _module.GetOrCreateMethodSymbol(method); - - return base.ResolveMethodSymbol(method); - } - - /// - [return: NotNullIfNotNull(nameof(field))] - public override IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) - { - if (field is null) - return null; - - if (field == UnderlyingMember) - return (IReflectionFieldSymbol)this; - - if (field.Module == _module.UnderlyingModule) - return _module.GetOrCreateFieldSymbol(field); - - return base.ResolveFieldSymbol(field); - } - - /// - [return: NotNullIfNotNull(nameof(field))] - public override IReflectionFieldSymbolBuilder? ResolveFieldSymbol(FieldBuilder? field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) - { - if (field is null) - return null; - - if (field == UnderlyingMember) - return (IReflectionFieldSymbolBuilder)this; - - if (field.Module == _module.UnderlyingModule) - return _module.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); - - return base.ResolveFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); - } - - /// - [return: NotNullIfNotNull(nameof(property))] - public override IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) - { - if (property is null) - return null; - - if (property == UnderlyingMember) - return (IReflectionPropertySymbol)this; - - if (property.Module == _module.UnderlyingModule) - return _module.GetOrCreatePropertySymbol(property); - - return base.ResolvePropertySymbol(property); - } - - /// - [return: NotNullIfNotNull(nameof(@event))] - public override IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) - { - if (@event is null) - return null; - - if (@event == UnderlyingMember) - return (IReflectionEventSymbol)this; - - if (@event.Module == _module.UnderlyingModule) - return _module.GetOrCreateEventSymbol(@event); - - return base.ResolveEventSymbol(@event); - } - - /// - [return: NotNullIfNotNull(nameof(parameter))] - public override IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - if (parameter.Member.Module == _module.UnderlyingModule) - return _module.GetOrCreateParameterSymbol(parameter); - - return base.ResolveParameterSymbol(parameter); - } - - #region IMemberSymbol - - /// - public virtual IModuleSymbol Module => ResolveModuleSymbol(UnderlyingMember.Module)!; - - /// - public virtual ITypeSymbol? DeclaringType => ResolveTypeSymbol(UnderlyingMember.DeclaringType)!; - - /// - public virtual MemberTypes MemberType => UnderlyingMember.MemberType; - - /// - public virtual int MetadataToken => UnderlyingMember.GetMetadataTokenSafe(); - - /// - public virtual string Name => UnderlyingMember.Name; - - /// - public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - if (inherit == true) - throw new NotSupportedException(); - - return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData()); - } - - /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - if (inherit == true) - throw new NotSupportedException(); - - var _attribyteType = attributeType.Unpack(); - return ResolveCustomAttributes(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attribyteType).ToArray()); - } - - /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - if (inherit == true) - throw new NotSupportedException(); - - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttribute(UnderlyingMember.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); - } - - /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingMember.IsDefined(attributeType.Unpack(), inherit); - } - - #endregion - - /// - public override string? ToString() => UnderlyingMember.ToString(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs deleted file mode 100644 index d30f9d8a47..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodBaseSymbol.cs +++ /dev/null @@ -1,135 +0,0 @@ -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - abstract class ReflectionMethodBaseSymbol : ReflectionMemberSymbol, IReflectionMethodBaseSymbol - { - - ReflectionParameterTable _parameterTable; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionMethodBaseSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol? resolvingType) : - base(context, resolvingModule, resolvingType) - { - _parameterTable = new ReflectionParameterTable(context, resolvingModule, this); - } - - #region IReflectionMethodBaseSymbol - - /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - return _parameterTable.GetOrCreateParameterSymbol(parameter); - } - - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return _parameterTable.GetOrCreateParameterSymbol(parameter); - } - - #endregion - - #region IMethodBaseSymbol - - /// - public abstract MethodBase UnderlyingMethodBase { get; } - - /// - public abstract MethodBase UnderlyingRuntimeMethodBase { get; } - - /// - public override sealed MemberInfo UnderlyingMember => UnderlyingMethodBase; - - /// - public override sealed MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeMethodBase; - - /// - public virtual System.Reflection.MethodAttributes Attributes => (System.Reflection.MethodAttributes)UnderlyingMethodBase.Attributes; - - /// - public virtual System.Reflection.CallingConventions CallingConvention => (System.Reflection.CallingConventions)UnderlyingMethodBase.CallingConvention; - - /// - public virtual bool ContainsGenericParameters => UnderlyingMethodBase.ContainsGenericParameters; - - /// - public virtual bool IsAbstract => UnderlyingMethodBase.IsAbstract; - - /// - public virtual bool IsAssembly => UnderlyingMethodBase.IsAssembly; - - /// - public virtual bool IsConstructor => UnderlyingMethodBase.IsConstructor; - - /// - public virtual bool IsFamily => UnderlyingMethodBase.IsFamily; - - /// - public virtual bool IsFamilyAndAssembly => UnderlyingMethodBase.IsFamilyAndAssembly; - - /// - public virtual bool IsFamilyOrAssembly => UnderlyingMethodBase.IsFamilyOrAssembly; - - /// - public virtual bool IsFinal => UnderlyingMethodBase.IsFinal; - - /// - public virtual bool IsGenericMethod => UnderlyingMethodBase.IsGenericMethod; - - /// - public virtual bool IsGenericMethodDefinition => UnderlyingMethodBase.IsGenericMethodDefinition; - - /// - public virtual bool IsHideBySig => UnderlyingMethodBase.IsHideBySig; - - /// - public virtual bool IsPrivate => UnderlyingMethodBase.IsPrivate; - - /// - public virtual bool IsPublic => UnderlyingMethodBase.IsPublic; - - /// - public virtual bool IsStatic => UnderlyingMethodBase.IsStatic; - - /// - public virtual bool IsVirtual => UnderlyingMethodBase.IsVirtual; - - /// - public virtual bool IsSpecialName => UnderlyingMethodBase.IsSpecialName; - - /// - public virtual System.Reflection.MethodImplAttributes MethodImplementationFlags => (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.MethodImplementationFlags; - - /// - public virtual ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingMethodBase.GetGenericArguments()); - } - - /// - public virtual System.Reflection.MethodImplAttributes GetMethodImplementationFlags() - { - return (System.Reflection.MethodImplAttributes)UnderlyingMethodBase.GetMethodImplementationFlags(); - } - - /// - public virtual IParameterSymbol[] GetParameters() - { - return ResolveParameterSymbols(UnderlyingMethodBase.GetParameters()); - } - - #endregion - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs deleted file mode 100644 index 63c4da0ece..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSpecTable.cs +++ /dev/null @@ -1,64 +0,0 @@ -using System; -using System.Collections.Concurrent; -using System.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionMethodSpecTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol? _type; - readonly IReflectionMethodSymbol _method; - - ConcurrentDictionary? _genericMethodSymbols; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - /// - public ReflectionMethodSpecTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type, IReflectionMethodSymbol method) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type; - _method = method ?? throw new ArgumentNullException(nameof(method)); - } - - /// - /// Gets or creates a representing a specialized generic of this method. - /// - /// - /// - public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(IReflectionTypeSymbol[] genericTypeArguments) - { - if (genericTypeArguments is null) - throw new ArgumentNullException(nameof(genericTypeArguments)); - - if (_method.IsGenericMethodDefinition == false) - throw new InvalidOperationException(); - - if (_genericMethodSymbols == null) - Interlocked.CompareExchange(ref _genericMethodSymbols, new(TypeSymbolListEqualityComparer.Instance), null); - - return _genericMethodSymbols.GetOrAdd(genericTypeArguments, CreateGenericMethodSymbol); - } - - /// - /// Creates a new representing a specialized generic of this type. - /// - /// - /// - readonly IReflectionMethodSymbol CreateGenericMethodSymbol(IReflectionTypeSymbol[] genericTypeArguments) - { - return new ReflectionMethodSymbol(_context, _module, _type, _method.UnderlyingMethod.MakeGenericMethod(genericTypeArguments.Unpack())); - } - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs index bc75e98a5e..67c0a57083 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodSymbol.cs @@ -1,209 +1,151 @@ using System; +using System.Collections.Immutable; using System.Reflection; -using System.Reflection.Emit; using System.Threading; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; - namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionMethodSymbol : ReflectionMethodBaseSymbol, IReflectionMethodSymbol + class ReflectionMethodSymbol : DefinitionMethodSymbol { - readonly MethodInfo _method; - - ReflectionGenericTypeParameterTable _genericTypeParameterTable; - ReflectionMethodSpecTable _specTable; + readonly MethodInfo _underlyingMethod; - ReflectionParameterSpecInfo[]? _specParameters; - ReflectionParameterSpecInfo? _specReturnParameter; + ImmutableArray _genericArguments; + ReflectionParameterSymbol? _returnParameter; + TypeSymbol? _returnType; + MethodSymbol? _baseDefinition; + MethodSymbol? _genericMethodDefinition; + ImmutableArray _parameters; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// /// - /// - /// - public ReflectionMethodSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type, MethodInfo method) : - base(context, module, type) + /// + /// + public ReflectionMethodSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, ReflectionTypeSymbol? declaringType, MethodInfo underlyingMethod) : + base(context, module, declaringType) { - _method = method ?? throw new ArgumentNullException(nameof(method)); - _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, module, this); - _specTable = new ReflectionMethodSpecTable(context, module, type, this); + _underlyingMethod = underlyingMethod ?? throw new ArgumentNullException(nameof(underlyingMethod)); } + /// + /// Gets the context that owns this symbol. + /// + new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; + /// - public virtual MethodInfo UnderlyingMethod => _method; + public override string Name => _underlyingMethod.Name; /// - public virtual MethodInfo UnderlyingRuntimeMethod => GetUnderlyingRuntimeMethod(); + public override ParameterSymbol ReturnParameter => GetReturnParameter(); /// - /// Gets the underlying runtime method. + /// Gets the value for ; /// /// - MethodInfo GetUnderlyingRuntimeMethod() - { - if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) - return GetUnderlyingRuntimeMethodForMethodOnTypeBuilderInstantiation(); - else if (ReflectionExtensions.MethodBuilderInstantiationType.IsInstanceOfType(_method)) - return GetUnderlyingRuntimeMethodForMethodBuilderInstantiationType(); - else - return _method; - } - - MethodInfo GetUnderlyingRuntimeMethodForMethodOnTypeBuilderInstantiation() + ParameterSymbol GetReturnParameter() { - return _method; - } + if (_returnParameter == null) + Interlocked.CompareExchange(ref _returnParameter, new ReflectionParameterSymbol(Context, this, _underlyingMethod.ReturnParameter), null); - MethodInfo GetUnderlyingRuntimeMethodForMethodBuilderInstantiationType() - { - return _method; + return _returnParameter; } /// - public override MethodBase UnderlyingMethodBase => UnderlyingMethod; + public override MethodAttributes Attributes => _underlyingMethod.Attributes; /// - public override MethodBase UnderlyingRuntimeMethodBase => UnderlyingRuntimeMethod; - - #region IReflectionMethodSymbol + public override CallingConventions CallingConvention => _underlyingMethod.CallingConvention; /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericTypeParameter) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } + public override bool ContainsGenericParameters => _underlyingMethod.ContainsGenericParameters; /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } + public override bool IsGenericMethod => _underlyingMethod.IsGenericMethod; /// - public IReflectionMethodSymbol GetOrCreateGenericMethodSymbol(MethodInfo method) - { - return _specTable.GetOrCreateGenericMethodSymbol(ResolveTypeSymbols(method.GetGenericArguments())); - } - - #endregion - - #region IMethodSymbol + public override bool IsGenericMethodDefinition => _underlyingMethod.IsGenericMethodDefinition; /// - public IParameterSymbol ReturnParameter => GetReturnParameter(); + public override MethodImplAttributes MethodImplementationFlags => _underlyingMethod.MethodImplementationFlags; - /// - /// Gets the return type of the method. - /// - /// - IParameterSymbol GetReturnParameter() - { - if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) - return GetReturnParameterForMethodOnTypeBuilderInstantiation(); - else if (IsComplete) - return ResolveParameterSymbol(UnderlyingRuntimeMethod.ReturnParameter); - else - return ResolveParameterSymbol(UnderlyingMethod.ReturnParameter); - } + /// + public override TypeSymbol ReturnType => _returnType ??= Context.ResolveTypeSymbol(_underlyingMethod.ReturnType); - /// - /// Gets the return parameter in the case that this method is a . - /// - /// - IParameterSymbol GetReturnParameterForMethodOnTypeBuilderInstantiation() - { - if (_specReturnParameter == null) - Interlocked.CompareExchange(ref _specReturnParameter, new ReflectionParameterSpecInfo(_method, _method.ReturnParameter, _method.DeclaringType!.GetGenericArguments()), null); + /// + public override ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); - return ResolveParameterSymbol(_specReturnParameter); - } + /// + public override bool IsMissing => false; /// - public ITypeSymbol ReturnType => GetReturnType(); + public override bool ContainsMissing => false; - /// - /// Gets the return type of the method. - /// - /// - ITypeSymbol GetReturnType() - { - if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) - return GetReturnTypeForMethodOnTypeBuilderInstantiation(); - else - return ResolveTypeSymbol(UnderlyingMethod.ReturnType); - } + /// + public override bool IsComplete => true; - /// - /// Gets the return type in the case that this method is a . - /// - /// - ITypeSymbol GetReturnTypeForMethodOnTypeBuilderInstantiation() + /// + public override MethodImplAttributes GetMethodImplementationFlags() { - return ResolveTypeSymbol(_method.ReturnType.SubstituteGenericTypes(_method.DeclaringType!.GetGenericArguments())); + return _underlyingMethod.GetMethodImplementationFlags(); } /// - public ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); - - /// - public IMethodSymbol GetBaseDefinition() + public override MethodSymbol GetBaseDefinition() { - return ResolveMethodSymbol(UnderlyingMethod.GetBaseDefinition()); + return _baseDefinition ??= Context.ResolveMethodSymbol(_underlyingMethod.GetBaseDefinition()); } /// - public IMethodSymbol GetGenericMethodDefinition() + public override MethodSymbol GetGenericMethodDefinition() { - return ResolveMethodSymbol(UnderlyingMethod.GetGenericMethodDefinition()); + return _genericMethodDefinition ??= Context.ResolveMethodSymbol(_underlyingMethod.GetGenericMethodDefinition()); } /// - public override IParameterSymbol[] GetParameters() + public override ImmutableArray GetGenericArguments() { - if (ReflectionExtensions.MethodOnTypeBuilderInstantiationType.IsInstanceOfType(_method)) - return GetParametersForMethodOnTypeBuilderInstantiation(); - else - return base.GetParameters(); + if (_genericArguments == default) + { + var l = _underlyingMethod.GetGenericArguments(); + var b = ImmutableArray.CreateBuilder(); + for (int i = 0; i < l.Length; i++) + b.Add(new ReflectionGenericMethodParameterTypeSymbol(Context, this, l[i])); + + ImmutableInterlocked.InterlockedInitialize(ref _genericArguments, b.ToImmutable()); + } + + return _genericArguments; } - /// - /// Gets the parameters in the case that this method is a . - /// - /// - IParameterSymbol[] GetParametersForMethodOnTypeBuilderInstantiation() + /// + public override ImmutableArray GetParameters() { - // we cache the spec parameters to avoid creating them repeatidly - if (_specParameters == null) + if (_parameters == default) { - var l = _method.GetParameters(); - var a = new ReflectionParameterSpecInfo[l.Length]; + var l = _underlyingMethod.GetParameters(); + var b = ImmutableArray.CreateBuilder(); for (int i = 0; i < l.Length; i++) - a[i] = new ReflectionParameterSpecInfo(_method, l[i], _method.DeclaringType!.GetGenericArguments()); + b.Add(new ReflectionParameterSymbol(Context, this, l[i])); - Interlocked.CompareExchange(ref _specParameters, a, null); + ImmutableInterlocked.InterlockedInitialize(ref _parameters, b.ToImmutable()); } - // resolve into symbols - var symbols = new IParameterSymbol[_specParameters.Length]; - for (int i = 0; i < _specParameters.Length; i++) - symbols[i] = ResolveParameterSymbol(_specParameters[i]); - - return symbols; + return _parameters; } /// - public IMethodSymbol MakeGenericMethod(params ITypeSymbol[] typeArguments) + internal override ImmutableArray GetDeclaredCustomAttributes() { - return ResolveMethodSymbol(UnderlyingMethod.MakeGenericMethod(typeArguments.Unpack())); - } + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingMethod.GetCustomAttributesData())); - #endregion + return _customAttributes; + } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs deleted file mode 100644 index 47fde2273c..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionMethodTable.cs +++ /dev/null @@ -1,141 +0,0 @@ -using System; -using System.Diagnostics.Eventing.Reader; -using System.Reflection; -using System.Reflection.Emit; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionMethodTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol? _type; - - IndexRangeDictionary _table = new(); - ReaderWriterLockSlim? _lock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionMethodTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type; - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - if (method.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(method)); - if (method is MethodInfo m_ && m_.IsMethodDefinition() == false) - throw new ArgumentException(nameof(method)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var row = method.GetMetadataTokenRowNumberSafe(); - if (_table[row] == null) - using (_lock.CreateWriteLock()) - return _table[row] ??= CreateMethodBaseSymbol(_context, _module, _type, method); - - return _table[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Creates a new symbol. - /// - /// - /// - /// - static IReflectionMethodBaseSymbol CreateMethodBaseSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type, MethodBase method) - { - if (method is ConstructorInfo c) - { - if (type == null) - throw new InvalidOperationException(); - - if (method is ConstructorBuilder builder) - return new ReflectionConstructorSymbolBuilder(context, (IReflectionModuleSymbolBuilder)module, (IReflectionTypeSymbolBuilder)type, builder); - else - return new ReflectionConstructorSymbol(context, module, type, c); - } - else if (method is MethodInfo m) - { - if (method is MethodBuilder builder) - return new ReflectionMethodSymbolBuilder(context, (IReflectionModuleSymbolBuilder)module, (IReflectionTypeSymbolBuilder?)type, builder); - else - return new ReflectionMethodSymbol(context, module, type, m); - } - else - { - throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return (IReflectionConstructorSymbol)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return (IReflectionConstructorSymbolBuilder)GetOrCreateMethodBaseSymbol(ctor); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - return (IReflectionMethodSymbol)GetOrCreateMethodBaseSymbol(method); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return (IReflectionMethodSymbolBuilder)GetOrCreateMethodBaseSymbol(method); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs index fcac53de7e..66018baa9e 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleSymbol.cs @@ -1,397 +1,116 @@ using System; -using System.Linq; +using System.Collections.Immutable; using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; +using System.Threading; namespace IKVM.CoreLib.Symbols.Reflection { - /// - /// Implementation of derived from System.Reflection. - /// - class ReflectionModuleSymbol : ReflectionSymbol, IReflectionModuleSymbol + class ReflectionModuleSymbol : ModuleSymbol { - readonly IReflectionAssemblySymbol _resolvingAssembly; - readonly Module _module; + readonly Module _underlyingModule; - ReflectionTypeTable _typeTable; - ReflectionMethodTable _methodTable; - ReflectionFieldTable _fieldTable; + ImmutableArray _fields; + ImmutableArray _methods; + ImmutableArray _types; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// - /// + /// /// - /// - public ReflectionModuleSymbol(ReflectionSymbolContext context, IReflectionAssemblySymbol resolvingAssembly, Module module) : - base(context) - { - _resolvingAssembly = resolvingAssembly ?? throw new ArgumentNullException(nameof(resolvingAssembly)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - - _typeTable = new ReflectionTypeTable(context, this, null); - _methodTable = new ReflectionMethodTable(context, this, null); - _fieldTable = new ReflectionFieldTable(context, this, null); - } - - /// - public virtual Module UnderlyingModule => _module; - - /// - public virtual Module UnderlyingRuntimeModule => _module; - - /// - public IReflectionAssemblySymbol ResolvingAssembly => _resolvingAssembly; - - #region IModuleSymbol - - /// - public IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingModule.Assembly); - - /// - public string FullyQualifiedName => UnderlyingModule.FullyQualifiedName; - - /// - public int MetadataToken => UnderlyingModule.MetadataToken; - - /// - public Guid ModuleVersionId => UnderlyingModule.ModuleVersionId; - - /// - public string Name => UnderlyingModule.Name; - - /// - public string ScopeName => UnderlyingModule.ScopeName; - - /// - public IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingModule.GetField(name)); - } - - /// - public IFieldSymbol? GetField(string name, BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingModule.GetField(name, bindingAttr)); - } - - /// - public IFieldSymbol[] GetFields(BindingFlags bindingFlags) + public ReflectionModuleSymbol(ReflectionSymbolContext context, ReflectionAssemblySymbol assembly, Module module) : + base(context, assembly) { - return ResolveFieldSymbols(UnderlyingModule.GetFields(bindingFlags))!; + _underlyingModule = module ?? throw new ArgumentNullException(nameof(module)); } - /// - public IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingModule.GetFields())!; - } - - /// - public IMethodSymbol? GetMethod(string name) - { - return ResolveMethodSymbol(UnderlyingModule.GetMethod(name)); - } - - /// - public IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, types.Unpack())); - } - - /// - public IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingModule.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers)); - } - - /// - public IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(UnderlyingModule.GetMethods())!; - } - - /// - public IMethodSymbol[] GetMethods(BindingFlags bindingFlags) - { - return ResolveMethodSymbols(UnderlyingModule.GetMethods(bindingFlags))!; - } - - /// - public ITypeSymbol? GetType(string className) - { - return ResolveTypeSymbol(UnderlyingModule.GetType(className)); - } - - /// - public ITypeSymbol? GetType(string className, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingModule.GetType(className, ignoreCase)); - } - - /// - public ITypeSymbol? GetType(string className, bool throwOnError, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingModule.GetType(className, throwOnError, ignoreCase)); - } - - /// - public ITypeSymbol[] GetTypes() - { - return ResolveTypeSymbols(UnderlyingModule.GetTypes())!; - } - - /// - public bool IsResource() - { - return UnderlyingModule.IsResource(); - } - - /// - public IFieldSymbol? ResolveField(int metadataToken) - { - return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken)); - } - - /// - public IFieldSymbol? ResolveField(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveFieldSymbol(UnderlyingModule.ResolveField(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public IMemberSymbol? ResolveMember(int metadataToken) - { - return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken)); - } - - /// - public IMemberSymbol? ResolveMember(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveMemberSymbol(UnderlyingModule.ResolveMember(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public IMethodBaseSymbol? ResolveMethod(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public IMethodBaseSymbol? ResolveMethod(int metadataToken) - { - return ResolveMethodBaseSymbol(UnderlyingModule.ResolveMethod(metadataToken)); - } - - /// - public byte[] ResolveSignature(int metadataToken) - { - return UnderlyingModule.ResolveSignature(metadataToken); - } - - /// - public string ResolveString(int metadataToken) - { - return UnderlyingModule.ResolveString(metadataToken); - } - - /// - public ITypeSymbol ResolveType(int metadataToken) - { - return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken)); - } - - /// - public ITypeSymbol ResolveType(int metadataToken, ITypeSymbol[]? genericTypeArguments, ITypeSymbol[]? genericMethodArguments) - { - return ResolveTypeSymbol(UnderlyingModule.ResolveType(metadataToken, genericTypeArguments?.Unpack(), genericMethodArguments?.Unpack())); - } - - /// - public CustomAttribute[] GetCustomAttributes(bool inherit = false) - { - return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData()); - } - - /// - public CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttributes(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).ToArray()); - } - - /// - public CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) - { - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttribute(UnderlyingModule.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); - } + /// + /// Gets the context that owns this symbol. + /// + new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; /// - public bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingModule.IsDefined(attributeType.Unpack(), false); - } - - #endregion - - #region IReflectionModuleSymbol + public sealed override string FullyQualifiedName => _underlyingModule.FullyQualifiedName; /// - public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - if (type.IsTypeDefinition()) - return _typeTable.GetOrCreateTypeSymbol(type); - else if (type.IsGenericType) - return ResolveTypeSymbol(type.GetGenericTypeDefinition()).GetOrCreateGenericTypeSymbol(ResolveTypeSymbols(type.GetGenericArguments())); - else if (type.IsSZArray()) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateSZArrayTypeSymbol(); - else if (type.IsArray) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateArrayTypeSymbol(type.GetArrayRank()); - else if (type.IsPointer) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreatePointerTypeSymbol(); - else if (type.IsByRef) - return ResolveTypeSymbol(type.GetElementType()!).GetOrCreateByRefTypeSymbol(); - else if (type.IsGenericParameter && type.DeclaringMethod is MethodInfo dm) - return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(type); - else if (type.IsGenericParameter && type.DeclaringType is Type t) - return ResolveTypeSymbol(t).GetOrCreateGenericTypeParameterSymbol(type); - - throw new InvalidOperationException(); - } + public sealed override string Name => _underlyingModule.Name; /// - public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) - { - if (type.IsTypeDefinition()) - return (IReflectionTypeSymbolBuilder)_typeTable.GetOrCreateTypeSymbol(type); - - throw new InvalidOperationException(); - } + public sealed override bool IsMissing => false; /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method.DeclaringType is { } dt) - return ResolveTypeSymbol(dt).GetOrCreateMethodBaseSymbol(method); - else - return _methodTable.GetOrCreateMethodBaseSymbol(method); - } + public sealed override bool ContainsMissing => false; /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return ResolveTypeSymbol(ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); - } + public sealed override bool IsComplete => true; /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + internal sealed override ImmutableArray GetDeclaredFields() { - return ResolveTypeSymbol((TypeBuilder)ctor.DeclaringType!).GetOrCreateConstructorSymbol(ctor); - } + if (_fields == default) + { + var l = _underlyingModule.GetFields(DeclaredOnlyLookup); + var b = ImmutableArray.CreateBuilder(); + for (int i = 0; i < l.Length; i++) + b.Add(new ReflectionFieldSymbol(Context, this, null, l[i])); - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - if (method.DeclaringType is { } dt) - return ResolveTypeSymbol(dt).GetOrCreateMethodSymbol(method); - else - return _methodTable.GetOrCreateMethodSymbol(method); - } + ImmutableInterlocked.InterlockedInitialize(ref _fields, b.ToImmutable()); + } - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - if (method.DeclaringType is { } dt) - return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateMethodSymbol(method); - else - return _methodTable.GetOrCreateMethodSymbol(method); + return _fields; } /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + internal sealed override ImmutableArray GetDeclaredMethods() { - if (field.DeclaringType is { } dt) - return ResolveTypeSymbol(dt).GetOrCreateFieldSymbol(field); - else - return _fieldTable.GetOrCreateFieldSymbol(field, ResolveTypeSymbols(field.GetRequiredCustomModifiers()), ResolveTypeSymbols(field.GetOptionalCustomModifiers())); - } + if (_methods == default) + { + var l = _underlyingModule.GetMethods(DeclaredOnlyLookup); + var b = ImmutableArray.CreateBuilder(); + for (int i = 0; i < l.Length; i++) + b.Add(new ReflectionMethodSymbol(Context, this, null, l[i])); - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) - { - if (field.DeclaringType is { } dt) - return ResolveTypeSymbol((TypeBuilder)dt).GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); - else - return _fieldTable.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); - } + ImmutableInterlocked.InterlockedInitialize(ref _methods, b.ToImmutable()); + } - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return ResolveTypeSymbol(property.DeclaringType!).GetOrCreatePropertySymbol(property); + return _methods; } /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + internal sealed override ImmutableArray GetDeclaredTypes() { - return ResolveTypeSymbol(property.GetTypeBuilder()).GetOrCreatePropertySymbol(property); - } + if (_types == default) + { + var l = _underlyingModule.GetTypes(); + var b = ImmutableArray.CreateBuilder(); + for (int i = 0; i < l.Length; i++) + b.Add(new ReflectionTypeSymbol(Context, this, l[i])); - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return ResolveTypeSymbol(@event.DeclaringType!).GetOrCreateEventSymbol(@event); - } + ImmutableInterlocked.InterlockedInitialize(ref _types, b.ToImmutable()); + } - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return ResolveTypeSymbol(@event.GetTypeBuilder()).GetOrCreateEventSymbol(@event); + return _types; } /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + public sealed override bool IsResource() { - return ResolveMemberSymbol(parameter.Member) switch - { - IReflectionMethodBaseSymbol method => method.GetOrCreateParameterSymbol(parameter), - IReflectionPropertySymbol property => property.GetOrCreateParameterSymbol(parameter), - _ => throw new InvalidOperationException(), - }; + return _underlyingModule.IsResource(); } /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(IReflectionMemberSymbolBuilder member, ParameterBuilder parameter) + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return member switch - { - IReflectionMethodBaseSymbolBuilder method => method.GetOrCreateParameterSymbol(parameter), - IReflectionPropertySymbolBuilder property => property.GetOrCreateParameterSymbol(parameter), - _ => throw new InvalidOperationException(), - }; - } + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingModule.GetCustomAttributesData())); - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericParameterType) - { - if (genericParameterType.DeclaringMethod is MethodBuilder dm) - return ResolveMethodSymbol(dm).GetOrCreateGenericTypeParameterSymbol(genericParameterType); - else - return ResolveTypeSymbol((TypeBuilder)genericParameterType.DeclaringType!).GetOrCreateGenericTypeParameterSymbol(genericParameterType); + return _customAttributes; } - #endregion - - /// - public override string? ToString() => UnderlyingModule.ToString(); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs index 951bb374bd..c9a86de3c5 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs @@ -5,7 +5,6 @@ using IKVM.CoreLib.Collections; using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; using IKVM.CoreLib.Threading; namespace IKVM.CoreLib.Symbols.Reflection @@ -15,9 +14,9 @@ struct ReflectionModuleTable { readonly ReflectionSymbolContext _context; - readonly IReflectionAssemblySymbol _assembly; + readonly ReflectionAssemblySymbol _assembly; - IndexRangeDictionary _moduleSymbols = new(); + IndexRangeDictionary _moduleSymbols = new(); ReaderWriterLockSlim? _moduleLock; /// @@ -25,21 +24,23 @@ struct ReflectionModuleTable /// /// /// - public ReflectionModuleTable(ReflectionSymbolContext context, IReflectionAssemblySymbol assembly) + public ReflectionModuleTable(ReflectionSymbolContext context, ReflectionAssemblySymbol assembly) { _context = context ?? throw new ArgumentNullException(nameof(context)); _assembly = assembly ?? throw new ArgumentNullException(nameof(assembly)); } /// - /// Gets or creates the cached for the module. + /// Gets or creates the cached for the module. /// /// /// - public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + public ReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) { if (module is null) throw new ArgumentNullException(nameof(module)); + if (module is ModuleBuilder) + throw new ArgumentException(nameof(module)); // create lock on demand if (_moduleLock == null) @@ -50,11 +51,8 @@ public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) var row = module.GetMetadataTokenRowNumberSafe(); if (_moduleSymbols[row] == null) using (_moduleLock.CreateWriteLock()) - if (module is ModuleBuilder builder) - return _moduleSymbols[row] = new ReflectionModuleSymbolBuilder(_context, _assembly, builder); - else - return _moduleSymbols[row] = new ReflectionModuleSymbol(_context, _assembly, module); - + return _moduleSymbols[row] = new ReflectionModuleSymbol(_context, _assembly, module); + return _moduleSymbols[row] ?? throw new InvalidOperationException(); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs deleted file mode 100644 index 42bc91d6bf..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSpecInfo.cs +++ /dev/null @@ -1,51 +0,0 @@ -using System; -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - /// - /// Fake implementation that is used for instantiated method parameters. - /// - class ReflectionParameterSpecInfo : ParameterInfo - { - - readonly MemberInfo _member; - readonly ParameterInfo _parameter; - readonly Type[] _genericTypeArguments; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionParameterSpecInfo(MemberInfo member, ParameterInfo parameter, Type[] genericTypeArguments) - { - _member = member ?? throw new ArgumentNullException(nameof(member)); - _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); - _genericTypeArguments = genericTypeArguments ?? throw new ArgumentNullException(nameof(genericTypeArguments)); - } - - /// - public override ParameterAttributes Attributes => (ParameterAttributes)_parameter.Attributes; - - /// - public override MemberInfo Member => _member; - - /// - public override string? Name => _parameter.Name; - - /// - public override int Position => _parameter.Position; - - /// - public override int MetadataToken => throw new InvalidOperationException(); - - /// - public override Type ParameterType => _parameter.ParameterType.SubstituteGenericTypes(_genericTypeArguments); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs index ff2e53811a..5d3300176f 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterSymbol.cs @@ -1,137 +1,85 @@ using System; -using System.Linq; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionParameterSymbol : ReflectionSymbol, IReflectionParameterSymbol + class ReflectionParameterSymbol : DefinitionParameterSymbol { - readonly IReflectionModuleSymbol _resolvingModule; - readonly IReflectionMemberSymbol _resolvingMember; - readonly ParameterInfo _parameter; + readonly ParameterInfo _underlyingParameter; + + TypeSymbol? _parameterType; + ImmutableArray _optionalCustomModifiers; + ImmutableArray _requiredCustomModifiers; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// - /// - /// - /// - public ReflectionParameterSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionMemberSymbol? resolvingMember, ParameterInfo parameter) : - base(context) + /// + /// + public ReflectionParameterSymbol(ReflectionSymbolContext context, MemberSymbol declaringMember, ParameterInfo underlyingParameter) : + base(context, declaringMember, underlyingParameter.Position) { - _resolvingModule = resolvingModule ?? throw new ArgumentNullException(nameof(resolvingModule)); - _resolvingMember = resolvingMember ?? throw new ArgumentNullException(nameof(resolvingMember)); - _parameter = parameter ?? throw new ArgumentNullException(nameof(parameter)); + _underlyingParameter = underlyingParameter ?? throw new ArgumentNullException(nameof(underlyingParameter)); } - /// - public IReflectionModuleSymbol ResolvingModule => _resolvingModule; - - /// - public IReflectionMemberSymbol ResolvingMember => _resolvingMember; - - /// - public ParameterInfo UnderlyingParameter => _parameter; - - /// - public ParameterInfo UnderlyingRuntimeParameter => UnderlyingParameter; - - #region IParameterSymbol - - /// - public System.Reflection.ParameterAttributes Attributes => (System.Reflection.ParameterAttributes)UnderlyingParameter.Attributes; - - /// - public object? DefaultValue => UnderlyingParameter.RawDefaultValue; - - /// - public bool HasDefaultValue => UnderlyingParameter.HasDefaultValue; - - /// - public bool IsIn => UnderlyingParameter.IsIn; - - /// - public bool IsLcid => UnderlyingParameter.IsLcid; - - /// - public bool IsOptional => UnderlyingParameter.IsOptional; + /// + /// Gets the context that owns this parameter. + /// + new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; /// - public bool IsOut => UnderlyingParameter.IsOut; + public override ParameterAttributes Attributes => _underlyingParameter.Attributes; /// - public bool IsRetval => UnderlyingParameter.IsRetval; + public override TypeSymbol ParameterType => _parameterType ??= Context.ResolveTypeSymbol(_underlyingParameter.ParameterType); /// - public IMemberSymbol Member => ResolveMemberSymbol(UnderlyingParameter.Member); + public override string? Name => _underlyingParameter.Name; /// - public int MetadataToken => UnderlyingParameter.MetadataToken; + public override object? DefaultValue => _underlyingParameter.DefaultValue; /// - public string? Name => UnderlyingParameter.Name; + public override bool IsMissing => false; /// - public ITypeSymbol ParameterType => ResolveTypeSymbol(UnderlyingParameter.ParameterType); + public override bool ContainsMissing => false; /// - public int Position => UnderlyingParameter.Position; + public override bool IsComplete => true; /// - public virtual CustomAttribute[] GetCustomAttributes(bool inherit = false) + public override ImmutableArray GetOptionalCustomModifiers() { - if (inherit == true) - throw new NotSupportedException(); + if (_optionalCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, Context.ResolveTypeSymbols(_underlyingParameter.GetOptionalCustomModifiers())); - return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData()); + return _optionalCustomModifiers; } /// - public virtual CustomAttribute[] GetCustomAttributes(ITypeSymbol attributeType, bool inherit = false) + public override ImmutableArray GetRequiredCustomModifiers() { - if (inherit == true) - throw new NotSupportedException(); + if (_requiredCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, Context.ResolveTypeSymbols(_underlyingParameter.GetRequiredCustomModifiers())); - var _attribyteType = attributeType.Unpack(); - return ResolveCustomAttributes(UnderlyingParameter.GetCustomAttributesData().Where(i => i.AttributeType == _attribyteType).ToArray()); + return _requiredCustomModifiers; } /// - public virtual CustomAttribute? GetCustomAttribute(ITypeSymbol attributeType, bool inherit = false) + internal override ImmutableArray GetDeclaredCustomAttributes() { - if (inherit == true) - throw new NotSupportedException(); - - var _attributeType = attributeType.Unpack(); - return ResolveCustomAttribute(UnderlyingParameter.GetCustomAttributesData().Where(i => i.AttributeType == _attributeType).FirstOrDefault()); - } + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingParameter.GetCustomAttributesData())); - /// - public virtual bool IsDefined(ITypeSymbol attributeType, bool inherit = false) - { - return UnderlyingParameter.IsDefined(attributeType.Unpack(), inherit); + return _customAttributes; } - /// - public ITypeSymbol[] GetOptionalCustomModifiers() - { - return ResolveTypeSymbols(UnderlyingParameter.GetOptionalCustomModifiers()); - } - - /// - public ITypeSymbol[] GetRequiredCustomModifiers() - { - return ResolveTypeSymbols(UnderlyingParameter.GetRequiredCustomModifiers()); - } - - #endregion - - /// - public override string? ToString() => UnderlyingParameter.ToString(); - } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs deleted file mode 100644 index b4d03c1d69..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionParameterTable.cs +++ /dev/null @@ -1,98 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionParameterTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionMemberSymbol _member; - - IndexRangeDictionary _table = new(); - ReaderWriterLockSlim? _lock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionParameterTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionMemberSymbol member) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _member = member ?? throw new ArgumentNullException(nameof(member)); - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - if (parameter.Member.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(parameter)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var position = parameter.Position; - if (_table[position] == null) - using (_lock.CreateWriteLock()) - _table[position] ??= new ReflectionParameterSymbol(_context, _module, _member, parameter); - - var item = _table[position] ?? throw new InvalidOperationException(); - if (item.IsComplete == false && item is IReflectionParameterSymbolBuilder builder) - builder.OnComplete(parameter); - - return item; - } - } - - /// - /// Gets or creates the cached for the type by method. - /// - /// - /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - if (parameter.GetMethodBuilder().Module != _module.UnderlyingModule) - throw new ArgumentException(nameof(parameter)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var position = parameter.Position - 1; - if (_table[position] == null) - using (_lock.CreateWriteLock()) - _table[position] ??= new ReflectionParameterSymbolBuilder(_context, _module, (IReflectionMethodBaseSymbol)_member, parameter); - - return (IReflectionParameterSymbolBuilder?)_table[position] ?? throw new InvalidOperationException(); - } - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs deleted file mode 100644 index fa959d0ba3..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPointerTypeSymbol.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionPointerTypeSymbol : ReflectionTypeSpecSymbol - { - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionPointerTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : - base(context, resolvingModule, elementType) - { - - } - - /// - public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakePointerType(); - - /// - public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakePointerType(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs index fab3b8cde1..82c24c1251 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertySymbol.cs @@ -1,152 +1,160 @@ using System; +using System.Collections.Immutable; using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { - class ReflectionPropertySymbol : ReflectionMemberSymbol, IReflectionPropertySymbol + class ReflectionPropertySymbol : PropertySymbol { - readonly PropertyInfo _property; + readonly PropertyInfo _underlyingProperty; - ReflectionParameterTable _parameterTable; + TypeSymbol? _propertyType; + MethodSymbol? _getMethod; + MethodSymbol? _nonPublicGetMethod; + MethodSymbol? _setMethod; + MethodSymbol? _nonPublicSetMethod; + ImmutableArray _accessors; + ImmutableArray _nonPublicAccessors; + ImmutableArray _indexParameters; + ImmutableArray _optionalCustomModifiers; + ImmutableArray _requiredCustomModifiers; + ImmutableArray _customAttributes; /// /// Initializes a new instance. /// /// - /// - /// - /// - public ReflectionPropertySymbol(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol type, PropertyInfo property) : - base(context, module, type) + /// + /// + public ReflectionPropertySymbol(ReflectionSymbolContext context, ReflectionTypeSymbol declaringType, PropertyInfo underlyingProperty) : + base(context, declaringType) { - _property = property ?? throw new ArgumentNullException(nameof(property)); - _parameterTable = new ReflectionParameterTable(context, module, this); + _underlyingProperty = underlyingProperty ?? throw new ArgumentNullException(nameof(underlyingProperty)); } - /// - public virtual PropertyInfo UnderlyingProperty => _property; - - /// - public virtual PropertyInfo UnderlyingRuntimeProperty => UnderlyingProperty; - - /// - public override MemberInfo UnderlyingMember => UnderlyingProperty; + /// + /// Gets the context that owns this parameter. + /// + new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; /// - public override MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeProperty; - - #region IReflectionPropertySymbol + public override PropertyAttributes Attributes => _underlyingProperty.Attributes; /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) - { - return _parameterTable.GetOrCreateParameterSymbol(parameter); - } + public override TypeSymbol PropertyType => _propertyType ??= Context.ResolveTypeSymbol(_underlyingProperty.PropertyType); /// - public IReflectionParameterSymbolBuilder GetOrCreateParameterSymbol(ParameterBuilder parameter) - { - return _parameterTable.GetOrCreateParameterSymbol(parameter); - } - - #endregion - - #region IPropertySymbol + public override bool CanRead => _underlyingProperty.CanRead; /// - public System.Reflection.PropertyAttributes Attributes => (System.Reflection.PropertyAttributes)UnderlyingProperty.Attributes; + public override bool CanWrite => _underlyingProperty.CanWrite; /// - public bool CanRead => UnderlyingProperty.CanRead; + public override string Name => _underlyingProperty.Name; /// - public bool CanWrite => UnderlyingProperty.CanWrite; + public override bool IsMissing => false; /// - public bool IsSpecialName => UnderlyingProperty.IsSpecialName; + public override bool ContainsMissing => false; /// - public ITypeSymbol PropertyType => ResolveTypeSymbol(UnderlyingProperty.PropertyType); + public override bool IsComplete => false; /// - public IMethodSymbol? GetMethod => ResolveMethodSymbol(UnderlyingProperty.GetMethod); - - /// - public IMethodSymbol? SetMethod => ResolveMethodSymbol(UnderlyingProperty.SetMethod); - - /// - public object? GetRawConstantValue() + public override MethodSymbol? GetGetMethod(bool nonPublic) { - return UnderlyingProperty.GetRawConstantValue(); + if (nonPublic) + return _nonPublicGetMethod ??= Context.ResolveMethodSymbol(_underlyingProperty.GetGetMethod(true)); + else + return _getMethod ??= Context.ResolveMethodSymbol(_underlyingProperty.GetGetMethod(false)); } /// - public IMethodSymbol[] GetAccessors() + public override MethodSymbol? GetSetMethod(bool nonPublic) { - return ResolveMethodSymbols(UnderlyingProperty.GetAccessors()); + if (nonPublic) + return _nonPublicSetMethod ??= Context.ResolveMethodSymbol(_underlyingProperty.GetSetMethod(true)); + else + return _setMethod ??= Context.ResolveMethodSymbol(_underlyingProperty.GetSetMethod(false)); } /// - public IMethodSymbol[] GetAccessors(bool nonPublic) + public override ImmutableArray GetAccessors(bool nonPublic) { - return ResolveMethodSymbols(UnderlyingProperty.GetAccessors(nonPublic)); + if (nonPublic) + { + if (_nonPublicAccessors == default) + ImmutableInterlocked.InterlockedInitialize(ref _nonPublicAccessors, Context.ResolveMethodSymbols(_underlyingProperty.GetAccessors(true))); + + return _nonPublicAccessors; + } + else + { + if (_accessors == default) + ImmutableInterlocked.InterlockedInitialize(ref _accessors, Context.ResolveMethodSymbols(_underlyingProperty.GetAccessors(false))); + + return _accessors; + } } /// - public IParameterSymbol[] GetIndexParameters() + public override ImmutableArray GetIndexParameters() { - return ResolveParameterSymbols(UnderlyingProperty.GetIndexParameters()); - } + if (_indexParameters == default) + { + var l = _underlyingProperty.GetIndexParameters(); + var b = ImmutableArray.CreateBuilder(); + for (int i = 0; i < l.Length; i++) + b.Add(new ReflectionParameterSymbol(Context, this, l[i])); - /// - public IMethodSymbol? GetGetMethod() - { - return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod()); - } + ImmutableInterlocked.InterlockedInitialize(ref _indexParameters, b.ToImmutable()); + } - /// - public IMethodSymbol? GetGetMethod(bool nonPublic) - { - return ResolveMethodSymbol(UnderlyingProperty.GetGetMethod(nonPublic)); + return _indexParameters; } /// - public IMethodSymbol? GetSetMethod() + public override object? GetRawConstantValue() { - return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod()); + return _underlyingProperty.GetRawConstantValue(); } /// - public IMethodSymbol? GetSetMethod(bool nonPublic) + public override TypeSymbol GetModifiedPropertyType() { - return ResolveMethodSymbol(UnderlyingProperty.GetSetMethod(nonPublic)); + throw new NotImplementedException(); } /// - public ITypeSymbol GetModifiedPropertyType() + public override ImmutableArray GetOptionalCustomModifiers() { - throw new NotImplementedException(); + if (_optionalCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, Context.ResolveTypeSymbols(_underlyingProperty.GetOptionalCustomModifiers())); + + return _optionalCustomModifiers; } /// - public ITypeSymbol[] GetOptionalCustomModifiers() + public override ImmutableArray GetRequiredCustomModifiers() { - return ResolveTypeSymbols(UnderlyingProperty.GetOptionalCustomModifiers()); + if (_requiredCustomModifiers == default) + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, Context.ResolveTypeSymbols(_underlyingProperty.GetRequiredCustomModifiers())); + + return _requiredCustomModifiers; } /// - public ITypeSymbol[] GetRequiredCustomModifiers() + internal override ImmutableArray GetDeclaredCustomAttributes() { - return ResolveTypeSymbols(UnderlyingProperty.GetRequiredCustomModifiers()); - } + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingProperty.GetCustomAttributesData())); - #endregion + return _customAttributes; + } } -} \ No newline at end of file +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs deleted file mode 100644 index c8a96fceb5..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionPropertyTable.cs +++ /dev/null @@ -1,81 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionPropertyTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol _type; - - IndexRangeDictionary _table = new(); - ReaderWriterLockSlim? _lock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionPropertyTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol type) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type ?? throw new ArgumentNullException(nameof(type)); - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - if (property.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(property)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var row = property.GetMetadataTokenRowNumberSafe(); - if (_table[row] == null) - using (_lock.CreateWriteLock()) - if (property is PropertyBuilder builder) - return _table[row] ??= new ReflectionPropertySymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, (IReflectionTypeSymbolBuilder)_type, builder); - else - return _table[row] ??= new ReflectionPropertySymbol(_context, _module, _type, property); - - return _table[row] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates the cached for the type by property. - /// - /// - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return (IReflectionPropertySymbolBuilder)GetOrCreatePropertySymbol((PropertyInfo)property); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs deleted file mode 100644 index 760074bc88..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSZArrayTypeSymbol.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionSZArrayTypeSymbol : ReflectionTypeSpecSymbol - { - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionSZArrayTypeSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol elementType) : - base(context, resolvingModule, elementType) - { - - } - - /// - public override Type UnderlyingType => SpecifiedType.UnderlyingType.MakeArrayType(); - - /// - public override Type UnderlyingRuntimeType => SpecifiedType.UnderlyingRuntimeType.MakeArrayType(); - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs deleted file mode 100644 index 0cbdc11897..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbol.cs +++ /dev/null @@ -1,589 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Collections.Immutable; -using System.Diagnostics.CodeAnalysis; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - /// - /// Base class for managed symbols. - /// - abstract class ReflectionSymbol : IReflectionSymbol - { - - readonly ReflectionSymbolContext _context; - - /// - /// Initializes a new instance. - /// - /// - public ReflectionSymbol(ReflectionSymbolContext context) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - } - - #region IReflectionSymbol - - /// - /// Gets the associated . - /// - public ReflectionSymbolContext Context => _context; - - /// - public virtual bool IsMissing => false; - - /// - public virtual bool ContainsMissing => false; - - /// - public virtual bool IsComplete => true; - - /// - [return: NotNullIfNotNull(nameof(assembly))] - public virtual IReflectionAssemblySymbol? ResolveAssemblySymbol(Assembly? assembly) - { - return assembly == null ? null : _context.GetOrCreateAssemblySymbol(assembly); - } - - /// - [return: NotNullIfNotNull(nameof(assembly))] - public virtual IReflectionAssemblySymbolBuilder ResolveAssemblySymbol(AssemblyBuilder assembly) - { - if (assembly is null) - throw new ArgumentNullException(nameof(assembly)); - - return _context.GetOrCreateAssemblySymbol(assembly); - } - - /// - [return: NotNullIfNotNull(nameof(assemblies))] - public IReflectionAssemblySymbol[]? ResolveAssemblySymbols(Assembly[]? assemblies) - { - if (assemblies == null) - return null; - if (assemblies.Length == 0) - return []; - - var a = new IReflectionAssemblySymbol[assemblies.Length]; - for (int i = 0; i < assemblies.Length; i++) - if (ResolveAssemblySymbol(assemblies[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(module))] - public virtual IReflectionModuleSymbol? ResolveModuleSymbol(Module? module) - { - return module == null ? null : _context.GetOrCreateModuleSymbol(module); - } - - /// - [return: NotNullIfNotNull(nameof(module))] - public virtual IReflectionModuleSymbolBuilder ResolveModuleSymbol(ModuleBuilder module) - { - if (module is null) - throw new ArgumentNullException(nameof(module)); - - return _context.GetOrCreateModuleSymbol(module); - } - - /// - [return: NotNullIfNotNull(nameof(modules))] - public IReflectionModuleSymbol[]? ResolveModuleSymbols(Module[]? modules) - { - if (modules == null) - return null; - if (modules.Length == 0) - return []; - - var a = new IReflectionModuleSymbol[modules.Length]; - for (int i = 0; i < modules.Length; i++) - if (ResolveModuleSymbol(modules[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - public IEnumerable ResolveModuleSymbols(IEnumerable modules) - { - foreach (var module in modules) - if (ResolveModuleSymbol(module) is { } symbol) - yield return symbol; - } - - /// - [return: NotNullIfNotNull(nameof(member))] - public virtual IReflectionMemberSymbol? ResolveMemberSymbol(MemberInfo? member) - { - if (member == null) - return null; - - return member switch - { - ConstructorInfo ctor => ResolveConstructorSymbol(ctor), - EventInfo @event => ResolveEventSymbol(@event), - FieldInfo field => ResolveFieldSymbol(field), - MethodInfo method => ResolveMethodSymbol(method), - PropertyInfo property => ResolvePropertySymbol(property), - Type type => ResolveTypeSymbol(type), - _ => throw new InvalidOperationException(), - }; - } - - /// - [return: NotNullIfNotNull(nameof(members))] - public IReflectionMemberSymbol[]? ResolveMemberSymbols(MemberInfo[]? members) - { - if (members == null) - return null; - if (members.Length == 0) - return []; - - var a = new IReflectionMemberSymbol[members.Length]; - for (int i = 0; i < members.Length; i++) - if (ResolveMemberSymbol(members[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(type))] - public virtual IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) - { - return type == null ? null : _context.GetOrCreateTypeSymbol(type); - } - - /// - [return: NotNullIfNotNull(nameof(type))] - public virtual IReflectionTypeSymbolBuilder ResolveTypeSymbol(TypeBuilder type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - - return _context.GetOrCreateTypeSymbol(type); - } - - /// - [return: NotNullIfNotNull(nameof(types))] - public IReflectionTypeSymbol[]? ResolveTypeSymbols(Type[]? types) - { - if (types == null) - return null; - if (types.Length == 0) - return []; - - var a = new IReflectionTypeSymbol[types.Length]; - for (int i = 0; i < types.Length; i++) - if (ResolveTypeSymbol(types[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - public IEnumerable ResolveTypeSymbols(IEnumerable types) - { - foreach (var type in types) - if (ResolveTypeSymbol(type) is { } symbol) - yield return symbol; - } - - /// - [return: NotNullIfNotNull(nameof(method))] - public virtual IReflectionMethodBaseSymbol? ResolveMethodBaseSymbol(MethodBase? method) - { - return method switch - { - ConstructorInfo ctor => ResolveConstructorSymbol(ctor), - MethodInfo method_ => ResolveMethodSymbol(method_), - _ => null, - }; - } - - /// - [return: NotNullIfNotNull(nameof(ctor))] - public virtual IReflectionConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) - { - return ctor == null ? null : _context.GetOrCreateConstructorSymbol(ctor); - } - - /// - [return: NotNullIfNotNull(nameof(ctor))] - public virtual IReflectionConstructorSymbolBuilder ResolveConstructorSymbol(ConstructorBuilder ctor) - { - if (ctor is null) - throw new ArgumentNullException(nameof(ctor)); - - return _context.GetOrCreateConstructorSymbol(ctor); - } - - /// - [return: NotNullIfNotNull(nameof(ctors))] - public IReflectionConstructorSymbol[]? ResolveConstructorSymbols(ConstructorInfo[]? ctors) - { - if (ctors == null) - return null; - if (ctors.Length == 0) - return []; - - var a = new IReflectionConstructorSymbol[ctors.Length]; - for (int i = 0; i < ctors.Length; i++) - if (ResolveConstructorSymbol(ctors[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(method))] - public virtual IReflectionMethodSymbol? ResolveMethodSymbol(MethodInfo? method) - { - return method == null ? null : _context.GetOrCreateMethodSymbol(method); - } - - /// - [return: NotNullIfNotNull(nameof(method))] - public virtual IReflectionMethodSymbolBuilder ResolveMethodSymbol(MethodBuilder method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - return _context.GetOrCreateMethodSymbol(method); - } - - /// - [return: NotNullIfNotNull(nameof(methods))] - public IReflectionMethodSymbol[]? ResolveMethodSymbols(MethodInfo[]? methods) - { - if (methods == null) - return null; - if (methods.Length == 0) - return []; - - var a = new IReflectionMethodSymbol[methods.Length]; - for (int i = 0; i < methods.Length; i++) - if (ResolveMethodSymbol(methods[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(field))] - public virtual IReflectionFieldSymbol? ResolveFieldSymbol(FieldInfo? field) - { - return field == null ? null : _context.GetOrCreateFieldSymbol(field); - } - - /// - [return: NotNullIfNotNull(nameof(field))] - public virtual IReflectionFieldSymbolBuilder ResolveFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) - { - if (field is null) - throw new ArgumentNullException(nameof(field)); - - return _context.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); - } - - /// - [return: NotNullIfNotNull(nameof(fields))] - public IReflectionFieldSymbol[]? ResolveFieldSymbols(FieldInfo[]? fields) - { - if (fields == null) - return null; - if (fields.Length == 0) - return []; - - var a = new IReflectionFieldSymbol[fields.Length]; - for (int i = 0; i < fields.Length; i++) - if (ResolveFieldSymbol(fields[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(property))] - public virtual IReflectionPropertySymbol? ResolvePropertySymbol(PropertyInfo? property) - { - return property == null ? null : _context.GetOrCreatePropertySymbol(property); - } - - /// - [return: NotNullIfNotNull(nameof(property))] - public virtual IReflectionPropertySymbolBuilder ResolvePropertySymbol(PropertyBuilder property) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - return _context.GetOrCreatePropertySymbol(property); - } - - /// - [return: NotNullIfNotNull(nameof(properties))] - public IReflectionPropertySymbol[]? ResolvePropertySymbols(PropertyInfo[]? properties) - { - if (properties == null) - return null; - if (properties.Length == 0) - return []; - - var a = new IReflectionPropertySymbol[properties.Length]; - for (int i = 0; i < properties.Length; i++) - if (ResolvePropertySymbol(properties[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(@event))] - public virtual IReflectionEventSymbol? ResolveEventSymbol(EventInfo? @event) - { - if (@event is null) - return null; - - return _context.GetOrCreateEventSymbol(@event); - } - - /// - [return: NotNullIfNotNull(nameof(@event))] - public virtual IReflectionEventSymbolBuilder? ResolveEventSymbol(EventBuilder @event) - { - if (@event is null) - throw new ArgumentNullException(nameof(@event)); - - return _context.GetOrCreateEventSymbol(@event); - } - - /// - [return: NotNullIfNotNull(nameof(events))] - public IReflectionEventSymbol[]? ResolveEventSymbols(EventInfo[]? events) - { - if (@events == null) - return null; - if (@events.Length == 0) - return []; - - var a = new IReflectionEventSymbol[events.Length]; - for (int i = 0; i < events.Length; i++) - if (ResolveEventSymbol(events[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(parameter))] - public virtual IReflectionParameterSymbol? ResolveParameterSymbol(ParameterInfo? parameter) - { - if (parameter is null) - throw new ArgumentNullException(nameof(parameter)); - - return _context.GetOrCreateParameterSymbol(parameter); - } - - /// - [return: NotNullIfNotNull(nameof(parameter))] - public virtual IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionMethodBaseSymbolBuilder method, ParameterBuilder parameter) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - if (parameter is null) - return null; - - return method.GetOrCreateParameterSymbol(parameter); - } - - /// - [return: NotNullIfNotNull(nameof(parameter))] - public virtual IReflectionParameterSymbolBuilder? ResolveParameterSymbol(IReflectionPropertySymbolBuilder property, ParameterBuilder parameter) - { - if (property is null) - throw new ArgumentNullException(nameof(property)); - - if (parameter is null) - return null; - - return property.GetOrCreateParameterSymbol(parameter); - } - - /// - [return: NotNullIfNotNull(nameof(parameters))] - public IReflectionParameterSymbol[]? ResolveParameterSymbols(ParameterInfo[]? parameters) - { - if (parameters == null) - return null; - if (parameters.Length == 0) - return []; - - var a = new IReflectionParameterSymbol[parameters.Length]; - for (int i = 0; i < parameters.Length; i++) - if (ResolveParameterSymbol(parameters[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(genericTypeParameter))] - public IReflectionGenericTypeParameterSymbolBuilder? ResolveGenericTypeParameterSymbol(GenericTypeParameterBuilder? genericTypeParameter) - { - if (genericTypeParameter == null) - return null; - - return _context.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - - /// - [return: NotNullIfNotNull(nameof(genericTypeParameters))] - public IReflectionGenericTypeParameterSymbolBuilder[]? ResolveGenericTypeParameterSymbols(GenericTypeParameterBuilder[]? genericTypeParameters) - { - if (genericTypeParameters == null) - return null; - if (genericTypeParameters.Length == 0) - return []; - - var a = new IReflectionGenericTypeParameterSymbolBuilder[genericTypeParameters.Length]; - for (int i = 0; i < genericTypeParameters.Length; i++) - if (ResolveGenericTypeParameterSymbol(genericTypeParameters[i]) is { } symbol) - a[i] = symbol; - - return a; - } - - /// - [return: NotNullIfNotNull(nameof(attributes))] - public CustomAttribute[]? ResolveCustomAttributes(IList? attributes) - { - if (attributes == null) - return null; - if (attributes.Count == 0) - return []; - - var a = new CustomAttribute[attributes.Count]; - for (int i = 0; i < attributes.Count; i++) - if (ResolveCustomAttribute(attributes[i]) is { } v) - a[i] = v; - - return a; - } - - /// - public IEnumerable ResolveCustomAttributes(IEnumerable attributes) - { - if (attributes is null) - throw new ArgumentNullException(nameof(attributes)); - - var a = new List(); - foreach (var i in attributes) - if (ResolveCustomAttribute(i) is { } v) - a.Add(v); - - return a.ToArray(); - } - - /// - [return: NotNullIfNotNull(nameof(customAttributeData))] - public CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) - { - if (customAttributeData == null) - return null; - - return new CustomAttribute( - ResolveTypeSymbol(customAttributeData.AttributeType)!, - ResolveConstructorSymbol(customAttributeData.Constructor)!, - ResolveCustomAttributeTypedArguments(customAttributeData.ConstructorArguments), - ResolveCustomAttributeNamedArguments(customAttributeData.NamedArguments)); - } - - /// - public ImmutableArray ResolveCustomAttributeTypedArguments(IList args) - { - if (args is null) - throw new ArgumentNullException(nameof(args)); - if (args.Count == 0) - return []; - - var a = new CustomAttributeTypedArgument[args.Count]; - for (int i = 0; i < args.Count; i++) - a[i] = ResolveCustomAttributeTypedArgument(args[i]); - - return a.ToImmutableArray(); - } - - /// - public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg) - { - return new CustomAttributeTypedArgument( - ResolveTypeSymbol(arg.ArgumentType)!, - ResolveCustomAttributeTypedValue(arg.Value)); - } - - /// - public object? ResolveCustomAttributeTypedValue(object? value) - { - return value switch - { - IList aa => ResolveCustomAttributeTypedArguments(aa), - Type v => ResolveTypeSymbol(v), - _ => value - }; - } - - /// - public ImmutableArray ResolveCustomAttributeNamedArguments(IList args) - { - if (args is null) - throw new ArgumentNullException(nameof(args)); - if (args.Count == 0) - return []; - - var a = new CustomAttributeNamedArgument[args.Count]; - for (int i = 0; i < args.Count; i++) - a[i] = ResolveCustomAttributeNamedArgument(args[i]); - - return ImmutableArray.Create(a); - } - - /// - public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg) - { - return new CustomAttributeNamedArgument( - arg.IsField, - ResolveMemberSymbol(arg.MemberInfo)!, - arg.MemberName, - ResolveCustomAttributeTypedArgument(arg.TypedValue)); - } - - /// - public InterfaceMapping ResolveInterfaceMapping(System.Reflection.InterfaceMapping mapping) - { - return new InterfaceMapping( - ResolveMethodSymbols(mapping.InterfaceMethods), - ResolveTypeSymbol(mapping.InterfaceType), - ResolveMethodSymbols(mapping.TargetMethods), - ResolveTypeSymbol(mapping.TargetType)); - } - - /// - public ManifestResourceInfo? ResolveManifestResourceInfo(System.Reflection.ManifestResourceInfo? info) - { - return info != null ? new ManifestResourceInfo((System.Reflection.ResourceLocation)info.ResourceLocation, info.FileName, ResolveAssemblySymbol(info.ReferencedAssembly)) : null; - } - - #endregion - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs index aef481677e..3e0d65d74a 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolContext.cs @@ -1,13 +1,14 @@ using System; using System.Collections.Concurrent; +using System.Collections.Generic; using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; using IKVM.CoreLib.Reflection; using IKVM.CoreLib.Symbols.Emit; -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -15,365 +16,401 @@ namespace IKVM.CoreLib.Symbols.Reflection /// /// Holds references to symbols derived from System.Reflection. /// - class ReflectionSymbolContext : ISymbolContext + class ReflectionSymbolContext : SymbolContext { - readonly ConcurrentDictionary> _symbolByName = new(); - readonly ConditionalWeakTable _symbolByAssembly = new(); + readonly AssemblySymbol _coreLib; + readonly ConcurrentDictionary> _symbolByName = new(); + readonly ConditionalWeakTable _symbolByAssembly = new(); /// /// Initializes a new instance. /// - public ReflectionSymbolContext() + public ReflectionSymbolContext(Assembly coreLib) { + _coreLib = ResolveAssemblySymbol(coreLib); + // check that we can successfully resolve the object type + if (coreLib.GetType("System.Object") == null) + throw new InvalidOperationException("Cannot resolve System.Object from corelib."); } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, bool collectable, bool saveable) + public override TypeSymbol ResolveCoreType(string typeName) { - if (name is null) - throw new ArgumentNullException(nameof(name)); - if (collectable && saveable) - throw new NotSupportedException("Assembly cannot be both colletable and saveable."); - -#if NET - if (saveable) - throw new NotSupportedException("Assembly cannot be saveable."); - else if (collectable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect)); - else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run)); -#else - if (saveable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave)); - else if (collectable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect)); - else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run)); -#endif + return _coreLib.GetType(typeName) ?? throw new InvalidOperationException($"Failed to resolve core type {typeName}"); } /// - public IAssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes, bool collectable, bool saveable) + public override AssemblySymbolBuilder DefineAssembly(AssemblyIdentity identity, ImmutableArray attributes) { - if (name is null) - throw new ArgumentNullException(nameof(name)); - if (collectable && saveable) - throw new NotSupportedException("Assembly cannot be both colletable and saveable."); - -#if NET - if (saveable) - throw new NotSupportedException("Assembly cannot be saveable."); - else if (collectable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, attributes.Unpack())); - else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, attributes.Unpack())); -#else - if (saveable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndSave, attributes.Unpack())); - else if (collectable) - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.RunAndCollect, attributes.Unpack())); - else - return GetOrCreateAssemblySymbol(AssemblyBuilder.DefineDynamicAssembly(name.Unpack(), AssemblyBuilderAccess.Run, attributes.Unpack())); -#endif - } + if (identity is null) + throw new ArgumentNullException(nameof(identity)); - /// - /// Gets or creates a indexed based on the assembly's name. - /// - /// - /// - IReflectionAssemblySymbol GetOrCreateAssemblySymbolByName(Assembly assembly) - { - var r = _symbolByName.GetOrAdd(assembly.FullName ?? throw new InvalidOperationException(), _ => new(null)); + // find or create weak-reference to name + var r = _symbolByName.GetOrAdd(identity.FullName, _ => new(null)); + // look the reference to set it up lock (r) { // reference has no target, reset if (r.TryGetTarget(out var s) == false) { - if (assembly is AssemblyBuilder builder) - { - // we were passed in a builder, so generate a symbol builder and set it as the builder and symbol. - r.SetTarget(s = new ReflectionAssemblySymbolBuilder(this, builder)); - } - else - { - // we were passed a non builder, so generate a symbol and set it to the symbol - // TODO the weakness here is if we pass it the RuntimeAssembly from a non-associated builder - r.SetTarget(s = new ReflectionAssemblySymbol(this, assembly)); - } + // we were passed a non builder, so generate a symbol and set it to the symbol + // TODO the weakness here is if we pass it the RuntimeAssembly from a non-associated builder + r.SetTarget(s = new AssemblySymbolBuilder(this, identity)); } - return s ?? throw new InvalidOperationException(); + return (AssemblySymbolBuilder?)s ?? throw new InvalidOperationException(); } } /// - /// Gets or creates a indexed based on the assembly's name. + /// Gets or creates a indexed based on the assembly's name. /// /// /// - IReflectionAssemblySymbolBuilder GetOrCreateAssemblySymbolByName(AssemblyBuilder assembly) + public AssemblySymbol ResolveAssemblySymbol(Assembly assembly) { - return (IReflectionAssemblySymbolBuilder)GetOrCreateAssemblySymbolByName((Assembly)assembly); - } + if (assembly is null) + throw new ArgumentNullException(nameof(assembly)); + if (assembly is AssemblyBuilder) + throw new NotSupportedException(); - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionAssemblySymbol GetOrCreateAssemblySymbol(Assembly assembly) - { - return _symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); + // find or create weak-reference to name + var r = _symbolByName.GetOrAdd(assembly.GetName().FullName, _ => new(null)); + + // look the reference to set it up + lock (r) + { + // reference has no target, reset + if (r.TryGetTarget(out var s) == false) + { + // we were passed a non builder, so generate a symbol and set it to the symbol + // TODO the weakness here is if we pass it the RuntimeAssembly from a non-associated builder + r.SetTarget(s = new ReflectionAssemblySymbol(this, assembly)); + } + + return (ReflectionAssemblySymbol?)s ?? throw new InvalidOperationException(); + } } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - public IReflectionAssemblySymbolBuilder GetOrCreateAssemblySymbol(AssemblyBuilder assembly) + [return: NotNullIfNotNull(nameof(module))] + public ModuleSymbol? ResolveModuleSymbol(Module? module) { - return (IReflectionAssemblySymbolBuilder)_symbolByAssembly.GetValue(assembly, GetOrCreateAssemblySymbolByName); + if (module is ModuleBuilder) + throw new NotSupportedException(); + else if (module is null) + return null; + else + return ResolveAssemblySymbol(module.Assembly).GetModule(module.Name) ?? throw new InvalidOperationException(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a list of for the specified . /// - /// + /// /// - public IReflectionModuleSymbol GetOrCreateModuleSymbol(Module module) + public ImmutableList ResolveModuleSymbols(Module[] modules) { - if (module is ModuleBuilder builder) - return GetOrCreateModuleSymbol(builder); - else - return GetOrCreateAssemblySymbol(module.Assembly).GetOrCreateModuleSymbol(module); + var b = ImmutableList.CreateBuilder(); + foreach (var i in modules) + b.Add(ResolveModuleSymbol(i)); + + return b.ToImmutable(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a list of for the specified . /// - /// + /// /// - public IReflectionModuleSymbolBuilder GetOrCreateModuleSymbol(ModuleBuilder module) + public ImmutableList ResolveModuleSymbols(IEnumerable modules) { - return GetOrCreateAssemblySymbol((AssemblyBuilder)module.Assembly).GetOrCreateModuleSymbol(module); + var b = ImmutableList.CreateBuilder(); + foreach (var i in modules) + b.Add(ResolveModuleSymbol(i)); + + return b.ToImmutable(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) + /// + [return: NotNullIfNotNull(nameof(member))] + public MemberSymbol? ResolveMemberSymbol(MemberInfo? member) { - if (type is TypeBuilder builder) - return GetOrCreateTypeSymbol(builder); + if (member is null) + return null; + else if (member is Type type) + return ResolveTypeSymbol(type); + else if (member is ConstructorInfo ctor) + return ResolveConstructorSymbol(ctor); + else if (member is MethodInfo method) + return ResolveMethodSymbol(method); + else if (member is FieldInfo field) + return ResolveFieldSymbol(field); + else if (member is PropertyInfo property) + return ResolvePropertySymbol(property); + else if (member is EventInfo @event) + return ResolveEventSymbol(@event); else - return GetOrCreateModuleSymbol(type.Module).GetOrCreateTypeSymbol(type); + throw new InvalidOperationException(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public IReflectionTypeSymbolBuilder GetOrCreateTypeSymbol(TypeBuilder type) + [return: NotNullIfNotNull(nameof(type))] + public TypeSymbol? ResolveTypeSymbol(Type? type) { - return GetOrCreateModuleSymbol((ModuleBuilder)type.Module).GetOrCreateTypeSymbol(type); + if (type is null) + return null; + else if (type is TypeBuilder) + throw new NotSupportedException(); + else if (type.IsTypeDefinition()) + return ResolveModuleSymbol(type.Module).GetType(type.FullName ?? throw new InvalidOperationException()) ?? throw new InvalidOperationException(); + else if (type.IsSZArray()) + return ResolveTypeSymbol(type.GetElementType()!).MakeArrayType(); + else if (type.IsArray) + return ResolveTypeSymbol(type.GetElementType()!).MakeArrayType(type.GetArrayRank()); + else if (type.IsPointer) + return ResolveTypeSymbol(type.GetElementType()!).MakePointerType(); + else if (type.IsByRef) + return ResolveTypeSymbol(type.GetElementType()!).MakeByRefType(); + else if (type.IsGenericParameter && type.DeclaringMethod is MethodInfo m) + return ResolveMethodSymbol(m).GetGenericArguments()[type.GenericParameterPosition]; + else if (type.IsGenericParameter && type.DeclaringType is Type t) + return ResolveTypeSymbol(t).GetGenericArguments()[type.GenericParameterPosition]; + + throw new InvalidOperationException(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a list of for the specified . /// - /// + /// /// - public IReflectionMemberSymbol GetOrCreateMemberSymbol(MemberInfo member) + public ImmutableArray ResolveTypeSymbols(Type[] types) { - return member switch - { - MethodBase method => GetOrCreateMethodBaseSymbol(method), - FieldInfo field => GetOrCreateFieldSymbol(field), - PropertyInfo property => GetOrCreatePropertySymbol(property), - EventInfo @event => GetOrCreateEventSymbol(@event), - _ => throw new InvalidOperationException(), - }; + var b = ImmutableArray.CreateBuilder(types.Length); + for (var i = 0; i < types.Length; i++) + b.Add(ResolveTypeSymbol(types[i])); + + return b.ToImmutable(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a list of for the specified . /// - /// + /// /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) + public IEnumerable ResolveTypeSymbols(IEnumerable type) { - return method switch - { - ConstructorInfo ctor => GetOrCreateConstructorSymbol(ctor), - _ => GetOrCreateMethodSymbol((MethodInfo)method) - }; + foreach (var i in type) + yield return ResolveTypeSymbol(i); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) + [return: NotNullIfNotNull(nameof(field))] + public FieldSymbol? ResolveFieldSymbol(FieldInfo? field) { - return ctor switch - { - ConstructorBuilder builder => GetOrCreateConstructorSymbol(builder), - _ => GetOrCreateModuleSymbol(ctor.Module).GetOrCreateConstructorSymbol(ctor) - }; + if (field is null) + return null; + else if (field is FieldBuilder) + throw new NotSupportedException(); + else if (field.DeclaringType is { } dt) + return ResolveTypeSymbol(field.DeclaringType)!.GetField(field.Name, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance | BindingFlags.DeclaredOnly) ?? throw new InvalidOperationException(); + else + return ResolveModuleSymbol(field.Module)!.GetField(field.Name, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance | BindingFlags.DeclaredOnly) ?? throw new InvalidOperationException(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) + [return: NotNullIfNotNull(nameof(ctor))] + public ConstructorSymbol? ResolveConstructorSymbol(ConstructorInfo? ctor) { - return GetOrCreateModuleSymbol((ModuleBuilder)ctor.Module).GetOrCreateConstructorSymbol(ctor); + if (ctor is null) + return null; + else if (ctor is ConstructorBuilder) + throw new NotSupportedException(); + else if (ctor.IsStatic) + return ResolveTypeSymbol(ctor.DeclaringType)!.TypeInitializer ?? throw new InvalidOperationException(); + else + return ResolveTypeSymbol(ctor.DeclaringType)!.GetConstructor(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static | BindingFlags.DeclaredOnly, ResolveTypeSymbols(ctor.GetParameterTypes())) ?? throw new InvalidOperationException(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// /// /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) + [return: NotNullIfNotNull(nameof(method))] + public MethodSymbol? ResolveMethodSymbol(MethodInfo? method) { - return method switch - { - MethodBuilder builder => GetOrCreateMethodSymbol(builder), - _ => GetOrCreateModuleSymbol(method.Module).GetOrCreateMethodSymbol(method) - }; + if (method is null) + return null; + else if (method is MethodBuilder) + throw new NotSupportedException(); + else if (method.DeclaringType is { } dt) + return ResolveTypeSymbol(method.DeclaringType)!.GetMethod(method.Name, method.GetGenericArguments().Length, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance | BindingFlags.DeclaredOnly, CallingConventions.Any, ResolveTypeSymbols(method.GetParameterTypes()), null) ?? throw new InvalidOperationException(); + else + return ResolveModuleSymbol(method.Module)!.GetMethod(method.Name, BindingFlags.Public | BindingFlags.NonPublic, CallingConventions.Any, ResolveTypeSymbols(method.GetParameterTypes()), null) ?? throw new InvalidOperationException(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a list of for the specified . /// - /// + /// /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) + public ImmutableArray ResolveMethodSymbols(MethodInfo[] type) { - return GetOrCreateModuleSymbol((ModuleBuilder)method.Module).GetOrCreateMethodSymbol(method); + var b = ImmutableArray.CreateBuilder(); + foreach (var i in type) + b.Add(ResolveMethodSymbol(i)); + + return b.ToImmutable(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - public IReflectionParameterSymbol GetOrCreateParameterSymbol(ParameterInfo parameter) + [return: NotNullIfNotNull(nameof(property))] + public PropertySymbol? ResolvePropertySymbol(PropertyInfo? property) { - return GetOrCreateModuleSymbol(parameter.Member.Module).GetOrCreateParameterSymbol(parameter); + if (property is null) + return null; + else if (property is PropertyBuilder) + throw new NotSupportedException(); + else + return ResolveTypeSymbol(property.DeclaringType)!.GetProperty(property.Name, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance | BindingFlags.DeclaredOnly) ?? throw new InvalidOperationException(); } /// - /// Gets or creates a for the specified . + /// Gets or creates a for the specified . /// - /// + /// /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) + [return: NotNullIfNotNull(nameof(@event))] + public EventSymbol? ResolveEventSymbol(EventInfo? @event) { - return GetOrCreateModuleSymbol(field.Module).GetOrCreateFieldSymbol(field); + if (@event is null) + return null; + else + return ResolveTypeSymbol(@event.DeclaringType)!.GetEvent(@event.Name, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance | BindingFlags.DeclaredOnly) ?? throw new InvalidOperationException(); } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? optionalCustomModifiers, ITypeSymbol[]? requiredCustomModifiers) + /// + public ImmutableArray ResolveCustomAttributes(IList? attributes) { - return GetOrCreateModuleSymbol((ModuleBuilder)field.Module).GetOrCreateFieldSymbol(field, optionalCustomModifiers, requiredCustomModifiers); + if (attributes == null || attributes.Count == 0) + return []; + + var a = ImmutableArray.CreateBuilder(); + for (int i = 0; i < attributes.Count; i++) + if (ResolveCustomAttribute(attributes[i]) is { } v) + a.Add(v); + + return a.ToImmutable(); } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) + /// + public IEnumerable ResolveCustomAttributes(IEnumerable attributes) { - return property switch - { - PropertyBuilder builder => GetOrCreatePropertySymbol(builder), - _ => GetOrCreateModuleSymbol(property.Module).GetOrCreatePropertySymbol(property) - }; + if (attributes is null) + throw new ArgumentNullException(nameof(attributes)); + + foreach (var i in attributes) + if (ResolveCustomAttribute(i) is { } v) + yield return v; } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) + /// + [return: NotNullIfNotNull(nameof(customAttributeData))] + public CustomAttribute? ResolveCustomAttribute(CustomAttributeData? customAttributeData) { - return GetOrCreateModuleSymbol((ModuleBuilder)property.Module).GetOrCreatePropertySymbol(property); + if (customAttributeData == null) + return null; + + return new CustomAttribute( + ResolveTypeSymbol(customAttributeData.AttributeType)!, + ResolveConstructorSymbol(customAttributeData.Constructor)!, + ResolveCustomAttributeTypedArguments(customAttributeData.ConstructorArguments), + ResolveCustomAttributeNamedArguments(customAttributeData.NamedArguments)); } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) + /// + public ImmutableArray ResolveCustomAttributeTypedArguments(IList args) { - return GetOrCreateModuleSymbol(@event.Module).GetOrCreateEventSymbol(@event); + if (args is null || args.Count == 0) + return []; + + var a = ImmutableArray.CreateBuilder(args.Count); + for (int i = 0; i < args.Count; i++) + a.Add(ResolveCustomAttributeTypedArgument(args[i])); + + return a.ToImmutable(); } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) + /// + public CustomAttributeTypedArgument ResolveCustomAttributeTypedArgument(System.Reflection.CustomAttributeTypedArgument arg) { - return GetOrCreateModuleSymbol(@event.GetModuleBuilder()).GetOrCreateEventSymbol(@event); + return new CustomAttributeTypedArgument( + ResolveTypeSymbol(arg.ArgumentType)!, + ResolveCustomAttributeTypedValue(arg.Value)); } - /// - /// Gets or creates a for the specified . - /// - /// - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) + /// + public object? ResolveCustomAttributeTypedValue(object? value) { - return GetOrCreateModuleSymbol((ModuleBuilder)genericTypeParameter.Module).GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); + return value switch + { + IList aa => ResolveCustomAttributeTypedArguments(aa), + Type v => ResolveTypeSymbol(v), + _ => value + }; } - /// - /// Unpacks a single constructor argument. - /// - /// - /// - object? UnpackArgument(object? constructorArg) + /// + public ImmutableArray ResolveCustomAttributeNamedArguments(IList args) { - if (constructorArg is ITypeSymbol type) - return type.Unpack(); + if (args is null || args.Count == 0) + return []; - return constructorArg; + var a = ImmutableArray.CreateBuilder(args.Count); + for (int i = 0; i < args.Count; i++) + a.Add(ResolveCustomAttributeNamedArgument(args[i])); + + return a.ToImmutable(); } - /// - /// Unpacks a set of constructor arguments. - /// - /// - /// - object?[] UnpackArguments(object?[] constructorArgs) + /// + public CustomAttributeNamedArgument ResolveCustomAttributeNamedArgument(System.Reflection.CustomAttributeNamedArgument arg) { - var l = new object?[constructorArgs.Length]; - for (int i = 0; i < constructorArgs.Length; i++) - l[i] = UnpackArgument(constructorArgs[i]); - - return l; + return new CustomAttributeNamedArgument( + arg.IsField, + ResolveMemberSymbol(arg.MemberInfo)!, + arg.MemberName, + ResolveCustomAttributeTypedArgument(arg.TypedValue)); } } diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs deleted file mode 100644 index 55b1fd5ef7..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolExtensions.cs +++ /dev/null @@ -1,11 +0,0 @@ -namespace IKVM.CoreLib.Symbols.Reflection -{ - - static class ReflectionSymbolExtensions - { - - - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeDefSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeDefSymbol.cs deleted file mode 100644 index 5f04f8c93d..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeDefSymbol.cs +++ /dev/null @@ -1,46 +0,0 @@ -using System; -using System.Diagnostics.CodeAnalysis; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - class ReflectionTypeDefSymbol : ReflectionTypeSymbolBase - { - - readonly Type _type; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionTypeDefSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, Type type) : - base(context, resolvingModule) - { - _type = type ?? throw new ArgumentNullException(nameof(type)); - } - - /// - public override Type UnderlyingType => _type; - - /// - public override Type UnderlyingRuntimeType => _type; - - #region IReflectionSymbol - - /// - [return: NotNullIfNotNull(nameof(type))] - public override IReflectionTypeSymbol? ResolveTypeSymbol(Type? type) - { - if (type == _type) - return this; - else - return base.ResolveTypeSymbol(type); - } - - #endregion - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs deleted file mode 100644 index 71ae05a00b..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecSymbol.cs +++ /dev/null @@ -1,33 +0,0 @@ -using System; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - abstract class ReflectionTypeSpecSymbol : ReflectionTypeSymbolBase - { - - readonly IReflectionTypeSymbol _specifiedType; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - public ReflectionTypeSpecSymbol(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule, IReflectionTypeSymbol specifiedType) : - base(context, resolvingModule) - { - _specifiedType = specifiedType ?? throw new ArgumentNullException(nameof(specifiedType)); - } - - /// - /// Gets the element type. - /// - protected IReflectionTypeSymbol SpecifiedType => _specifiedType; - - /// - public override bool IsComplete => SpecifiedType.IsComplete; - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs deleted file mode 100644 index db46cc187b..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSpecTable.cs +++ /dev/null @@ -1,128 +0,0 @@ -using System; -using System.Collections.Concurrent; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionTypeSpecTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol _elementType; - - IndexRangeDictionary _asArray; - ReaderWriterLockSlim? _asArrayLock; - ReflectionSZArrayTypeSymbol? _asSZArray; - ReflectionPointerTypeSymbol? _asPointer; - ReflectionByRefTypeSymbol? _asByRef; - ConcurrentDictionary? _genericTypeSymbols; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionTypeSpecTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol elementType) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); - _asArray = new IndexRangeDictionary(); - } - - /// - /// Gets or creates a representing an Array of this type. - /// - /// - /// - /// - public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) - { - if (_asArrayLock == null) - Interlocked.CompareExchange(ref _asArrayLock, new(), null); - - using (_asArrayLock.CreateUpgradeableReadLock()) - { - if (_asArray[rank] == null) - using (_asArrayLock.CreateWriteLock()) - _asArray[rank] = new ReflectionArrayTypeSymbol(_context, _module, _elementType, rank); - - return _asArray[rank] ?? throw new InvalidOperationException(); - } - } - - /// - /// Gets or creates a representing a SZArray of this type. - /// - /// - public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() - { - if (_asSZArray == null) - Interlocked.CompareExchange(ref _asSZArray, new ReflectionSZArrayTypeSymbol(_context, _module, _elementType), null); - - return _asSZArray; - } - - /// - /// Gets or creates a representing a pointer of this type. - /// - /// - public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() - { - if (_asPointer == null) - Interlocked.CompareExchange(ref _asPointer, new ReflectionPointerTypeSymbol(_context, _module, _elementType), null); - - return _asPointer; - } - - /// - /// Gets or creates a representing a by-ref of this type. - /// - /// - public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() - { - if (_asByRef == null) - Interlocked.CompareExchange(ref _asByRef, new ReflectionByRefTypeSymbol(_context, _module, _elementType), null); - - return _asByRef; - } - - /// - /// Gets or creates a representing a specialized generic of this type. - /// - /// - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) - { - if (genericTypeArguments is null) - throw new ArgumentNullException(nameof(genericTypeArguments)); - - if (_elementType.IsGenericTypeDefinition == false) - throw new InvalidOperationException(); - - if (_genericTypeSymbols == null) - Interlocked.CompareExchange(ref _genericTypeSymbols, new(TypeSymbolListEqualityComparer.Instance), null); - - return _genericTypeSymbols.GetOrAdd(genericTypeArguments, CreateGenericTypeSymbol); - } - - /// - /// Creates a new representing a specialized generic of this type. - /// - /// - /// - readonly ReflectionGenericInstantiationTypeSymbol CreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeArguments) - { - return new ReflectionGenericInstantiationTypeSymbol(_context, _module, _elementType, genericTypeArguments); - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs new file mode 100644 index 0000000000..e16d2056a5 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbol.cs @@ -0,0 +1,239 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols.Reflection +{ + + class ReflectionTypeSymbol : DefinitionTypeSymbol + { + + readonly Type _underlyingType; + + ImmutableArray _typeArguments; + ImmutableArray _typeConstraints; + ImmutableArray _interfaces; + ImmutableArray _constructors; + ImmutableArray _methods; + ImmutableArray _fields; + ImmutableArray _properties; + ImmutableArray _events; + ImmutableArray _nestedTypes; + ImmutableArray _customAttributes; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + public ReflectionTypeSymbol(ReflectionSymbolContext context, ReflectionModuleSymbol module, Type underlyingType) : + base(context, module) + { + _underlyingType = underlyingType ?? throw new ArgumentNullException(nameof(underlyingType)); + } + + /// + /// Gets the context that owns this type. + /// + public new ReflectionSymbolContext Context => (ReflectionSymbolContext)base.Context; + + /// + public override TypeAttributes Attributes => _underlyingType.Attributes; + + /// + public override string? FullName => _underlyingType.FullName; + + /// + public override string? Namespace => _underlyingType.Namespace; + + /// + public override TypeCode TypeCode => Type.GetTypeCode(_underlyingType); + + /// + public override TypeSymbol? BaseType => Context.ResolveTypeSymbol(_underlyingType.BaseType); + + /// + public override bool ContainsGenericParameters => _underlyingType.ContainsGenericParameters; + + /// + public override GenericParameterAttributes GenericParameterAttributes => _underlyingType.GenericParameterAttributes; + + /// + public override bool IsPrimitive => _underlyingType.IsPrimitive; + + /// + public override bool IsGenericTypeDefinition => _underlyingType.IsGenericTypeDefinition; + + /// + public override bool IsEnum => _underlyingType.IsEnum; + + /// + public override string Name => _underlyingType.Name; + + /// + public override string? GetEnumName(object value) + { + return _underlyingType.GetEnumName(value); + } + + /// + public override ImmutableArray GetEnumNames() + { + return _underlyingType.GetEnumNames().ToImmutableArray(); + } + + /// + public override TypeSymbol GetEnumUnderlyingType() + { + return Context.ResolveTypeSymbol(_underlyingType.GetEnumUnderlyingType()); + } + + /// + public override bool IsEnumDefined(object value) + { + return _underlyingType.IsEnumDefined(value); + } + + /// + public override ImmutableArray GetGenericArguments() + { + if (_typeArguments == default) + { + var c = _underlyingType.GetGenericArguments(); + var b = ImmutableArray.CreateBuilder(c.Length); + foreach (var i in c) + b.Add(new ReflectionGenericTypeParameterTypeSymbol(Context, this, i)); + + ImmutableInterlocked.InterlockedInitialize(ref _typeArguments, b.ToImmutable()); + } + + return _typeArguments; + } + + /// + public override ImmutableArray GetGenericParameterConstraints() + { + if (_typeConstraints == default) + ImmutableInterlocked.InterlockedInitialize(ref _typeArguments, Context.ResolveTypeSymbols(_underlyingType.GetGenericParameterConstraints())); + + return _typeConstraints; + } + + /// + internal override ImmutableArray GetDeclaredNestedTypes() + { + if (_nestedTypes == default) + ImmutableInterlocked.InterlockedInitialize(ref _nestedTypes, Context.ResolveTypeSymbols(_underlyingType.GetNestedTypes(DeclaredOnlyLookup))); + + return _nestedTypes; + } + + /// + public override ImmutableArray GetInterfaces() + { + if (_interfaces == default) + ImmutableInterlocked.InterlockedInitialize(ref _interfaces, Context.ResolveTypeSymbols(_underlyingType.GetInterfaces())); + + return _interfaces; + } + + /// + public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + { + throw new NotImplementedException(); + } + + /// + internal override ImmutableArray GetDeclaredFields() + { + if (_fields == default) + { + var c = _underlyingType.GetFields(DeclaredOnlyLookup); + var b = ImmutableArray.CreateBuilder(c.Length); + foreach (var i in c) + b.Add(new ReflectionFieldSymbol(Context, Module, this, i)); + + ImmutableInterlocked.InterlockedInitialize(ref _fields, b.ToImmutable()); + } + + return _fields; + } + + /// + internal override ImmutableArray GetDeclaredConstructors() + { + if (_constructors == default) + { + var c = _underlyingType.GetConstructors(DeclaredOnlyLookup); + var b = ImmutableArray.CreateBuilder(c.Length); + foreach (var i in c) + b.Add(new ReflectionConstructorSymbol(Context, this, i)); + + ImmutableInterlocked.InterlockedInitialize(ref _constructors, b.ToImmutable()); + } + + return _constructors; + } + + /// + internal override ImmutableArray GetDeclaredMethods() + { + if (_methods == default) + { + var c = _underlyingType.GetMethods(DeclaredOnlyLookup); + var b = ImmutableArray.CreateBuilder(c.Length); + foreach (var i in c) + b.Add(new ReflectionMethodSymbol(Context, (ReflectionModuleSymbol)Module, this, i)); + + ImmutableInterlocked.InterlockedInitialize(ref _methods, b.ToImmutable()); + } + + return _methods; + } + + /// + internal override ImmutableArray GetDeclaredProperties() + { + if (_properties == default) + { + var c = _underlyingType.GetProperties(DeclaredOnlyLookup); + var b = ImmutableArray.CreateBuilder(c.Length); + foreach (var i in c) + b.Add(new ReflectionPropertySymbol(Context, this, i)); + + ImmutableInterlocked.InterlockedInitialize(ref _properties, b.ToImmutable()); + } + + return _properties; + } + + /// + internal override ImmutableArray GetDeclaredEvents() + { + if (_events == default) + { + var c = _underlyingType.GetEvents(DeclaredOnlyLookup); + var b = ImmutableArray.CreateBuilder(); + foreach (var i in c) + b.Add(new ReflectionEventSymbol(Context, this, i)); + + ImmutableInterlocked.InterlockedInitialize(ref _events, b.ToImmutable()); + } + + return _events; + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + if (_customAttributes == default) + ImmutableInterlocked.InterlockedInitialize(ref _customAttributes, Context.ResolveCustomAttributes(_underlyingType.GetCustomAttributesData())); + + return _customAttributes; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs deleted file mode 100644 index 2961f315a9..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeSymbolBase.cs +++ /dev/null @@ -1,695 +0,0 @@ -using System; -using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - abstract class ReflectionTypeSymbolBase : ReflectionMemberSymbol, IReflectionTypeSymbol - { - - protected ReflectionMethodTable _methodTable; - protected ReflectionFieldTable _fieldTable; - protected ReflectionPropertyTable _propertyTable; - protected ReflectionEventTable _eventTable; - protected ReflectionGenericTypeParameterTable _genericTypeParameterTable; - protected ReflectionTypeSpecTable _specTable; - - /// - /// Initializes a new instance. - /// - /// - /// - public ReflectionTypeSymbolBase(ReflectionSymbolContext context, IReflectionModuleSymbol resolvingModule) : - base(context, resolvingModule, null) - { - _methodTable = new ReflectionMethodTable(context, resolvingModule, this); - _fieldTable = new ReflectionFieldTable(context, resolvingModule, this); - _propertyTable = new ReflectionPropertyTable(context, resolvingModule, this); - _eventTable = new ReflectionEventTable(context, resolvingModule, this); - _genericTypeParameterTable = new ReflectionGenericTypeParameterTable(context, resolvingModule, this); - _specTable = new ReflectionTypeSpecTable(context, resolvingModule, this); - } - - /// - public abstract Type UnderlyingType { get; } - - /// - public abstract Type UnderlyingRuntimeType { get; } - - /// - public override sealed MemberInfo UnderlyingMember => UnderlyingType; - - /// - public override sealed MemberInfo UnderlyingRuntimeMember => UnderlyingRuntimeType; - - #region IReflectionTypeSymbol - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeSymbol(IReflectionTypeSymbol[] genericTypeDefinition) - { - return _specTable.GetOrCreateGenericTypeSymbol(genericTypeDefinition); - } - - /// - public IReflectionConstructorSymbol GetOrCreateConstructorSymbol(ConstructorInfo ctor) - { - return _methodTable.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionConstructorSymbolBuilder GetOrCreateConstructorSymbol(ConstructorBuilder ctor) - { - return _methodTable.GetOrCreateConstructorSymbol(ctor); - } - - /// - public IReflectionMethodBaseSymbol GetOrCreateMethodBaseSymbol(MethodBase method) - { - if (method is ConstructorInfo ctor) - return GetOrCreateConstructorSymbol(ctor); - else - return GetOrCreateMethodSymbol((MethodInfo)method); - } - - /// - public IReflectionMethodSymbol GetOrCreateMethodSymbol(MethodInfo method) - { - if (method.IsMethodDefinition()) - return _methodTable.GetOrCreateMethodSymbol(method); - else - return ResolveMethodSymbol(method.GetGenericMethodDefinition()).GetOrCreateGenericMethodSymbol(method); - } - - /// - public IReflectionMethodSymbolBuilder GetOrCreateMethodSymbol(MethodBuilder method) - { - return _methodTable.GetOrCreateMethodSymbol(method); - } - - /// - public IReflectionFieldSymbol GetOrCreateFieldSymbol(FieldInfo field) - { - return _fieldTable.GetOrCreateFieldSymbol(field, null, null); - } - - /// - public IReflectionFieldSymbolBuilder GetOrCreateFieldSymbol(FieldBuilder field, ITypeSymbol[]? requiredCustomModifiers, ITypeSymbol[]? optionalCustomModifiers) - { - return _fieldTable.GetOrCreateFieldSymbol(field, requiredCustomModifiers, optionalCustomModifiers); - } - - /// - public IReflectionPropertySymbol GetOrCreatePropertySymbol(PropertyInfo property) - { - return _propertyTable.GetOrCreatePropertySymbol(property); - } - - /// - public IReflectionPropertySymbolBuilder GetOrCreatePropertySymbol(PropertyBuilder property) - { - return _propertyTable.GetOrCreatePropertySymbol(property); - } - - /// - public IReflectionEventSymbol GetOrCreateEventSymbol(EventInfo @event) - { - return _eventTable.GetOrCreateEventSymbol(@event); - } - - /// - public IReflectionEventSymbolBuilder GetOrCreateEventSymbol(EventBuilder @event) - { - return _eventTable.GetOrCreateEventSymbol(@event); - } - - /// - public IReflectionTypeSymbol GetOrCreateGenericTypeParameterSymbol(Type genericType) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericType); - } - - /// - public IReflectionGenericTypeParameterSymbolBuilder GetOrCreateGenericTypeParameterSymbol(GenericTypeParameterBuilder genericTypeParameter) - { - return _genericTypeParameterTable.GetOrCreateGenericTypeParameterSymbol(genericTypeParameter); - } - - /// - public IReflectionTypeSymbol GetOrCreateSZArrayTypeSymbol() - { - return _specTable.GetOrCreateSZArrayTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateArrayTypeSymbol(int rank) - { - return _specTable.GetOrCreateArrayTypeSymbol(rank); - } - - /// - public IReflectionTypeSymbol GetOrCreatePointerTypeSymbol() - { - return _specTable.GetOrCreatePointerTypeSymbol(); - } - - /// - public IReflectionTypeSymbol GetOrCreateByRefTypeSymbol() - { - return _specTable.GetOrCreateByRefTypeSymbol(); - } - - #endregion - - #region ITypeSymbol - - /// - public virtual IAssemblySymbol Assembly => ResolveAssemblySymbol(UnderlyingType.Assembly); - - /// - public virtual string? AssemblyQualifiedName => UnderlyingType.AssemblyQualifiedName; - - /// - public virtual TypeAttributes Attributes => UnderlyingType.Attributes; - - /// - public virtual ITypeSymbol? BaseType => ResolveTypeSymbol(UnderlyingType.BaseType); - - /// - public virtual bool ContainsGenericParameters => UnderlyingType.ContainsGenericParameters; - - /// - public virtual IMethodBaseSymbol? DeclaringMethod => ResolveMethodBaseSymbol(UnderlyingType.DeclaringMethod); - - /// - public virtual string? FullName => UnderlyingType.FullName; - - /// - public virtual string? Namespace => UnderlyingType.Namespace; - - /// - public virtual GenericParameterAttributes GenericParameterAttributes => UnderlyingType.GenericParameterAttributes; - - /// - public virtual int GenericParameterPosition => UnderlyingType.GenericParameterPosition; - - /// - public virtual ITypeSymbol[] GenericTypeArguments => ResolveTypeSymbols(UnderlyingType.GenericTypeArguments); - - /// - public virtual bool HasElementType => UnderlyingType.HasElementType; - - /// - public virtual TypeCode TypeCode => Type.GetTypeCode(UnderlyingType); - - /// - public virtual bool IsAbstract => UnderlyingType.IsAbstract; - - /// - public virtual bool IsSZArray => UnderlyingType.IsSZArray(); - - /// - public virtual bool IsArray => UnderlyingType.IsArray; - - /// - public virtual bool IsAutoLayout => UnderlyingType.IsAutoLayout; - - /// - public virtual bool IsExplicitLayout => UnderlyingType.IsExplicitLayout; - - /// - public virtual bool IsByRef => UnderlyingType.IsByRef; - - /// - public virtual bool IsClass => UnderlyingType.IsClass; - - /// - public virtual bool IsEnum => UnderlyingType.IsEnum; - - /// - public virtual bool IsInterface => UnderlyingType.IsInterface; - - /// - public virtual bool IsConstructedGenericType => UnderlyingType.IsConstructedGenericType; - - /// - public virtual bool IsGenericParameter => UnderlyingType.IsGenericParameter; - - /// - public virtual bool IsGenericType => UnderlyingType.IsGenericType; - - /// - public virtual bool IsGenericTypeDefinition => UnderlyingType.IsGenericTypeDefinition; - - /// - public virtual bool IsLayoutSequential => UnderlyingType.IsLayoutSequential; - - /// - public virtual bool IsNested => UnderlyingType.IsNested; - - /// - public virtual bool IsNestedAssembly => UnderlyingType.IsNestedAssembly; - - /// - public virtual bool IsNestedFamANDAssem => UnderlyingType.IsNestedFamANDAssem; - - /// - public virtual bool IsNestedFamORAssem => UnderlyingType.IsNestedFamORAssem; - - /// - public virtual bool IsNestedFamily => UnderlyingType.IsNestedFamily; - - /// - public virtual bool IsNestedPrivate => UnderlyingType.IsNestedPrivate; - - /// - public virtual bool IsNestedPublic => UnderlyingType.IsNestedPublic; - - /// - public virtual bool IsNotPublic => UnderlyingType.IsNotPublic; - - /// - public virtual bool IsPointer => UnderlyingType.IsPointer; - -#if NET8_0_OR_GREATER - - /// - public virtual bool IsFunctionPointer => UnderlyingType.IsFunctionPointer; - - /// - public virtual bool IsUnmanagedFunctionPointer => UnderlyingType.IsUnmanagedFunctionPointer; - -#else - - /// - public virtual bool IsFunctionPointer => throw new NotImplementedException(); - - /// - public virtual bool IsUnmanagedFunctionPointer => throw new NotImplementedException(); - -#endif - - /// - public virtual bool IsPrimitive => UnderlyingType.IsPrimitive; - - /// - public virtual bool IsPublic => UnderlyingType.IsPublic; - - /// - public virtual bool IsSealed => UnderlyingType.IsSealed; - - /// - public virtual bool IsSerializable => UnderlyingType.IsSerializable; - - /// - public virtual bool IsValueType => UnderlyingType.IsValueType; - - /// - public virtual bool IsVisible => UnderlyingType.IsVisible; - - /// - public virtual bool IsSignatureType => throw new NotImplementedException(); - - /// - public virtual bool IsSpecialName => UnderlyingType.IsSpecialName; - - /// - public virtual IConstructorSymbol? TypeInitializer => ResolveConstructorSymbol(UnderlyingType.TypeInitializer); - - /// - public virtual int GetArrayRank() - { - return UnderlyingType.GetArrayRank(); - } - - /// - public virtual IConstructorSymbol? GetConstructor(BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(bindingAttr, binder: null, types.Unpack(), modifiers: null)); - } - - /// - public virtual IConstructorSymbol? GetConstructor(ITypeSymbol[] types) - { - return ResolveConstructorSymbol(UnderlyingType.GetConstructor(types.Unpack())); - } - - /// - public virtual IConstructorSymbol[] GetConstructors() - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors()); - } - - /// - public virtual IConstructorSymbol[] GetConstructors(BindingFlags bindingAttr) - { - return ResolveConstructorSymbols(UnderlyingType.GetConstructors(bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetDefaultMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetDefaultMembers()); - } - - /// - public virtual ITypeSymbol? GetElementType() - { - return ResolveTypeSymbol(UnderlyingType.GetElementType()); - } - - /// - public virtual string? GetEnumName(object value) - { - return UnderlyingType.GetEnumName(value); - } - - /// - public virtual string[] GetEnumNames() - { - return UnderlyingType.GetEnumNames(); - } - - /// - public virtual ITypeSymbol GetEnumUnderlyingType() - { - return ResolveTypeSymbol(UnderlyingType.GetEnumUnderlyingType()); - } - - /// - public virtual Array GetEnumValues() - { - return UnderlyingType.GetEnumValues(); - } - - /// - public virtual IEventSymbol? GetEvent(string name) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name)); - } - - /// - public virtual IEventSymbol? GetEvent(string name, BindingFlags bindingAttr) - { - return ResolveEventSymbol(UnderlyingType.GetEvent(name, bindingAttr)); - } - - /// - public virtual IEventSymbol[] GetEvents() - { - return ResolveEventSymbols(UnderlyingType.GetEvents()); - } - - /// - public virtual IEventSymbol[] GetEvents(BindingFlags bindingAttr) - { - return ResolveEventSymbols(UnderlyingType.GetEvents(bindingAttr)); - } - - /// - public virtual IFieldSymbol? GetField(string name) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name)); - } - - /// - public virtual IFieldSymbol? GetField(string name, BindingFlags bindingAttr) - { - return ResolveFieldSymbol(UnderlyingType.GetField(name, bindingAttr)); - } - - /// - public virtual IFieldSymbol[] GetFields() - { - return ResolveFieldSymbols(UnderlyingType.GetFields()); - } - - /// - public virtual IFieldSymbol[] GetFields(BindingFlags bindingAttr) - { - return ResolveFieldSymbols(UnderlyingType.GetFields(bindingAttr)); - } - - /// - public virtual ITypeSymbol[] GetGenericArguments() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericArguments()); - } - - /// - public virtual ITypeSymbol[] GetGenericParameterConstraints() - { - return ResolveTypeSymbols(UnderlyingType.GetGenericParameterConstraints()); - } - - /// - public virtual ITypeSymbol GetGenericTypeDefinition() - { - return ResolveTypeSymbol(UnderlyingType.GetGenericTypeDefinition()); - } - - /// - public virtual ITypeSymbol? GetInterface(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name)); - } - - /// - public virtual ITypeSymbol? GetInterface(string name, bool ignoreCase) - { - return ResolveTypeSymbol(UnderlyingType.GetInterface(name, ignoreCase)); - } - - /// - public virtual InterfaceMapping GetInterfaceMap(ITypeSymbol interfaceType) - { - return ResolveInterfaceMapping(UnderlyingType.GetInterfaceMap(interfaceType.Unpack())); - } - - /// - public virtual ITypeSymbol[] GetInterfaces(bool inherit = true) - { - if (inherit) - return ResolveTypeSymbols(UnderlyingType.GetInterfaces()); - else - throw new NotImplementedException(); - } - - /// - public virtual IMemberSymbol[] GetMembers(string name) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name)); - } - - /// - public virtual IMemberSymbol[] GetMembers(string name, BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetMembers(string name, MemberTypes type, BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMember(name, type, bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetMembers(BindingFlags bindingAttr) - { - return ResolveMemberSymbols(UnderlyingType.GetMembers(bindingAttr)); - } - - /// - public virtual IMemberSymbol[] GetMembers() - { - return ResolveMemberSymbols(UnderlyingType.GetMembers()); - } - - /// - public virtual IMethodSymbol? GetMethod(string name) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name)); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr)); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, types.Unpack())); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), null)); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, types.Unpack(), modifiers?.Unpack())); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - return ResolveMethodSymbol(UnderlyingType.GetMethod(name, bindingAttr, null, callConvention, types.Unpack(), modifiers?.Unpack())); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public virtual IMethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingAttr, CallingConventions callConvention, ITypeSymbol[] types, ParameterModifier[]? modifiers) - { - throw new NotImplementedException(); - } - - /// - public virtual IMethodSymbol[] GetMethods(BindingFlags bindingAttr) - { - return ResolveMethodSymbols(UnderlyingType.GetMethods(bindingAttr)); - } - - /// - public virtual IMethodSymbol[] GetMethods() - { - return ResolveMethodSymbols(UnderlyingType.GetMethods()); - } - - /// - public virtual ITypeSymbol? GetNestedType(string name) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name)); - } - - /// - public virtual ITypeSymbol? GetNestedType(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbol(UnderlyingType.GetNestedType(name, bindingAttr)); - } - - /// - public virtual ITypeSymbol[] GetNestedTypes() - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes()); - } - - /// - public virtual ITypeSymbol[] GetNestedTypes(System.Reflection.BindingFlags bindingAttr) - { - return ResolveTypeSymbols(UnderlyingType.GetNestedTypes((BindingFlags)bindingAttr)); - } - - /// - public virtual IPropertySymbol[] GetProperties() - { - return ResolvePropertySymbols(UnderlyingType.GetProperties()); - } - - /// - public virtual IPropertySymbol[] GetProperties(System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbols(UnderlyingType.GetProperties((BindingFlags)bindingAttr)); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, types.Unpack())); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType, ITypeSymbol[] types) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack(), types.Unpack())); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, System.Reflection.BindingFlags bindingAttr) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, (BindingFlags)bindingAttr)); - } - - /// - public virtual IPropertySymbol? GetProperty(string name) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name)); - } - - /// - public virtual IPropertySymbol? GetProperty(string name, ITypeSymbol? returnType) - { - return ResolvePropertySymbol(UnderlyingType.GetProperty(name, returnType?.Unpack())); - } - - /// - public virtual bool IsAssignableFrom(ITypeSymbol? c) - { - return UnderlyingType.IsAssignableFrom(c?.Unpack()); - } - - /// - public virtual bool IsEnumDefined(object value) - { - return UnderlyingType.IsEnumDefined(value); - } - - /// - public virtual bool IsSubclassOf(ITypeSymbol c) - { - return UnderlyingType.IsSubclassOf(c.Unpack()); - } - - /// - public virtual ITypeSymbol MakeArrayType() - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType()); - } - - /// - public virtual ITypeSymbol MakeArrayType(int rank) - { - return ResolveTypeSymbol(UnderlyingType.MakeArrayType(rank)); - } - - /// - public virtual ITypeSymbol MakeByRefType() - { - return ResolveTypeSymbol(UnderlyingType.MakeByRefType()); - } - - /// - public virtual ITypeSymbol MakePointerType() - { - return ResolveTypeSymbol(UnderlyingType.MakePointerType()); - } - - /// - public virtual ITypeSymbol MakeGenericType(params ITypeSymbol[] typeArguments) - { - return ResolveTypeSymbol(UnderlyingType.MakeGenericType(typeArguments.Unpack())); - } - - #endregion - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs deleted file mode 100644 index f3a9f249ad..0000000000 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionTypeTable.cs +++ /dev/null @@ -1,75 +0,0 @@ -using System; -using System.Reflection.Emit; -using System.Reflection.Metadata.Ecma335; -using System.Threading; - -using IKVM.CoreLib.Collections; -using IKVM.CoreLib.Reflection; -using IKVM.CoreLib.Symbols.Reflection.Emit; -using IKVM.CoreLib.Threading; - -namespace IKVM.CoreLib.Symbols.Reflection -{ - - struct ReflectionTypeTable - { - - readonly ReflectionSymbolContext _context; - readonly IReflectionModuleSymbol _module; - readonly IReflectionTypeSymbol? _type; - - IndexRangeDictionary _table = new(); - ReaderWriterLockSlim? _lock; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - public ReflectionTypeTable(ReflectionSymbolContext context, IReflectionModuleSymbol module, IReflectionTypeSymbol? type) - { - _context = context ?? throw new ArgumentNullException(nameof(context)); - _module = module ?? throw new ArgumentNullException(nameof(module)); - _type = type; - } - - /// - /// Gets or creates the cached for the module by type. - /// - /// - /// - public IReflectionTypeSymbol GetOrCreateTypeSymbol(Type type) - { - if (type is null) - throw new ArgumentNullException(nameof(type)); - if (type.Module.MetadataToken != _module.MetadataToken) - throw new ArgumentException(nameof(type)); - if (type.IsGenericParameter) - throw new ArgumentException(nameof(type)); - if (type.IsTypeDefinition() == false) - throw new ArgumentException(nameof(type)); - - // create lock on demand - if (_lock == null) - Interlocked.CompareExchange(ref _lock, new ReaderWriterLockSlim(), null); - - using (_lock.CreateUpgradeableReadLock()) - { - var row = type.GetMetadataTokenRowNumberSafe(); - if (_table[row] == null) - using (_lock.CreateWriteLock()) - if (_table[row] == null) - if (type is TypeBuilder builder) - return _table[row] = new ReflectionTypeSymbolBuilder(_context, (IReflectionModuleSymbolBuilder)_module, builder); - else - return _table[row] = new ReflectionTypeDefSymbol(_context, _module, type); - - return _table[row] ?? throw new InvalidOperationException(); - } - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs index c42fa284a8..39ca6dc108 100644 --- a/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs +++ b/src/IKVM.CoreLib/Symbols/Reflection/ReflectionUtil.cs @@ -1,11 +1,6 @@ using System; -using System.Collections.Generic; using System.Collections.Immutable; using System.Reflection; -using System.Reflection.Emit; - -using IKVM.CoreLib.Symbols.Emit; -using IKVM.CoreLib.Symbols.Reflection.Emit; namespace IKVM.CoreLib.Symbols.Reflection { @@ -41,16 +36,16 @@ public static AssemblyIdentity Pack(this AssemblyName assemblyName) /// /// /// - public static AssemblyIdentity[] Pack(this AssemblyName[] assemblyNames) + public static ImmutableArray Pack(this AssemblyName[] assemblyNames) { if (assemblyNames.Length == 0) return []; - var a = new AssemblyIdentity[assemblyNames.Length]; + var a = ImmutableArray.CreateBuilder(assemblyNames.Length); for (int i = 0; i < assemblyNames.Length; i++) a[i] = assemblyNames[i].Pack(); - return a; + return a.ToImmutable(); } /// @@ -80,419 +75,116 @@ public static AssemblyName[] Unpack(this AssemblyIdentity[] assemblyNameInfos) return a; } - /// - /// Unpacks the symbol into their original assembly. - /// - /// - /// - public static Assembly Unpack(this IAssemblySymbol type) - { - if (type is IReflectionAssemblySymbol symbol) - return symbol.UnderlyingAssembly; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static Module Unpack(this IModuleSymbol module) - { - if (module is IReflectionModuleSymbol symbol) - return symbol.UnderlyingModule; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static Module[] Unpack(this IModuleSymbol[] modules) - { - if (modules.Length == 0) - return []; - - var a = new Module[modules.Length]; - for (int i = 0; i < modules.Length; i++) - a[i] = modules[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static Type Unpack(this ITypeSymbol type) - { - if (type is IReflectionTypeSymbol symbol) - return symbol.UnderlyingType; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static Type[] Unpack(this ITypeSymbol[] types) - { - if (types.Length == 0) - return []; - - var a = new Type[types.Length]; - for (int i = 0; i < types.Length; i++) - a[i] = types[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static Type[][] Unpack(this ITypeSymbol[][] types) - { - if (types.Length == 0) - return []; - - var a = new Type[types.Length][]; - for (int i = 0; i < types.Length; i++) - a[i] = types[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static MemberInfo Unpack(this IMemberSymbol member) - { - if (member is IReflectionMemberSymbol symbol) - return symbol.UnderlyingMember; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static MemberInfo[] Unpack(this IMemberSymbol[] members) - { - if (members.Length == 0) - return []; - - var a = new MemberInfo[members.Length]; - for (int i = 0; i < members.Length; i++) - a[i] = members[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static ConstructorInfo Unpack(this IConstructorSymbol ctor) - { - if (ctor is IReflectionConstructorSymbol symbol) - return symbol.UnderlyingConstructor; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static ConstructorInfo[] Unpack(this IConstructorSymbol[] ctor) - { - if (ctor.Length == 0) - return []; - - var a = new ConstructorInfo[ctor.Length]; - for (int i = 0; i < ctor.Length; i++) - a[i] = ctor[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static MethodInfo Unpack(this IMethodSymbol ctor) - { - if (ctor is IReflectionMethodSymbol symbol) - return symbol.UnderlyingMethod; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static MethodInfo[] Unpack(this IMethodSymbol[] ctor) - { - if (ctor.Length == 0) - return []; - - var a = new MethodInfo[ctor.Length]; - for (int i = 0; i < ctor.Length; i++) - a[i] = ctor[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static FieldInfo Unpack(this IFieldSymbol field) - { - if (field is IReflectionFieldSymbol symbol) - return symbol.UnderlyingField; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static FieldInfo[] Unpack(this IFieldSymbol[] fields) - { - if (fields.Length == 0) - return []; - - var a = new FieldInfo[fields.Length]; - for (int i = 0; i < fields.Length; i++) - a[i] = fields[i].Unpack(); - - return a; - } - - /// - /// Unpacks the symbol into their original type. - /// - /// - /// - public static PropertyInfo Unpack(this IPropertySymbol property) - { - if (property is IReflectionPropertySymbol symbol) - return symbol.UnderlyingProperty; - - throw new InvalidOperationException(); - } - - /// - /// Unpacks the symbols into their original type. - /// - /// - /// - public static PropertyInfo[] Unpack(this IPropertySymbol[] properties) - { - if (properties.Length == 0) - return []; - - var a = new PropertyInfo[properties.Length]; - for (int i = 0; i < properties.Length; i++) - a[i] = properties[i].Unpack(); - - return a; - } - - /// - /// Unpacks the parameter modifier. - /// - /// - /// - /// - public static ParameterModifier Unpack(this System.Reflection.ParameterModifier modifier) - { - throw new NotSupportedException(); - } - - /// - /// Unpacks the parameter modifier. - /// - /// - /// - /// - public static ParameterModifier[] Unpack(this System.Reflection.ParameterModifier[] modifiers) - { - if (modifiers.Length == 0) - return []; - - var a = new ParameterModifier[modifiers.Length]; - for (int i = 0; i < modifiers.Length; i++) - a[i] = modifiers[i].Unpack(); - - return a; - } - - /// - /// Unpacks the . - /// - /// - /// - public static LocalBuilder Unpack(this ILocalBuilder builder) - { - return ((ReflectionLocalBuilder)builder).UnderlyingLocalBuilder; - } - - /// - /// Unpacks the . - /// - /// - /// - public static Label Unpack(this ILabel label) - { - return ((ReflectionLabel)label).UnderlyingLabel; - } - - /// - /// Unpacks the s. - /// - /// - /// - public static Label[] Unpack(this ILabel[] labels) - { - var a = new Label[labels.Length]; - for (int i = 0; i < labels.Length; i++) - a[i] = labels[i].Unpack(); - - return a; - } - - /// - /// Unpacks the . - /// - /// - /// - public static CustomAttributeBuilder Unpack(this CustomAttribute attributes) - { - // unpack constructor arg values - var constructorValues = new object?[attributes.ConstructorArguments.Length]; - for (int i = 0; i < attributes.ConstructorArguments.Length; i++) - constructorValues[i] = UnpackCustomAttributeValue(attributes.ConstructorArguments[i]); - - // unpack named arguments into sets of properties and fields - List? namedProperties = null; - List? propertyValues = null; - List? namedFields = null; - List? fieldValues = null; - - // split named arguments into two sets - foreach (var i in attributes.NamedArguments) - { - var v = UnpackCustomAttributeValue(i.TypedValue.Value); - if (i.IsField == false) - { - namedProperties ??= new(); - namedProperties.Add(((IPropertySymbol)i.MemberInfo).Unpack()); - propertyValues ??= new(); - propertyValues.Add(v); - } - else - { - namedFields ??= new(); - namedFields.Add(((IFieldSymbol)i.MemberInfo).Unpack()); - fieldValues ??= new(); - fieldValues.Add(v); - } - } - - return new CustomAttributeBuilder( - attributes.Constructor.Unpack(), - constructorValues, - namedProperties?.ToArray() ?? [], - propertyValues?.ToArray() ?? [], - namedFields?.ToArray() ?? [], - fieldValues?.ToArray() ?? []); - } - - /// - /// Unpacks the s. - /// - /// - /// - public static CustomAttributeBuilder[] Unpack(this CustomAttribute[] customAttributes) - { - if (customAttributes.Length == 0) - return []; - - var a = new CustomAttributeBuilder[customAttributes.Length]; - for (int i = 0; i < customAttributes.Length; i++) - a[i] = customAttributes[i].Unpack(); - - return a; - } - - /// - /// Unpacks the s. - /// - /// - /// - public static CustomAttributeBuilder[] Unpack(this ImmutableArray attributes) - { - if (attributes.Length == 0) - return []; - - var a = new CustomAttributeBuilder[attributes.Length]; - for (int i = 0; i < attributes.Length; i++) - a[i] = attributes[i].Unpack(); - - return a; - } - - /// - /// Unpacks the attribute value object. - /// - /// - /// - static object? UnpackCustomAttributeValue(object? value) - { - return value switch - { - IReadOnlyList l => UnpackCustomAttributeArrayValue(l), - ITypeSymbol t => t.Unpack(), - CustomAttributeTypedArgument a => UnpackCustomAttributeValue(a.Value), - _ => value, - }; - } - - /// - /// Unpacks the attribute value array. - /// - /// - /// - static object?[] UnpackCustomAttributeArrayValue(IReadOnlyList items) - { - var a = new object?[items.Count]; - for (int i = 0; i < items.Count; i++) - a[i] = UnpackCustomAttributeValue(items[i]); - - return a; - } + ///// + ///// Unpacks the . + ///// + ///// + ///// + //public static CustomAttributeBuilder Unpack(this CustomAttribute attributes) + //{ + // // unpack constructor arg values + // var constructorValues = new object?[attributes.ConstructorArguments.Length]; + // for (int i = 0; i < attributes.ConstructorArguments.Length; i++) + // constructorValues[i] = UnpackCustomAttributeValue(attributes.ConstructorArguments[i]); + + // // unpack named arguments into sets of properties and fields + // List? namedProperties = null; + // List? propertyValues = null; + // List? namedFields = null; + // List? fieldValues = null; + + // // split named arguments into two sets + // foreach (var i in attributes.NamedArguments) + // { + // var v = UnpackCustomAttributeValue(i.TypedValue.Value); + // if (i.IsField == false) + // { + // namedProperties ??= new(); + // namedProperties.Add(((ReflectionPropertySymbol)i.MemberInfo).Unpack()); + // propertyValues ??= new(); + // propertyValues.Add(v); + // } + // else + // { + // namedFields ??= new(); + // namedFields.Add(((FieldSymbol)i.MemberInfo).Unpack()); + // fieldValues ??= new(); + // fieldValues.Add(v); + // } + // } + + // return new CustomAttributeBuilder( + // attributes.Constructor.Unpack(), + // constructorValues, + // namedProperties?.ToArray() ?? [], + // propertyValues?.ToArray() ?? [], + // namedFields?.ToArray() ?? [], + // fieldValues?.ToArray() ?? []); + //} + + ///// + ///// Unpacks the s. + ///// + ///// + ///// + //public static CustomAttributeBuilder[] Unpack(this CustomAttribute[] customAttributes) + //{ + // if (customAttributes.Length == 0) + // return []; + + // var a = new CustomAttributeBuilder[customAttributes.Length]; + // for (int i = 0; i < customAttributes.Length; i++) + // a[i] = customAttributes[i].Unpack(); + + // return a; + //} + + ///// + ///// Unpacks the s. + ///// + ///// + ///// + //public static CustomAttributeBuilder[] Unpack(this ImmutableArray attributes) + //{ + // if (attributes.Length == 0) + // return []; + + // var a = new CustomAttributeBuilder[attributes.Length]; + // for (int i = 0; i < attributes.Length; i++) + // a[i] = attributes[i].Unpack(); + + // return a; + //} + + ///// + ///// Unpacks the attribute value object. + ///// + ///// + ///// + //static object? UnpackCustomAttributeValue(object? value) + //{ + // return value switch + // { + // IReadOnlyList l => UnpackCustomAttributeArrayValue(l), + // TypeSymbol t => t.Unpack(), + // System.Reflection.CustomAttributeTypedArgument a => UnpackCustomAttributeValue(a.Value), + // _ => value, + // }; + //} + + ///// + ///// Unpacks the attribute value array. + ///// + ///// + ///// + //static object?[] UnpackCustomAttributeArrayValue(IReadOnlyList items) + //{ + // var a = new object?[items.Count]; + // for (int i = 0; i < items.Count; i++) + // a[i] = UnpackCustomAttributeValue(items[i]); + + // return a; + //} /// /// Returns true if the given type represents a type definition. @@ -511,19 +203,6 @@ public static bool IsTypeDefinition(this Type type) #endif } - /// - /// Returns true if the given method represents a method definition. - /// - /// - /// - public static bool IsMethodDefinition(this MethodBase method) - { - if (method is null) - throw new ArgumentNullException(nameof(method)); - - return method.IsGenericMethod == false || method.IsGenericMethodDefinition; - } - /// /// Substitutes generic type parameters into the specified type. /// diff --git a/src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs index c06ec483cb..b947ae5566 100644 --- a/src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs @@ -1,4 +1,5 @@ -using System.Collections.Immutable; +using System; +using System.Collections.Immutable; using System.Reflection; namespace IKVM.CoreLib.Symbols @@ -7,19 +8,23 @@ namespace IKVM.CoreLib.Symbols class SZArrayTypeSymbol : HasElementSymbol { + ImmutableArray _interfaces; + ImmutableArray _constructors; + ImmutableArray _methods; + /// /// Initializes a new instance. /// /// /// - public SZArrayTypeSymbol(ISymbolContext context, TypeSymbol elementType) : + public SZArrayTypeSymbol(SymbolContext context, TypeSymbol elementType) : base(context, elementType) { } /// - protected override string NameSuffix => "[]"; + protected sealed override string NameSuffix => "[]"; /// public sealed override TypeAttributes Attributes => TypeAttributes.AutoLayout | TypeAttributes.AnsiClass | TypeAttributes.Class | TypeAttributes.Public | TypeAttributes.Sealed | TypeAttributes.Serializable; @@ -31,7 +36,7 @@ public SZArrayTypeSymbol(ISymbolContext context, TypeSymbol elementType) : public sealed override bool IsSZArray => true; /// - public sealed override ITypeSymbol? BaseType => Context.ResolveCoreType("System.Array"); + public sealed override TypeSymbol? BaseType => Context.ResolveCoreType("System.Array"); /// public sealed override int GetArrayRank() @@ -40,15 +45,65 @@ public sealed override int GetArrayRank() } /// - public sealed override IImmutableList GetDeclaredConstructors() + public sealed override ImmutableArray GetInterfaces() + { + if (_interfaces == default) + ImmutableInterlocked.InterlockedInitialize(ref _interfaces, [ + Context.ResolveCoreType("System.Collections.Generic.IEnumerable`1").MakeGenericType([GetElementType()!]), + Context.ResolveCoreType("System.Collections.Generic.ICollection`1").MakeGenericType([GetElementType()!]), + Context.ResolveCoreType("System.Collections.Generic.IList`1").MakeGenericType([GetElementType()!]), + ]); + + return _interfaces; + } + + /// + public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + { + throw new NotImplementedException(); + } + + /// + internal sealed override ImmutableArray GetDeclaredConstructors() { - return ImmutableList.Empty; + if (_constructors == default) + { + var int32 = Context.ResolveCoreType("System.Int32"); + var param = ImmutableArray.Empty; + + var b = ImmutableArray.CreateBuilder(); + for (TypeSymbol? type = this; type != null && type.IsSZArray; type = type.GetElementType()) + b.Add(new SyntheticConstructorSymbol(Context, Module, this, MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, param = param.Add(int32))); + + ImmutableInterlocked.InterlockedInitialize(ref _constructors, b.ToImmutable()); + } + + return _constructors; + } + + /// + internal sealed override ImmutableArray GetDeclaredMethods() + { + if (_methods == default) + { + var int32 = Context.ResolveCoreType("System.Int32"); + var args = ImmutableArray.Create(int32); + + ImmutableInterlocked.InterlockedInitialize(ref _methods, + [ + new SyntheticMethodSymbol(Context, Module, this, "Set", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, null, [int32, GetElementType()!]), + new SyntheticMethodSymbol(Context, Module, this, "Address", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, GetElementType()!.MakeByRefType(), args), + new SyntheticMethodSymbol(Context, Module, this, "Get", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, GetElementType(), args), + ]); + } + + return _methods; } /// - public sealed override IImmutableList GetDeclaredMethods() + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return ImmutableList.Empty; + throw new NotImplementedException(); } } diff --git a/src/IKVM.CoreLib/Symbols/Symbol.cs b/src/IKVM.CoreLib/Symbols/Symbol.cs new file mode 100644 index 0000000000..bbb9fdd149 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Symbol.cs @@ -0,0 +1,35 @@ +using System; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Base type for symbols. + /// + abstract class Symbol + { + + internal const BindingFlags DefaultLookup = BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public; + internal const BindingFlags DeclaredOnlyLookup = BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static | BindingFlags.DeclaredOnly; + + readonly SymbolContext _context; + + /// + /// Initializes a new instance. + /// + /// + /// + protected Symbol(SymbolContext context) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + } + + /// + /// Gets the associated symbol context. + /// + public SymbolContext Context => _context; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/SymbolContext.cs b/src/IKVM.CoreLib/Symbols/SymbolContext.cs new file mode 100644 index 0000000000..5ab303fb6e --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/SymbolContext.cs @@ -0,0 +1,41 @@ +using System.Collections.Immutable; + +using IKVM.CoreLib.Symbols.Emit; + +namespace IKVM.CoreLib.Symbols +{ + + abstract class SymbolContext + { + + /// + /// Initializes a new instance. + /// + protected SymbolContext() + { + DefaultBinder = new DefaultBinder(this); + } + + /// + /// Gets the binder. + /// + internal DefaultBinder DefaultBinder { get; } + + /// + /// Resolves the named type from the core assembly. + /// + /// + /// + public abstract TypeSymbol ResolveCoreType(string typeName); + + /// + /// Defines a dynamic assembly that has the specified name. + /// + /// + /// + /// + public abstract AssemblySymbolBuilder DefineAssembly(AssemblyIdentity name, ImmutableArray attributes); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/SymbolUtil.cs b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs index 71e68dc1b1..3cc0859f57 100644 --- a/src/IKVM.CoreLib/Symbols/SymbolUtil.cs +++ b/src/IKVM.CoreLib/Symbols/SymbolUtil.cs @@ -1,10 +1,4 @@ -using System; -using System.Collections.Generic; -using System.Collections.Immutable; -using System.Linq; -using System.Reflection; - -using IKVM.CoreLib.Collections; +using System.Reflection; namespace IKVM.CoreLib.Symbols { @@ -31,164 +25,24 @@ static bool BindingFlagsMatch(bool state, BindingFlags flags, BindingFlags trueF /// /// /// - public static bool BindingFlagsMatch(IMethodSymbol member, BindingFlags flags) + public static bool BindingFlagsMatch(MethodBaseSymbol member, BindingFlags flags) { return BindingFlagsMatch(member.IsPublic, flags, BindingFlags.Public, BindingFlags.NonPublic) && BindingFlagsMatch(member.IsStatic, flags, BindingFlags.Static, BindingFlags.Instance); } /// - /// Evaluates whether the specified would match the . + /// Evaluates whether the specified would match the . /// /// /// /// - public static bool BindingFlagsMatchInherited(IMethodSymbol method, BindingFlags flags) + public static bool BindingFlagsMatchInherited(MethodBaseSymbol method, BindingFlags flags) { return BindingFlagsMatch(method.IsPublic, flags, BindingFlags.Public, BindingFlags.NonPublic) && BindingFlagsMatch(method.IsStatic, flags, BindingFlags.Static | BindingFlags.FlattenHierarchy, BindingFlags.Instance); } - /// - /// Selects the single method that corresponds to the given query. Throws an if multiple candidates are found. - /// - /// - /// - /// - /// - /// - /// - /// - /// - public static IMethodSymbol? SelectMethod(ITypeSymbol type, BindingFlags bindingFlags, string? name, IReadOnlyList? parameterTypes, IReadOnlyList? modifiers) - { - var list = SelectMethods(type, bindingFlags, name, parameterTypes, modifiers); - if (list == null) - throw new InvalidOperationException(); - - return list.Count switch - { - 0 => null, - 1 => list[0], - _ => throw new AmbiguousMatchException(), - }; - } - - /// - /// Selects the methods that corresponds to the given query. - /// - /// - /// - /// - public static IImmutableList SelectMethods(ITypeSymbol type, BindingFlags bindingFlags, string? name, IReadOnlyList? parameterTypes, IReadOnlyList? modifiers) - { - // we start by copying the declared methods and either removing or adding - // optimally, if doing no work, we end up returning the same list - // but we might also be appending only, thus preserving some space thanks to the immutable collection - var list = type.GetDeclaredMethods(); - - // remove items that do not match binding flags - foreach (var declaredMethod in list) - if (BindingFlagsMatch(declaredMethod, bindingFlags) == false) - list = list.Remove(declaredMethod); - - // we do want to check inherited methods - if ((bindingFlags & BindingFlags.DeclaredOnly) == 0) - { - // keep a record of those methods which have been preserved - var baseMethods = new HashSet(); - - // record base methods of already emitted virtual methods - foreach (var method in list) - if (method.IsVirtual) - baseMethods.Add(method.GetBaseDefinition()); - - for (var baseType = type.BaseType; baseType != null; baseType = baseType.BaseType) - { - var baseTypeMethods = baseType.GetDeclaredMethods(); - if (baseTypeMethods == null) - throw new InvalidOperationException(); - - // remove base methods that do not match inherited binding flags - // remove base methods that are virtual and already tracked - foreach (var baseTypeMethod in baseTypeMethods) - if (BindingFlagsMatchInherited(baseTypeMethod, bindingFlags) == false || baseTypeMethod.IsVirtual && baseMethods.Contains(baseTypeMethod.GetBaseDefinition())) - baseTypeMethods = baseTypeMethods.Remove(baseTypeMethod); - - // append to emitted list - list = list.AddRange(baseTypeMethods); - } - } - - // remove methods that do not match filter conditions - foreach (var method in list) - if (MethodFilterPredicate(method, bindingFlags, name, parameterTypes, modifiers) == false) - list = list.Remove(method); - - // return final list - return list; - } - - /// - /// Predicate that determines if the method matches the specification. - /// - /// - /// - /// - /// - /// - static bool MethodFilterPredicate(IMethodSymbol method, BindingFlags bindingFlags, string? name, IReadOnlyList? parameterTypes, IReadOnlyList? modifiers) - { - if (name != null) - { - var nameComparison = StringComparison.Ordinal; - if ((bindingFlags & BindingFlags.IgnoreCase) != 0) - nameComparison = StringComparison.OrdinalIgnoreCase; - if (string.Equals(method.Name, name, nameComparison) == false) - return false; - } - - if (parameterTypes != null) - if (MatchParameterTypes(method, parameterTypes) == false) - return false; - - if (modifiers != null) - if (MatchModifiers(method, modifiers) == false) - return false; - - return true; - } - - /// - /// Checks that the parameters types of the method match the given parameter types. - /// - /// - /// - /// - static bool MatchParameterTypes(IMethodSymbol method, IReadOnlyList parameterTypes) - { - var methodParameters = method.GetParameters(); - if (methodParameters.Length != parameterTypes.Count) - return false; - - for (int i = 0; i < methodParameters.Length; i++) - if (methodParameters[i].ParameterType != parameterTypes[i]) - return false; - - return true; - } - - /// - /// Checks that the parameter modifiers match. For now does nothing. - /// - /// - /// - /// - static bool MatchModifiers(IMethodSymbol method, IReadOnlyList modifiers) - { - return true; - } - } } diff --git a/src/IKVM.CoreLib/Symbols/SyntheticConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/SyntheticConstructorSymbol.cs new file mode 100644 index 0000000000..049713d511 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/SyntheticConstructorSymbol.cs @@ -0,0 +1,109 @@ +using System; +using System.Collections.Immutable; +using System.Linq; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class SyntheticConstructorSymbol : ConstructorSymbol + { + + readonly TypeSymbol? _declaringType; + readonly MethodAttributes _attributes; + readonly CallingConventions _callingConventions; + readonly ImmutableArray _parameters; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public SyntheticConstructorSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol declaringType, MethodAttributes attributes, CallingConventions callingConventions, ImmutableArray parameters) : + base(context, declaringType) + { + _declaringType = declaringType; + _attributes = attributes; + _callingConventions = callingConventions; + _parameters = parameters; + } + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public SyntheticConstructorSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol declaringType, MethodAttributes attributes, CallingConventions callingConventions, ImmutableArray parameters) : + base(context, declaringType) + { + _declaringType = declaringType; + _attributes = attributes; + _callingConventions = callingConventions; + _parameters = parameters.Select((i, j) => new SyntheticParameterSymbol(context, this, null, ParameterAttributes.None, i, j)).ToImmutableArray(); + } + + /// + public override MethodAttributes Attributes => _attributes; + + /// + public override CallingConventions CallingConvention => _callingConventions; + + /// + public override bool ContainsGenericParameters => false; + + /// + public override bool IsGenericMethod => false; + + /// + public override bool IsGenericMethodDefinition => false; + + /// + public override MethodImplAttributes MethodImplementationFlags => MethodImplAttributes.Managed; + + /// + public override string Name => IsStatic ? ConstructorInfo.TypeConstructorName : ConstructorInfo.ConstructorName; + + /// + public override bool IsMissing => false; + + /// + public override bool ContainsMissing => false; + + /// + public override bool IsComplete => true; + + /// + public override ImmutableArray GetGenericArguments() + { + throw new NotImplementedException(); + } + + /// + public override MethodImplAttributes GetMethodImplementationFlags() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetParameters() + { + return _parameters; + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/SyntheticMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/SyntheticMethodSymbol.cs new file mode 100644 index 0000000000..76f27f1f07 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/SyntheticMethodSymbol.cs @@ -0,0 +1,140 @@ +using System; +using System.Collections.Immutable; +using System.Linq; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class SyntheticMethodSymbol : MethodSymbol + { + + readonly TypeSymbol? _declaringType; + readonly string _name; + readonly MethodAttributes _attributes; + readonly CallingConventions _callingConventions; + readonly ParameterSymbol _returnParameter; + readonly ImmutableArray _parameters; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + /// + /// + public SyntheticMethodSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol? declaringType, string name, MethodAttributes attributes, CallingConventions callingConventions, ParameterSymbol? returnParameter, ImmutableArray parameters) : + base(context, module, declaringType) + { + _declaringType = declaringType; + _name = name ?? throw new ArgumentNullException(nameof(name)); + _attributes = attributes; + _callingConventions = callingConventions; + _returnParameter = returnParameter ?? new SyntheticParameterSymbol(context, this, null, ParameterAttributes.Retval, context.ResolveCoreType("System.Void"), -1); + _parameters = parameters; + } + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + /// + /// + public SyntheticMethodSymbol(SymbolContext context, ModuleSymbol module, TypeSymbol? declaringType, string name, MethodAttributes attributes, CallingConventions callingConventions, TypeSymbol? returnType, ImmutableArray parameters) : + base(context, module, declaringType) + { + _declaringType = declaringType; + _name = name ?? throw new ArgumentNullException(nameof(name)); + _attributes = attributes; + _callingConventions = callingConventions; + _returnParameter = new SyntheticParameterSymbol(context, this, null, ParameterAttributes.Retval, returnType ?? context.ResolveCoreType("System.Void"), -1); + _parameters = parameters.Select((i, j) => new SyntheticParameterSymbol(context, this, null, ParameterAttributes.None, i, j)).ToImmutableArray(); + } + + /// + public override ParameterSymbol ReturnParameter => _returnParameter; + + /// + public override TypeSymbol ReturnType => ReturnParameter.ParameterType; + + /// + public override ICustomAttributeProvider ReturnTypeCustomAttributes => throw new NotImplementedException(); + + /// + public override MethodAttributes Attributes => _attributes; + + /// + public override CallingConventions CallingConvention => _callingConventions; + + /// + public override bool ContainsGenericParameters => false; + + /// + public override bool IsGenericMethod => false; + + /// + public override bool IsGenericMethodDefinition => false; + + /// + public override MethodImplAttributes MethodImplementationFlags => MethodImplAttributes.Managed; + + /// + public override string Name => _name; + + /// + public override bool IsMissing => false; + + /// + public override bool ContainsMissing => false; + + /// + public override bool IsComplete => true; + + /// + public override MethodSymbol GetBaseDefinition() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetGenericArguments() + { + throw new NotImplementedException(); + } + + /// + public override MethodSymbol GetGenericMethodDefinition() + { + throw new NotImplementedException(); + } + + /// + public override MethodImplAttributes GetMethodImplementationFlags() + { + throw new NotImplementedException(); + } + + /// + public override ImmutableArray GetParameters() + { + return _parameters; + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + throw new NotImplementedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/SyntheticParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/SyntheticParameterSymbol.cs new file mode 100644 index 0000000000..66230ac6ca --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/SyntheticParameterSymbol.cs @@ -0,0 +1,73 @@ +using System; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + class SyntheticParameterSymbol : ParameterSymbol + { + + readonly string? _name; + readonly ParameterAttributes _attributes; + readonly TypeSymbol _type; + + /// + /// Initializes a new instance. + /// + /// + /// + /// + /// + /// + /// + public SyntheticParameterSymbol(SymbolContext context, MemberSymbol declaringMember, string? name, ParameterAttributes attributes, TypeSymbol type, int position) : + base(context, declaringMember, position) + { + _name = name ?? throw new ArgumentNullException(nameof(name)); + _attributes = attributes; + _type = type; + } + + /// + public override ParameterAttributes Attributes => _attributes; + + /// + public override TypeSymbol ParameterType => _type; + + /// + public override string? Name => _name; + + /// + public override object? DefaultValue => null; + + /// + public override bool IsMissing => false; + + /// + public override bool ContainsMissing => false; + + /// + public override bool IsComplete => true; + + /// + public override ImmutableArray GetOptionalCustomModifiers() + { + return ImmutableArray.Empty; + } + + /// + public override ImmutableArray GetRequiredCustomModifiers() + { + return ImmutableArray.Empty; + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + return ImmutableArray.Empty; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeConstructorSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/TypeConstructorSymbolPolicy.cs new file mode 100644 index 0000000000..bf6d1ecb80 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeConstructorSymbolPolicy.cs @@ -0,0 +1,53 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for constructor symbols. + /// + class TypeConstructorSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(TypeSymbol type) => type.GetDeclaredConstructors(); + + /// + public sealed override TypeSymbol? GetInheritedParent(TypeSymbol parent) => parent.BaseType; + + public sealed override BindingFlags ModifyBindingFlags(BindingFlags bindingFlags) + { + return bindingFlags | BindingFlags.DeclaredOnly; + } + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => true; + + /// + public sealed override void GetMemberAttributes(ConstructorSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + var methodAttributes = member.Attributes; + visibility = methodAttributes & MethodAttributes.MemberAccessMask; + isStatic = 0 != (methodAttributes & MethodAttributes.Static); + isVirtual = false; + isNewSlot = false; + } + + /// + public sealed override bool ImplicitlyOverrides(ConstructorSymbol? baseMember, ConstructorSymbol? derivedMember) => false; + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(ConstructorSymbol member, List priorMembers) => false; + + /// + public sealed override bool OkToIgnoreAmbiguity(ConstructorSymbol m1, ConstructorSymbol m2) + { + throw new NotSupportedException(); + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeEventSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/TypeEventSymbolPolicy.cs new file mode 100644 index 0000000000..e0fa470e97 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeEventSymbolPolicy.cs @@ -0,0 +1,79 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for members on a . + /// + class TypeEventSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(TypeSymbol type) => type.GetDeclaredEvents(); + + /// + public override TypeSymbol? GetInheritedParent(TypeSymbol parent) => parent.BaseType; + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => false; + + /// + public sealed override void GetMemberAttributes(EventSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + var accessorMethod = GetAccessorMethod(member); + if (accessorMethod == null) + { + // If we got here, this is a inherited EventSymbol that only had private accessors and is now refusing to give them out + // because that's what the rules of inherited EventSymbol's are. Such a EventSymbol is also considered private and will never be + // given out of a Type.GetProperty() call. So all we have to do is set its visibility to Private and it will get filtered out. + // Other values need to be set to satisfy C# but they are meaningless. + visibility = MethodAttributes.Private; + isStatic = false; + isVirtual = false; + isNewSlot = true; + return; + } + + var methodAttributes = accessorMethod.Attributes; + visibility = methodAttributes & MethodAttributes.MemberAccessMask; + isStatic = (0 != (methodAttributes & MethodAttributes.Static)); + isVirtual = (0 != (methodAttributes & MethodAttributes.Virtual)); + isNewSlot = (0 != (methodAttributes & MethodAttributes.NewSlot)); + } + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(EventSymbol member, List priorMembers) + { + foreach (var i in priorMembers) + if (i.Name == member.Name) + return true; + + return false; + } + + /// + public sealed override bool ImplicitlyOverrides(EventSymbol? baseMember, EventSymbol? derivedMember) + { + var baseAccessor = GetAccessorMethod(baseMember!); + var derivedAccessor = GetAccessorMethod(derivedMember!); + return MemberSymbolPolicy.Default.ImplicitlyOverrides(baseAccessor, derivedAccessor); + } + + /// + public sealed override bool OkToIgnoreAmbiguity(EventSymbol m1, EventSymbol m2) + { + return false; + } + + /// + static MethodSymbol? GetAccessorMethod(EventSymbol e) + { + return e.AddMethod; + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeFieldSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/TypeFieldSymbolPolicy.cs new file mode 100644 index 0000000000..4b091df2cd --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeFieldSymbolPolicy.cs @@ -0,0 +1,44 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for field symbols. + /// + class TypeFieldSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(TypeSymbol type) => type.GetDeclaredFields(); + + /// + public sealed override TypeSymbol? GetInheritedParent(TypeSymbol parent) => parent.BaseType; + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => false; + + /// + public sealed override void GetMemberAttributes(FieldSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + var fieldAttributes = member.Attributes; + visibility = (MethodAttributes)(fieldAttributes & FieldAttributes.FieldAccessMask); + isStatic = (0 != (fieldAttributes & FieldAttributes.Static)); + isVirtual = false; + isNewSlot = false; + } + + /// + public sealed override bool ImplicitlyOverrides(FieldSymbol? baseMember, FieldSymbol? derivedMember) => false; + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(FieldSymbol member, List priorMembers) => false; + + /// + public sealed override bool OkToIgnoreAmbiguity(FieldSymbol m1, FieldSymbol m2) => true; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeMethodSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/TypeMethodSymbolPolicy.cs new file mode 100644 index 0000000000..14ab960da8 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeMethodSymbolPolicy.cs @@ -0,0 +1,65 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for constructor symbols. + /// + class TypeMethodSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(TypeSymbol type) => type.GetDeclaredMethods(); + + /// + public sealed override TypeSymbol? GetInheritedParent(TypeSymbol parent) => parent.BaseType; + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => false; + + /// + public sealed override void GetMemberAttributes(MethodSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + var methodAttributes = member.Attributes; + visibility = methodAttributes & MethodAttributes.MemberAccessMask; + isStatic = (0 != (methodAttributes & MethodAttributes.Static)); + isVirtual = (0 != (methodAttributes & MethodAttributes.Virtual)); + isNewSlot = (0 != (methodAttributes & MethodAttributes.NewSlot)); + } + + /// + public sealed override bool ImplicitlyOverrides(MethodSymbol? baseMember, MethodSymbol? derivedMember) + { + return AreNamesAndSignaturesEqual(baseMember!, derivedMember!); + } + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(MethodSymbol member, List priorMembers) + { + if (!member.IsVirtual) + return false; + + foreach (var prior in priorMembers) + { + var attributes = prior.Attributes & (MethodAttributes.Virtual | MethodAttributes.VtableLayoutMask); + if (attributes != (MethodAttributes.Virtual | MethodAttributes.ReuseSlot)) + continue; + if (!ImplicitlyOverrides(member, prior)) + continue; + + return true; + } + return false; + } + + public sealed override bool OkToIgnoreAmbiguity(MethodSymbol m1, MethodSymbol m2) + { + return DefaultBinder.CompareMethodSig(m1, m2); // If all candidates have the same signature, pick the most derived one without throwing an AmbiguousMatchException. + } + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypePropertySymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/TypePropertySymbolPolicy.cs new file mode 100644 index 0000000000..d3308bc0aa --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypePropertySymbolPolicy.cs @@ -0,0 +1,87 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for property symbols. + /// + class TypePropertySymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(TypeSymbol type) => type.GetDeclaredProperties(); + + /// + public sealed override TypeSymbol? GetInheritedParent(TypeSymbol parent) => parent.BaseType; + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => false; + + /// + public sealed override void GetMemberAttributes(PropertySymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + var accessorMethod = GetAccessorMethod(member); + if (accessorMethod == null) + { + // If we got here, this is a inherited PropertySymbol that only had private accessors and is now refusing to give them out + // because that's what the rules of inherited PropertySymbol's are. Such a PropertySymbol is also considered private and will never be + // given out of a Type.GetProperty() call. So all we have to do is set its visibility to Private and it will get filtered out. + // Other values need to be set to satisfy C# but they are meaningless. + visibility = MethodAttributes.Private; + isStatic = false; + isVirtual = false; + isNewSlot = true; + return; + } + + var methodAttributes = accessorMethod.Attributes; + visibility = methodAttributes & MethodAttributes.MemberAccessMask; + isStatic = (0 != (methodAttributes & MethodAttributes.Static)); + isVirtual = (0 != (methodAttributes & MethodAttributes.Virtual)); + isNewSlot = (0 != (methodAttributes & MethodAttributes.NewSlot)); + } + + /// + public sealed override bool ImplicitlyOverrides(PropertySymbol? baseMember, PropertySymbol? derivedMember) + { + var baseAccessor = GetAccessorMethod(baseMember!); + var derivedAccessor = GetAccessorMethod(derivedMember!); + return MemberSymbolPolicy.Default.ImplicitlyOverrides(baseAccessor, derivedAccessor); + } + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(PropertySymbol member, List priorMembers) + { + var baseAccessor = GetAccessorMethod(member)!; + + foreach (var prior in priorMembers) + { + var derivedAccessor = GetAccessorMethod(prior)!; + if (!AreNamesAndSignaturesEqual(baseAccessor, derivedAccessor)) + continue; + if (derivedAccessor.IsStatic != baseAccessor.IsStatic) + continue; + if (!(prior.PropertyType.Equals(member.PropertyType))) + continue; + + return true; + } + + return false; + } + + /// + public sealed override bool OkToIgnoreAmbiguity(PropertySymbol m1, PropertySymbol m2) + { + return false; + } + + /// + static MethodSymbol? GetAccessorMethod(PropertySymbol property) => property.GetMethod ?? property.SetMethod; + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/TypeSpecTable.cs b/src/IKVM.CoreLib/Symbols/TypeSpecTable.cs index e6a94c1a2c..dc9099acc3 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSpecTable.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSpecTable.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Concurrent; using System.Collections.Immutable; +using System.Linq; using System.Threading; using IKVM.CoreLib.Collections; @@ -12,7 +13,7 @@ namespace IKVM.CoreLib.Symbols struct TypeSpecTable { - readonly ISymbolContext _context; + readonly SymbolContext _context; readonly TypeSymbol _elementType; IndexRangeDictionary _asArray; @@ -20,7 +21,7 @@ struct TypeSpecTable SZArrayTypeSymbol? _asSZArray; PointerTypeSymbol? _asPointer; ByRefTypeSymbol? _asByRef; - ConcurrentDictionary, ConstructedGenericTypeSymbol>? _genericTypeSymbols; + ConcurrentDictionary, ConstructedGenericTypeSymbol>? _genericTypeSymbols; /// /// Initializes a new instance. @@ -28,7 +29,7 @@ struct TypeSpecTable /// /// /// - public TypeSpecTable(ISymbolContext context, TypeSymbol elementType) + public TypeSpecTable(SymbolContext context, TypeSymbol elementType) { _context = context ?? throw new ArgumentNullException(nameof(context)); _elementType = elementType ?? throw new ArgumentNullException(nameof(elementType)); @@ -50,7 +51,7 @@ public ArrayTypeSymbol GetOrCreateArrayTypeSymbol(int rank) { if (_asArray[rank] == null) using (_asArrayLock.CreateWriteLock()) - _asArray[rank] = new ArrayTypeSymbol(_context, _elementType, rank); + _asArray[rank] = new ArrayTypeSymbol(_context, _elementType, rank, ImmutableArray.Empty, Enumerable.Repeat(0, rank).ToImmutableArray()); return _asArray[rank] ?? throw new InvalidOperationException(); } @@ -97,9 +98,9 @@ public ByRefTypeSymbol GetOrCreateByRefTypeSymbol() /// /// /// - public ConstructedGenericTypeSymbol GetOrCreateGenericTypeSymbol(IImmutableList genericTypeArguments) + public ConstructedGenericTypeSymbol GetOrCreateGenericTypeSymbol(ImmutableArray genericTypeArguments) { - if (genericTypeArguments is null) + if (genericTypeArguments == default) throw new ArgumentNullException(nameof(genericTypeArguments)); if (_elementType.IsGenericTypeDefinition == false) @@ -116,9 +117,9 @@ public ConstructedGenericTypeSymbol GetOrCreateGenericTypeSymbol(IImmutableList< /// /// /// - readonly ConstructedGenericTypeSymbol CreateGenericTypeSymbol(IImmutableList genericTypeArguments) + readonly ConstructedGenericTypeSymbol CreateGenericTypeSymbol(ImmutableArray genericTypeArguments) { - return new ConstructedGenericTypeSymbol(_context, _elementType, genericTypeArguments); + return new ConstructedGenericTypeSymbol(_context, _elementType, new GenericContext(genericTypeArguments, null)); } } diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbol.cs b/src/IKVM.CoreLib/Symbols/TypeSymbol.cs index ea7e51f45a..4cc65672a8 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSymbol.cs @@ -1,5 +1,8 @@ using System; +using System.Collections.Generic; using System.Collections.Immutable; +using System.Diagnostics; +using System.Linq; using System.Reflection; namespace IKVM.CoreLib.Symbols @@ -8,21 +11,20 @@ namespace IKVM.CoreLib.Symbols abstract class TypeSymbol : MemberSymbol { - const BindingFlags DefaultLookup = BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public; - const BindingFlags DeclaredOnlyLookup = BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static | BindingFlags.DeclaredOnly; - TypeSpecTable _typeSpecTable; string? _assemblyQualifiedName; + ImmutableList? _genericTypeArguments; /// /// Initializes a new instance. /// /// - public TypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? declaringType) : - base(context, module, declaringType) + /// + public TypeSymbol(SymbolContext context, ModuleSymbol module) : + base(context, module, null) { - _typeSpecTable = new TypeSpecTable(Context, this); + _typeSpecTable = new TypeSpecTable(context, this); } /// @@ -31,7 +33,7 @@ public TypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? decl public abstract TypeAttributes Attributes { get; } /// - /// Gets a that represents the declaring method, if the current represents a type parameter of a generic method. + /// Gets a that represents the declaring method, if the current represents a type parameter of a generic method. /// public abstract MethodBaseSymbol? DeclaringMethod { get; } @@ -95,7 +97,7 @@ public TypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? decl /// /// Gets an array of the generic type arguments for this type. /// - public abstract ImmutableList GenericTypeArguments { get; } + public ImmutableArray GenericTypeArguments => IsGenericTypeDefinition ? ImmutableArray.Empty : GetGenericArguments(); /// /// Gets a value that indicates whether the type is a type definition. @@ -118,9 +120,19 @@ public TypeSymbol(ISymbolContext context, IModuleSymbol module, TypeSymbol? decl public bool IsGenericType => IsConstructedGenericType || IsGenericTypeDefinition; /// - /// Gets a value indicating whether the current represents a type parameter in the definition of a generic type or method. + /// Gets a value indicating whether the current represents a type parameter in the definition of a generic type or method. /// - public abstract bool IsGenericParameter { get; } + public bool IsGenericParameter => IsGenericTypeParameter || IsGenericMethodParameter; + + /// + /// Gets a value that indicates whether the current represents a type parameter in the definition of a generic type. + /// + public abstract bool IsGenericTypeParameter { get; } + + /// + /// Gets a value that indicates whether the current represents a type parameter in the definition of a generic method. + /// + public abstract bool IsGenericMethodParameter { get; } /// /// Gets a value indicating whether the fields of the current type are laid out automatically by the common language runtime. @@ -300,11 +312,6 @@ bool ComputeIsVisible() /// public bool IsSerializable => (Attributes & TypeAttributes.Serializable) != 0; - /// - /// Gets a value that indicates whether the type is a signature type. - /// - public abstract bool IsSignatureType { get; } - /// /// Gets a value indicating whether the type has a name that requires special handling. /// @@ -313,7 +320,7 @@ bool ComputeIsVisible() /// /// Gets the initializer for the type. /// - public abstract ConstructorSymbol? TypeInitializer { get; } + public ConstructorSymbol? TypeInitializer => GetConstructor(BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic, CallingConventions.Any, [], null); /// /// Gets the number of dimensions in an array. @@ -325,14 +332,14 @@ bool ComputeIsVisible() /// Returns all the declared constructors of the current . /// /// - public abstract ImmutableList GetDeclaredConstructors(); + internal abstract ImmutableArray GetDeclaredConstructors(); /// /// Searches for a public instance constructor whose parameters match the types in the specified array. /// /// /// - public ConstructorSymbol? GetConstructor(ImmutableList? types) => GetConstructor(BindingFlags.Public | BindingFlags.Instance, types); + public ConstructorSymbol? GetConstructor(ImmutableArray types) => GetConstructor(BindingFlags.Public | BindingFlags.Instance, types, null); /// /// Searches for a constructor whose parameters match the specified argument types, using the specified binding constraints. @@ -340,26 +347,65 @@ bool ComputeIsVisible() /// /// /// - public abstract ConstructorSymbol? GetConstructor(BindingFlags bindingFlags, ImmutableList? types); + public ConstructorSymbol? GetConstructor(BindingFlags bindingFlags, ImmutableArray types) => GetConstructor(bindingFlags, types, null); + + /// + /// Searches for a constructor whose parameters match the specified argument types and modifiers, using the specified binding constraints. + /// + /// + /// + /// + /// + public ConstructorSymbol? GetConstructor(BindingFlags bindingFlags, ImmutableArray types, ImmutableArray? modifiers) => GetConstructor(bindingFlags, CallingConventions.Any, types, modifiers); /// - /// Returns all the public constructors defined for the current . + /// Searches for a constructor whose parameters match the specified argument types, using the specified binding constraints. /// + /// + /// /// - public ImmutableList GetConstructors() => GetConstructors(BindingFlags.Public | BindingFlags.Instance); + public ConstructorSymbol? GetConstructor(BindingFlags bindingFlags, CallingConventions callConvention, ImmutableArray types, ImmutableArray? modifiers) + { + var query = new MemberQuery(this, null, bindingFlags); + var candidates = new List(); + foreach (var candidate in query) + if (QualifiesBasedOnParameterCount(candidate, bindingFlags, callConvention, types)) + candidates.Add(candidate); + + // For perf and .NET Framework compat, fast-path these specific checks before calling on the binder to break ties. + if (candidates.Count == 0) + return null; + + if (types.Length == 0 && candidates.Count == 1) + { + var firstCandidate = candidates[0]; + var parameters = firstCandidate.GetParameters(); + if (parameters.Length == 0) + return firstCandidate; + } + + if ((bindingFlags & BindingFlags.ExactBinding) != 0) + return Context.DefaultBinder.ExactBinding(candidates, types) as ConstructorSymbol; + + return Context.DefaultBinder.SelectMethod(candidates, bindingFlags, types, modifiers) as ConstructorSymbol; + } /// - /// When overridden in a derived class, searches for the constructors defined for the current , using the specified BindingFlags. + /// When overridden in a derived class, searches for the constructors defined for the current , using the specified . /// /// /// - public abstract ImmutableList GetConstructors(BindingFlags bindingFlags); + public IEnumerable GetConstructors() => GetConstructors(DefaultLookup); /// - /// Searches for the members defined for the current whose DefaultMemberAttribute is set. + /// When overridden in a derived class, searches for the constructors defined for the current , using the specified . /// + /// /// - public abstract ImmutableList GetDefaultMembers(); + public IEnumerable GetConstructors(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } /// /// When overridden in a derived class, returns the of the object encompassed or referred to by the current array, pointer or reference type. @@ -378,7 +424,7 @@ bool ComputeIsVisible() /// Returns the names of the members of the current enumeration type. /// /// - public abstract ImmutableList GetEnumNames(); + public abstract ImmutableArray GetEnumNames(); /// /// Returns the underlying type of the current enumeration type. @@ -390,7 +436,7 @@ bool ComputeIsVisible() /// Returns all the declared events of the current . /// /// - public abstract ImmutableList GetDeclaredEvents(); + internal abstract ImmutableArray GetDeclaredEvents(); /// /// Returns the object representing the specified public event. @@ -405,26 +451,32 @@ bool ComputeIsVisible() /// /// /// - public abstract EventSymbol? GetEvent(string name, BindingFlags bindingFlags); + public EventSymbol? GetEvent(string name, BindingFlags bindingFlags) + { + return new MemberQuery(this, name, bindingFlags).Disambiguate(); + } /// /// Returns all the public events that are declared or inherited by the current . /// /// - public ImmutableList GetEvents() => GetEvents(DefaultLookup); + public IEnumerable GetEvents() => GetEvents(DefaultLookup); /// /// When overridden in a derived class, searches for events that are declared or inherited by the current , using the specified binding constraints. /// /// /// - public abstract ImmutableList GetEvents(BindingFlags bindingFlags); + public IEnumerable GetEvents(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } /// /// Returns all the declared fields of the current . /// /// - public abstract ImmutableList GetDeclaredFields(); + internal abstract ImmutableArray GetDeclaredFields(); /// /// Searches for the public field with the specified name. @@ -439,32 +491,38 @@ bool ComputeIsVisible() /// /// /// - public abstract FieldSymbol? GetField(string name, BindingFlags bindingFlags); + public FieldSymbol? GetField(string name, BindingFlags bindingFlags) + { + return new MemberQuery(this, name, bindingFlags).Disambiguate(); + } /// /// Returns all the public fields of the current . /// /// - public ImmutableList GetFields() => GetFields(DefaultLookup); + public IEnumerable GetFields() => GetFields(DefaultLookup); /// /// When overridden in a derived class, searches for the fields defined for the current , using the specified binding constraints. /// /// /// - public abstract ImmutableList GetFields(BindingFlags bindingFlags); + public IEnumerable GetFields(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } /// /// Returns an array of objects that represent the type arguments of a closed generic type or the type parameters of a generic type definition. /// /// - public abstract ImmutableList GetGenericArguments(); + public abstract ImmutableArray GetGenericArguments(); /// /// Returns an array of objects that represent the constraints on the current generic type parameter. /// /// - public abstract ImmutableList GetGenericParameterConstraints(); + public abstract ImmutableArray GetGenericParameterConstraints(); /// /// Returns a object that represents a generic type definition from which the current generic type can be constructed. @@ -477,21 +535,20 @@ bool ComputeIsVisible() /// /// /// - public TypeSymbol? GetInterface(string name) => GetInterface(name, false); + public TypeSymbol? GetInterface(string name) + { + foreach (var i in GetInterfaces()) + if (i.Name == name) + return i; - /// - /// When overridden in a derived class, searches for the specified interface, specifying whether to do a case-insensitive search for the interface name. - /// - /// - /// - /// - public abstract TypeSymbol? GetInterface(string name, bool ignoreCase); + return null; + } /// - /// When overridden in a derived class, gets all the interfaces implemented or if specified,inherited by the current . + /// When overridden in a derived class, gets all the interfaces implemented by the current . /// /// - public abstract ImmutableList GetInterfaces(bool inherit = true); + public abstract ImmutableArray GetInterfaces(); /// /// Returns an interface mapping for the specified interface type. @@ -504,7 +561,7 @@ bool ComputeIsVisible() /// Returns all the declared methods of the current . /// /// - public abstract ImmutableList GetDeclaredMethods(); + internal abstract ImmutableArray GetDeclaredMethods(); /// /// Searches for the public method with the specified name. @@ -519,7 +576,7 @@ bool ComputeIsVisible() /// /// /// - public MethodSymbol? GetMethod(string name, ImmutableList? types) => GetMethod(name, DefaultLookup, types); + public MethodSymbol? GetMethod(string name, ImmutableArray? types) => GetMethod(name, DefaultLookup, types); /// /// Searches for the specified method, using the specified binding constraints. @@ -537,7 +594,7 @@ bool ComputeIsVisible() /// /// /// - public MethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, bindingAttr, CallingConventions.Any, types, modifiers); + public MethodSymbol? GetMethod(string name, BindingFlags bindingAttr, ImmutableArray? types, ImmutableArray? modifiers) => GetMethod(name, bindingAttr, CallingConventions.Any, types, modifiers); /// /// Searches for the specified method whose parameters match the specified argument types, using the specified binding constraints. @@ -546,7 +603,7 @@ bool ComputeIsVisible() /// /// /// - public MethodSymbol? GetMethod(string name, BindingFlags bindingFlags, ImmutableList? types) => GetMethod(name, bindingFlags, CallingConventions.Any, types, null); + public MethodSymbol? GetMethod(string name, BindingFlags bindingFlags, ImmutableArray? types) => GetMethod(name, bindingFlags, CallingConventions.Any, types, null); /// /// Searches for the specified method whose parameters match the specified argument types and modifiers, using the specified binding constraints and the specified calling convention. @@ -557,7 +614,7 @@ bool ComputeIsVisible() /// /// /// - public MethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, 0, bindingFlags, callConvention, types, modifiers); + public MethodSymbol? GetMethod(string name, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableArray? types, ImmutableArray? modifiers) => GetMethod(name, -1, bindingFlags, callConvention, types, modifiers); /// /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints. @@ -568,7 +625,7 @@ bool ComputeIsVisible() /// /// /// - public MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, genericParameterCount, bindingFlags, CallingConventions.Any, types, modifiers); + public MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, ImmutableArray? types, ImmutableArray? modifiers) => GetMethod(name, genericParameterCount, bindingFlags, CallingConventions.Any, types, modifiers); /// /// Searches for the specified public method whose parameters match the specified generic parameter count, argument types and modifiers. @@ -578,7 +635,7 @@ bool ComputeIsVisible() /// /// /// - public MethodSymbol? GetMethod(string name, int genericParameterCount, ImmutableList? types, ImmutableList? modifiers) => GetMethod(name, genericParameterCount, DefaultLookup, CallingConventions.Any, types, modifiers); + public MethodSymbol? GetMethod(string name, int genericParameterCount, ImmutableArray? types, ImmutableArray? modifiers) => GetMethod(name, genericParameterCount, DefaultLookup, CallingConventions.Any, types, modifiers); /// /// Searches for the specified method whose parameters match the specified generic parameter count, argument types and modifiers, using the specified binding constraints and the specified calling convention. @@ -590,20 +647,126 @@ bool ComputeIsVisible() /// /// /// - public abstract MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableList? types, ImmutableList? modifiers); + public MethodSymbol? GetMethod(string name, int genericParameterCount, BindingFlags bindingFlags, CallingConventions callConvention, ImmutableArray? types, ImmutableArray? modifiers) + { + Debug.Assert(name != null); + + // GetMethodImpl() is a funnel for two groups of api. We can distinguish by comparing "types" to null. + if (types == null) + { + // Group #1: This group of api accept only a name and BindingFlags. The other parameters are hard-wired by the non-virtual api entrypoints. + Debug.Assert(genericParameterCount == -1); + Debug.Assert(callConvention == CallingConventions.Any); + Debug.Assert(modifiers == null); + return new MemberQuery(this, name, bindingFlags).Disambiguate(); + } + else + { + // Group #2: This group of api takes a set of parameter types and an optional binder. + var queryResult = new MemberQuery(this, name, bindingFlags); + var candidates = new List(); + foreach (var candidate in queryResult) + { + if (genericParameterCount != -1 && genericParameterCount != candidate.GetGenericArguments().Length) + continue; + if (QualifiesBasedOnParameterCount(candidate, bindingFlags, callConvention, types)) + candidates.Add(candidate); + } + + if (candidates.Count == 0) + return null; + + // For perf and .NET Framework compat, fast-path these specific checks before calling on the binder to break ties. + if (types.Value.Length == 0 && candidates.Count == 1) + return (MethodSymbol)candidates[0]; + + return Context.DefaultBinder.SelectMethod(candidates, bindingFlags, types.Value, modifiers) as MethodSymbol; + } + } + + /// + /// Returns true if the given method symbol would qualify as a candidate in a query for the specified binding flags and argument type count. + /// + /// + /// + /// + /// + /// + /// + static bool QualifiesBasedOnParameterCount(MethodBaseSymbol methodBase, BindingFlags bindingFlags, CallingConventions callConvention, IReadOnlyList types) + { + #region Check CallingConvention + + if ((callConvention & CallingConventions.Any) == 0) + { + if ((callConvention & CallingConventions.VarArgs) != 0 && (methodBase.CallingConvention & CallingConventions.VarArgs) == 0) + return false; + + if ((callConvention & CallingConventions.Standard) != 0 && (methodBase.CallingConvention & CallingConventions.Standard) == 0) + return false; + } + + #endregion + + #region ArgumentTypes + + var parameterInfos = methodBase.GetParameters(); + + if (types.Count != parameterInfos.Length) + { + return false; + } + else + { + #region Exact Binding + + if ((bindingFlags & BindingFlags.ExactBinding) != 0) + { + // Legacy behavior is to ignore ExactBinding when InvokeMember is specified. + // Why filter by InvokeMember? If the answer is we leave this to the binder then why not leave + // all the rest of this to the binder too? Further, what other semanitc would the binder + // use for BindingFlags.ExactBinding besides this one? Further, why not include CreateInstance + // in this if statement? That's just InvokeMethod with a constructor, right? + if ((bindingFlags & (BindingFlags.InvokeMethod)) == 0) + { + for (int i = 0; i < parameterInfos.Length; i++) + { + // a null argument type implies a null arg which is always a perfect match + if (types[i] is not null && types[i] != parameterInfos[i].ParameterType) + return false; + } + } + } + + #endregion + } + + #endregion + + return true; + } /// /// Returns all the public methods of the current . /// /// - public ImmutableList GetMethods() => GetMethods(DefaultLookup); + public IEnumerable GetMethods() => GetMethods(DefaultLookup); /// /// When overridden in a derived class, searches for the methods defined for the current , using the specified binding constraints. /// /// /// - public abstract ImmutableList GetMethods(BindingFlags bindingFlags); + public IEnumerable GetMethods(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } + + /// + /// Returns all the declared nested types of the current . + /// + /// + internal abstract ImmutableArray GetDeclaredNestedTypes(); /// /// Searches for the public nested type with the specified name. @@ -618,33 +781,39 @@ bool ComputeIsVisible() /// /// /// - public abstract TypeSymbol? GetNestedType(string name, BindingFlags bindingFlags); + public TypeSymbol? GetNestedType(string name, BindingFlags bindingFlags) + { + return new MemberQuery(this, name, bindingFlags).Disambiguate(); + } /// /// Returns the public types nested in the current . /// /// - public ImmutableList GetNestedTypes() => GetNestedTypes(DefaultLookup); + public IEnumerable GetNestedTypes() => GetNestedTypes(DefaultLookup); /// /// When overridden in a derived class, searches for the types nested in the current , using the specified binding constraints. /// /// /// - public abstract ImmutableList GetNestedTypes(BindingFlags bindingFlags); + public IEnumerable GetNestedTypes(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } /// /// Returns all the declared properties of the current . /// /// - public abstract ImmutableList GetDeclaredProperties(); + internal abstract ImmutableArray GetDeclaredProperties(); /// /// Searches for the public property with the specified name. /// /// /// - public PropertySymbol? GetProperty(string name) => GetProperty(name, DefaultLookup); + public PropertySymbol? GetProperty(string name) => GetProperty(name, DefaultLookup, null, null, null); /// /// Searches for the specified property, using the specified binding constraints. @@ -652,7 +821,7 @@ bool ComputeIsVisible() /// /// /// - public abstract PropertySymbol? GetProperty(string name, BindingFlags bindingFlags); + public PropertySymbol? GetProperty(string name, BindingFlags bindingFlags) => GetProperty(name, bindingFlags, null, null, null); /// /// Searches for the specified public property whose parameters match the specified argument types. @@ -660,37 +829,99 @@ bool ComputeIsVisible() /// /// /// - public PropertySymbol? GetProperty(string name, ImmutableList? types) => GetProperty(name, null, types); + public PropertySymbol? GetProperty(string name, ImmutableArray? types) => GetProperty(name, DefaultLookup, null, types, null); /// /// Searches for the public property with the specified name and return type. /// /// - /// + /// /// - public PropertySymbol? GetProperty(string name, TypeSymbol? returnType) => GetProperty(name, returnType, null); + public PropertySymbol? GetProperty(string name, TypeSymbol? propertyType) => GetProperty(name, DefaultLookup, propertyType, null, null); /// /// Searches for the specified public property whose parameters match the specified argument types. /// /// - /// + /// /// /// - public abstract PropertySymbol? GetProperty(string name, TypeSymbol? returnType, ImmutableList? types); + public PropertySymbol? GetProperty(string name, TypeSymbol? propertyType, ImmutableArray? types) => GetProperty(name, DefaultLookup, propertyType, types, null); + + /// + /// Searches for the specified public property whose parameters match the specified argument types. + /// + /// + /// + /// + /// + public PropertySymbol? GetProperty(string name, BindingFlags bindingFlags, TypeSymbol? propertyType, ImmutableArray? types, ImmutableArray? modifiers) + { + if (types == null && propertyType == null) + { + // Group #1: This group of api accept only a name and BindingFlags. The other parameters are hard-wired by the non-virtual api entrypoints. + return new MemberQuery(this, name, bindingFlags).Disambiguate(); + } + else + { + // Group #2: This group of api takes a set of parameter types, a return type (both cannot be null) and an optional binder. + var query = new MemberQuery(this, name, bindingFlags).ToArray(); + + // compose candidates, removing mismatched parameters + var candidates = new List(query.Length); + foreach (var candidate in query) + if (types == null || (candidate.GetIndexParameters().Length == types.Value.Length)) + candidates.Add(candidate); + + // no candidates were found + if (candidates.Count == 0) + return null; + + // For perf and desktop compat, fast-path these specific checks before calling on the binder to break ties. + if (types == null || types.Value.Length == 0) + { + // no arguments + var firstCandidate = candidates[0]; + + if (candidates.Count == 1) + { + if (propertyType is not null && propertyType != firstCandidate.PropertyType) + return null; + + return firstCandidate; + } + else + { + if (propertyType is null) + { + // if we are here we have no args or property type to select over and we have more than one property with that name + throw new AmbiguousMatchException($"Ambiguous match found for '{firstCandidate.DeclaringType} {firstCandidate}'."); + } + } + } + + if ((bindingFlags & BindingFlags.ExactBinding) != 0) + return Context.DefaultBinder.ExactPropertyBinding(candidates, propertyType, types.Value); + + return Context.DefaultBinder.SelectProperty(bindingFlags, candidates.ToImmutableList(), propertyType, types, modifiers); + } + } /// /// Returns all the public properties of the current . /// /// - public ImmutableList GetProperties() => GetProperties(DefaultLookup); + public IEnumerable GetProperties() => GetProperties(DefaultLookup); /// /// When overridden in a derived class, searches for the properties of the current , using the specified binding constraints. /// /// /// - public abstract ImmutableList GetProperties(BindingFlags bindingFlags); + public IEnumerable GetProperties(BindingFlags bindingFlags) + { + return new MemberQuery(this, null, bindingFlags); + } /// /// Determines whether an instance of a specified type c can be assigned to a variable of the current type. @@ -716,7 +947,7 @@ public bool IsAssignableFrom(TypeSymbol? c) else if (IsGenericParameter) { var constraints = GetGenericParameterConstraints(); - for (int i = 0; i < constraints.Count; i++) + for (int i = 0; i < constraints.Length; i++) if (!constraints[i].IsAssignableFrom(c)) return false; @@ -740,7 +971,7 @@ bool ImplementInterface(TypeSymbol? interfaceType) var interfaces = t.GetInterfaces(); if (interfaces != null) { - for (int i = 0; i < interfaces.Count; i++) + for (int i = 0; i < interfaces.Length; i++) { // Interfaces don't derive from other interfaces, they implement them. // So instead of IsSubclassOf, we should use ImplementInterface instead. @@ -808,7 +1039,7 @@ public bool IsSubclassOf(TypeSymbol c) /// /// /// - public TypeSymbol MakeGenericType(ImmutableList typeArguments) => _typeSpecTable.GetOrCreateGenericTypeSymbol(typeArguments); + public TypeSymbol MakeGenericType(ImmutableArray typeArguments) => _typeSpecTable.GetOrCreateGenericTypeSymbol(typeArguments); /// /// Returns a object that represents a pointer to the current type. @@ -816,6 +1047,9 @@ public bool IsSubclassOf(TypeSymbol c) /// public TypeSymbol MakePointerType() => _typeSpecTable.GetOrCreatePointerTypeSymbol(); + /// + internal override ICustomAttributeProviderInternal? GetInheritedCustomAttributeProvider() => BaseType; + /// /// Specializes the current given the specified generic arguments. /// @@ -827,17 +1061,15 @@ internal virtual TypeSymbol Specialize(GenericContext context) return this; var args = GetGenericArguments(); - for (int i = 0; i < args.Count; i++) + for (int i = 0; i < args.Length; i++) if (args[i].ContainsGenericParameters) args = args.SetItem(i, args[i].Specialize(context)); return MakeGenericType(args); } - ImmutableList Query() where T : MemberSymbol - { - - } + /// + public override string ToString() => FullName ?? ""; } diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs index f6c3ac835a..f1de79bf78 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolExtensions.cs @@ -12,7 +12,7 @@ static class TypeSymbolExtensions /// /// /// - public static Type GetSystemType(this ITypeSymbol symbol) + public static Type GetSystemType(this TypeSymbol symbol) { return symbol.TypeCode switch { diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs index 33de80afef..093251806c 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolListEqualityComparer.cs @@ -1,4 +1,5 @@ using System.Collections.Generic; +using System.Collections.Immutable; namespace IKVM.CoreLib.Symbols { @@ -6,7 +7,7 @@ namespace IKVM.CoreLib.Symbols /// /// Compares two ReflectionTypeSymbol array instances for equality. /// - class TypeSymbolListEqualityComparer : IEqualityComparer> + class TypeSymbolListEqualityComparer : IEqualityComparer>, IEqualityComparer> { public static readonly TypeSymbolListEqualityComparer Instance = new(); @@ -46,6 +47,41 @@ public int GetHashCode(IReadOnlyList obj) return result; } + /// + public bool Equals(ImmutableArray x, ImmutableArray y) + { + if (x == y) + return true; + + if (x == null || y == null) + return false; + + if (x.Length != y.Length) + return false; + + for (int i = 0; i < x.Length; i++) + if (x[i] != y[i]) + return false; + + return true; + } + + /// + public int GetHashCode(ImmutableArray obj) + { + int result = 17; + + for (int i = 0; i < obj.Length; i++) + { + unchecked + { + result = result * 23 + obj[i].GetHashCode(); + } + } + + return result; + } + } } diff --git a/src/IKVM.CoreLib/Symbols/TypeSymbolName.cs b/src/IKVM.CoreLib/Symbols/TypeSymbolName.cs index 8743f4b7a9..afc1db53a1 100644 --- a/src/IKVM.CoreLib/Symbols/TypeSymbolName.cs +++ b/src/IKVM.CoreLib/Symbols/TypeSymbolName.cs @@ -1,15 +1,12 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. -using System.Collections.Generic; using System.Diagnostics; using System.Diagnostics.CodeAnalysis; -using System.Runtime.InteropServices; -using System.Text; -using IKVM.CoreLib.Text; -using System; +using IKVM.CoreLib.Text; +using System; #if !SYSTEM_PRIVATE_CORELIB using System.Collections.Immutable; @@ -343,7 +340,6 @@ public TypeSymbolName GetGenericTypeDefinition() /// Parses a span of characters into a type name. /// /// A span containing the characters representing the type name to parse. - /// An object that describes optional parameters to use. /// Parsed type name. /// Provided type name was invalid. /// Parsing has exceeded the limit set by . @@ -354,12 +350,11 @@ public static TypeSymbolName Parse(ReadOnlySpan typeName) /// Tries to parse a span of characters into a type name. /// /// A span containing the characters representing the type name to parse. - /// An object that describes optional parameters to use. /// Contains the result when parsing succeeds. /// true if type name was converted successfully, otherwise, false. - public static bool TryParse(ReadOnlySpan typeName, [NotNullWhen(true)] out TypeSymbolName? result, TypeNameParseOptions? options = default) + public static bool TryParse(ReadOnlySpan typeName, [NotNullWhen(true)] out TypeSymbolName? result) { - result = TypeNameParser.Parse(typeName, throwOnError: false, options); + result = TypeNameParser.Parse(typeName, throwOnError: false); return result is not null; } @@ -370,12 +365,14 @@ public static bool TryParse(ReadOnlySpan typeName, [NotNullWhen(true)] out /// The current type is not an array. public int GetArrayRank() { - if (!(_rankOrModifier == TypeNameParserHelpers.SZArray || _rankOrModifier > 0)) - { - TypeNameParserHelpers.ThrowInvalidOperation_HasToBeArrayClass(); - } + throw new NotImplementedException(); + + //if (!(_rankOrModifier == TypeNameParserHelpers.SZArray || _rankOrModifier > 0)) + //{ + // TypeNameParserHelpers.ThrowInvalidOperation_HasToBeArrayClass(); + //} - return _rankOrModifier == TypeNameParserHelpers.SZArray ? 1 : _rankOrModifier; + //return _rankOrModifier == TypeNameParserHelpers.SZArray ? 1 : _rankOrModifier; } /// diff --git a/src/IKVM.CoreLib/Symbols/TypeTypeSymbolPolicy.cs b/src/IKVM.CoreLib/Symbols/TypeTypeSymbolPolicy.cs new file mode 100644 index 0000000000..b15c75d80c --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/TypeTypeSymbolPolicy.cs @@ -0,0 +1,57 @@ +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; + +namespace IKVM.CoreLib.Symbols +{ + + /// + /// Policy for type symbols. + /// + class TypeTypeSymbolPolicy : MemberSymbolPolicy + { + + /// + public sealed override ImmutableArray GetDeclaredMembers(TypeSymbol type) => type.GetDeclaredNestedTypes(); + + /// + public override TypeSymbol? GetInheritedParent(TypeSymbol parent) => parent.BaseType; + + /// + public sealed override bool AlwaysTreatAsDeclaredOnly => true; + + /// + public sealed override void GetMemberAttributes(TypeSymbol member, out MethodAttributes visibility, out bool isStatic, out bool isVirtual, out bool isNewSlot) + { + isStatic = true; + isVirtual = false; + isNewSlot = false; + + // Since we never search base types for nested types, we don't need to map every visibility value one to one. + // We just need to distinguish between "public" and "everything else." + visibility = member.IsNestedPublic ? MethodAttributes.Public : MethodAttributes.Private; + } + + /// + public sealed override bool ImplicitlyOverrides(TypeSymbol? baseMember, TypeSymbol? derivedMember) => false; + + /// + public sealed override bool IsSuppressedByMoreDerivedMember(TypeSymbol member, List priorMembers) => false; + + /// + public sealed override BindingFlags ModifyBindingFlags(BindingFlags bindingFlags) + { + bindingFlags &= BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.IgnoreCase; + bindingFlags |= BindingFlags.Static | BindingFlags.DeclaredOnly; + return bindingFlags; + } + + /// + public sealed override bool OkToIgnoreAmbiguity(TypeSymbol m1, TypeSymbol m2) + { + return false; + } + + } + +} diff --git a/src/IKVM.Runtime/Annotation.cs b/src/IKVM.Runtime/Annotation.cs index 932b6e7e8f..d061c75a5d 100644 --- a/src/IKVM.Runtime/Annotation.cs +++ b/src/IKVM.Runtime/Annotation.cs @@ -25,8 +25,6 @@ Jeroen Frijters using System.Diagnostics; using IKVM.Attributes; -using IKVM.CoreLib.Symbols; -using IKVM.CoreLib.Symbols.Emit; namespace IKVM.Runtime { From 775e202b5c36164c1ea1733c95ee8ef5583b7211 Mon Sep 17 00:00:00 2001 From: Jerome Haltom Date: Thu, 28 Nov 2024 13:34:21 -0600 Subject: [PATCH 54/59] So much. --- .../Collections/ImmutableExtensions.cs | 122 +++ src/IKVM.CoreLib/IKVM.CoreLib.csproj | 43 +- .../IkvmReflectionExtensions.cs | 26 + .../Reflection/ReflectionExtensions.cs | 35 + src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs | 59 +- src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs | 5 +- .../AssemblyIdentityParts.cs | 0 src/IKVM.CoreLib/Symbols/AssemblySymbol.cs | 80 +- src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs | 23 +- .../ConstructedGenericConstructorSymbol.cs | 79 -- .../Symbols/ConstructedGenericEventSymbol.cs | 13 +- .../Symbols/ConstructedGenericFieldSymbol.cs | 25 +- .../Symbols/ConstructedGenericMethodSymbol.cs | 63 +- .../ConstructedGenericParameterSymbol.cs | 16 +- .../ConstructedGenericPropertySymbol.cs | 60 +- .../Symbols/ConstructedGenericTypeSymbol.cs | 276 ++--- src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs | 34 - src/IKVM.CoreLib/Symbols/CustomAttribute.cs | 42 +- .../Symbols/CustomAttributeImpl.cs | 45 +- .../Symbols/CustomAttributeNamedArgument.cs | 25 +- .../Symbols/CustomAttributeTypedArgument.cs | 10 +- src/IKVM.CoreLib/Symbols/DefaultBinder.cs | 179 +--- .../Symbols/DefinitionConstructorSymbol.cs | 20 - .../Symbols/DefinitionTypeSymbol.cs | 22 +- .../Symbols/Emit/AssemblySymbolBuilder.cs | 199 +++- .../Symbols/Emit/ConstructorSymbolBuilder.cs | 69 -- .../Symbols/Emit/EventSymbolBuilder.cs | 117 +- .../Symbols/Emit/FieldSymbolBuilder.cs | 81 +- ...GenericMethodParameterTypeSymbolBuilder.cs | 85 +- .../GenericTypeParameterTypeSymbolBuilder.cs | 84 +- .../Symbols/Emit/ICustomAttributeBuilder.cs | 15 + src/IKVM.CoreLib/Symbols/Emit/ILGenerator.cs | 759 +++++++++++++ src/IKVM.CoreLib/Symbols/Emit/ILabel.cs | 10 - .../Symbols/Emit/ILocalBuilder.cs | 42 - .../Symbols/Emit/ISignatureSymbolBuilder.cs | 12 + src/IKVM.CoreLib/Symbols/Emit/Label.cs | 25 + src/IKVM.CoreLib/Symbols/Emit/LocalBuilder.cs | 56 + .../Symbols/Emit/MethodSymbolBuilder.cs | 195 +++- .../Symbols/Emit/ModuleSymbolBuilder.cs | 380 ++++--- src/IKVM.CoreLib/Symbols/Emit/OpCodeValue.cs | 238 +++++ src/IKVM.CoreLib/Symbols/Emit/PEFileKinds.cs | 2 +- .../Symbols/Emit/ParameterSymbolBuilder.cs | 84 ++ .../Symbols/Emit/PropertySymbolBuilder.cs | 163 ++- .../Symbols/Emit/SourceDocument.cs | 60 ++ .../Symbols/Emit/TypeSymbolBuilder.cs | 847 ++++++++++----- .../IILGeneratorWriter.cs} | 118 +-- src/IKVM.CoreLib/Symbols/EventSymbol.cs | 16 +- src/IKVM.CoreLib/Symbols/FieldSymbol.cs | 13 +- src/IKVM.CoreLib/Symbols/GenericContext.cs | 6 +- .../GenericMethodParameterTypeSymbol.cs | 10 +- .../Symbols/GenericParameterTypeSymbol.cs | 83 +- .../Symbols/GenericTypeParameterTypeSymbol.cs | 13 +- src/IKVM.CoreLib/Symbols/HasElementSymbol.cs | 46 +- .../Symbols/ICustomAttributeProvider.cs | 3 +- .../ICustomAttributeProviderInternal.cs | 2 +- src/IKVM.CoreLib/Symbols/IGenericContext.cs | 21 + .../Symbols/ITypeSymbolNameProvider.cs | 47 + .../IIkvmReflectionAssemblySymbolBuilder.cs | 24 - ...IIkvmReflectionConstructorSymbolBuilder.cs | 17 - ...eflectionCustomAttributeProviderBuilder.cs | 13 - .../Emit/IIkvmReflectionEventSymbolBuilder.cs | 17 - .../Emit/IIkvmReflectionFieldSymbolBuilder.cs | 14 - ...ectionGenericTypeParameterSymbolBuilder.cs | 22 - .../IIkvmReflectionMemberSymbolBuilder.cs | 22 - .../IIkvmReflectionMethodBaseSymbolBuilder.cs | 19 - .../IIkvmReflectionMethodSymbolBuilder.cs | 24 - .../IIkvmReflectionModuleSymbolBuilder.cs | 74 -- .../IIkvmReflectionParameterSymbolBuilder.cs | 22 - .../IIkvmReflectionPropertySymbolBuilder.cs | 24 - .../Emit/IIkvmReflectionSymbolBuilder.cs | 86 -- .../Emit/IIkvmReflectionTypeSymbolBuilder.cs | 59 -- .../IkvmReflectionAssemblySymbolBuilder.cs | 275 ----- ...kvmReflectionAssemblySymbolBuilderState.cs | 13 + .../IkvmReflectionConstructorSymbolBuilder.cs | 99 -- .../Emit/IkvmReflectionEventSymbolBuilder.cs | 160 --- .../IkvmReflectionEventSymbolBuilderState.cs | 13 + .../Emit/IkvmReflectionFieldSymbolBuilder.cs | 145 --- .../IkvmReflectionFieldSymbolBuilderState.cs | 13 + ...ectionGenericTypeParameterSymbolBuilder.cs | 718 ------------- .../Emit/IkvmReflectionILGenerator.cs | 498 --------- .../Emit/IkvmReflectionLabel.cs | 28 - .../Emit/IkvmReflectionLocalBuilder.cs | 55 - .../Emit/IkvmReflectionMemberSymbolBuilder.cs | 356 ------- .../IkvmReflectionMethodBaseSymbolBuilder.cs | 158 --- .../Emit/IkvmReflectionMethodSymbolBuilder.cs | 195 ---- .../IkvmReflectionMethodSymbolBuilderState.cs | 13 + .../Emit/IkvmReflectionModuleSymbolBuilder.cs | 547 ---------- .../IkvmReflectionModuleSymbolBuilderState.cs | 13 + .../IkvmReflectionParameterBuilderInfo.cs | 73 -- .../IkvmReflectionParameterSymbolBuilder.cs | 170 --- .../IkvmReflectionPropertySymbolBuilder.cs | 204 ---- ...kvmReflectionPropertySymbolBuilderState.cs | 13 + .../Emit/IkvmReflectionSymbolBuilder.cs | 34 - .../Emit/IkvmReflectionTypeSymbolBuilder.cs | 999 ------------------ .../IkvmReflectionTypeSymbolBuilderPhase.cs | 33 + .../IkvmReflectionTypeSymbolBuilderState.cs | 16 + .../Emit/OpCodeValueExtensions.cs | 250 +++++ .../IkvmReflectionILGenerationWriter.cs | 321 ++++++ .../IIkvmReflectionAssemblySymbol.cs | 23 - .../IIkvmReflectionConstructorSymbol.cs | 16 - .../IIkvmReflectionEventSymbol.cs | 16 - .../IIkvmReflectionFieldSymbol.cs | 16 - .../IIkvmReflectionMemberSymbol.cs | 26 - .../IIkvmReflectionMethodBaseSymbol.cs | 23 - .../IIkvmReflectionMethodSymbol.cs | 30 - .../IIkvmReflectionModuleSymbol.cs | 79 -- .../IIkvmReflectionParameterSymbol.cs | 26 - .../IIkvmReflectionPropertySymbol.cs | 23 - .../IkvmReflection/IIkvmReflectionSymbol.cs | 269 ----- .../IIkvmReflectionTypeSymbol.cs | 99 -- .../IkvmReflectionAssemblySymbol.cs | 169 +-- .../IkvmReflectionConstructorSymbol.cs | 34 - .../IkvmReflectionEventSymbol.cs | 114 +- .../IkvmReflectionEventTable.cs | 112 -- .../IkvmReflectionFieldSymbol.cs | 112 +- .../IkvmReflectionFieldTable.cs | 110 -- ...lectionGenericMethodParameterTypeSymbol.cs | 102 ++ ...kvmReflectionGenericTypeParameterSymbol.cs | 652 ------------ ...IkvmReflectionGenericTypeParameterTable.cs | 80 -- ...eflectionGenericTypeParameterTypeSymbol.cs | 93 ++ .../IkvmReflectionMemberSymbol.cs | 216 ---- .../IkvmReflectionMethodBaseSymbol.cs | 120 --- .../IkvmReflectionMethodSpecTable.cs | 66 -- .../IkvmReflectionMethodSymbol.cs | 135 ++- .../IkvmReflectionMethodTable.cs | 160 --- .../IkvmReflectionModuleSymbol.cs | 331 +----- .../IkvmReflectionModuleTable.cs | 74 -- .../IkvmReflectionParameterSymbol.cs | 115 +- .../IkvmReflectionParameterTable.cs | 101 -- .../IkvmReflectionPropertySymbol.cs | 150 +-- .../IkvmReflectionPropertyTable.cs | 110 -- .../IkvmReflection/IkvmReflectionSymbol.cs | 559 ---------- .../IkvmReflectionSymbolContext.cs | 890 +++++++++++++--- .../IkvmReflectionSymbolExtensions.cs | 11 - .../IkvmReflectionSymbolOptions.cs | 11 + .../IkvmReflectionTypeSpecTable.cs | 127 --- .../IkvmReflectionTypeSymbol.cs | 699 +++--------- .../IkvmReflection/IkvmReflectionTypeTable.cs | 114 -- .../IkvmReflection/IkvmReflectionUtil.cs | 462 +------- src/IKVM.CoreLib/Symbols/ImageFileMachine.cs | 2 +- src/IKVM.CoreLib/Symbols/InterfaceMapping.cs | 17 +- .../Symbols/ManifestResourceInfo.cs | 4 +- src/IKVM.CoreLib/Symbols/MemberSymbol.cs | 22 +- .../Symbols/MemberSymbolPolicy.cs | 22 +- src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs | 140 --- .../Symbols/MethodImplementationMapping.cs | 25 + src/IKVM.CoreLib/Symbols/MethodSymbol.cs | 276 ++++- .../Symbols/MethodSymbolSignature.cs | 141 +++ src/IKVM.CoreLib/Symbols/ModuleSymbol.cs | 20 +- src/IKVM.CoreLib/Symbols/ParameterSymbol.cs | 12 +- src/IKVM.CoreLib/Symbols/PointerTypeSymbol.cs | 22 +- src/IKVM.CoreLib/Symbols/PropertySymbol.cs | 13 +- .../Reflection/Emit/OpCodeValueExtensions.cs | 249 +++++ .../Emit/ReflectionAssemblySymbolBuilder.cs | 162 --- .../ReflectionAssemblySymbolBuilderState.cs | 13 + .../ReflectionConstructorSymbolBuilder.cs | 143 --- .../Emit/ReflectionDynamicMethod.cs | 195 ++++ .../Emit/ReflectionEventBuilderInfo.cs | 83 -- .../Emit/ReflectionEventSymbolBuilder.cs | 92 -- .../Emit/ReflectionEventSymbolBuilderState.cs | 13 + .../Emit/ReflectionFieldSymbolBuilder.cs | 95 -- .../Emit/ReflectionFieldSymbolBuilderState.cs | 13 + ...ectionGenericTypeParameterSymbolBuilder.cs | 84 -- .../Reflection/Emit/ReflectionILGenerator.cs | 325 ------ .../Reflection/Emit/ReflectionLabel.cs | 29 - .../Reflection/Emit/ReflectionLocalBuilder.cs | 59 -- .../Emit/ReflectionMethodSymbolBuilder.cs | 187 ---- .../ReflectionMethodSymbolBuilderState.cs | 13 + .../Emit/ReflectionModuleSymbolBuilder.cs | 208 ---- .../ReflectionModuleSymbolBuilderState.cs | 13 + .../Emit/ReflectionParameterBuilderInfo.cs | 51 - .../Emit/ReflectionParameterSymbolBuilder.cs | 164 --- .../Emit/ReflectionPropertySymbolBuilder.cs | 92 -- .../ReflectionPropertySymbolBuilderState.cs | 13 + .../Emit/ReflectionSymbolBuilder.cs | 24 - .../Emit/ReflectionTypeSymbolBuilder.cs | 418 -------- .../Emit/ReflectionTypeSymbolBuilderPhase.cs | 33 + .../Emit/ReflectionTypeSymbolBuilderState.cs | 16 + .../Writers/ReflectionILGenerationWriter.cs | 334 ++++++ .../Reflection/ReflectionAssemblySymbol.cs | 50 +- .../Reflection/ReflectionConstructorSymbol.cs | 93 -- .../Reflection/ReflectionEventSymbol.cs | 12 +- .../Reflection/ReflectionFieldSymbol.cs | 26 +- ...lectionGenericMethodParameterTypeSymbol.cs | 58 +- ...eflectionGenericTypeParameterTypeSymbol.cs | 58 +- .../Reflection/ReflectionMethodSymbol.cs | 82 +- .../Reflection/ReflectionModuleSymbol.cs | 35 +- .../Reflection/ReflectionModuleTable.cs | 62 -- .../Reflection/ReflectionParameterSymbol.cs | 20 +- .../Reflection/ReflectionPropertySymbol.cs | 42 +- .../Reflection/ReflectionSymbolContext.cs | 590 ++++++++++- .../Reflection/ReflectionSymbolOptions.cs | 11 + .../Reflection/ReflectionTypeSymbol.cs | 206 ++-- src/IKVM.CoreLib/Symbols/SZArrayTypeSymbol.cs | 45 +- src/IKVM.CoreLib/Symbols/Symbol.cs | 20 +- src/IKVM.CoreLib/Symbols/SymbolContext.cs | 16 +- src/IKVM.CoreLib/Symbols/SymbolUtil.cs | 6 +- .../Symbols/SyntheticConstructorSymbol.cs | 77 +- .../Symbols/SyntheticMethodSymbol.cs | 56 +- .../Symbols/TypeConstructorSymbolPolicy.cs | 53 - .../Symbols/TypeMethodSymbolPolicy.cs | 2 +- src/IKVM.CoreLib/Symbols/TypeSpecTable.cs | 4 +- src/IKVM.CoreLib/Symbols/TypeSymbol.cs | 547 ++++++---- .../Symbols/TypeSymbolNameBuilder.cs | 377 +++++++ .../Symbols/TypeSymbolSelector.cs | 257 +++++ .../Symbols/TypeSymbolSelectorList.cs | 109 ++ .../Text/StringBuilderExtensions.cs | 29 + src/IKVM.CoreLib/Text/ValueStringBuilder.cs | 189 +++- 208 files changed, 9567 insertions(+), 15129 deletions(-) create mode 100644 src/IKVM.CoreLib/Collections/ImmutableExtensions.cs create mode 100644 src/IKVM.CoreLib/IkvmReflection/IkvmReflectionExtensions.cs rename src/IKVM.CoreLib/{AssemblyIdentityParser => Symbols}/AssemblyIdentityParts.cs (100%) delete mode 100644 src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ILGenerator.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ILabel.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Emit/ILocalBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ISignatureSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/Label.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/LocalBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/OpCodeValue.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/ParameterSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Emit/SourceDocument.cs rename src/IKVM.CoreLib/Symbols/Emit/{IILGenerator.cs => Writers/IILGeneratorWriter.cs} (65%) create mode 100644 src/IKVM.CoreLib/Symbols/IGenericContext.cs create mode 100644 src/IKVM.CoreLib/Symbols/ITypeSymbolNameProvider.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionAssemblySymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionConstructorSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionCustomAttributeProviderBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionEventSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionFieldSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionGenericTypeParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMemberSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodBaseSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionMethodSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionModuleSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionPropertySymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IIkvmReflectionTypeSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionAssemblySymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionConstructorSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionEventSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionFieldSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionGenericTypeParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionILGenerator.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLabel.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionLocalBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMemberSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodBaseSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionMethodSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionModuleSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterBuilderInfo.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionPropertySymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilderPhase.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/IkvmReflectionTypeSymbolBuilderState.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/OpCodeValueExtensions.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/Emit/Writers/IkvmReflectionILGenerationWriter.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionAssemblySymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionEventSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionFieldSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMemberSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodBaseSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionMethodSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionModuleSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionParameterSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionPropertySymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IIkvmReflectionTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionEventTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionFieldTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericMethodParameterTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionGenericTypeParameterTypeSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMemberSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodBaseSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodSpecTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionMethodTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionModuleTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionParameterTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionPropertyTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolExtensions.cs create mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionSymbolOptions.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeSpecTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/IkvmReflection/IkvmReflectionTypeTable.cs delete mode 100644 src/IKVM.CoreLib/Symbols/MethodBaseSymbol.cs create mode 100644 src/IKVM.CoreLib/Symbols/MethodImplementationMapping.cs create mode 100644 src/IKVM.CoreLib/Symbols/MethodSymbolSignature.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/OpCodeValueExtensions.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionAssemblySymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionConstructorSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionDynamicMethod.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventBuilderInfo.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionEventSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionFieldSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionGenericTypeParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionILGenerator.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLabel.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionLocalBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionMethodSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionModuleSymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterBuilderInfo.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionParameterSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionPropertySymbolBuilderState.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionSymbolBuilder.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilderPhase.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/ReflectionTypeSymbolBuilderState.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/Emit/Writers/ReflectionILGenerationWriter.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionConstructorSymbol.cs delete mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionModuleTable.cs create mode 100644 src/IKVM.CoreLib/Symbols/Reflection/ReflectionSymbolOptions.cs delete mode 100644 src/IKVM.CoreLib/Symbols/TypeConstructorSymbolPolicy.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolNameBuilder.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolSelector.cs create mode 100644 src/IKVM.CoreLib/Symbols/TypeSymbolSelectorList.cs create mode 100644 src/IKVM.CoreLib/Text/StringBuilderExtensions.cs diff --git a/src/IKVM.CoreLib/Collections/ImmutableExtensions.cs b/src/IKVM.CoreLib/Collections/ImmutableExtensions.cs new file mode 100644 index 0000000000..044993b55c --- /dev/null +++ b/src/IKVM.CoreLib/Collections/ImmutableExtensions.cs @@ -0,0 +1,122 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; + +namespace IKVM.CoreLib.Collections +{ + + public static class ImmutableExtensions + { + + /// + /// Value-type implementation of . + /// + /// + public readonly struct ImmutableArrayValueComparer : IEqualityComparer> + where TComparer : IEqualityComparer + { + + readonly TComparer comparer; + + /// + /// Initializes a new instance. + /// + /// + public ImmutableArrayValueComparer(TComparer comparer) + { + this.comparer = comparer; + } + + /// + public bool Equals(ImmutableArray x, ImmutableArray y) + { + if (x == y) + return true; + + if (x.Length != y.Length) + return false; + + for (int i = 0; i < x.Length; i++) + if (comparer.Equals(x[i], y[i]) == false) + return false; + + return true; + } + + /// + public int GetHashCode([DisallowNull] ImmutableArray obj) + { + var h = new HashCode(); + h.Add(obj.Length); + + for (int i = 0; i < obj.Length; i++) + h.Add(obj[i], comparer); + + return h.ToHashCode(); + } + } + + /// + /// Value-type implementation of . + /// + /// + public readonly struct ValueReferenceEqualityComparer : IEqualityComparer + where T : class + { + + /// + public bool Equals(T? x, T? y) + { + return x == y; + } + + /// + public int GetHashCode([DisallowNull] T obj) + { + return obj.GetHashCode(); + } + + } + + /// + /// Returns true if the two given instances are exactly equal, including their contents. + /// + /// + /// + /// + /// + public static bool ImmutableArrayReferenceEquals(this ImmutableArray x, ImmutableArray y) + where T : class + { + return ImmutableArrayEquals(x, y, new ValueReferenceEqualityComparer()); + } + + /// + /// Returns true if the two given instances are exactly equal, including their contents. + /// + /// + /// + /// + /// + public static bool ImmutableArrayEquals(this ImmutableArray x, ImmutableArray y) + { + return ImmutableArrayEquals(x, y, EqualityComparer.Default); + } + + /// + /// Returns true if the two given instances are exactly equal, including their contents. + /// + /// + /// + /// + /// + public static bool ImmutableArrayEquals(this ImmutableArray x, ImmutableArray y, TComparer comparer) + where TComparer : IEqualityComparer + { + return new ImmutableArrayValueComparer(comparer).Equals(x, y); + } + + } + +} diff --git a/src/IKVM.CoreLib/IKVM.CoreLib.csproj b/src/IKVM.CoreLib/IKVM.CoreLib.csproj index 18066ddc58..df921ffefb 100644 --- a/src/IKVM.CoreLib/IKVM.CoreLib.csproj +++ b/src/IKVM.CoreLib/IKVM.CoreLib.csproj @@ -11,22 +11,29 @@ - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + @@ -130,8 +137,4 @@ - - - - diff --git a/src/IKVM.CoreLib/IkvmReflection/IkvmReflectionExtensions.cs b/src/IKVM.CoreLib/IkvmReflection/IkvmReflectionExtensions.cs new file mode 100644 index 0000000000..57fcc97302 --- /dev/null +++ b/src/IKVM.CoreLib/IkvmReflection/IkvmReflectionExtensions.cs @@ -0,0 +1,26 @@ +using IKVM.Reflection; + +namespace IKVM.CoreLib.IkvmReflection +{ + + public static class IkvmReflectionExtensions + { + + /// + /// Gets the parameters types of the specified method or constructor. + /// + /// + /// + public static Type[] GetParameterTypes(this MethodBase method) + { + var p = method.GetParameters(); + var a = p.Length > 0 ? new Type[p.Length] : []; + for (int i = 0; i < p.Length; i++) + a[i] = p[i].ParameterType; + + return a; + } + + } + +} diff --git a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs index 26552f2ecd..263c938be2 100644 --- a/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs +++ b/src/IKVM.CoreLib/Reflection/ReflectionExtensions.cs @@ -799,6 +799,41 @@ public static IEnumerable GetCustomAttributesData(this Memb return member.GetCustomAttributesData(); } + /// + /// Gets the interfaces that are directly declared on the specified type. The method is imperfect, as + /// GetInterfaceMap provides no way to discover interfaces on a type that have no implementation methods. + /// + /// + /// + public static IReadOnlyList GetDeclaredInterfaces(this Type type) + { + var b = new List(); + + foreach (var iface in type.GetInterfaces()) + if (IsInterfaceDirectlyImplementedOnType(type, iface)) + b.Add(iface); + + return b; + } + + /// + /// Returns true if the is directly implemented by . + /// + /// + /// + /// + static bool IsInterfaceDirectlyImplementedOnType(Type type, Type interfaceType) + { + var map = type.GetInterfaceMap(interfaceType); + + // if any of the target methods are declared on this type, the interface is implemented by this type + foreach (var method in map.TargetMethods) + if (method.DeclaringType == type) + return true; + + return false; + } + } } \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs index 461c6f1eec..e5e28fa04b 100644 --- a/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ArrayTypeSymbol.cs @@ -14,7 +14,6 @@ class ArrayTypeSymbol : HasElementSymbol string? _nameSuffix; ImmutableArray _interfaces; - ImmutableArray _constructors; ImmutableArray _methods; /// @@ -64,25 +63,20 @@ public sealed override int GetArrayRank() } /// - public sealed override ImmutableArray GetInterfaces() + internal override ImmutableArray GetDeclaredInterfaces() { return ImmutableArray.Empty; } /// - public sealed override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) - { - return new InterfaceMapping(ImmutableList.Empty, interfaceType, ImmutableList.Empty, this); - } - - /// - internal override ImmutableArray GetDeclaredConstructors() + internal override ImmutableArray GetDeclaredMethods() { - if (_constructors == default) + if (_methods == default) { var int32 = Context.ResolveCoreType("System.Int32"); - var ctor1Args = ImmutableArray.CreateBuilder(); - var ctor2Args = ImmutableArray.CreateBuilder(); + + var ctor1Args = ImmutableArray.CreateBuilder(_rank); + var ctor2Args = ImmutableArray.CreateBuilder(_rank * 2); for (int i = 0; i < _rank; i++) { ctor1Args.Add(int32); @@ -90,34 +84,19 @@ internal override ImmutableArray GetDeclaredConstructors() ctor2Args.Add(int32); } - ImmutableInterlocked.InterlockedInitialize(ref _constructors, - [ - new SyntheticConstructorSymbol(Context, Module, this, MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, ctor1Args.ToImmutable()), - new SyntheticConstructorSymbol(Context, Module, this, MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, ctor2Args.ToImmutable()), - ]); - } - - return _constructors; - } - - /// - internal override ImmutableArray GetDeclaredMethods() - { - if (_methods == default) - { - var int32 = Context.ResolveCoreType("System.Int32"); - // get and set args start at the same length - var argBuilder = ImmutableArray.CreateBuilder(); + var argBuilder = ImmutableArray.CreateBuilder(_rank); for (int i = 0; i < _rank; i++) argBuilder.Add(int32); - var args = argBuilder.ToImmutable(); + var args = argBuilder.DrainToImmutable(); var getArgs = args; var setArgs = args.Add(GetElementType()!); // set args takes a value ImmutableInterlocked.InterlockedInitialize(ref _methods, [ + new SyntheticConstructorSymbol(Context, Module, this, MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, ctor1Args.DrainToImmutable()), + new SyntheticConstructorSymbol(Context, Module, this, MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, ctor2Args.DrainToImmutable()), new SyntheticMethodSymbol(Context, Module, this, "Set", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, null, setArgs), new SyntheticMethodSymbol(Context, Module, this, "Address", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, GetElementType()!.MakeByRefType(), getArgs), new SyntheticMethodSymbol(Context, Module, this, "Get", MethodAttributes.Public, CallingConventions.Standard | CallingConventions.HasThis, GetElementType(), getArgs), @@ -127,10 +106,26 @@ internal override ImmutableArray GetDeclaredMethods() return _methods; } + /// + internal override MethodImplementationMapping GetMethodImplementations() + { + return MethodImplementationMapping.CreateEmpty(this); + } + /// internal override ImmutableArray GetDeclaredCustomAttributes() { - throw new NotImplementedException(); + return ImmutableArray.Empty; + } + + /// + internal override TypeSymbol Specialize(GenericContext context) + { + if (ContainsGenericParameters == false) + return this; + + var elementType = GetElementType() ?? throw new InvalidOperationException(); + return elementType.Specialize(context).MakeArrayType(GetArrayRank()); } } diff --git a/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs b/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs index e49f3612e2..847be2426e 100644 --- a/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs +++ b/src/IKVM.CoreLib/Symbols/AssemblyIdentity.cs @@ -13,7 +13,7 @@ namespace IKVM.CoreLib.Symbols /// /// Represents an identity of an assembly as defined by CLI metadata specification. /// - class AssemblyIdentity + public class AssemblyIdentity { /// @@ -131,7 +131,7 @@ static ImmutableArray CalculatePublicKeyToken(ImmutableArray publicK for (int i = 0; i < 8; i++) result.Add(hash[l - i]); - return result.ToImmutable(); + return result.DrainToImmutable(); } /// @@ -170,6 +170,7 @@ public static bool TryParse(ReadOnlySpan assemblyName, [NotNullWhen(true)] string? _fullName; ImmutableArray _publicKey; ImmutableArray _publicKeyToken; + int _hashCode = 0; /// diff --git a/src/IKVM.CoreLib/AssemblyIdentityParser/AssemblyIdentityParts.cs b/src/IKVM.CoreLib/Symbols/AssemblyIdentityParts.cs similarity index 100% rename from src/IKVM.CoreLib/AssemblyIdentityParser/AssemblyIdentityParts.cs rename to src/IKVM.CoreLib/Symbols/AssemblyIdentityParts.cs diff --git a/src/IKVM.CoreLib/Symbols/AssemblySymbol.cs b/src/IKVM.CoreLib/Symbols/AssemblySymbol.cs index 92596cc888..55c09ca171 100644 --- a/src/IKVM.CoreLib/Symbols/AssemblySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/AssemblySymbol.cs @@ -5,10 +5,12 @@ using System.Linq; using System.Reflection; +using IKVM.CoreLib.Text; + namespace IKVM.CoreLib.Symbols { - abstract class AssemblySymbol : Symbol, ICustomAttributeProviderInternal + public abstract class AssemblySymbol : Symbol, ICustomAttributeProviderInternal { CustomAttributeImpl _customAttributes; @@ -23,10 +25,16 @@ public AssemblySymbol(SymbolContext context) : _customAttributes = new CustomAttributeImpl(context, this); } + /// + /// Gets an for this assembly. + /// + /// + public abstract AssemblyIdentity Identity { get; } + /// /// Gets the display name of the assembly. /// - public abstract string? FullName { get; } + public string FullName => Identity.FullName; /// /// Gets a string representing the version of the common language runtime (CLR) saved in the file containing the manifest. @@ -51,12 +59,12 @@ public AssemblySymbol(SymbolContext context) : /// /// Gets a collection of the types defined in this assembly. /// - public abstract IEnumerable DefinedTypes { get; } + public IEnumerable DefinedTypes => GetTypes(); /// /// Gets a collection of the public types defined in this assembly that are visible outside the assembly. /// - public abstract IEnumerable ExportedTypes { get; } + public IEnumerable ExportedTypes => GetExportedTypes(); /// /// Gets a collection that contains the modules in this assembly. @@ -68,16 +76,6 @@ public AssemblySymbol(SymbolContext context) : /// public abstract bool IsMissing { get; } - /// - /// Returns true if the symbol contains a missing symbol. - /// - public abstract bool ContainsMissing { get; } - - /// - /// Returns true if the symbol is complete. That is, was created with a builder and completed. - /// - public abstract bool IsComplete { get; } - /// /// Gets the public types defined in this assembly that are visible outside the assembly. /// @@ -120,17 +118,11 @@ bool IsVisibleOutsideAssembly(TypeSymbol type) } /// - /// Gets all the modules that are part of this assembly, specifying whether to include resource modules. + /// Gets all the modules that are part of this assembly. /// /// public abstract ImmutableArray GetModules(); - /// - /// Gets an for this assembly. - /// - /// - public abstract AssemblyIdentity GetIdentity(); - /// /// Gets the objects for all the assemblies referenced by this assembly. /// @@ -150,13 +142,28 @@ bool IsVisibleOutsideAssembly(TypeSymbol type) /// /// /// - public abstract TypeSymbol? GetType(string name, bool throwOnError); + public TypeSymbol? GetType(string name, bool throwOnError) + { + foreach (var module in GetModules()) + if (module.GetType(name, false) is TypeSymbol type) + return type; + + if (throwOnError) + throw new TypeLoadException(); + + return null; + } /// /// Gets all types defined in this assembly. /// /// - public abstract ImmutableArray GetTypes(); + public IEnumerable GetTypes() + { + foreach (var module in GetModules()) + foreach (var type in module.GetTypes()) + yield return type; + } /// /// Loads the specified manifest resource from this assembly. @@ -178,7 +185,32 @@ bool IsVisibleOutsideAssembly(TypeSymbol type) /// /// /// - public abstract Stream? GetManifestResourceStream(TypeSymbol type, string name); + public Stream? GetManifestResourceStream(TypeSymbol type, string name) + { + var sb = new ValueStringBuilder(stackalloc char[256]); + + if (type == null) + { + if (name == null) + throw new ArgumentNullException(nameof(type)); + } + else + { + var ns = type.Namespace; + if (ns != null) + { + sb.Append(ns); + + if (name != null) + sb.Append(Type.Delimiter); + } + } + + if (name != null) + sb.Append(name); + + return GetManifestResourceStream(sb.ToString()); + } /// internal abstract ImmutableArray GetDeclaredCustomAttributes(); diff --git a/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs index 7138371e43..f2c66fa145 100644 --- a/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ByRefTypeSymbol.cs @@ -38,33 +38,36 @@ public sealed override int GetArrayRank() } /// - public override ImmutableArray GetInterfaces() + internal sealed override ImmutableArray GetDeclaredInterfaces() { return ImmutableArray.Empty; } /// - public override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + internal sealed override ImmutableArray GetDeclaredMethods() { - return new InterfaceMapping(ImmutableList.Empty, interfaceType, ImmutableList.Empty, this); + return ImmutableArray.Empty; } - /// - internal sealed override ImmutableArray GetDeclaredConstructors() + internal override MethodImplementationMapping GetMethodImplementations() { - return ImmutableArray.Empty; + return MethodImplementationMapping.CreateEmpty(this); } /// - internal sealed override ImmutableArray GetDeclaredMethods() + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return ImmutableArray.Empty; + return ImmutableArray.Empty; } /// - internal sealed override ImmutableArray GetDeclaredCustomAttributes() + internal override TypeSymbol Specialize(GenericContext context) { - throw new NotImplementedException(); + if (ContainsGenericParameters == false) + return this; + + var elementType = GetElementType() ?? throw new InvalidOperationException(); + return elementType.Specialize(context).MakeByRefType(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs deleted file mode 100644 index 3d1afb149d..0000000000 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericConstructorSymbol.cs +++ /dev/null @@ -1,79 +0,0 @@ -using System; -using System.Collections.Immutable; -using System.Reflection; - -namespace IKVM.CoreLib.Symbols -{ - - /// - /// Describes a constructor of a . - /// - class ConstructedGenericConstructorSymbol : ConstructorSymbol - { - - readonly ConstructorSymbol _definition; - readonly GenericContext _genericContext; - - /// - /// Initializes a new instance. - /// - /// - /// - /// - /// - /// - public ConstructedGenericConstructorSymbol(SymbolContext context, TypeSymbol declaringType, ConstructorSymbol definition, GenericContext genericContext) : - base(context, declaringType) - { - _definition = definition ?? throw new ArgumentNullException(nameof(definition)); - _genericContext = genericContext; - } - - /// - public override MethodAttributes Attributes => _definition.Attributes; - - /// - public override CallingConventions CallingConvention => _definition.CallingConvention; - - /// - public override MethodImplAttributes MethodImplementationFlags => _definition.MethodImplementationFlags; - - /// - public override string Name => _definition.Name; - - /// - public sealed override bool IsMissing => false; - - /// - public sealed override bool ContainsMissing => false; - - /// - public sealed override bool IsComplete => true; - - /// - public override ImmutableArray GetGenericArguments() - { - return _definition.GetGenericArguments(); - } - - /// - public override MethodImplAttributes GetMethodImplementationFlags() - { - return _definition.GetMethodImplementationFlags(); - } - - /// - public override ImmutableArray GetParameters() - { - return _definition.GetParameters(); - } - - /// - internal override ImmutableArray GetDeclaredCustomAttributes() - { - throw new NotImplementedException(); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs index 6718f7342f..6feddd06bd 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericEventSymbol.cs @@ -42,9 +42,6 @@ public ConstructedGenericEventSymbol(SymbolContext context, TypeSymbol declaring /// public sealed override bool IsMissing => false; - /// - public sealed override bool ContainsMissing => false; - /// public sealed override bool IsComplete => true; @@ -55,7 +52,7 @@ public ConstructedGenericEventSymbol(SymbolContext context, TypeSymbol declaring if (baseMethod is null) return null; - foreach (var i in DeclaringType!.GetMethods()) + foreach (var i in DeclaringType!.GetDeclaredMethods()) if (i is ConstructedGenericMethodSymbol m) if (m._definition == baseMethod) return m; @@ -70,7 +67,7 @@ public ConstructedGenericEventSymbol(SymbolContext context, TypeSymbol declaring if (baseMethod is null) return null; - foreach (var i in DeclaringType!.GetMethods()) + foreach (var i in DeclaringType!.GetDeclaredMethods()) if (i is ConstructedGenericMethodSymbol m) if (m._definition == baseMethod) return m; @@ -85,7 +82,7 @@ public ConstructedGenericEventSymbol(SymbolContext context, TypeSymbol declaring if (baseMethod is null) return null; - foreach (var i in DeclaringType!.GetMethods()) + foreach (var i in DeclaringType!.GetDeclaredMethods()) if (i is ConstructedGenericMethodSymbol m) if (m._definition == baseMethod) return m; @@ -101,13 +98,13 @@ public sealed override ImmutableArray GetOtherMethods(bool nonPubl foreach (var baseMethod in _definition.GetOtherMethods(nonPublic)) { if (baseMethod is not null) - foreach (var i in DeclaringType!.GetMethods()) + foreach (var i in DeclaringType!.GetDeclaredMethods()) if (i is ConstructedGenericMethodSymbol m) if (m._definition == baseMethod) b.Add(m); } - return b.ToImmutable(); + return b.DrainToImmutable(); } /// diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs index 193f7a4f69..b086e8419a 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericFieldSymbol.cs @@ -24,7 +24,7 @@ class ConstructedGenericFieldSymbol : FieldSymbol /// /// /// - /// + /// public ConstructedGenericFieldSymbol(SymbolContext context, TypeSymbol declaringType, FieldSymbol definition, GenericContext genericContext) : base(context, declaringType.Module, declaringType) { @@ -44,9 +44,6 @@ public ConstructedGenericFieldSymbol(SymbolContext context, TypeSymbol declaring /// public sealed override bool IsMissing => false; - /// - public sealed override bool ContainsMissing => false; - /// public sealed override bool IsComplete => true; @@ -59,13 +56,14 @@ public ConstructedGenericFieldSymbol(SymbolContext context, TypeSymbol declaring /// public sealed override ImmutableArray GetOptionalCustomModifiers() { - if (_optionalCustomModifiers == default) + if (_optionalCustomModifiers.IsDefault) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetOptionalCustomModifiers()) + var l = _definition.GetOptionalCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) b.Add(i.Specialize(_genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.DrainToImmutable()); } return _optionalCustomModifiers; @@ -74,13 +72,14 @@ public sealed override ImmutableArray GetOptionalCustomModifiers() /// public sealed override ImmutableArray GetRequiredCustomModifiers() { - if (_requiredCustomModifiers == default) + if (_requiredCustomModifiers.IsDefault) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetRequiredCustomModifiers()) + var l = _definition.GetRequiredCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) b.Add(i.Specialize(_genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.DrainToImmutable()); } return _requiredCustomModifiers; @@ -89,7 +88,7 @@ public sealed override ImmutableArray GetRequiredCustomModifiers() /// internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - throw new NotImplementedException(); + return _definition.GetDeclaredCustomAttributes(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs index 41d935920e..6b1826dacc 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericMethodSymbol.cs @@ -41,13 +41,10 @@ public ConstructedGenericMethodSymbol(SymbolContext context, ModuleSymbol module public sealed override MethodAttributes Attributes => _definition.Attributes; /// - public sealed override bool IsGenericMethod => true; + public sealed override bool IsGenericMethodDefinition => IsConstructedGenericMethod == false && GenericArguments.Length > 0; /// - public sealed override bool IsGenericMethodDefinition => false; - - /// - public sealed override bool ContainsGenericParameters => false; + public sealed override bool IsConstructedGenericMethod => _genericContext.GenericMethodArguments.IsDefault == false; /// public sealed override ParameterSymbol ReturnParameter => GetReturnParameter(); @@ -82,53 +79,46 @@ ConstructedGenericParameterSymbol GetReturnParameter() /// public sealed override bool IsMissing => false; - /// - public sealed override bool ContainsMissing => _genericContext.GenericMethodArguments != null && _genericContext.GenericMethodArguments.Value.Any(i => i.IsMissing || i.ContainsMissing); - /// public sealed override bool IsComplete => true; /// - public sealed override MethodSymbol GetBaseDefinition() - { - throw new NotImplementedException(); - } + public sealed override MethodSymbol? BaseDefinition => _definition.BaseDefinition; /// - public sealed override ImmutableArray GetGenericArguments() + public override ImmutableArray GenericArguments => ComputeGenericArguments(); + + ImmutableArray ComputeGenericArguments() { - if (_typeParameters == default) - ImmutableInterlocked.InterlockedInitialize(ref _typeParameters, _definition.GetGenericArguments().Select(i => i.Specialize(_genericContext)).ToImmutableArray()); + if (_typeParameters.IsDefault) + { + var l = _definition.GenericArguments; + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) + b.Add(i.Specialize(_genericContext)); + + ImmutableInterlocked.InterlockedInitialize(ref _typeParameters, b.DrainToImmutable()); + } return _typeParameters; } /// - public sealed override MethodSymbol GetGenericMethodDefinition() - { - // value only supported for generic method not method on generic type - if (_genericContext.GenericMethodArguments == null) - throw new InvalidOperationException(); - - return _definition; - } + public sealed override MethodSymbol GenericMethodDefinition => _definition; /// - public sealed override MethodImplAttributes GetMethodImplementationFlags() - { - return _definition.GetMethodImplementationFlags(); - } + public override ImmutableArray Parameters => ComputeParameters(); - /// - public sealed override ImmutableArray GetParameters() + ImmutableArray ComputeParameters() { - if (_parameters == default) + if (_parameters.IsDefault) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetParameters()) + var l = _definition.Parameters; + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) b.Add(new ConstructedGenericParameterSymbol(Context, this, i, _genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _parameters, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _parameters, b.DrainToImmutable()); } return _parameters; @@ -137,7 +127,12 @@ public sealed override ImmutableArray GetParameters() /// internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - throw new NotImplementedException(); + return _definition.GetDeclaredCustomAttributes(); + } + + public override string? ToString() + { + return base.ToString(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs index 73efab265a..258d18310b 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericParameterSymbol.cs @@ -55,11 +55,12 @@ public override ImmutableArray GetOptionalCustomModifiers() { if (_optionalCustomModifiers == default) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetOptionalCustomModifiers()) + var l = _definition.GetOptionalCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) b.Add(i.Specialize(_genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.DrainToImmutable()); } return _optionalCustomModifiers; @@ -70,11 +71,12 @@ public override ImmutableArray GetRequiredCustomModifiers() { if (_requiredCustomModifiers == default) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetRequiredCustomModifiers()) + var l = _definition.GetRequiredCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) b.Add(i.Specialize(_genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.DrainToImmutable()); } return _requiredCustomModifiers; @@ -83,7 +85,7 @@ public override ImmutableArray GetRequiredCustomModifiers() /// internal override ImmutableArray GetDeclaredCustomAttributes() { - throw new NotImplementedException(); + return _definition.GetDeclaredCustomAttributes(); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs index e2b3a472c3..8e39a0a00f 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericPropertySymbol.cs @@ -24,7 +24,7 @@ class ConstructedGenericPropertySymbol : PropertySymbol /// /// /// - /// + /// /// public ConstructedGenericPropertySymbol(SymbolContext context, TypeSymbol declaringType, PropertySymbol definition, GenericContext genericContext) : base(context, declaringType) @@ -51,9 +51,6 @@ public ConstructedGenericPropertySymbol(SymbolContext context, TypeSymbol declar /// public sealed override bool IsMissing => false; - /// - public sealed override bool ContainsMissing => false; - /// public sealed override bool IsComplete => true; @@ -71,7 +68,7 @@ public override ImmutableArray GetAccessors(bool nonPublic) b.Add(m); } - return b.ToImmutable(); + return b.DrainToImmutable(); } /// @@ -109,13 +106,12 @@ public override ImmutableArray GetIndexParameters() { if (_indexParameters == default) { - var b = ImmutableArray.CreateBuilder(); var l = _definition.GetIndexParameters(); - + var b = ImmutableArray.CreateBuilder(l.Length); foreach (var i in l) b.Add(new ConstructedGenericParameterSymbol(Context, this, i, _genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _indexParameters, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _indexParameters, b.DrainToImmutable()); } return _indexParameters; @@ -136,45 +132,33 @@ public override TypeSymbol GetModifiedPropertyType() /// public override ImmutableArray GetOptionalCustomModifiers() { - if (_optionalCustomModifiers == default) - ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, ComputeOptionalCustomModifiers()); - - return _optionalCustomModifiers; - } + if (_optionalCustomModifiers.IsDefault) + { + var l = _definition.GetOptionalCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) + b.Add(i.Specialize(_genericContext)); - /// - /// Computes the value for . - /// - /// - ImmutableArray ComputeOptionalCustomModifiers() - { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetOptionalCustomModifiers()) - b.Add(i.Specialize(_genericContext)); + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.DrainToImmutable()); + } - return b.ToImmutable(); + return _optionalCustomModifiers; } /// public override ImmutableArray GetRequiredCustomModifiers() { - if (_requiredCustomModifiers == default) - ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, ComputeRequiredCustomModifiers()); - - return _requiredCustomModifiers; - } + if (_requiredCustomModifiers.IsDefault) + { + var l = _definition.GetRequiredCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) + b.Add(i.Specialize(_genericContext)); - /// - /// Computes the value for . - /// - /// - ImmutableArray ComputeRequiredCustomModifiers() - { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetRequiredCustomModifiers()) - b.Add(i.Specialize(_genericContext)); + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.DrainToImmutable()); + } - return b.ToImmutable(); + return _requiredCustomModifiers; } /// diff --git a/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs index 2188686c6e..ea9dcf1987 100644 --- a/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/ConstructedGenericTypeSymbol.cs @@ -3,8 +3,6 @@ using System.Linq; using System.Reflection; -using IKVM.CoreLib.Text; - namespace IKVM.CoreLib.Symbols { @@ -14,38 +12,50 @@ namespace IKVM.CoreLib.Symbols class ConstructedGenericTypeSymbol : TypeSymbol { - readonly TypeSymbol _definition; + readonly TypeSymbol _typeDefinition; readonly GenericContext _genericContext; + ImmutableArray _typeArguments; ImmutableArray _interfaces; ImmutableArray _fields; - ImmutableArray _constructors; ImmutableArray _methods; ImmutableArray _properties; ImmutableArray _events; + ImmutableArray _optionalCustomModifiers; + ImmutableArray _requiredCustomModifiers; + MethodImplementationMapping _methodImpl; /// /// Initializes a new instance. /// /// - /// + /// /// /// - public ConstructedGenericTypeSymbol(SymbolContext context, TypeSymbol definition, GenericContext genericContext) : - base(context, definition.Module) + public ConstructedGenericTypeSymbol(SymbolContext context, TypeSymbol typeDefinition, GenericContext genericContext) : + base(context, typeDefinition.Module) { - _definition = definition ?? throw new ArgumentNullException(nameof(definition)); + _typeDefinition = typeDefinition ?? throw new ArgumentNullException(nameof(typeDefinition)); _genericContext = genericContext; } /// - public sealed override TypeAttributes Attributes => _definition.Attributes; + public sealed override TypeSymbol? DeclaringType => _typeDefinition.DeclaringType; + + /// + public sealed override string Name => _typeDefinition.Name; + + /// + public sealed override string? Namespace => _typeDefinition.Namespace; /// - public sealed override TypeCode TypeCode => _definition.TypeCode; + public sealed override TypeAttributes Attributes => _typeDefinition.Attributes; /// - public sealed override TypeSymbol? BaseType => _definition.BaseType?.Specialize(_genericContext); + public sealed override TypeCode TypeCode => _typeDefinition.TypeCode; + + /// + public sealed override TypeSymbol? BaseType => _typeDefinition.BaseType?.Specialize(_genericContext); /// public sealed override bool IsTypeDefinition => false; @@ -63,7 +73,7 @@ public ConstructedGenericTypeSymbol(SymbolContext context, TypeSymbol definition public sealed override bool IsGenericMethodParameter => false; /// - public sealed override bool ContainsGenericParameters => false; + public sealed override bool ContainsGenericParameters => GetGenericArguments().Any(i => i.ContainsGenericParameters); /// public sealed override int GenericParameterPosition => throw new NotSupportedException(); @@ -90,70 +100,30 @@ public ConstructedGenericTypeSymbol(SymbolContext context, TypeSymbol definition public sealed override bool IsUnmanagedFunctionPointer => false; /// - public sealed override MethodBaseSymbol? DeclaringMethod => _definition.DeclaringMethod; + public sealed override MethodSymbol? DeclaringMethod => _typeDefinition.DeclaringMethod; /// - public sealed override string? FullName => ComputeFullName(); - - /// - /// Computes the value for . - /// - /// - string? ComputeFullName() - { - if (ContainsGenericParameters) - return null; - - using var fullName = new ValueStringBuilder(stackalloc char[256]); - fullName.Append(_definition.FullName); - fullName.Append('['); - - if (_genericContext.GenericTypeArguments != null) - { - for (int i = 0; i < _genericContext.GenericTypeArguments.Value.Length; i++) - { - if (i != 0) - fullName.Append(','); - - fullName.Append('['); - fullName.Append(_genericContext.GenericTypeArguments.Value[i].AssemblyQualifiedName); - fullName.Append(']'); - } - } - - - fullName.Append(']'); - return fullName.ToString(); - } - - /// - public sealed override string? Namespace => _definition.Namespace; - - /// - public sealed override GenericParameterAttributes GenericParameterAttributes => _definition.GenericParameterAttributes; + public sealed override GenericParameterAttributes GenericParameterAttributes => _typeDefinition.GenericParameterAttributes; /// - public sealed override bool IsPrimitive => _definition.IsPrimitive; + public sealed override bool IsPrimitive => _typeDefinition.IsPrimitive; /// - public sealed override bool IsEnum => _definition.IsEnum; + public sealed override bool IsVisible => base.IsVisible && _typeArguments.All(i => i.IsVisible); /// - public sealed override string Name => _definition.Name; + public sealed override bool IsEnum => _typeDefinition.IsEnum; /// public sealed override bool IsMissing => false; - /// - public sealed override bool ContainsMissing => _genericContext.GenericTypeArguments != null && _genericContext.GenericTypeArguments.Value.Any(i => i.IsMissing || i.ContainsMissing); - /// public sealed override bool IsComplete => true; /// public sealed override TypeSymbol GetEnumUnderlyingType() { - return _definition.GetEnumUnderlyingType().Specialize(_genericContext); + return _typeDefinition.GetEnumUnderlyingType().Specialize(_genericContext); } /// @@ -169,83 +139,115 @@ public sealed override int GetArrayRank() } /// - public sealed override TypeSymbol GetGenericTypeDefinition() - { - return _definition; - } + public override TypeSymbol GenericTypeDefinition => _typeDefinition; /// - public sealed override ImmutableArray GetGenericArguments() + public override ImmutableArray GenericArguments => GetGenericArguments(); + + ImmutableArray GetGenericArguments() { - return _genericContext.GenericTypeArguments!.Value; + if (_typeArguments.IsDefault) + { + var l = _typeDefinition.GenericArguments; + var b = ImmutableArray.CreateBuilder(l.Length); + for (int i = 0; i < l.Length; i++) + b.Add(l[i].Specialize(_genericContext)); + + ImmutableInterlocked.InterlockedInitialize(ref _typeArguments, b.DrainToImmutable()); + } + + return _typeArguments; } /// - public sealed override ImmutableArray GetGenericParameterConstraints() - { - throw new InvalidOperationException(); - } + public sealed override ImmutableArray GenericParameterConstraints => throw new InvalidOperationException(); /// internal override ImmutableArray GetDeclaredFields() { - if (_fields == default) + if (_fields.IsDefault) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetFields(DeclaredOnlyLookup)) + var l = _typeDefinition.GetDeclaredFields(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) b.Add(new ConstructedGenericFieldSymbol(Context, this, i, _genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _fields, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _fields, b.DrainToImmutable()); } return _fields; } /// - internal override ImmutableArray GetDeclaredConstructors() + internal override ImmutableArray GetDeclaredMethods() { - if (_constructors == default) + if (_methods.IsDefault) { - var b = ImmutableArray.CreateBuilder(); - - // add static initializer as a declared constructor, though it is filtered out from GetConstructors - if (_definition.TypeInitializer != null) - b.Add(new ConstructedGenericConstructorSymbol(Context, this, _definition.TypeInitializer, _genericContext)); - - foreach (var i in _definition.GetConstructors(DeclaredOnlyLookup)) - b.Add(new ConstructedGenericConstructorSymbol(Context, this, i, _genericContext)); + var l = _typeDefinition.GetDeclaredMethods(); + var b = ImmutableArray.CreateBuilder(l.Length); + for (int i = 0; i < l.Length; i++) + b.Add(new ConstructedGenericMethodSymbol(Context, Module, this, l[i], _genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _constructors, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _methods, b.DrainToImmutable()); } - return _constructors; + return _methods; } /// - internal override ImmutableArray GetDeclaredMethods() + internal override MethodImplementationMapping GetMethodImplementations() { - if (_methods == default) + if (_methodImpl.Type == null) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetMethods(DeclaredOnlyLookup)) - b.Add(new ConstructedGenericMethodSymbol(Context, Module, this, i, _genericContext)); + var m = _typeDefinition.GetMethodImplementations(); + var impl = ImmutableArray.CreateBuilder(m.Implementations.Length); + var decl = ImmutableArray.CreateBuilder>(m.Implementations.Length); + for (int i = 0; i < m.Implementations.Length; i++) + { + impl.Add(Specialize(m.Implementations[i]) ?? throw new InvalidOperationException()); + + var declBuilder = ImmutableArray.CreateBuilder(m.Declarations[i].Length); + for (int j = 0; j < m.Declarations[i].Length; j++) + declBuilder.Add(Specialize(m.Declarations[i][j]) ?? throw new InvalidOperationException()); - ImmutableInterlocked.InterlockedInitialize(ref _methods, b.ToImmutable()); + decl.Add(declBuilder.DrainToImmutable()); + } + + lock (this) + if (_methodImpl.Type == null) + _methodImpl = new MethodImplementationMapping(this, impl.DrainToImmutable(), decl.DrainToImmutable()); } - return _methods; + return _methodImpl; + } + + /// + /// Searches this type for the constructed method that is constructed from the given definition method. + /// + /// + /// + MethodSymbol Specialize(MethodSymbol method) + { + if (method == null) + throw new ArgumentNullException(nameof(method)); + if (method.DeclaringType is not { } definitionType) + throw new InvalidOperationException(); + + // find method on specialized type + return definitionType.Specialize(_genericContext).FindMethod(method.Name, method.Signature.Specialize(_genericContext)) ?? throw new InvalidOperationException(); } /// internal override ImmutableArray GetDeclaredProperties() { - if (_properties == default) + if (_properties.IsDefault) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetProperties(DeclaredOnlyLookup)) - b.Add(new ConstructedGenericPropertySymbol(Context, this, i, _genericContext)); + var l = _typeDefinition.GetDeclaredProperties(); + var b = ImmutableArray.CreateBuilder(l.Length); + for (int i = 0; i < l.Length; i++) + b.Add(new ConstructedGenericPropertySymbol(Context, this, l[i], _genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _properties, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _properties, b.DrainToImmutable()); } return _properties; @@ -256,11 +258,12 @@ internal override ImmutableArray GetDeclaredEvents() { if (_events == default) { - var b = ImmutableArray.CreateBuilder(); - foreach (var i in _definition.GetEvents(DeclaredOnlyLookup)) - b.Add(new ConstructedGenericEventSymbol(Context, this, i, _genericContext)); + var l = _typeDefinition.GetDeclaredEvents(); + var b = ImmutableArray.CreateBuilder(l.Length); + for (int i = 0; i < l.Length; i++) + b.Add(new ConstructedGenericEventSymbol(Context, this, l[i], _genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _events, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _events, b.DrainToImmutable()); } return _events; @@ -275,70 +278,87 @@ internal override ImmutableArray GetDeclaredNestedTypes() /// public sealed override string? GetEnumName(object value) { - return _definition.GetEnumName(value); + return _typeDefinition.GetEnumName(value); } /// public sealed override ImmutableArray GetEnumNames() { - return _definition.GetEnumNames(); + return _typeDefinition.GetEnumNames(); } /// - public override ImmutableArray GetInterfaces() + internal override ImmutableArray GetDeclaredInterfaces() { if (_interfaces == default) { - var l = _definition.GetInterfaces(); - var b = ImmutableArray.CreateBuilder(); - foreach (var i in l) - b.Add(i.Specialize(_genericContext)); + var l = _typeDefinition.GetDeclaredInterfaces(); + var b = ImmutableArray.CreateBuilder(l.Length); + for (int i = 0; i < l.Length; i++) + b.Add(l[i].Specialize(_genericContext)); - ImmutableInterlocked.InterlockedInitialize(ref _interfaces, b.ToImmutable()); + ImmutableInterlocked.InterlockedInitialize(ref _interfaces, b.DrainToImmutable()); } return _interfaces; } /// - public sealed override InterfaceMapping GetInterfaceMap(TypeSymbol interfaceType) + public sealed override bool IsEnumDefined(object value) { - throw new NotImplementedException(); + return _typeDefinition.IsEnumDefined(value); } /// - public sealed override bool IsEnumDefined(object value) + internal sealed override ImmutableArray GetDeclaredCustomAttributes() { - return _definition.IsEnumDefined(value); + return _typeDefinition.GetDeclaredCustomAttributes(); } /// - internal sealed override ImmutableArray GetDeclaredCustomAttributes() + public sealed override ImmutableArray GetOptionalCustomModifiers() { - throw new NotImplementedException(); + if (_optionalCustomModifiers == default) + { + var l = _typeDefinition.GetOptionalCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) + b.Add(i.Specialize(_genericContext)); + + ImmutableInterlocked.InterlockedInitialize(ref _optionalCustomModifiers, b.DrainToImmutable()); + } + + return _optionalCustomModifiers; } /// - public override string ToString() + public sealed override ImmutableArray GetRequiredCustomModifiers() { - using var sb = new ValueStringBuilder(stackalloc char[256]); - sb.Append(_definition.ToString()); - sb.Append('['); - - if (_genericContext.GenericTypeArguments != null) + if (_requiredCustomModifiers == default) { - for (int i = 0; i < _genericContext.GenericTypeArguments.Value.Length; i++) - { - if (i != 0) - sb.Append(','); + var l = _typeDefinition.GetRequiredCustomModifiers(); + var b = ImmutableArray.CreateBuilder(l.Length); + foreach (var i in l) + b.Add(i.Specialize(_genericContext)); - sb.Append(_genericContext.GenericTypeArguments.Value[i].ToString()); - } + ImmutableInterlocked.InterlockedInitialize(ref _requiredCustomModifiers, b.DrainToImmutable()); } - sb.Append(']'); + return _requiredCustomModifiers; + } + + /// + internal override TypeSymbol Specialize(GenericContext context) + { + if (ContainsGenericParameters == false) + return this; + + var args = GetGenericArguments(); + for (int i = 0; i < args.Length; i++) + if (args[i].ContainsGenericParameters) + args = args.SetItem(i, args[i].Specialize(context)); - return sb.ToString(); + return _typeDefinition.MakeGenericType(args); } } diff --git a/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs deleted file mode 100644 index 2fbfa100d1..0000000000 --- a/src/IKVM.CoreLib/Symbols/ConstructorSymbol.cs +++ /dev/null @@ -1,34 +0,0 @@ -using System.Reflection; - -namespace IKVM.CoreLib.Symbols -{ - - abstract class ConstructorSymbol : MethodBaseSymbol - { - - /// - /// Initializes a new instance. - /// - /// - /// - public ConstructorSymbol(SymbolContext context, TypeSymbol declaringType) : - base(context, declaringType.Module, declaringType) - { - - } - - /// - public override MemberTypes MemberType => MemberTypes.Constructor; - - /// - public override bool IsGenericMethod => false; - - /// - public override bool IsGenericMethodDefinition => false; - - /// - public override bool ContainsGenericParameters => false; - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/CustomAttribute.cs b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs index 99188dbd62..4dffe0bcd0 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttribute.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttribute.cs @@ -1,18 +1,12 @@ using System; -using System.Collections.Generic; using System.Collections.Immutable; -using System.Linq; using IKVM.CoreLib.Text; namespace IKVM.CoreLib.Symbols { - readonly record struct CustomAttribute( - TypeSymbol AttributeType, - ConstructorSymbol Constructor, - ImmutableArray ConstructorArguments, - ImmutableArray NamedArguments) + public readonly record struct CustomAttribute(TypeSymbol AttributeType, MethodSymbol Constructor, ImmutableArray ConstructorArguments, ImmutableArray NamedArguments) { /// @@ -21,12 +15,12 @@ readonly record struct CustomAttribute( /// /// /// - public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs) + public static CustomAttribute Create(MethodSymbol ctor, ImmutableArray constructorArgs) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), ctor, - PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + PackTypedArgs(ctor.ParameterTypes, constructorArgs), ImmutableArray.Empty); } @@ -37,12 +31,12 @@ public static CustomAttribute Create(ConstructorSymbol ctor, object?[] construct /// /// /// - public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs, FieldSymbol[] namedFields, object?[] fieldValues) + public static CustomAttribute Create(MethodSymbol ctor, ImmutableArray constructorArgs, ImmutableArray namedFields, ImmutableArray fieldValues) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), ctor, - PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + PackTypedArgs(ctor.ParameterTypes, constructorArgs), PackNamedArgs([], [], namedFields, fieldValues)); } @@ -53,12 +47,12 @@ public static CustomAttribute Create(ConstructorSymbol ctor, object?[] construct /// /// /// - public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs, PropertySymbol[] namedProperties, object?[] propertyValues) + public static CustomAttribute Create(MethodSymbol ctor, ImmutableArray constructorArgs, ImmutableArray namedProperties, ImmutableArray propertyValues) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), ctor, - PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + PackTypedArgs(ctor.ParameterTypes, constructorArgs), PackNamedArgs(namedProperties, propertyValues, [], [])); } @@ -71,12 +65,12 @@ public static CustomAttribute Create(ConstructorSymbol ctor, object?[] construct /// /// /// - public static CustomAttribute Create(ConstructorSymbol ctor, object?[] constructorArgs, PropertySymbol[] namedProperties, object?[] propertyValues, FieldSymbol[] namedFields, object?[] fieldValues) + public static CustomAttribute Create(MethodSymbol ctor, ImmutableArray constructorArgs, ImmutableArray namedProperties, ImmutableArray propertyValues, ImmutableArray namedFields, ImmutableArray fieldValues) { return new CustomAttribute( ctor.DeclaringType ?? throw new InvalidOperationException(), ctor, - PackTypedArgs(ctor.GetParameters().Select(i => i.ParameterType).ToArray(), constructorArgs), + PackTypedArgs(ctor.ParameterTypes, constructorArgs), PackNamedArgs(namedProperties, propertyValues, namedFields, fieldValues)); } @@ -88,11 +82,11 @@ public static CustomAttribute Create(ConstructorSymbol ctor, object?[] construct /// /// /// - static ImmutableArray PackTypedArgs(TypeSymbol[] types, object?[] values) + static ImmutableArray PackTypedArgs(ImmutableArray types, ImmutableArray values) { - if (types is null) + if (types.IsDefault) throw new ArgumentNullException(nameof(types)); - if (values is null) + if (values.IsDefault) throw new ArgumentNullException(nameof(values)); if (types.Length != values.Length) throw new ArgumentException(); @@ -101,7 +95,7 @@ static ImmutableArray PackTypedArgs(TypeSymbol[] t for (int i = 0; i < types.Length; i++) a.Add(PackTypedArg(types[i], values[i])); - return a.ToImmutable(); + return a.DrainToImmutable(); } /// @@ -121,7 +115,7 @@ static CustomAttributeTypedArgument PackTypedArg(TypeSymbol type, object? value) /// /// /// - static ImmutableArray PackNamedArgs(PropertySymbol[] namedProperties, object?[] propertyValues, FieldSymbol[] namedFields, object?[] fieldValues) + static ImmutableArray PackNamedArgs(ImmutableArray namedProperties, ImmutableArray propertyValues, ImmutableArray namedFields, ImmutableArray fieldValues) { var a = ImmutableArray.CreateBuilder(namedProperties.Length + namedFields.Length); for (int i = 0; i < namedProperties.Length; i++) @@ -129,7 +123,7 @@ static ImmutableArray PackNamedArgs(PropertySymbol for (int i = 0; i < namedFields.Length; i++) a.Add(PackNamedArg(namedFields[i], fieldValues[i])); - return a.ToImmutable(); + return a.DrainToImmutable(); } /// @@ -140,7 +134,7 @@ static ImmutableArray PackNamedArgs(PropertySymbol /// static CustomAttributeNamedArgument PackNamedArg(PropertySymbol property, object? v) { - return new CustomAttributeNamedArgument(false, property, property.Name, PackTypedArg(property.PropertyType, v)); + return new CustomAttributeNamedArgument(property, PackTypedArg(property.PropertyType, v)); } /// @@ -151,7 +145,7 @@ static CustomAttributeNamedArgument PackNamedArg(PropertySymbol property, object /// static CustomAttributeNamedArgument PackNamedArg(FieldSymbol field, object? v) { - return new CustomAttributeNamedArgument(false, field, field.Name, PackTypedArg(field.FieldType, v)); + return new CustomAttributeNamedArgument(field, PackTypedArg(field.FieldType, v)); } /// @@ -180,7 +174,7 @@ public override string ToString() var namedArgumentsCount = namedArguments.Length; for (int i = 0; i < namedArgumentsCount; i++) { - if (!first) + if (!first) vsb.Append(", "); vsb.Append(namedArguments[i].ToString()); diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs index 8fbeb4c32f..9ce04b7cac 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeImpl.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Collections.Immutable; using System.Linq; using System.Reflection; @@ -39,15 +40,15 @@ public ImmutableArray GetCustomAttributes(bool inherit) { if (inherit == false) { - if (_declaredCustomAttributes == default) + if (_declaredCustomAttributes.IsDefault) ImmutableInterlocked.InterlockedInitialize(ref _declaredCustomAttributes, _provider.GetDeclaredCustomAttributes()); return _declaredCustomAttributes; } else { - if (_declaredAndInheritedCustomAttributes == default) - ImmutableInterlocked.InterlockedInitialize(ref _declaredAndInheritedCustomAttributes, ComputeInheritedCustomAttributes()); + if (_declaredAndInheritedCustomAttributes.IsDefault) + ImmutableInterlocked.InterlockedInitialize(ref _declaredAndInheritedCustomAttributes, ComputeDeclaredAndInheritedCustomAttributes()); return _declaredAndInheritedCustomAttributes; } @@ -57,7 +58,7 @@ public ImmutableArray GetCustomAttributes(bool inherit) /// Computes the custom attributes that are applied to this member, including those which are inherited. /// /// - ImmutableArray ComputeInheritedCustomAttributes() + ImmutableArray ComputeDeclaredAndInheritedCustomAttributes() { var list = _provider.GetDeclaredCustomAttributes(); @@ -82,15 +83,39 @@ bool IsInheritable(CustomAttribute customAttribute) if (_attributeUsageAttributeType == null) throw new InvalidOperationException("Could not find core type System.AttributeUsageAttribute."); - // find first AttributeUsageAttribute - var attributeUsageAttribute = customAttribute.AttributeType.GetCustomAttribute(_attributeUsageAttributeType, true); - if (attributeUsageAttribute.HasValue == false) - return false; + // AttributeUsageAttribute is inheritable; this prevents recursion + if (customAttribute.AttributeType == _attributeUsageAttributeType) + return true; + + // attribute usage should decorate the attribute type, either here or directly + var attributeUsageAttribute = GetNearestInheritedCustomAttribute(customAttribute.AttributeType, _attributeUsageAttributeType); + if (attributeUsageAttribute == null) + throw new InvalidOperationException(); // return whether the Inherited property is set return GetInheritedValue(attributeUsageAttribute.Value); } + /// + /// Gets the nearest custom attribute of the specified type. + /// + /// + /// + /// + CustomAttribute? GetNearestInheritedCustomAttribute(ICustomAttributeProviderInternal provider, TypeSymbol attributeType) + { + foreach (var customAttribute in provider.GetDeclaredCustomAttributes()) + if (customAttribute.AttributeType == attributeType) + return customAttribute; + + for (ICustomAttributeProviderInternal? baseProvider = provider.GetInheritedCustomAttributeProvider(); baseProvider != null; baseProvider = baseProvider.GetInheritedCustomAttributeProvider()) + foreach (var customAttribute in provider.GetDeclaredCustomAttributes()) + if (customAttribute.AttributeType == attributeType) + return customAttribute; + + return null; + } + /// /// Gets the boolean value of the property. /// @@ -99,7 +124,7 @@ bool IsInheritable(CustomAttribute customAttribute) bool GetInheritedValue(CustomAttribute attributeUsageAttribute) { foreach (var i in attributeUsageAttribute.NamedArguments) - if (i.IsField && i.MemberName == nameof(AttributeUsageAttribute.Inherited) && (bool?)i.TypedValue.Value == true) + if (i.MemberInfo is PropertySymbol property && property.Name == nameof(AttributeUsageAttribute.Inherited) && (bool?)i.TypedValue.Value == true) return true; return false; @@ -124,7 +149,7 @@ public ImmutableArray GetCustomAttributes(TypeSymbol attributeT /// public CustomAttribute? GetCustomAttribute(TypeSymbol attributeType, bool inherit) { - return GetCustomAttributes(attributeType, inherit).SingleOrDefaultOrThrow(() => new AmbiguousMatchException()); + return GetCustomAttributes(attributeType, inherit).Select(static i => new CustomAttribute?(i)).SingleOrDefaultOrThrow(static () => new AmbiguousMatchException()); } /// diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs index 97a90013a6..8985458255 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeNamedArgument.cs @@ -1,29 +1,20 @@ -using System.Runtime.InteropServices; - -namespace IKVM.CoreLib.Symbols +namespace IKVM.CoreLib.Symbols { - readonly record struct CustomAttributeNamedArgument( - bool IsField, - MemberSymbol MemberInfo, - string MemberName, - CustomAttributeTypedArgument TypedValue) + public readonly record struct CustomAttributeNamedArgument(MemberSymbol MemberInfo, CustomAttributeTypedArgument TypedValue) { - /// - public override string ToString() - { - if (MemberInfo is null) - return base.ToString()!; - - return $"{MemberInfo.Name} = {TypedValue.ToString(ArgumentType != ArgumentType.Context.ResolveCoreType("System.Object"))}"; - } - /// /// Gets the type of the argument. /// internal TypeSymbol ArgumentType => MemberInfo is FieldSymbol fi ? fi.FieldType : ((PropertySymbol)MemberInfo).PropertyType; + /// + public override string? ToString() + { + return $"{MemberInfo.Name} = {TypedValue.ToString(ArgumentType != ArgumentType.Context.ResolveCoreType("System.Object"))}"; + } + } } diff --git a/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs b/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs index 5f868c3f6a..3aec9a5c96 100644 --- a/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs +++ b/src/IKVM.CoreLib/Symbols/CustomAttributeTypedArgument.cs @@ -1,17 +1,13 @@ -using IKVM.CoreLib.Text; +using System.Collections.Generic; -using System; -using System.Collections.Generic; +using IKVM.CoreLib.Text; namespace IKVM.CoreLib.Symbols { - readonly record struct CustomAttributeTypedArgument( - TypeSymbol ArgumentType, - object? Value) + public readonly record struct CustomAttributeTypedArgument(TypeSymbol ArgumentType, object? Value) { - public override string ToString() => ToString(false); /// diff --git a/src/IKVM.CoreLib/Symbols/DefaultBinder.cs b/src/IKVM.CoreLib/Symbols/DefaultBinder.cs index 58a58a31e6..4e5177dfa2 100644 --- a/src/IKVM.CoreLib/Symbols/DefaultBinder.cs +++ b/src/IKVM.CoreLib/Symbols/DefaultBinder.cs @@ -48,47 +48,29 @@ public DefaultBinder(SymbolContext context) /// Given a set of methods that match the base criteria, select a method based upon an array of parameter types. This /// method should return null if no method matches the criteria. /// - public MethodBaseSymbol? SelectMethod(IReadOnlyList match, BindingFlags bindingFlags, ImmutableArray types, ImmutableArray? modifiers) + public MethodSymbol? SelectMethod(IReadOnlyList match, BindingFlags bindingFlags, TypeSymbolSelectorList types, ImmutableArray modifiers) { // we don't automatically jump out on exact match if (match == null || match.Count == 0) throw new ArgumentException("Unexpected empty array.", nameof(match)); - var candidates = new List(match); + var candidates = new List(match); // find all the methods that can be described by the types parameter // remove all of them that cannot int curIdx = 0; for (var i = 0; i < candidates.Count; i++) { - var par = candidates[i].GetParameters(); - if (par.Length != types.Length) + var par = candidates[i].Parameters; + if (par.Length != types.Indexes.Length) continue; int j; - for (j = 0; j < types.Length; j++) - { - var type = types[j]; - var parameterType = par[j].ParameterType; - - // exact parameter type match - if (type == parameterType) - continue; - - // everything is convertable to object - if (parameterType == ObjectType) - continue; - - // primitive paramter that can't be converted to parameter type - if (parameterType.IsPrimitive && CanChangePrimitive(type, parameterType) == false) + for (j = 0; j < types.Indexes.Length; j++) + if (types.Indexes[j].Match(_context, par[j].ParameterType) == false) break; - // can't otherwise assign type to parameter type - if (parameterType.IsAssignableFrom(type) == false) - break; - } - - if (j == types.Length) + if (j == types.Indexes.Length) candidates[curIdx++] = candidates[i]; } @@ -101,8 +83,8 @@ public DefaultBinder(SymbolContext context) int currentMin = 0; var ambig = false; - var paramOrder = types.Length > 0 ? stackalloc int[types.Length] : Array.Empty(); - for (var i = 0; i < types.Length; i++) + var paramOrder = types.Indexes.Length > 0 ? stackalloc int[types.Indexes.Length] : Array.Empty(); + for (var i = 0; i < types.Indexes.Length; i++) paramOrder[i] = i; for (var i = 1; i < curIdx; i++) @@ -139,11 +121,11 @@ public DefaultBinder(SymbolContext context) /// /// /// - public PropertySymbol? SelectProperty(BindingFlags bindingAttr, IReadOnlyList match, TypeSymbol? returnType, ImmutableArray? indexes, ImmutableArray? modifiers) + public PropertySymbol? SelectProperty(BindingFlags bindingAttr, IReadOnlyList match, TypeSymbol? returnType, TypeSymbolSelectorList indexes, ImmutableArray modifiers) { // if indexes is present every element must be non-null - if (indexes != null) - foreach (var index in indexes) + if (indexes.Indexes.IsDefault == false) + foreach (var index in indexes.Indexes) throw new ArgumentNullException(nameof(index)); if (match == null || match.Count == 0) @@ -157,37 +139,18 @@ public DefaultBinder(SymbolContext context) int curIdx = 0; for (i = 0; i < candidates.Count; i++) { - if (indexes != null) + if (indexes.Indexes.IsDefault == false) { var par = candidates[i].GetIndexParameters(); - if (par.Length != indexes.Value.Length) + if (par.Length != indexes.Indexes.Length) continue; - for (j = 0; j < indexes.Value.Length; j++) - { - var pCls = par[j].ParameterType; - - // If the classes exactly match continue - if (pCls == indexes.Value[j]) - continue; - - if (pCls == ObjectType) - continue; - - if (pCls.IsPrimitive) - { - if (CanChangePrimitive(indexes.Value[j], pCls) == false) - break; - } - else - { - if (pCls.IsAssignableFrom(indexes.Value[j]) == false) - break; - } - } + for (j = 0; j < indexes.Indexes.Length; j++) + if (indexes.Indexes[j].Match(_context, par[j].ParameterType) == false) + break; } - if (indexes == null || j == indexes.Value.Length) + if (indexes.Indexes.IsDefault || j == indexes.Indexes.Length) { if (returnType != null) { @@ -216,14 +179,14 @@ public DefaultBinder(SymbolContext context) int currentMin = 0; var ambig = false; - var paramOrder = indexes != null && indexes.Value.Length > 0 ? stackalloc int[indexes.Value.Length] : Array.Empty(); + var paramOrder = indexes.Indexes.IsDefault == false && indexes.Indexes.Length > 0 ? stackalloc int[indexes.Indexes.Length] : Array.Empty(); for (i = 0; i < paramOrder.Length; i++) paramOrder[i] = i; for (i = 1; i < curIdx; i++) { int newMin = FindMostSpecificType(candidates[currentMin].PropertyType, candidates[i].PropertyType, returnType); - if (newMin == 0 && indexes != null) + if (newMin == 0 && indexes.Indexes.IsDefault == false) newMin = FindMostSpecific(candidates[currentMin].GetIndexParameters(), paramOrder, null, candidates[i].GetIndexParameters(), paramOrder, null, indexes); if (newMin == 0) @@ -254,17 +217,17 @@ public DefaultBinder(SymbolContext context) /// /// /// - public MethodBaseSymbol? ExactBinding(IReadOnlyList match, ImmutableArray types) + public MethodSymbol? ExactBinding(IReadOnlyList match, ImmutableArray types) { if (match is null) throw new ArgumentNullException(nameof(match)); - var aExactMatches = new MethodBaseSymbol[match.Count]; + var aExactMatches = new MethodSymbol[match.Count]; int cExactMatches = 0; for (int i = 0; i < match.Count; i++) { - var par = match[i].GetParameters(); + var par = match[i].Parameters; if (par.Length == 0) continue; @@ -342,17 +305,19 @@ public DefaultBinder(SymbolContext context) int FindMostSpecific(ImmutableArray p1, ReadOnlySpan paramOrder1, TypeSymbol? paramArrayType1, ImmutableArray p2, ReadOnlySpan paramOrder2, TypeSymbol? paramArrayType2, - IReadOnlyList types) + TypeSymbolSelectorList types) { // a method using params is always less specific than one not using params - if (paramArrayType1 != null && paramArrayType2 == null) return 2; - if (paramArrayType2 != null && paramArrayType1 == null) return 1; + if (paramArrayType1 != null && paramArrayType2 == null) + return 2; + if (paramArrayType2 != null && paramArrayType1 == null) + return 1; // now either p1 and p2 both use params or neither does. var p1Less = false; var p2Less = false; - for (int i = 0; i < types.Count; i++) + for (int i = 0; i < types.Indexes.Length; i++) { TypeSymbol c1, c2; @@ -376,9 +341,10 @@ int FindMostSpecific(ImmutableArray p1, ReadOnlySpan param else c2 = p2[paramOrder2[i]].ParameterType; - if (c1 == c2) continue; + if (c1 == c2) + continue; - switch (FindMostSpecificType(c1, c2, types[i])) + switch (FindMostSpecificType(c1, c2, types.Indexes[i])) { case 0: return 0; case 1: p1Less = true; break; @@ -406,75 +372,18 @@ int FindMostSpecific(ImmutableArray p1, ReadOnlySpan param /// /// /// - int FindMostSpecificType(TypeSymbol c1, TypeSymbol c2, TypeSymbol? t) + int FindMostSpecificType(TypeSymbol c1, TypeSymbol c2, TypeSymbolSelector t) { - // if the two types are exact, move on - if (c1 == c2) - return 0; - - if (c1 == t) - return 1; - - if (c2 == t) - return 2; - - bool c1FromC2; - bool c2FromC1; - - if (c1.IsByRef || c2.IsByRef) - { - if (c1.IsByRef && c2.IsByRef) - { - c1 = c1.GetElementType()!; - c2 = c2.GetElementType()!; - } - else if (c1.IsByRef) - { - if (c1.GetElementType() == c2) - return 2; - - c1 = c1.GetElementType()!; - } - else // if (c2.IsByRef) - { - if (c2.GetElementType() == c1) - return 1; - - c2 = c2.GetElementType()!; - } - } - - if (c1.IsPrimitive && c2.IsPrimitive) - { - c1FromC2 = CanChangePrimitive(c2, c1); - c2FromC1 = CanChangePrimitive(c1, c2); - } - else - { - c1FromC2 = c1.IsAssignableFrom(c2); - c2FromC1 = c2.IsAssignableFrom(c1); - } - - if (c1FromC2 == c2FromC1) - return 0; - - if (c1FromC2) - { - return 2; - } - else - { - return 1; - } + return t.FindMostSpecific(_context, c1, c2); } - int FindMostSpecificMethod(MethodBaseSymbol m1, ReadOnlySpan paramOrder1, TypeSymbol? paramArrayType1, - MethodBaseSymbol m2, ReadOnlySpan paramOrder2, TypeSymbol? paramArrayType2, - ImmutableArray types) + int FindMostSpecificMethod(MethodSymbol m1, ReadOnlySpan paramOrder1, TypeSymbol? paramArrayType1, + MethodSymbol m2, ReadOnlySpan paramOrder2, TypeSymbol? paramArrayType2, + TypeSymbolSelectorList types) { // Find the most specific method based on the parameters. - int res = FindMostSpecific(m1.GetParameters(), paramOrder1, paramArrayType1, - m2.GetParameters(), paramOrder2, paramArrayType2, types); + int res = FindMostSpecific(m1.Parameters, paramOrder1, paramArrayType1, + m2.Parameters, paramOrder2, paramArrayType2, types); // If the match was not ambiguous then return the result. if (res != 0) @@ -552,10 +461,10 @@ int FindMostSpecificProperty(PropertySymbol cur1, PropertySymbol cur2) /// /// /// - public static bool CompareMethodSig(MethodBaseSymbol m1, MethodBaseSymbol m2) + public static bool CompareMethodSig(MethodSymbol m1, MethodSymbol m2) { - var params1 = m1.GetParameters(); - var params2 = m2.GetParameters(); + var params1 = m1.Parameters; + var params2 = m2.Parameters; if (params1.Length != params2.Length) return false; @@ -582,10 +491,10 @@ int GetHierarchyDepth(TypeSymbol type) return depth; } - internal MethodBaseSymbol? FindMostDerivedNewSlotMeth(ReadOnlySpan match, int cMatches) + internal MethodSymbol? FindMostDerivedNewSlotMeth(ReadOnlySpan match, int cMatches) { int deepestHierarchy = 0; - MethodBaseSymbol? methWithDeepestHierarchy = null; + MethodSymbol? methWithDeepestHierarchy = null; for (int i = 0; i < cMatches; i++) { diff --git a/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs deleted file mode 100644 index 887319c0e6..0000000000 --- a/src/IKVM.CoreLib/Symbols/DefinitionConstructorSymbol.cs +++ /dev/null @@ -1,20 +0,0 @@ -namespace IKVM.CoreLib.Symbols -{ - - abstract class DefinitionConstructorSymbol : ConstructorSymbol - { - - /// - /// Initializes a new instance. - /// - /// - /// - protected DefinitionConstructorSymbol(SymbolContext context, DefinitionTypeSymbol declaringType) : - base(context, declaringType) - { - - } - - } - -} diff --git a/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs b/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs index 97cc7d37a5..c062aa9e02 100644 --- a/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs +++ b/src/IKVM.CoreLib/Symbols/DefinitionTypeSymbol.cs @@ -21,7 +21,7 @@ protected DefinitionTypeSymbol(SymbolContext context, ModuleSymbol module) : } /// - public sealed override MethodBaseSymbol? DeclaringMethod => null; + public sealed override MethodSymbol? DeclaringMethod => null; /// public sealed override bool IsTypeDefinition => true; @@ -38,9 +38,6 @@ protected DefinitionTypeSymbol(SymbolContext context, ModuleSymbol module) : /// public sealed override bool IsFunctionPointer => false; - /// - public sealed override bool ContainsMissing => false; - /// public sealed override int GenericParameterPosition => throw new InvalidOperationException(); @@ -75,15 +72,26 @@ protected DefinitionTypeSymbol(SymbolContext context, ModuleSymbol module) : } /// - public sealed override TypeSymbol GetGenericTypeDefinition() + public sealed override TypeSymbol GenericTypeDefinition => throw new InvalidOperationException(); + + /// + public sealed override int GetArrayRank() { throw new InvalidOperationException(); } /// - public sealed override int GetArrayRank() + internal override TypeSymbol Specialize(GenericContext context) { - throw new InvalidOperationException(); + if (ContainsGenericParameters == false) + return this; + + var args = GenericArguments; + for (int i = 0; i < args.Length; i++) + if (args[i].ContainsGenericParameters) + args = args.SetItem(i, args[i].Specialize(context)); + + return MakeGenericType(args); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs index b3da39193f..f90292ef71 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/AssemblySymbolBuilder.cs @@ -1,108 +1,229 @@ using System; -using System.Collections.Generic; using System.Collections.Immutable; using System.IO; namespace IKVM.CoreLib.Symbols.Emit { - class AssemblySymbolBuilder : AssemblySymbol + public class AssemblySymbolBuilder : AssemblySymbol, ICustomAttributeBuilder { - readonly AssemblyIdentity _identity; + AssemblyIdentity _identity; + + ImmutableArray.Builder _modules = ImmutableArray.CreateBuilder(); + ImmutableArray _modulesCache; + ImmutableArray.Builder _win32Icons = ImmutableArray.CreateBuilder(); + ImmutableArray.Builder _manifestResources = ImmutableArray.CreateBuilder(); + ImmutableArray.Builder _resources = ImmutableArray.CreateBuilder(); + + ImmutableArray.Builder _typeForwarder = ImmutableArray.CreateBuilder(); + MethodSymbol? _entryPoint; + PEFileKinds _fileKind; + ImmutableArray<(string Name, string FileName)>.Builder _resourceFiles = ImmutableArray.CreateBuilder<(string, string)>(); + (string? product, string? productVersion, string? company, string? copyright, string? trademark)? _versionResource; + ImmutableArray.Builder _referencedAssemblies = ImmutableArray.CreateBuilder(); + ImmutableArray.Builder _customAttributes = ImmutableArray.CreateBuilder(); + + bool _frozen; + internal object? _state1; + internal object? _state2; /// /// Initializes a new instance. /// /// - public AssemblySymbolBuilder(SymbolContext context, AssemblyIdentity identity) : + internal AssemblySymbolBuilder(SymbolContext context, AssemblyIdentity identity) : base(context) { _identity = identity ?? throw new ArgumentNullException(nameof(identity)); } /// - public override string? FullName => throw new NotImplementedException(); + public override AssemblyIdentity Identity => _identity; /// - public override string ImageRuntimeVersion => throw new NotImplementedException(); + public override string ImageRuntimeVersion => throw new NotSupportedException(); /// - public override string Location => throw new NotImplementedException(); + public override string Location => throw new NotSupportedException(); /// - public override ModuleSymbol ManifestModule => throw new NotImplementedException(); + public override ModuleSymbol ManifestModule => throw new NotSupportedException(); /// - public override IEnumerable DefinedTypes => throw new NotImplementedException(); + public override MethodSymbol? EntryPoint => _entryPoint; /// - public override IEnumerable ExportedTypes => throw new NotImplementedException(); + public override bool IsMissing => false; /// - public override MethodSymbol? EntryPoint => throw new NotImplementedException(); + public override ManifestResourceInfo? GetManifestResourceInfo(string resourceName) + { + throw new NotImplementedException(); + } /// - public override bool IsMissing => false; + public override Stream? GetManifestResourceStream(string name) + { + throw new NotImplementedException(); + } /// - public override bool ContainsMissing => false; + public override ImmutableArray GetModules() + { + if (_modulesCache == default) + ImmutableInterlocked.InterlockedInitialize(ref _modulesCache, _modules.ToImmutable().CastArray()); - /// - public override bool IsComplete => false; + return _modulesCache; + } /// - public override AssemblyIdentity GetIdentity() + public override ImmutableArray GetReferencedAssemblies() { - return _identity; + return _referencedAssemblies.ToImmutable(); } /// - public override ManifestResourceInfo? GetManifestResourceInfo(string resourceName) + internal override ImmutableArray GetDeclaredCustomAttributes() { - throw new NotImplementedException(); + return _customAttributes.ToImmutable(); } - /// - public override Stream? GetManifestResourceStream(string name) + /// + /// Defines a named module in this assembly. + /// + /// + /// + public ModuleSymbolBuilder DefineModule(string name) { - throw new NotImplementedException(); + return DefineModule(name, null); } - /// - public override Stream? GetManifestResourceStream(TypeSymbol type, string name) + /// + /// Defines a named module in this assembly. + /// + /// + /// + /// + public ModuleSymbolBuilder DefineModule(string name, string? fileName) { - throw new NotImplementedException(); + var b = new ModuleSymbolBuilder(Context, this, name, fileName); + _modules.Add(b); + _modulesCache = default; + return b; } - /// - public override ImmutableArray GetModules() + /// + /// Sets a Win32 icon on the generated assembly. + /// + /// + public void DefineIconResource(byte[] bytes) { - throw new NotImplementedException(); + _win32Icons.Add(bytes); } - /// - public override ImmutableArray GetReferencedAssemblies() + /// + /// Sets a manifest resource on the generated assembly. + /// + /// + public void DefineManifestResource(byte[] bytes) { - throw new NotImplementedException(); + _manifestResources.Add(bytes); } - /// - public override TypeSymbol? GetType(string name, bool throwOnError) + /// + /// Sets a Win32 version info resource on the generated assembly. + /// + public void DefineVersionInfoResource() { - throw new NotImplementedException(); + _versionResource = (null, null, null, null, null); } - /// - public override ImmutableArray GetTypes() + /// + /// Sets a Win32 version info resource on the generated assembly. + /// + public void DefineVersionInfoResource(string product, string productVersion, string company, string copyright, string trademark) { - throw new NotImplementedException(); + _versionResource = (product, productVersion, company, copyright, trademark); + } + + /// + /// Sets the entry point for this assembly, assuming that a console application is being built. + /// + /// + public void SetEntryPoint(MethodSymbol entryMethod) + { + SetEntryPoint(entryMethod, PEFileKinds.Dll); + } + + /// + /// Sets the entry point for this assembly and defines the type of the portable executable (PE file) being built. + /// + /// + /// + public void SetEntryPoint(MethodSymbol entryMethod, PEFileKinds fileKind) + { + _entryPoint = entryMethod; + _fileKind = fileKind; + } + + /// + /// Adds a forwarded type to this assembly. + /// + /// + public void AddTypeForwarder(TypeSymbol type) + { + _typeForwarder.Add(type); + } + + /// + /// Adds an external resource file to the assembly. + /// + /// + /// + public void AddResourceFile(string name, string fileName) + { + _resourceFiles.Add((name, fileName)); } /// - internal override ImmutableArray GetDeclaredCustomAttributes() + public void SetCustomAttribute(CustomAttribute attribute) { - throw new NotImplementedException(); + _customAttributes.Add(attribute); + } + + /// + /// Sets the assembly version. + /// + /// + /// + public void SetAssemblyVersion(Version version) + { + _identity = new AssemblyIdentity( + _identity.Name, + version, + _identity.CultureName, + _identity.HasPublicKey ? _identity.PublicKey : _identity.PublicKeyToken, + _identity.HasPublicKey, + _identity.ContentType, + _identity.ProcessorArchitecture); + } + + /// + /// Sets the assembly culture. + /// + /// + /// + public void SetAssemblyCulture(string cultureName) + { + _identity = new AssemblyIdentity( + _identity.Name, + _identity.Version, + cultureName, + _identity.HasPublicKey ? _identity.PublicKey : _identity.PublicKeyToken, + _identity.HasPublicKey, + _identity.ContentType, + _identity.ProcessorArchitecture); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs deleted file mode 100644 index da8da14a7a..0000000000 --- a/src/IKVM.CoreLib/Symbols/Emit/ConstructorSymbolBuilder.cs +++ /dev/null @@ -1,69 +0,0 @@ -using System; -using System.Collections.Immutable; -using System.Reflection; - -namespace IKVM.CoreLib.Symbols.Emit -{ - - class ConstructorSymbolBuilder : ConstructorSymbol - { - - /// - /// Initializes a new instance. - /// - /// - /// - public ConstructorSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : - base(context, declaringType) - { - - } - - /// - public override MethodAttributes Attributes => throw new NotImplementedException(); - - /// - public override CallingConventions CallingConvention => throw new NotImplementedException(); - - /// - public override MethodImplAttributes MethodImplementationFlags => throw new NotImplementedException(); - - /// - public override string Name => throw new NotImplementedException(); - - /// - public override bool IsMissing => throw new NotImplementedException(); - - /// - public override bool ContainsMissing => throw new NotImplementedException(); - - /// - public override bool IsComplete => throw new NotImplementedException(); - - /// - public override ImmutableArray GetGenericArguments() - { - throw new NotImplementedException(); - } - - /// - public override MethodImplAttributes GetMethodImplementationFlags() - { - throw new NotImplementedException(); - } - - /// - public override ImmutableArray GetParameters() - { - throw new NotImplementedException(); - } - - /// - internal override ImmutableArray GetDeclaredCustomAttributes() - { - throw new NotImplementedException(); - } - - } - -} \ No newline at end of file diff --git a/src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs index fbabc5c356..aeba68d7d6 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/EventSymbolBuilder.cs @@ -5,66 +5,145 @@ namespace IKVM.CoreLib.Symbols.Emit { - class EventSymbolBuilder : EventSymbol + public sealed class EventSymbolBuilder : EventSymbol, ICustomAttributeBuilder { + readonly string _name; + readonly EventAttributes _attributes; + readonly TypeSymbol _eventType; + + MethodSymbolBuilder? _addMethod; + MethodSymbolBuilder? _removeMethod; + MethodSymbolBuilder? _raiseMethod; + readonly ImmutableArray.Builder _otherMethods = ImmutableArray.CreateBuilder(); + readonly ImmutableArray.Builder _customAttributes = ImmutableArray.CreateBuilder(); + /// /// Initializes a new instance. /// /// /// - public EventSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : + /// + /// + /// + internal EventSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType, string name, EventAttributes attributes, TypeSymbol eventType) : base(context, declaringType) { - + _name = name ?? throw new ArgumentNullException(nameof(name)); + _attributes = attributes; + _eventType = eventType ?? throw new ArgumentNullException(nameof(eventType)); } /// - public override EventAttributes Attributes => throw new NotImplementedException(); - - /// - public override TypeSymbol? EventHandlerType => throw new NotImplementedException(); + public override EventAttributes Attributes => _attributes; /// - public override string Name => throw new NotImplementedException(); + public override TypeSymbol? EventHandlerType => _eventType; /// - public override bool IsMissing => throw new NotImplementedException(); + public override string Name => _name; /// - public override bool ContainsMissing => throw new NotImplementedException(); + public override bool IsMissing => false; /// - public override bool IsComplete => throw new NotImplementedException(); + public override bool IsComplete => false; /// public override MethodSymbol? GetAddMethod(bool nonPublic) { - throw new NotImplementedException(); + if (nonPublic && _addMethod != null && _addMethod.IsPublic == false) + return _addMethod; + else if (nonPublic == false && _addMethod != null && _addMethod.IsPublic) + return _addMethod; + else + return null; } /// - public override ImmutableArray GetOtherMethods(bool nonPublic) + public override MethodSymbol? GetRaiseMethod(bool nonPublic) { - throw new NotImplementedException(); + if (nonPublic && _raiseMethod != null && _raiseMethod.IsPublic == false) + return _raiseMethod; + else if (nonPublic == false && _raiseMethod != null && _raiseMethod.IsPublic) + return _raiseMethod; + else + return null; } /// - public override MethodSymbol? GetRaiseMethod(bool nonPublic) + public override MethodSymbol? GetRemoveMethod(bool nonPublic) { - throw new NotImplementedException(); + if (nonPublic && _removeMethod != null && _removeMethod.IsPublic == false) + return _removeMethod; + else if (nonPublic == false && _removeMethod != null && _removeMethod.IsPublic) + return _removeMethod; + else + return null; } /// - public override MethodSymbol? GetRemoveMethod(bool nonPublic) + public override ImmutableArray GetOtherMethods(bool nonPublic) { - throw new NotImplementedException(); + var b = ImmutableArray.CreateBuilder(_otherMethods.Count); + + foreach (var i in _otherMethods) + { + if (nonPublic && i != null && i.IsPublic == false) + b.Add(i); + else if (nonPublic == false && i != null && i.IsPublic) + b.Add(i); + } + + return b.DrainToImmutable(); } /// internal override ImmutableArray GetDeclaredCustomAttributes() { - throw new NotImplementedException(); + return _customAttributes.ToImmutable(); + } + + /// + /// Sets the method used to subscribe to this event. + /// + /// + public void SetAddOnMethod(MethodSymbolBuilder method) + { + _addMethod = method; + } + + /// + /// Sets the method used to unsubscribe to this event. + /// + /// + public void SetRemoveOnMethod(MethodSymbolBuilder method) + { + _removeMethod = method; + } + + /// + /// Sets the method used to raise this event. + /// + /// + public void SetRaiseMethod(MethodSymbolBuilder method) + { + _raiseMethod = method; + } + + /// + /// Adds one of the "other" methods associated with this event. "Other" methods are methods other than the "on" and "raise" methods associated with an event. This function can be called many times to add as many "other" methods. + /// + /// + public void AddOtherMethod(MethodSymbolBuilder method) + { + _otherMethods.Add(method); + } + + /// + public void SetCustomAttribute(CustomAttribute attribute) + { + _customAttributes.Add(attribute); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs index 4d35f4cffd..750e795f47 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/FieldSymbolBuilder.cs @@ -5,71 +5,100 @@ namespace IKVM.CoreLib.Symbols.Emit { - class FieldSymbolBuilder : FieldSymbol + public sealed class FieldSymbolBuilder : FieldSymbol, ICustomAttributeBuilder { - /// - /// Initializes a new instance. - /// - /// - /// - public FieldSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : - base(context, declaringType.Module, declaringType) - { - - } + readonly string _name; + readonly FieldAttributes _attributes; + readonly TypeSymbol _fieldType; + readonly ImmutableArray _requiredCustomModifiers; + readonly ImmutableArray _optionalCustomModifiers; + object? _constantValue; + int? _offset; + readonly ImmutableArray.Builder _customAttributes = ImmutableArray.CreateBuilder(); /// /// Initializes a new instance. /// /// /// - public FieldSymbolBuilder(SymbolContext context, ModuleSymbolBuilder declaringModule) : - base(context, declaringModule, null) + /// + /// + /// + /// + /// + /// + internal FieldSymbolBuilder(SymbolContext context, ModuleSymbol declaringModule, TypeSymbolBuilder? declaringType, string name, FieldAttributes attributes, TypeSymbol fieldType, ImmutableArray requiredCustomModifiers, ImmutableArray optionalCustomModifiers) : + base(context, declaringModule, declaringType) { - + _name = name ?? throw new ArgumentNullException(nameof(name)); + _attributes = attributes; + _fieldType = fieldType ?? throw new ArgumentNullException(nameof(fieldType)); + _requiredCustomModifiers = requiredCustomModifiers; + _optionalCustomModifiers = optionalCustomModifiers; } /// - public override FieldAttributes Attributes => throw new NotImplementedException(); + public override FieldAttributes Attributes => _attributes; /// - public override TypeSymbol FieldType => throw new NotImplementedException(); + public override TypeSymbol FieldType => _fieldType; /// - public override string Name => throw new NotImplementedException(); + public override string Name => _name; /// - public override bool IsMissing => throw new NotImplementedException(); + public override bool IsMissing => false; /// - public override bool ContainsMissing => throw new NotImplementedException(); - - /// - public override bool IsComplete => throw new NotImplementedException(); + public override bool IsComplete => false; /// public override object? GetRawConstantValue() { - throw new NotImplementedException(); + return _constantValue; } /// public override ImmutableArray GetOptionalCustomModifiers() { - throw new NotImplementedException(); + return _optionalCustomModifiers; } /// public override ImmutableArray GetRequiredCustomModifiers() { - throw new NotImplementedException(); + return _requiredCustomModifiers; } /// internal override ImmutableArray GetDeclaredCustomAttributes() { - throw new NotImplementedException(); + return _customAttributes.ToImmutable(); + } + + /// + /// Sets the default value of this field. + /// + /// + public void SetConstant(object? defaultValue) + { + _constantValue = default; + } + + /// + /// Specifies the field layout. + /// + /// + public void SetOffset(int iOffset) + { + _offset = iOffset; + } + + /// + public void SetCustomAttribute(CustomAttribute attribute) + { + _customAttributes.Add(attribute); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs index 9a8b1a8423..4ad06b0fca 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/GenericMethodParameterTypeSymbolBuilder.cs @@ -5,43 +5,106 @@ namespace IKVM.CoreLib.Symbols.Emit { - class GenericMethodParameterTypeSymbolBuilder : GenericMethodParameterTypeSymbol + public sealed class GenericMethodParameterTypeSymbolBuilder : GenericMethodParameterTypeSymbol, ICustomAttributeBuilder { + readonly string _name; + GenericParameterAttributes _attributes; + readonly int _position; + readonly ImmutableArray.Builder _customAttributes = ImmutableArray.CreateBuilder(); + TypeSymbol? _baseTypeConstraint; + ImmutableArray _interfaceConstraints = ImmutableArray.Empty; + ImmutableArray _constraints; + /// /// Initializes a new instance. /// /// /// /// - public GenericMethodParameterTypeSymbolBuilder(SymbolContext context, MethodSymbolBuilder declaringMethod) : + public GenericMethodParameterTypeSymbolBuilder(SymbolContext context, MethodSymbolBuilder declaringMethod, string name, GenericParameterAttributes attributes, int position) : base(context, declaringMethod) { - + _name = name ?? throw new ArgumentNullException(nameof(name)); + _attributes = attributes; + _position = position; } /// - public override string? FullName => throw new NotImplementedException(); + public sealed override string Name => _name; /// - public override string? Namespace => throw new NotImplementedException(); + public sealed override string? Namespace => ""; /// - public override GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); + public sealed override GenericParameterAttributes GenericParameterAttributes => _attributes; /// - public override int GenericParameterPosition => throw new NotImplementedException(); + public sealed override int GenericParameterPosition => _position; /// - public override string Name => throw new NotImplementedException(); + public override TypeSymbol? BaseType => _baseTypeConstraint; /// - public override bool IsComplete => throw new NotImplementedException(); + public sealed override bool IsComplete => throw new NotImplementedException(); + + /// + internal sealed override ImmutableArray GetDeclaredInterfaces() + { + return _interfaceConstraints; + } + + /// + internal sealed override ImmutableArray GetDeclaredCustomAttributes() + { + return _customAttributes.ToImmutable(); + } + + /// + public sealed override ImmutableArray GetOptionalCustomModifiers() + { + return []; + } + + /// + public sealed override ImmutableArray GetRequiredCustomModifiers() + { + return []; + } + + /// + /// Sets the variance characteristics and special constraints of the generic parameter, such as the parameterless constructor constraint. + /// + /// + public void SetGenericParameterAttributes(GenericParameterAttributes genericParameterAttributes) + { + _attributes = genericParameterAttributes; + } + + /// + /// Sets the base type that a type must inherit in order to be substituted for the type parameter. + /// + /// + public void SetBaseTypeConstraint(TypeSymbol? baseTypeConstraint) + { + _baseTypeConstraint = baseTypeConstraint; + ClearGenericParameterConstraints(); + } + + /// + /// Sets the interfaces a type must implement in order to be substituted for the type parameter. + /// + /// + public void SetInterfaceConstraints(ImmutableArray interfaceConstraints) + { + _interfaceConstraints = interfaceConstraints; + ClearGenericParameterConstraints(); + } /// - public override ImmutableArray GetInterfaces() + public void SetCustomAttribute(CustomAttribute attribute) { - throw new NotImplementedException(); + _customAttributes.Add(attribute); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs index 8da8419572..b5b68cbba7 100644 --- a/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs +++ b/src/IKVM.CoreLib/Symbols/Emit/GenericTypeParameterTypeSymbolBuilder.cs @@ -5,43 +5,105 @@ namespace IKVM.CoreLib.Symbols.Emit { - class GenericTypeParameterTypeSymbolBuilder : GenericTypeParameterTypeSymbol + public sealed class GenericTypeParameterTypeSymbolBuilder : GenericTypeParameterTypeSymbol, ICustomAttributeBuilder { + readonly string _name; + GenericParameterAttributes _attributes; + readonly int _position; + readonly ImmutableArray.Builder _customAttributes = ImmutableArray.CreateBuilder(); + TypeSymbol? _baseTypeConstraint; + ImmutableArray _interfaceConstraints; + /// /// Initializes a new instance. /// /// /// /// - public GenericTypeParameterTypeSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType) : + internal GenericTypeParameterTypeSymbolBuilder(SymbolContext context, TypeSymbolBuilder declaringType, string name, GenericParameterAttributes attributes, int position) : base(context, declaringType) { - + _name = name ?? throw new ArgumentNullException(nameof(name)); + _attributes = attributes; + _position = position; } /// - public override string? FullName => throw new NotImplementedException(); + public sealed override string Name => _name; /// - public override string? Namespace => throw new NotImplementedException(); + public sealed override string? Namespace => ""; /// - public override GenericParameterAttributes GenericParameterAttributes => throw new NotImplementedException(); + public sealed override GenericParameterAttributes GenericParameterAttributes => _attributes; /// - public override int GenericParameterPosition => throw new NotImplementedException(); + public sealed override int GenericParameterPosition => _position; /// - public override string Name => throw new NotImplementedException(); + public override TypeSymbol? BaseType => _baseTypeConstraint; /// - public override bool IsComplete => throw new NotImplementedException(); + public sealed override bool IsComplete => throw new NotImplementedException(); + + /// + internal override ImmutableArray GetDeclaredInterfaces() + { + return _interfaceConstraints; + } + + /// + internal override ImmutableArray GetDeclaredCustomAttributes() + { + return _customAttributes.ToImmutable(); + } + + /// + public sealed override ImmutableArray GetOptionalCustomModifiers() + { + return []; + } + + /// + public sealed override ImmutableArray GetRequiredCustomModifiers() + { + return []; + } + + /// + /// Sets the variance characteristics and special constraints of the generic parameter, such as the parameterless constructor constraint. + /// + /// + public void SetGenericParameterAttributes(GenericParameterAttributes genericParameterAttributes) + { + _attributes = genericParameterAttributes; + } + + /// + /// Sets the base type that a type must inherit in order to be substituted for the type parameter. + /// + /// + public void SetBaseTypeConstraint(TypeSymbol? baseTypeConstraint) + { + _baseTypeConstraint = baseTypeConstraint; + ClearGenericParameterConstraints(); + } + + /// + /// Sets the interfaces a type must implement in order to be substituted for the type parameter. + /// + /// + public void SetInterfaceConstraints(ImmutableArray interfaceConstraints) + { + _interfaceConstraints = interfaceConstraints; + ClearGenericParameterConstraints(); + } /// - public override ImmutableArray GetInterfaces() + public void SetCustomAttribute(CustomAttribute attribute) { - throw new NotImplementedException(); + _customAttributes.Add(attribute); } } diff --git a/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs new file mode 100644 index 0000000000..210591f31e --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ICustomAttributeBuilder.cs @@ -0,0 +1,15 @@ +namespace IKVM.CoreLib.Symbols.Emit +{ + + interface ICustomAttributeBuilder + { + + /// + /// Sets a custom attribute. + /// + /// + void SetCustomAttribute(CustomAttribute attribute); + + } + +} diff --git a/src/IKVM.CoreLib/Symbols/Emit/ILGenerator.cs b/src/IKVM.CoreLib/Symbols/Emit/ILGenerator.cs new file mode 100644 index 0000000000..20f259ffc5 --- /dev/null +++ b/src/IKVM.CoreLib/Symbols/Emit/ILGenerator.cs @@ -0,0 +1,759 @@ +using System; +using System.Collections; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Reflection; +using System.Reflection.Emit; +using System.Runtime.InteropServices; + +using IKVM.CoreLib.Collections; + +namespace IKVM.CoreLib.Symbols.Emit +{ + + public class ILGenerator + { + + const int BlockSize = 64; + + /// + /// Decscribes the IL node. + /// + enum NodeKind : byte + { + + OpCode, + OpCode_Local, + OpCode_Type, + OpCode_Method, + OpCode_Field, + OpCode_Float, + OpCode_String, + OpCode_SByte, + OpCode_Byte, + OpCode_Short, + OpCode_Double, + OpCode_Integer, + OpCode_Long, + OpCode_Label, + OpCode_ManyLabel, + Call, + Calli, + CalliManaged, + BeginScope, + EndScope, + UsingNamespace, + DeclareLocal, + SequencePoint, + Label, + BeginExceptionBlock, + BeginCatchBlock, + BeginFaultBlock, + BeginFinallyBlock, + BeginFilterBlock, + EndExceptionBlock, + + } + + struct Node + { + + public NodeKind Kind; + public OpCodeValue OpCode; + public object? ObjectArg; + public long NumberArg0; + public long NumberArg1; + + /// + /// Initializes a new instance. + /// + public Node(NodeKind kind, OpCodeValue opcode, object? objectArg, long numberArg0, long numberArg1) + { + Kind = kind; + OpCode = opcode; + ObjectArg = objectArg; + NumberArg0 = numberArg0; + NumberArg1 = numberArg1; + } + + } + +#if NET8_0_OR_GREATER + + [System.Runtime.CompilerServices.InlineArray(BlockSize)] + struct ILInlineNodeArray + { + + public Node Item; + + } + +#endif + + /// + /// IL stream is a series of double-linked blocks. Head always points to the first in the sequence. + /// + class ILBlock + { + + public ILBlock Head; + public ILBlock Prev; + public ILBlock Next; +#if NET8_0_OR_GREATER + public ILInlineNodeArray Data; +#else + public Node[] Data; +#endif + public int Size = 0; + + /// + /// Initializes a head block. + /// + public ILBlock() + { + Head = this; + Prev = this; + Next = this; +#if NET8_0_OR_GREATER + Data = new ILInlineNodeArray(); +#else + Data = new Node[BlockSize]; +#endif + } + + /// + /// Initializes a new tail block. + /// + /// + public ILBlock(ILBlock prev) : this() + { + Head = prev.Head; + Prev = prev; + Prev.Next = this; + } + + } + + /// + /// Describes an IL stream, which is a pointer to the latest tail block, and to which s can be appended. + /// + struct NodeStream : IEnumerable + { + + ILBlock Tail; + int Size; + + /// + /// Initializes a new instance. + /// + public NodeStream() + { + Tail = new ILBlock(); + Size = 0; + } + + /// + /// Appends a new node to the stream. + /// + /// + public void Append(Node node) + { + // append a new tail block if required + if (Tail.Size >= BlockSize) + Tail = new ILBlock(Tail); + + // append onto existing tail + Tail.Data[Tail.Size++] = node; + Size++; + } + + /// + public IEnumerator GetEnumerator() + { + for (var node = Tail.Head; node != node.Next; node = node.Next) + for (int i = 0; i < node.Size; i++) + yield return node.Data[i]; + } + + /// + IEnumerator IEnumerable.GetEnumerator() + { + return GetEnumerator(); + } + + } + + record class CallNode(MethodSymbol Method, ImmutableArray OptionalParameterTypes); + + record class CalliNode(CallingConvention UnmanagedCallConv, TypeSymbol? ReturnType, ImmutableArray ParameterTypes); + + record class ManagedCalliNode(CallingConventions CallConv, TypeSymbol? ReturnType, ImmutableArray ParameterTypes, ImmutableArray OptionalParameterTypes); + + readonly SymbolContext _context; + NodeStream _stream; + int _iloffset; + int _labelIndex; + int _localIndex; + + /// + /// Initializes a new instance. + /// + /// + public ILGenerator(SymbolContext context) + { + _context = context ?? throw new ArgumentNullException(nameof(context)); + _stream = new NodeStream(); + } + + /// + /// Gets the current offset, in bytes, in the Microsoft intermediate language (MSIL) stream that is being emitted by the . + /// + public int ILOffset => _iloffset; + + /// + /// Begins a lexical scope. + /// + public void BeginScope() + { + _stream.Append(new Node(NodeKind.BeginScope, 0, null, 0, 0)); + } + + /// + /// Specifies the namespace to be used in evaluating locals and watches for the current active lexical scope. + /// + /// + public void UsingNamespace(string usingNamespace) + { + _stream.Append(new Node(NodeKind.UsingNamespace, 0, usingNamespace, 0, 0)); + } + + /// + /// Ends a lexical scope. + /// + public void EndScope() + { + _stream.Append(new Node(NodeKind.EndScope, 0, null, 0, 0)); + } + + /// + /// Marks a sequence point in the Microsoft intermediate language (MSIL) stream. + /// + /// + /// + /// + /// + /// + public void MarkSequencePoint(SourceDocument document, int startLine, int startColumn, int endLine, int endColumn) + { + if (startLine < 1) + throw new ArgumentOutOfRangeException(nameof(startLine)); + if (endLine < 1) + throw new ArgumentOutOfRangeException(nameof(endLine)); + + _stream.Append(new Node(NodeKind.SequencePoint, 0, document, startLine << 32 | startColumn, endLine << 32 | endColumn)); + } + + /// + /// Declares a local variable of the specified type, optionally pinning the object referred to by the variable. + /// + /// + /// + /// + public LocalBuilder DeclareLocal(TypeSymbol localType, bool pinned) + { + var b = new LocalBuilder(localType, pinned, _localIndex++); + _stream.Append(new Node(NodeKind.DeclareLocal, 0, b, pinned ? 1 : 0, 0)); + return b; + } + + /// + /// Declares a local variable of the specified type. + /// + /// + /// + public LocalBuilder DeclareLocal(TypeSymbol localType) + { + var b = new LocalBuilder(localType, false, _localIndex++); + _stream.Append(new Node(NodeKind.DeclareLocal, 0, b, 0, 0)); + return b; + } + + /// + /// Declares a new label. + /// + /// + public Label DefineLabel() + { + return new Label(_labelIndex++); + } + + /// + /// Begins an exception block for a non-filtered exception. + /// + /// + public Label BeginExceptionBlock() + { + var l = new Label(_labelIndex++); + _stream.Append(new Node(NodeKind.BeginExceptionBlock, 0, null, l.Index, 0)); + return l; + } + + /// + /// Marks the Microsoft intermediate language (MSIL) stream's current position with the given label. + /// + /// + public void MarkLabel(Label loc) + { + _stream.Append(new Node(NodeKind.Label, 0, null, loc.Index, 0)); + } + + /// + /// Begins an exception block for a filtered exception. + /// + public void BeginExceptFilterBlock() + { + _stream.Append(new Node(NodeKind.BeginFilterBlock, 0, null, 0, 0)); + } + + /// + /// Begins a catch block. + /// + /// + public void BeginCatchBlock(TypeSymbol? exceptionType) + { + _stream.Append(new Node(NodeKind.BeginCatchBlock, 0, exceptionType, 0, 0)); + } + + /// + /// Begins an exception fault block in the Microsoft intermediate language (MSIL) stream. + /// + public void BeginFaultBlock() + { + _stream.Append(new Node(NodeKind.BeginFaultBlock, 0, null, 0, 0)); + } + + /// + /// Begins a finally block in the Microsoft intermediate language (MSIL) instruction stream. + /// + public void BeginFinallyBlock() + { + _stream.Append(new Node(NodeKind.BeginFinallyBlock, 0, null, 0, 0)); + } + + /// + /// Ends an exception block. + /// + public void EndExceptionBlock() + { + _stream.Append(new Node(NodeKind.EndExceptionBlock, 0, null, 0, 0)); + } + + /// + /// Emits an instruction to throw an exception. + /// + /// + public void ThrowException(TypeSymbol exceptionType) + { + if (exceptionType is null) + throw new ArgumentNullException(nameof(exceptionType)); + + var exceptionTypeSymbol = _context.ResolveCoreType("System.Exception"); + if (exceptionType.IsSubclassOf(exceptionTypeSymbol) == false && exceptionType != exceptionTypeSymbol) + throw new ArgumentException("Not exception type."); + + var con = exceptionType.GetConstructor([]); + if (con == null) + throw new ArgumentException("No default constructor."); + + Emit(OpCodes.Newobj, con); + Emit(OpCodes.Throw); + } + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the index of the given local variable. + /// + /// + /// + public void Emit(OpCode opcode, LocalBuilder local) + { + _iloffset += opcode.Size; + _stream.Append(new Node(NodeKind.OpCode_Local, (OpCodeValue)opcode.Value, local, 0, 0)); + } + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the metadata token for the given type. + /// + /// + /// + public void Emit(OpCode opcode, TypeSymbol cls) + { + _iloffset += opcode.Size; + _stream.Append(new Node(NodeKind.OpCode_Type, (OpCodeValue)opcode.Value, cls, 0, 0)); + } + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the metadata token for the given string. + /// + /// + /// + public void Emit(OpCode opcode, string str) + { + _iloffset += opcode.Size; + _stream.Append(new Node(NodeKind.OpCode_String, (OpCodeValue)opcode.Value, str, 0, 0)); + } + + /// + /// Puts the specified instruction and numerical argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + public unsafe void Emit(OpCode opcode, float arg) + { + _iloffset += opcode.Size; + _stream.Append(new Node(NodeKind.OpCode_Float, (OpCodeValue)opcode.Value, null, *(int*)&arg, 0)); + } + + /// + /// Puts the specified instruction and character argument onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + public void Emit(OpCode opcode, sbyte arg) + { + _iloffset += opcode.Size; + _stream.Append(new Node(NodeKind.OpCode_SByte, (OpCodeValue)opcode.Value, null, arg, 0)); + } + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream followed by the metadata token for the given method. + /// + /// + /// + public void Emit(OpCode opcode, MethodSymbol method) + { + _iloffset += opcode.Size; + _stream.Append(new Node(NodeKind.OpCode_Method, (OpCodeValue)opcode.Value, method, 0, 0)); + } + + /// + /// Puts the specified instruction and a signature token onto the Microsoft intermediate language (MSIL) stream of instructions. + /// + /// + /// + public void Emit(OpCode opcode, SignatureHelper signature) + { + _iloffset += opcode.Size; + throw new NotImplementedException(); + } + + /// + /// Puts the specified instruction onto the Microsoft intermediate language (MSIL) stream and leaves space to include a label when fixes are done. + /// + /// + /// + public void Emit(OpCode opcode, ImmutableArray