' 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.
Imports System.Collections.Immutable
Imports System.Reflection.Metadata
Imports Microsoft.CodeAnalysis.CodeGen
Imports Microsoft.CodeAnalysis.ExpressionEvaluator
Imports Microsoft.CodeAnalysis.ExpressionEvaluator.UnitTests
Imports Microsoft.CodeAnalysis.VisualBasic.Symbols.Metadata.PE
Imports Microsoft.CodeAnalysis.VisualBasic.UnitTests
Imports Microsoft.VisualStudio.Debugger.Evaluation
Imports Roslyn.Test.Utilities
Imports Xunit
Namespace Microsoft.CodeAnalysis.VisualBasic.ExpressionEvaluator.UnitTests
Public Class WinMdTests
Inherits ExpressionCompilerTestBase
'''
''' Handle runtime assemblies rather than Windows.winmd
''' (compile-time assembly) since those are the assemblies
''' loaded in the debuggee.
'''
Public Sub Win8RuntimeAssemblies()
Const source =
"Class C
Shared Sub M(f As Windows.Storage.StorageFolder, p As Windows.Foundation.Collections.PropertySet)
End Sub
End Class"
Dim comp = CreateEmptyCompilation({source}, options:=TestOptions.DebugDll, references:=WinRtRefs)
Dim runtimeAssemblies = ExpressionCompilerTestHelpers.GetRuntimeWinMds("Windows.Storage", "Windows.Foundation.Collections")
Assert.True(runtimeAssemblies.Length >= 2)
' no reference to Windows.winmd
WithRuntimeInstance(comp, {MscorlibRef}.Concat(runtimeAssemblies),
Sub(runtime)
Dim context = CreateMethodContext(runtime, "C.M")
Dim errorMessage As String = Nothing
Dim testData = New CompilationTestData()
context.CompileExpression("If(p Is Nothing, f, Nothing)", errorMessage, testData)
testData.GetMethodData("<>x.<>m0").VerifyIL(
"{
// Code size 7 (0x7)
.maxstack 1
IL_0000: ldarg.1
IL_0001: brfalse.s IL_0005
IL_0003: ldnull
IL_0004: ret
IL_0005: ldarg.0
IL_0006: ret
}")
End Sub)
End Sub
Public Sub Win8OnWin8()
CompileTimeAndRuntimeAssemblies(
ImmutableArray.Create(
MscorlibRef,
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.Windows)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.LibraryA)).GetReference(),
AssemblyMetadata.CreateFromImage(TestResources.ExpressionCompiler.LibraryB).GetReference()),
ImmutableArray.Create(
MscorlibRef,
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.WindowsData)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.WindowsStorage)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.LibraryA)).GetReference(),
AssemblyMetadata.CreateFromImage(TestResources.ExpressionCompiler.LibraryB).GetReference()),
"Windows.Storage")
End Sub
Public Sub Win8OnWin10()
CompileTimeAndRuntimeAssemblies(
ImmutableArray.Create(
MscorlibRef,
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.Windows)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.LibraryA)).GetReference(),
AssemblyMetadata.CreateFromImage(TestResources.ExpressionCompiler.LibraryB).GetReference()),
ImmutableArray.Create(
MscorlibRef,
AssemblyMetadata.CreateFromImage(ToVersion1_4(TestResources.ExpressionCompiler.WindowsData)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_4(TestResources.ExpressionCompiler.WindowsStorage)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_3(TestResources.ExpressionCompiler.LibraryA)).GetReference(),
AssemblyMetadata.CreateFromImage(TestResources.ExpressionCompiler.LibraryB).GetReference()),
"Windows.Storage")
End Sub
Public Sub Win10OnWin10()
CompileTimeAndRuntimeAssemblies(
ImmutableArray.Create(
MscorlibRef,
AssemblyMetadata.CreateFromImage(ToVersion1_4(TestResources.ExpressionCompiler.WindowsData)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_4(TestResources.ExpressionCompiler.WindowsStorage)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_4(TestResources.ExpressionCompiler.LibraryA)).GetReference(),
AssemblyMetadata.CreateFromImage(TestResources.ExpressionCompiler.LibraryB).GetReference()),
ImmutableArray.Create(
MscorlibRef,
AssemblyMetadata.CreateFromImage(ToVersion1_4(TestResources.ExpressionCompiler.Windows)).GetReference(),
AssemblyMetadata.CreateFromImage(ToVersion1_4(TestResources.ExpressionCompiler.LibraryA)).GetReference(),
AssemblyMetadata.CreateFromImage(TestResources.ExpressionCompiler.LibraryB).GetReference()),
"Windows")
End Sub
Private Sub CompileTimeAndRuntimeAssemblies(
compileReferences As ImmutableArray(Of MetadataReference),
runtimeReferences As ImmutableArray(Of MetadataReference),
storageAssemblyName As String)
Const source =
"Class C
Shared Sub M(a As LibraryA.A, b As LibraryB.B, t As Windows.Data.Text.TextSegment, f As Windows.Storage.StorageFolder)
End Sub
End Class"
Dim c0 = CreateEmptyCompilation({source}, compileReferences, TestOptions.DebugDll)
WithRuntimeInstance(c0, runtimeReferences,
Sub(runtime)
Dim context = CreateMethodContext(runtime, "C.M")
Dim errorMessage As String = Nothing
Dim testData = New CompilationTestData()
context.CompileExpression("If(a, If(b, If(t, f)))", errorMessage, testData)
Assert.Null(errorMessage)
testData.GetMethodData("<>x.<>m0").VerifyIL(
"{
// Code size 17 (0x11)
.maxstack 2
IL_0000: ldarg.0
IL_0001: dup
IL_0002: brtrue.s IL_0010
IL_0004: pop
IL_0005: ldarg.1
IL_0006: dup
IL_0007: brtrue.s IL_0010
IL_0009: pop
IL_000a: ldarg.2
IL_000b: dup
IL_000c: brtrue.s IL_0010
IL_000e: pop
IL_000f: ldarg.3
IL_0010: ret
}")
testData = New CompilationTestData()
Dim result = context.CompileExpression("f", errorMessage, testData)
Assert.Null(errorMessage)
Dim methodData = testData.GetMethodData("<>x.<>m0")
methodData.VerifyIL(
"{
// Code size 2 (0x2)
.maxstack 1
IL_0000: ldarg.3
IL_0001: ret
}")
' Check return type is from runtime assembly.
Dim assemblyReference = AssemblyMetadata.CreateFromImage(result.Assembly).GetReference()
Dim comp = VisualBasicCompilation.Create(
assemblyName:=ExpressionCompilerUtilities.GenerateUniqueName(),
references:=runtimeReferences.Concat(ImmutableArray.Create(Of MetadataReference)(assemblyReference)))
Using metadata = ModuleMetadata.CreateFromImage(result.Assembly)
Dim reader = metadata.MetadataReader
Dim typeDef = reader.GetTypeDef("<>x")
Dim methodHandle = reader.GetMethodDefHandle(typeDef, "<>m0")
Dim [module] = DirectCast(comp.GetMember("<>x").ContainingModule, PEModuleSymbol)
Dim metadataDecoder = New MetadataDecoder([module])
Dim signatureHeader As SignatureHeader = Nothing
Dim metadataException As BadImageFormatException = Nothing
Dim parameters = metadataDecoder.GetSignatureForMethod(methodHandle, signatureHeader, metadataException)
Assert.Equal(parameters.Length, 5)
Dim actualReturnType = parameters(0).Type
Assert.Equal(actualReturnType.TypeKind, TypeKind.Class) ' not error
Dim expectedReturnType = comp.GetMember("Windows.Storage.StorageFolder")
Assert.Equal(expectedReturnType, actualReturnType)
Assert.Equal(storageAssemblyName, actualReturnType.ContainingAssembly.Name)
End Using
End Sub)
End Sub
'''
''' Assembly-qualified name containing "ContentType=WindowsRuntime",
''' and referencing runtime assembly.
'''
Public Sub AssemblyQualifiedName()
Const source =
"Class C
Shared Sub M(f As Windows.Storage.StorageFolder, p As Windows.Foundation.Collections.PropertySet)
End Sub
End Class"
Dim comp = CreateEmptyCompilation({source}, WinRtRefs, TestOptions.DebugDll)
Dim runtimeAssemblies = ExpressionCompilerTestHelpers.GetRuntimeWinMds("Windows.Storage", "Windows.Foundation.Collections")
WithRuntimeInstance(comp, {MscorlibRef}.Concat(runtimeAssemblies),
Sub(runtime)
Dim context = CreateMethodContext(runtime, "C.M")
Dim aliases = ImmutableArray.Create(
VariableAlias("s", "Windows.Storage.StorageFolder, Windows.Storage, Version=255.255.255.255, Culture=neutral, PublicKeyToken=null, ContentType=WindowsRuntime"),
VariableAlias("d", "Windows.Foundation.DateTime, Windows.Foundation, Version=255.255.255.255, Culture=neutral, PublicKeyToken=null, ContentType=WindowsRuntime"))
Dim errorMessage As String = Nothing
Dim testData = New CompilationTestData()
context.CompileExpression(
"If(DirectCast(s.Attributes, Object), d.UniversalTime)",
DkmEvaluationFlags.TreatAsExpression,
aliases,
errorMessage,
testData)
testData.GetMethodData("<>x.<>m0").VerifyIL(
"{
// Code size 55 (0x37)
.maxstack 2
IL_0000: ldstr ""s""
IL_0005: call ""Function Microsoft.VisualStudio.Debugger.Clr.IntrinsicMethods.GetObjectByAlias(String) As Object""
IL_000a: castclass ""Windows.Storage.StorageFolder""
IL_000f: callvirt ""Function Windows.Storage.StorageFolder.get_Attributes() As Windows.Storage.FileAttributes""
IL_0014: box ""Windows.Storage.FileAttributes""
IL_0019: dup
IL_001a: brtrue.s IL_0036
IL_001c: pop
IL_001d: ldstr ""d""
IL_0022: call ""Function Microsoft.VisualStudio.Debugger.Clr.IntrinsicMethods.GetObjectByAlias(String) As Object""
IL_0027: unbox.any ""Windows.Foundation.DateTime""
IL_002c: ldfld ""Windows.Foundation.DateTime.UniversalTime As Long""
IL_0031: box ""Long""
IL_0036: ret
}")
End Sub)
End Sub
Private Shared Function ToVersion1_3(bytes As Byte()) As Byte()
Return ExpressionCompilerTestHelpers.ToVersion1_3(bytes)
End Function
Private Shared Function ToVersion1_4(bytes As Byte()) As Byte()
Return ExpressionCompilerTestHelpers.ToVersion1_4(bytes)
End Function
End Class
End Namespace