Skip to content

Commit

Permalink
Updates of SDKs (Fake 6, Cecil 11.5, more)
Browse files Browse the repository at this point in the history
  -- remove Cecil 11.4 workrounds
  • Loading branch information
SteveGilham committed May 8, 2023
1 parent 64ee3ba commit a7a68a1
Show file tree
Hide file tree
Showing 7 changed files with 27 additions and 211 deletions.
2 changes: 1 addition & 1 deletion .config/dotnet-tools.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"isRoot": true,
"tools": {
"dotnet-reportgenerator-globaltool": {
"version": "5.1.19",
"version": "5.1.20",
"commands": [
"reportgenerator"
]
Expand Down
135 changes: 0 additions & 135 deletions AltCover.Engine/CecilEx.fs
Original file line number Diff line number Diff line change
Expand Up @@ -130,7 +130,6 @@ type internal AssemblyResolver() as self =
"dotnet|shared"
.Replace('|', Path.DirectorySeparatorChar)


let sources =
[ AssemblyConstants.packageEnv
[ Environment.GetEnvironmentVariable "ProgramFiles"
Expand Down Expand Up @@ -180,140 +179,6 @@ type internal AssemblyResolver() as self =

[<AutoOpen>]
module internal CecilExtension =
let internal scopesSeen =
System.Collections.Generic.HashSet<ScopeDebugInformation>()

let internal safeOffset (point: InstructionOffset) =
if point.IsEndOfMethod then
None
else
Some point.Offset

// workround for old MCS + Cecil 0.11.4
let pruneLocalScopes (m: MethodDefinition) =
scopesSeen.Clear()

let rec pruneScope (scope: ScopeDebugInformation) =
let novel = scopesSeen.Add scope

if novel then
let scopes = scope.Scopes // non-null by construction

scopes
|> Seq.filter (fun subScope ->
let repeat =
subScope
|> Option.ofObj
|> Option.map pruneScope
|> Option.defaultValue true

repeat || subScope.Start.IsEndOfMethod)
|> Seq.toList
|> List.iter (scopes.Remove >> ignore)

not novel

m.DebugInformation.Scope
|> Option.ofObj
|> Option.map pruneScope
|> ignore

// address issue 135
let internal isResolvedProp =
typeof<InstructionOffset>
.GetProperty(
"IsResolved",
System.Reflection.BindingFlags.Instance
||| System.Reflection.BindingFlags.NonPublic
)

let etypeField =
typeof<TypeReference>
.GetField(
"etype",
System.Reflection.BindingFlags.Instance
||| System.Reflection.BindingFlags.NonPublic
)

let internal offsetTable =
System.Collections.Generic.SortedDictionary<int, Instruction>()

let unresolved (point: InstructionOffset) =
isResolvedProp.GetValue(point) :?> bool |> not

let checkScopeConstants (m: MethodDefinition) =
scopesSeen
|> Seq.iter (fun scope ->
let sus =
scope.Constants
|> Seq.filter (fun c ->
(isNull c.Value)
&& match etypeField.GetValue(c.ConstantType) :?> byte with
| 0x14uy // ElementType.Array
| 0x1duy // ElementType.SzArray
| 0x12uy // ElementType.Class
| 0x1cuy // ElementType.Object
| 0x00uy // ElementType.None
| 0x13uy // ElementType.Var
| 0x1euy // ElementType.MVar
| 0x0euy -> // ElementType.String
false
| _ -> not c.ConstantType.IsPrimitive)
|> Seq.toList

sus
|> Seq.iter (fun c ->
scope.Constants.Remove c |> ignore

sprintf "Null Constant %s elided in method %s" c.Name m.FullName
|> Output.verbose))

let prepareLocalScopes (m: MethodDefinition) =
offsetTable.Clear()
scopesSeen.Clear()

let size =
m.Body.Instructions
|> Seq.fold
(fun _ i ->
offsetTable.Add(i.Offset, i)
i.Offset + i.GetSize())
0

let resolvePoint (point: InstructionOffset) =
point
|> safeOffset
|> Option.map (fun offset ->
let o = Math.Max(offset, 0)
let ok, i = offsetTable.TryGetValue(o)

if ok then
InstructionOffset(i)
else
offsetTable.Keys
|> Seq.filter (fun kk -> o < size && kk <= o)
|> Seq.tryLast
|> Option.map (fun k -> InstructionOffset(offsetTable.[k]))
|> Option.defaultValue (InstructionOffset()))
|> Option.defaultValue (InstructionOffset())

let rec resolveScope (scope: ScopeDebugInformation) =
if scope.IsNotNull then
if scopesSeen.Add scope then
scope.Scopes // non-null by construction
|> Seq.iter resolveScope

if unresolved scope.Start then
scope.Start <- resolvePoint scope.Start

if unresolved scope.End then
scope.End <- resolvePoint scope.End

m.DebugInformation.Scope |> resolveScope

checkScopeConstants m

pruneLocalScopes m

// Adjust the IL for exception handling
// param name="handler">The exception handler</param>
Expand Down
13 changes: 2 additions & 11 deletions AltCover.Engine/Instrument.fs
Original file line number Diff line number Diff line change
Expand Up @@ -363,8 +363,7 @@ module internal Instrument =
let head = initialBody |> Seq.head
worker.InsertBefore(head, value (worker))
worker.InsertBefore(head, worker.Create(OpCodes.Ret))
initialBody |> Seq.iter worker.Remove
pruneLocalScopes pathGetterDef)
initialBody |> Seq.iter worker.Remove)

[ ("get_Timer", // set the timer interval in ticks
CoverageParameters.interval ()) ]
Expand All @@ -385,8 +384,7 @@ module internal Instrument =
worker.InsertBefore(head, worker.Create(OpCodes.Ldc_I4, value))
worker.InsertBefore(head, worker.Create(OpCodes.Conv_I8))
worker.InsertBefore(head, worker.Create(OpCodes.Ret))
initialBody |> Seq.iter worker.Remove
pruneLocalScopes pathGetterDef))
initialBody |> Seq.iter worker.Remove))

[<System.Diagnostics.CodeAnalysis.SuppressMessage("Gendarme.Rules.Correctness",
"EnsureLocalDisposalRule",
Expand Down Expand Up @@ -696,9 +694,6 @@ module internal Instrument =
| true ->
let mt = m.Method

if mt.HasBody then
prepareLocalScopes mt

let body = mt.Body

{ state with
Expand Down Expand Up @@ -1046,8 +1041,6 @@ module internal Instrument =
body.SimplifyMacros()
// changes "long" conditional operators to their short representation where possible
body.OptimizeMacros()
// purge dodgy scope data
state.MethodBody.Method |> pruneLocalScopes

doTrack state m

Expand Down Expand Up @@ -1333,8 +1326,6 @@ module internal Instrument =

bulkInsertBefore worker head store true |> ignore

pruneLocalScopes getterDef

let recorderFileName =
(extractName state.RecordingAssembly) + ".dll"

Expand Down
4 changes: 2 additions & 2 deletions AltCover.Engine/NativeJson.fs
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,9 @@ open Manatee.Json

module
#if GUI || RUNNER
internal
internal
#endif
NativeJson =
NativeJson =

type internal TimeStamp = string

Expand Down
59 changes: 8 additions & 51 deletions AltCover.Tests/Tests2.fs
Original file line number Diff line number Diff line change
Expand Up @@ -851,28 +851,15 @@ module AltCoverTests2 =
writer.SymbolWriterProvider <- Mono.Cecil.Cil.EmbeddedPortablePdbWriterProvider()
writer.WriteSymbols <- true

let save = Output.verbose
let b = System.Text.StringBuilder()

Output.verbose <- b.AppendLine >> ignore

let def =
``module``.MainModule.GetTypes()
|> Seq.collect (fun t -> t.Methods)
|> Seq.find (fun m -> m.Name.Equals("MakeConst"))

prepareLocalScopes def
Output.verbose <- save

test
<@
b.ToString() = "Null Constant thing elided in method System.Void NullConst.Program::MakeConst()"
+ Environment.NewLine
@>

use sink =
File.Open(outputdll, FileMode.Create, FileAccess.ReadWrite)

// should not throw
``module``.Write(sink, writer)

[<Test>]
Expand Down Expand Up @@ -907,11 +894,12 @@ module AltCoverTests2 =
"Scope.Start.IsEndOfMethod"
)

Assert.True(
Assert.That(
pathGetterDef.DebugInformation.Scope.Scopes
|> Seq.exists (fun subscope -> subscope.Start.IsEndOfMethod),
Is.False,
"subscope.Start.IsEndOfMethod"
) // this one needs the home-built Sample31
)

// big test -- if we can write w/o crashing when the previous asserts are removed
let output = Path.GetTempFileName()
Expand All @@ -925,10 +913,7 @@ module AltCoverTests2 =
use sink =
File.Open(outputdll, FileMode.Create, FileAccess.ReadWrite)

Assert.Throws<NotSupportedException>(fun () -> ``module``.Write(sink, writer))
|> ignore

pruneLocalScopes pathGetterDef
// should not throw
``module``.Write(sink, writer)

Assert.That(
Expand All @@ -937,11 +922,6 @@ module AltCoverTests2 =
"pruned Scope.Start.IsEndOfMethod"
)

Assert.True(
pathGetterDef.DebugInformation.Scope.Scopes
|> Seq.isEmpty,
"pruned subscope.Start.IsEndOfMethod"
)
(* was
IL_0000: ldarg.0
IL_0001: ldfld bool Sample31.Class3/Class4::'<Defer>k__BackingField'
Expand Down Expand Up @@ -994,42 +974,19 @@ has been prefixed with Ldc_I4_1 (1 byte)

rescope.Scopes.Add rescope

let save = Output.verbose
let b = System.Text.StringBuilder()

Output.verbose <- b.AppendLine >> ignore

prepareLocalScopes pathGetterDef

Assert.True(
InstructionOffset() |> safeOffset |> Option.isNone,
InstructionOffset().IsEndOfMethod,
"End should go to none"
)

// prune 1 recursion and 2 at end
Assert.That(rescope.Scopes |> Seq.length, Is.EqualTo 4)
// prune 1 recursion and 2 at end => 3
Assert.That(rescope.Scopes |> Seq.length, Is.EqualTo (4+3))

test <@ start.Offset = 0 @>
test <@ start.Next.Offset = 1 @>
test <@ start.Next.Next.Offset = 2 @>
test <@ start.Next.Next.Next.Offset = 7 @>

let expected =
[ Some start.Offset
Some start.Next.Next.Offset
Some finish.Offset
Some finish.Offset ]

let result =
rescope.Scopes
|> Seq.map (fun s -> safeOffset s.Start)
|> Seq.toList

test <@ result = expected @>
test <@ b.ToString() = String.Empty @>

Output.verbose <- save

[<Test>]
let ShouldWriteMonoAssemblyOK () =
try
Expand Down
22 changes: 11 additions & 11 deletions Directory.Packages.props
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@
<PackageVersion Include="AltCode.Fake.DotNet.Gendarme" Version="5.23.0.42" />
<PackageVersion Include="AltCode.Dixon" Version="2022.12.6.11014" />
<PackageVersion Include="altcode.gendarme" Version="2023.1.22.12221" />
<PackageVersion Include="altcover" Version="8.6.14" />
<PackageVersion Include="AltCover.Api" Version="8.6.14" />
<PackageVersion Include="AltCover.Fake" Version="8.6.14" />
<PackageVersion Include="altcover" Version="8.6.45" />
<PackageVersion Include="AltCover.Api" Version="8.6.45" />
<PackageVersion Include="AltCover.Fake" Version="8.6.45" />
<PackageVersion Include="Avalonia" Version="0.10.18" />
<PackageVersion Include="Avalonia.Desktop" Version="0.10.18" />
<PackageVersion Include="Avalonia.Themes.Fluent" Version="11.0.0-preview4" />
Expand All @@ -17,18 +17,18 @@
<PackageVersion Include="Cake.Common" Condition="'$(TargetFramework)' == 'netcoreapp3.1'" Version="2.0.0" />
<PackageVersion Include="Cake.Core" Condition="'$(TargetFramework)' == 'netstandard2.0'" Version="1.0.0" />
<PackageVersion Include="Cake.Core" Condition="'$(TargetFramework)' == 'netcoreapp3.1'" Version="2.0.0" />
<PackageVersion Include="CommunityToolkit.Diagnostics" Version="8.1.0" />
<PackageVersion Include="CommunityToolkit.Diagnostics" Version="8.2.0" />
<PackageVersion Include="coverlet.collector" Version="3.2.0" />
<PackageVersion Include="CsvTextFieldParser" Version="1.2.2" />
<PackageVersion Include="DotNet.ReproducibleBuilds" Version="1.1.1" />
<PackageVersion Include="Expecto" Version="9.0.4" />
<PackageVersion Include="Expecto.TestResults" Version="8.13.2" />
<PackageVersion Include="FAKE.Core.Environment" Version="5.23.0" />
<PackageVersion Include="FAKE.Core.Process" Version="5.23.0" />
<PackageVersion Include="FAKE.Core.Trace" Version="5.23.0" />
<PackageVersion Include="FAKE.Core.Environment" Version="6.0.0" />
<PackageVersion Include="FAKE.Core.Process" Version="6.0.0" />
<PackageVersion Include="FAKE.Core.Trace" Version="6.0.0" />
<PackageVersion Include="Fake.Core.Target" Version="5.23.0" />
<PackageVersion Include="Fake.dotNet.AssemblyInfoFile" Version="5.23.0" />
<PackageVersion Include="FAKE.DotNet.Cli" Version="5.23.0" />
<PackageVersion Include="FAKE.DotNet.Cli" Version="6.0.0" />
<PackageVersion Include="Fake.dotNet.fxcop" Version="5.23.0" />
<PackageVersion Include="Fake.dotNet.msbuild" Version="5.23.0" />
<PackageVersion Include="Fake.DotNet.NuGet" Version="5.23.0" />
Expand All @@ -41,7 +41,7 @@
<PackageVersion Include="Fake.Tools.git" Version="5.23.0" />
<PackageVersion Include="FSharp.Compiler.Tools" Version="10.2.3" />
<PackageVersion Include="FSharp.Core" Version="7.0.200" />
<PackageVersion Include="FsUnit" Version="5.2.0" />
<PackageVersion Include="FsUnit" Version="5.3.0" />
<PackageVersion Include="FuChu" Version="1.1.0" />
<PackageVersion Include="GtkSharp" Version="3.24.24.38" />
<PackageVersion Include="Handlebars.Net" Version="2.1.4" />
Expand All @@ -55,12 +55,12 @@
<PackageVersion Include="Microsoft.NET.Test.Sdk" Version="17.5.0" />
<PackageVersion Include="Microsoft.SourceLink.GitHub" Version="1.1.1" />
<PackageVersion Include="Microsoft.TestPlatform.ObjectModel" Version="16.0.0" />
<PackageVersion Include="Mono.Cecil" Version="0.11.4" />
<PackageVersion Include="Mono.Cecil" Version="0.11.5" />
<PackageVersion Include="Mono.CSharp" Version="4.0.0.143" />
<PackageVersion Include="Mono.Options" Version="6.12.0.148" />
<PackageVersion Include="MSTest.TestFramework" Version="2.2.10" />
<PackageVersion Include="MSTest.TestAdapter" Version="2.2.10" />
<PackageVersion Include="Nerdbank.GitVersioning" Version="3.5.119" />
<PackageVersion Include="Nerdbank.GitVersioning" Version="3.6.128" />
<PackageVersion Include="Newtonsoft.Json" Version="13.0.3" />
<PackageVersion Include="NuGet.CommandLine" Version="6.5.0" />
<PackageVersion Include="NUnit" Version="3.13.3" />
Expand Down
Loading

0 comments on commit a7a68a1

Please sign in to comment.