diff --git a/src/ILCompiler.WebAssembly/src/CodeGen/WebAssemblyObjectWriter.cs b/src/ILCompiler.WebAssembly/src/CodeGen/WebAssemblyObjectWriter.cs index d51316510..f6a78769d 100644 --- a/src/ILCompiler.WebAssembly/src/CodeGen/WebAssemblyObjectWriter.cs +++ b/src/ILCompiler.WebAssembly/src/CodeGen/WebAssemblyObjectWriter.cs @@ -6,19 +6,15 @@ using System; using System.Collections.Generic; using System.IO; using System.Diagnostics; -using System.Runtime.InteropServices; using ILCompiler.DependencyAnalysisFramework; using Internal.Text; using Internal.TypeSystem; -using Internal.TypeSystem.TypesDebugInfo; using ObjectData = ILCompiler.DependencyAnalysis.ObjectNode.ObjectData; using LLVMSharp; using ILCompiler.CodeGen; -using System.Linq; -using Internal.IL; namespace ILCompiler.DependencyAnalysis { @@ -36,7 +32,6 @@ namespace ILCompiler.DependencyAnalysis if (symbol is ObjectNode) { - ObjectNode objNode = (ObjectNode)symbol; ISymbolDefinitionNode symbolDefNode = (ISymbolDefinitionNode)symbol; if (symbolDefNode.Offset == 0) { @@ -387,16 +382,8 @@ namespace ILCompiler.DependencyAnalysis if (ObjectSymbolRefs.TryGetValue(curOffset, out symbolRef)) { LLVMValueRef pointedAtValue = symbolRef.ToLLVMValueRef(module); - //TODO: why did this come back null - if (pointedAtValue.Pointer != IntPtr.Zero) - { - var ptrValue = LLVM.ConstBitCast(pointedAtValue, intPtrType); - entries.Add(ptrValue); - } - else - { - entries.Add(LLVM.ConstPointerNull(intPtrType)); - } + var ptrValue = LLVM.ConstBitCast(pointedAtValue, intPtrType); + entries.Add(ptrValue); } else { @@ -424,7 +411,6 @@ namespace ILCompiler.DependencyAnalysis public void DoneObjectNode() { - int pointerSize = _nodeFactory.Target.PointerSize; EmitAlignment(_nodeFactory.Target.PointerSize); Debug.Assert(_nodeFactory.Target.PointerSize == 4); int countOfPointerSizedElements = _currentObjectData.Count / _nodeFactory.Target.PointerSize; @@ -837,7 +823,17 @@ namespace ILCompiler.DependencyAnalysis delta = Relocation.ReadValue(reloc.RelocType, location); } } - int size = objectWriter.EmitSymbolReference(reloc.Target, (int)delta, reloc.RelocType); + ISymbolNode symbolToWrite = reloc.Target; + var eeTypeNode = reloc.Target as EETypeNode; + if (eeTypeNode != null) + { + if (eeTypeNode.ShouldSkipEmittingObjectNode(factory)) + { + symbolToWrite = factory.ConstructedTypeSymbol(eeTypeNode.Type); + } + } + + int size = objectWriter.EmitSymbolReference(symbolToWrite, (int)delta, reloc.RelocType); /* WebAssembly has no thumb diff --git a/src/ILCompiler.WebAssembly/src/Compiler/WebAssemblyMetadataBlockingPolicy.cs b/src/ILCompiler.WebAssembly/src/Compiler/WebAssemblyMetadataBlockingPolicy.cs index 80d102880..ebab3ace1 100644 --- a/src/ILCompiler.WebAssembly/src/Compiler/WebAssemblyMetadataBlockingPolicy.cs +++ b/src/ILCompiler.WebAssembly/src/Compiler/WebAssemblyMetadataBlockingPolicy.cs @@ -21,7 +21,7 @@ namespace ILCompiler public override bool IsBlocked(FieldDesc field) { - return true; + return false; } } } diff --git a/tests/src/Simple/HelloWasm/Program.cs b/tests/src/Simple/HelloWasm/Program.cs index b5044e161..5a2892542 100644 --- a/tests/src/Simple/HelloWasm/Program.cs +++ b/tests/src/Simple/HelloWasm/Program.cs @@ -6,6 +6,8 @@ using System; using System.Threading; using System.Runtime.InteropServices; using System.Collections.Generic; +using System.Reflection; + #if PLATFORM_WINDOWS using CpObj; #endif @@ -734,6 +736,7 @@ internal static class Program [System.Runtime.InteropServices.DllImport("*")] private static extern void CallMe(int x); + private static void TestMetaData() { @@ -754,15 +757,15 @@ internal static class Program var typeofChar = typeof(Char); if (typeofChar == null) { - PrintLine("type == null. Simple class metadata test: Failed"); + PrintLine("type == null. Simple struct metadata test: Failed"); } else { if (typeofChar.FullName != "System.Char") { - PrintLine("type != System.Char. Simple class metadata test: Failed"); + PrintLine("type != System.Char. Simple struct metadata test: Failed"); } - else PrintLine("Simple class metadata test (typeof(Char)): Ok."); + else PrintLine("Simple struct metadata test (typeof(Char)): Ok."); } var gentT = new Gen(); @@ -801,8 +804,124 @@ internal static class Program { PrintLine("Ok."); } + + PrintString("Type GetFields length: "); + var x = new ClassForMetaTests(); + var s = x.StringField; + var i = x.IntField; + var fieldClassType = typeof(ClassForMetaTests); + FieldInfo[] fields = fieldClassType.GetFields(); + if (fields.Length == 3) + { + PrintLine("Ok."); + } + else + { + PrintLine(" Failed."); + } + + PrintString("Type get string field via reflection: "); + var stringFieldInfo = fieldClassType.GetField("StringField"); + if ((string)stringFieldInfo.GetValue(x) == s) + { + PrintLine("Ok."); + } + else + { + PrintLine("Failed."); + } + PrintString("Type get int field via reflection: "); + var intFieldInfo = fieldClassType.GetField("IntField"); + if ((int)intFieldInfo.GetValue(x) == i) + { + PrintLine("Ok."); + } + else + { + PrintLine("Failed."); + } + + PrintString("Type get static int field via reflection: "); + var staticIntFieldInfo = fieldClassType.GetField("StaticIntField"); + if ((int)staticIntFieldInfo.GetValue(x) == 23) + { + PrintLine("Ok."); + } + else + { + PrintLine("Failed."); + } + + PrintString("Type set string field via reflection: "); + stringFieldInfo.SetValue(x, "bcd"); + if (x.StringField == "bcd") + { + PrintLine("Ok."); + } + else + { + PrintLine("Failed."); + } + + PrintString("Type set int field via reflection: "); + intFieldInfo.SetValue(x, 456); + if (x.IntField == 456) + { + PrintLine("Ok."); + } + else + { + PrintLine("Failed."); + } + + PrintString("Type set static int field via reflection: "); + staticIntFieldInfo.SetValue(x, 987); + if (ClassForMetaTests.StaticIntField == 987) + { + PrintLine("Ok."); + } + else + { + PrintLine("Failed."); + } + var st = new StructForMetaTests(); + st.StringField = "xyz"; + var fieldStructType = typeof(StructForMetaTests); + var structStringFieldInfo = fieldStructType.GetField("StringField"); + PrintString("Struct get string field via reflection: "); + if ((string)structStringFieldInfo.GetValue(st) == "xyz") + { + PrintLine("Ok."); + } + else + { + PrintLine("Failed."); + } } + public class ClassForMetaTests + { + // used via reflection +#pragma warning disable 0169 + public int IntField; + public string StringField; +#pragma warning restore 0169 + public static int StaticIntField; + + public ClassForMetaTests() + { + StringField = "ab"; + IntField = 12; + StaticIntField = 23; + } + } + + public struct StructForMetaTests + { + public string StringField; + } + + /// /// Ensures all of the blocks of a try/finally function are hit when there aren't exceptions ///