Skip to content

Commit

Permalink
[rel/3.8] Fix serialization of exceptions by BinaryFormatter in .NET …
Browse files Browse the repository at this point in the history
…Framework (#5055)

Co-authored-by: Jakub Jareš <me@jakubjares.com>
Co-authored-by: Amaury Levé <amauryleve@microsoft.com>
Co-authored-by: Youssef Victor <youssefvictor00@gmail.com>
  • Loading branch information
4 people authored Feb 18, 2025
1 parent 51d51a8 commit ac22a6d
Show file tree
Hide file tree
Showing 8 changed files with 120 additions and 1 deletion.
3 changes: 3 additions & 0 deletions src/Adapter/MSTest.Engine/Assertions/AssertFailedException.cs
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,9 @@ public AssertFailedException(string message, Exception ex)
{
}

#if NET8_0_OR_GREATER
[Obsolete(DiagnosticId = "SYSLIB0051")]
#endif
private AssertFailedException(SerializationInfo serializationInfo, StreamingContext streamingContext)
{
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.

using System.ComponentModel;
using System.Runtime.Serialization;

namespace Microsoft.VisualStudio.TestTools.UnitTesting;

/// <summary>
Expand Down Expand Up @@ -35,4 +38,18 @@ public AssertFailedException()
: base()
{
}

/// <summary>
/// Initializes a new instance of the <see cref="AssertFailedException"/> class.
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Streaming context.</param>
#if NET8_0_OR_GREATER
[Obsolete(DiagnosticId = "SYSLIB0051")]
#endif
[EditorBrowsable(EditorBrowsableState.Never)]
protected AssertFailedException(SerializationInfo info, StreamingContext context)
: base(info, context)
{
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.

using System.ComponentModel;
using System.Runtime.Serialization;

namespace Microsoft.VisualStudio.TestTools.UnitTesting;

/// <summary>
Expand Down Expand Up @@ -35,4 +38,18 @@ public AssertInconclusiveException()
: base()
{
}

/// <summary>
/// Initializes a new instance of the <see cref="AssertInconclusiveException"/> class.
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Streaming context.</param>
#if NET8_0_OR_GREATER
[Obsolete(DiagnosticId = "SYSLIB0051")]
#endif
[EditorBrowsable(EditorBrowsableState.Never)]
protected AssertInconclusiveException(SerializationInfo info, StreamingContext context)
: base(info, context)
{
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.

using System.ComponentModel;
using System.Runtime.Serialization;

namespace Microsoft.VisualStudio.TestTools.UnitTesting;

/// <summary>
Expand Down Expand Up @@ -46,4 +49,18 @@ public InternalTestFailureException()
: base()
{
}

/// <summary>
/// Initializes a new instance of the <see cref="InternalTestFailureException"/> class.
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Streaming context.</param>
#if NET8_0_OR_GREATER
[Obsolete(DiagnosticId = "SYSLIB0051")]
#endif
[EditorBrowsable(EditorBrowsableState.Never)]
protected InternalTestFailureException(SerializationInfo info, StreamingContext context)
: base(info, context)
{
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.

using System.ComponentModel;
using System.Runtime.Serialization;

namespace Microsoft.VisualStudio.TestTools.UnitTesting;

/// <summary>
Expand Down Expand Up @@ -34,4 +37,18 @@ protected UnitTestAssertException(string msg)
: base(msg)
{
}

/// <summary>
/// Initializes a new instance of the <see cref="UnitTestAssertException"/> class.
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Streaming context.</param>
#if NET8_0_OR_GREATER
[Obsolete(DiagnosticId = "SYSLIB0051")]
#endif
[EditorBrowsable(EditorBrowsableState.Never)]
protected UnitTestAssertException(SerializationInfo info, StreamingContext context)
: base(info, context)
{
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -375,3 +375,7 @@ static Microsoft.VisualStudio.TestTools.UnitTesting.Assert.ThrowsExactlyAsync<TE
[MSTESTEXP]Microsoft.VisualStudio.TestTools.UnitTesting.RetryResult
[MSTESTEXP]Microsoft.VisualStudio.TestTools.UnitTesting.RetryResult.AddResult(Microsoft.VisualStudio.TestTools.UnitTesting.TestResult![]! testResults) -> void
[MSTESTEXP]Microsoft.VisualStudio.TestTools.UnitTesting.RetryResult.RetryResult() -> void
Microsoft.VisualStudio.TestTools.UnitTesting.AssertFailedException.AssertFailedException(System.Runtime.Serialization.SerializationInfo! info, System.Runtime.Serialization.StreamingContext context) -> void
Microsoft.VisualStudio.TestTools.UnitTesting.AssertInconclusiveException.AssertInconclusiveException(System.Runtime.Serialization.SerializationInfo! info, System.Runtime.Serialization.StreamingContext context) -> void
Microsoft.VisualStudio.TestTools.UnitTesting.InternalTestFailureException.InternalTestFailureException(System.Runtime.Serialization.SerializationInfo! info, System.Runtime.Serialization.StreamingContext context) -> void
Microsoft.VisualStudio.TestTools.UnitTesting.UnitTestAssertException.UnitTestAssertException(System.Runtime.Serialization.SerializationInfo! info, System.Runtime.Serialization.StreamingContext context) -> void
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.

using System.Runtime.Serialization.Formatters.Binary;

using Microsoft.VisualStudio.TestTools.UnitTesting;

using TestFramework.ForTestingMSTest;

namespace Microsoft.VisualStudio.TestPlatform.TestFramework.UnitTests.Attributes;

[Obsolete]
public sealed class BinaryFormatterExceptionSerializationTests : TestContainer
{
public void AssertFailedExceptionCanBeSerializedAndDeserialized()
=> VerifySerialization(Assert.Fail);

public void AssertInconclusiveExceptionCanBeSerializedAndDeserialized()
=> VerifySerialization(Assert.Inconclusive);

public void InternalTestFailureExceptionCanBeSerializedAndDeserialized()
=> VerifySerialization(() => throw new InternalTestFailureException("Some internal error."));

private void VerifySerialization(Action actionThatThrows)
{
try
{
actionThatThrows();
}
catch (Exception ex)
{
// Ensure the thrown exception can be serialized and deserialized by binary formatter to keep compatibility with it,
// even though it is obsoleted and removed in .NET.
var mem = new MemoryStream();
new BinaryFormatter().Serialize(mem, ex);
mem.Position = 0;
new BinaryFormatter().Deserialize(mem);

return;
}

throw new InvalidOperationException($"The provided '{nameof(actionThatThrows)}' did not throw any exception.");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
</PropertyGroup>

<ItemGroup>
<ProjectReference Include="$(RepoRoot)src\TestFramework\TestFramework\TestFramework.csproj"/>
<ProjectReference Include="$(RepoRoot)src\TestFramework\TestFramework\TestFramework.csproj" />
<ProjectReference Include="$(RepoRoot)test\Utilities\TestFramework.ForTestingMSTest\TestFramework.ForTestingMSTest.csproj" />
</ItemGroup>

Expand Down

0 comments on commit ac22a6d

Please sign in to comment.