diff --git a/src/DataProtection/DataProtection/src/AuthenticatedEncryption/ManagedAuthenticatedEncryptorFactory.cs b/src/DataProtection/DataProtection/src/AuthenticatedEncryption/ManagedAuthenticatedEncryptorFactory.cs index 42b08734cc31b3961fad6fb68e49e1464e1521c0..97e35e9441e172930ff51ecd956a119b26cc4ab7 100644 --- a/src/DataProtection/DataProtection/src/AuthenticatedEncryption/ManagedAuthenticatedEncryptorFactory.cs +++ b/src/DataProtection/DataProtection/src/AuthenticatedEncryption/ManagedAuthenticatedEncryptorFactory.cs @@ -74,7 +74,7 @@ public sealed class ManagedAuthenticatedEncryptorFactory : IAuthenticatedEncrypt } else { - return AlgorithmActivator.CreateFactory<KeyedHashAlgorithm>(configuration.ValidationAlgorithmType); + return AlgorithmActivator.CreateFactory<KeyedHashAlgorithm>(ValidateHasPublicParameterlessConstructor(configuration.ValidationAlgorithmType)); } } @@ -99,10 +99,23 @@ public sealed class ManagedAuthenticatedEncryptorFactory : IAuthenticatedEncrypt } else { - return AlgorithmActivator.CreateFactory<SymmetricAlgorithm>(configuration.EncryptionAlgorithmType); + return AlgorithmActivator.CreateFactory<SymmetricAlgorithm>(ValidateHasPublicParameterlessConstructor(configuration.EncryptionAlgorithmType)); } } + [UnconditionalSuppressMessage("Trimmer", "IL2068", Justification = "Reflecting over the async Task types contract")] + [UnconditionalSuppressMessage("Trimmer", "IL2070", Justification = "Reflecting over the async Task types contract")] + [return: DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)] + private static Type ValidateHasPublicParameterlessConstructor(Type type) + { + if (type.GetConstructor(Type.EmptyTypes) == null) + { + throw new InvalidOperationException($"Unable to find public parameterless constructor for type '{type.FullName}'. If the app is published with trimming then it may have been trimmed. Ensure the type's assembly is excluded from trimming."); + } + + return type; + } + /// <summary> /// Contains helper methods for generating cryptographic algorithm factories. /// </summary> @@ -111,7 +124,7 @@ public sealed class ManagedAuthenticatedEncryptorFactory : IAuthenticatedEncrypt /// <summary> /// Creates a factory that wraps a call to <see cref="Activator.CreateInstance{T}"/>. /// </summary> - public static Func<T> CreateFactory<T>(Type implementation) + public static Func<T> CreateFactory<T>([DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)] Type implementation) { return ((IActivator<T>)Activator.CreateInstance(typeof(AlgorithmActivatorCore<>).MakeGenericType(implementation))!).Creator; }