diff --git a/build-tools/trim-analyzers/trim-analyzers.props b/build-tools/trim-analyzers/trim-analyzers.props
new file mode 100644
index 00000000000..a76e6902b74
--- /dev/null
+++ b/build-tools/trim-analyzers/trim-analyzers.props
@@ -0,0 +1,49 @@
+
+
+
+
+ true
+ true
+ true
+
+ true
+
+
+ $(WarningsAsErrors);
+ IL2000;IL2001;IL2002;IL2003;IL2004;
+ IL2005;IL2006;IL2007;IL2008;IL2009;
+ IL2010;IL2011;IL2012;IL2013;IL2014;
+ IL2015;IL2016;IL2017;IL2018;IL2019;
+ IL2020;IL2021;IL2022;IL2023;IL2024;
+ IL2025;IL2026;IL2027;IL2028;IL2029;
+ IL2030;IL2031;IL2032;IL2033;IL2034;
+ IL2035;IL2036;IL2037;IL2038;IL2039;
+ IL2040;IL2041;IL2042;IL2043;IL2044;
+ IL2045;IL2046;IL2047;IL2048;IL2049;
+ IL2050;IL2051;IL2052;IL2053;IL2054;
+ IL2055;IL2056;IL2057;IL2058;IL2059;
+ IL2060;IL2061;IL2062;IL2063;IL2064;
+ IL2065;IL2066;IL2067;IL2068;IL2069;
+ IL2070;IL2071;IL2072;IL2073;IL2074;
+ IL2075;IL2076;IL2077;IL2078;IL2079;
+ IL2080;IL2081;IL2082;IL2083;IL2084;
+ IL2085;IL2086;IL2087;IL2088;IL2089;
+ IL2090;IL2091;IL2092;IL2093;IL2094;
+ IL2095;IL2096;IL2097;IL2098;IL2099;
+ IL2100;IL2101;IL2102;IL2103;IL2104;
+ IL2105;IL2106;IL2107;IL2108;IL2109;
+
+
+
+ $(WarningsAsErrors);
+ IL3050;IL3051;IL3052;IL3053;IL3054;IL3055;IL3056;
+
+
+
diff --git a/src/Mono.Android/Android.OS/AsyncTask.cs b/src/Mono.Android/Android.OS/AsyncTask.cs
index ad5db1b113b..e66a162a145 100644
--- a/src/Mono.Android/Android.OS/AsyncTask.cs
+++ b/src/Mono.Android/Android.OS/AsyncTask.cs
@@ -9,7 +9,16 @@ namespace Android.OS {
[global::System.Runtime.Versioning.ObsoletedOSPlatform ("android30.0")]
[Register ("android/os/AsyncTask", DoNotGenerateAcw=true)]
- public abstract class AsyncTask : AsyncTask {
+ public abstract class AsyncTask<
+ [DynamicallyAccessedMembers (Constructors)]
+ TParams,
+ [DynamicallyAccessedMembers (Constructors)]
+ TProgress,
+ [DynamicallyAccessedMembers (Constructors)]
+ TResult
+ > : AsyncTask {
+
+ const DynamicallyAccessedMemberTypes Constructors = DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors;
static IntPtr java_class_handle;
internal static IntPtr class_ref {
diff --git a/src/Mono.Android/Android.Runtime/AndroidEnvironment.cs b/src/Mono.Android/Android.Runtime/AndroidEnvironment.cs
index edfe42ec449..2c9ab61499f 100644
--- a/src/Mono.Android/Android.Runtime/AndroidEnvironment.cs
+++ b/src/Mono.Android/Android.Runtime/AndroidEnvironment.cs
@@ -24,6 +24,7 @@ public static class AndroidEnvironment {
static IX509TrustManager? sslTrustManager;
static KeyStore? certStore;
static object lock_ = new object ();
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)]
static Type? httpMessageHandlerType;
static void SetupTrustManager ()
@@ -335,11 +336,25 @@ static IWebProxy GetDefaultProxy ()
[DynamicDependency (DynamicallyAccessedMemberTypes.PublicParameterlessConstructor, typeof (Xamarin.Android.Net.AndroidMessageHandler))]
static object GetHttpMessageHandler ()
{
+ const string justification = "DynamicDependency should preserve AndroidMessageHandler.";
+
+ [UnconditionalSuppressMessage ("Trimming", "IL2057", Justification = justification)]
+ [return: DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)]
+ static Type TypeGetType (string typeName) =>
+ Type.GetType (typeName, throwOnError: false);
+
+ [UnconditionalSuppressMessage ("Trimming", "IL2077", Justification = justification)]
+ [return: DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)]
+ static object ActivatorCreateInstance (
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)]
+ Type type) =>
+ Activator.CreateInstance (type);
+
if (httpMessageHandlerType is null) {
var handlerTypeName = Environment.GetEnvironmentVariable ("XA_HTTP_CLIENT_HANDLER_TYPE")?.Trim ();
Type? handlerType = null;
if (!String.IsNullOrEmpty (handlerTypeName))
- handlerType = Type.GetType (handlerTypeName, throwOnError: false);
+ handlerType = TypeGetType (handlerTypeName);
// We don't do any type checking or casting here to avoid dependency on System.Net.Http in Mono.Android.dll
if (handlerType is null || !IsAcceptableHttpMessageHandlerType (handlerType)) {
@@ -349,33 +364,33 @@ static object GetHttpMessageHandler ()
httpMessageHandlerType = handlerType;
}
- return Activator.CreateInstance (httpMessageHandlerType)
+ return ActivatorCreateInstance (httpMessageHandlerType)
?? throw new InvalidOperationException ($"Could not create an instance of HTTP message handler type {httpMessageHandlerType.AssemblyQualifiedName}");
}
static bool IsAcceptableHttpMessageHandlerType (Type handlerType)
{
- if (Extends (handlerType, "System.Net.Http.HttpClientHandler, System.Net.Http")) {
+ if (Type.GetType ("System.Net.Http.HttpClientHandler, System.Net.Http", throwOnError: false) is Type httpClientHandlerType &&
+ httpClientHandlerType.IsAssignableFrom (handlerType)) {
// It's not possible to construct HttpClientHandler in this method because it would cause infinite recursion
// as HttpClientHandler's constructor calls the GetHttpMessageHandler function
Logger.Log (LogLevel.Warn, "MonoAndroid", $"The type {handlerType.AssemblyQualifiedName} cannot be used as the native HTTP handler because it is derived from System.Net.Htt.HttpClientHandler. Use a type that extends System.Net.Http.HttpMessageHandler instead.");
return false;
}
- if (!Extends (handlerType, "System.Net.Http.HttpMessageHandler, System.Net.Http")) {
- Logger.Log (LogLevel.Warn, "MonoAndroid", $"The type {handlerType.AssemblyQualifiedName} set as the default HTTP handler is invalid. Use a type that extends System.Net.Http.HttpMessageHandler.");
- return false;
+ if (Type.GetType ("System.Net.Http.HttpMessageHandler, System.Net.Http", throwOnError: false) is Type httpMessageHandlerType &&
+ httpMessageHandlerType.IsAssignableFrom (handlerType)) {
+ return true;
}
- return true;
- }
-
- static bool Extends (Type handlerType, string baseTypeName) {
- var baseType = Type.GetType (baseTypeName, throwOnError: false);
- return baseType?.IsAssignableFrom (handlerType) ?? false;
+ // Was not an acceptable type
+ Logger.Log (LogLevel.Warn, "MonoAndroid", $"The type {handlerType.AssemblyQualifiedName} set as the default HTTP handler is invalid. Use a type that extends System.Net.Http.HttpMessageHandler.");
+ return false;
}
- static Type GetFallbackHttpMessageHandlerType (string typeName = "Xamarin.Android.Net.AndroidMessageHandler, Mono.Android")
+ [return: DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)]
+ static Type GetFallbackHttpMessageHandlerType ()
{
+ const string typeName = "Xamarin.Android.Net.AndroidMessageHandler, Mono.Android";
var handlerType = Type.GetType (typeName, throwOnError: false)
?? throw new InvalidOperationException ($"The {typeName} was not found. The type was probably linked away.");
diff --git a/src/Mono.Android/Android.Runtime/JNIEnv.cs b/src/Mono.Android/Android.Runtime/JNIEnv.cs
index 80f214a1454..0f937eb6535 100644
--- a/src/Mono.Android/Android.Runtime/JNIEnv.cs
+++ b/src/Mono.Android/Android.Runtime/JNIEnv.cs
@@ -16,11 +16,27 @@
namespace Android.Runtime {
public static partial class JNIEnv {
+ const DynamicallyAccessedMemberTypes Constructors = DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors;
+
[ThreadStatic]
static byte[]? mvid_bytes;
public static IntPtr Handle => JniEnvironment.EnvironmentPointer;
+ static Array ArrayCreateInstance (Type elementType, int length) =>
+ // FIXME: https://github.com/xamarin/java.interop/issues/1192
+ // IL3050 disabled in source: if someone uses NativeAOT, they will get the warning.
+ #pragma warning disable IL3050
+ Array.CreateInstance (elementType, length);
+ #pragma warning restore IL3050
+
+ static Type MakeArrayType (Type type) =>
+ // FIXME: https://github.com/xamarin/java.interop/issues/1192
+ // IL3050 disabled in source: if someone uses NativeAOT, they will get the warning.
+ #pragma warning disable IL3050
+ type.MakeArrayType ();
+ #pragma warning restore IL3050
+
internal static IntPtr IdentityHash (IntPtr v)
{
return JNIEnvInit.LocalRefsAreIndirect ? RuntimeNativeMethods._monodroid_get_identity_hash_code (Handle, v) : v;
@@ -807,7 +823,7 @@ public static void CopyArray (IntPtr src, Array dest, Type? elementType = null)
throw new ArgumentNullException ("dest");
if (elementType != null && elementType.IsValueType)
- AssertCompatibleArrayTypes (src, elementType.MakeArrayType ());
+ AssertCompatibleArrayTypes (src, MakeArrayType (elementType));
if (elementType != null && elementType.IsArray) {
for (int i = 0; i < dest.Length; ++i) {
@@ -950,7 +966,7 @@ public static void CopyArray (Array source, Type elementType, IntPtr dest)
throw new ArgumentNullException ("elementType");
if (elementType.IsValueType)
- AssertCompatibleArrayTypes (elementType.MakeArrayType (), dest);
+ AssertCompatibleArrayTypes (MakeArrayType (elementType), dest);
Action converter = GetConverter (CopyManagedToNativeArray, elementType, dest);
@@ -1057,12 +1073,12 @@ public static void CopyArray (T[] src, IntPtr dest)
}
} },
{ typeof (IJavaObject), (type, source, len) => {
- var r = Array.CreateInstance (type!, len);
+ var r = ArrayCreateInstance (type!, len);
CopyArray (source, r, type);
return r;
} },
{ typeof (Array), (type, source, len) => {
- var r = Array.CreateInstance (type!, len);
+ var r = ArrayCreateInstance (type!, len);
CopyArray (source, r, type);
return r;
} },
@@ -1075,7 +1091,7 @@ public static void CopyArray (T[] src, IntPtr dest)
return null;
if (element_type != null && element_type.IsValueType)
- AssertCompatibleArrayTypes (array_ptr, element_type.MakeArrayType ());
+ AssertCompatibleArrayTypes (array_ptr, MakeArrayType (element_type));
int cnt = _GetArrayLength (array_ptr);
@@ -1130,7 +1146,10 @@ static int _GetArrayLength (IntPtr array_ptr)
return ret;
}
- public static T[]? GetArray (Java.Lang.Object[] array)
+ public static T[]? GetArray<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ > (Java.Lang.Object[] array)
{
if (array == null)
return null;
@@ -1244,7 +1263,10 @@ static IntPtr GetArrayElementClass(T[] values)
return FindClass (elementType);
}
- public static void CopyObjectArray(IntPtr source, T[] destination)
+ public static void CopyObjectArray<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ >(IntPtr source, T[] destination)
{
if (source == IntPtr.Zero)
return;
diff --git a/src/Mono.Android/Android.Runtime/JavaCollection.cs b/src/Mono.Android/Android.Runtime/JavaCollection.cs
index 70660bc24a3..8e23660f33b 100644
--- a/src/Mono.Android/Android.Runtime/JavaCollection.cs
+++ b/src/Mono.Android/Android.Runtime/JavaCollection.cs
@@ -14,6 +14,8 @@ namespace Android.Runtime {
// java.util.Collection allows null values
public class JavaCollection : Java.Lang.Object, System.Collections.ICollection {
+ internal const DynamicallyAccessedMemberTypes Constructors = DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors;
+
internal static IntPtr collection_class = JNIEnv.FindClass ("java/util/Collection");
internal static IntPtr id_add;
@@ -148,6 +150,11 @@ internal Java.Lang.Object[] ToArray ()
//
public void CopyTo (Array array, int array_index)
{
+ [UnconditionalSuppressMessage ("Trimming", "IL2073", Justification = "JavaCollection constructors are preserved by the MarkJavaObjects trimmer step.")]
+ [return: DynamicallyAccessedMembers (Constructors)]
+ static Type GetElementType (Array array) =>
+ array.GetType ().GetElementType ();
+
if (array == null)
throw new ArgumentNullException ("array");
if (array_index < 0)
@@ -164,7 +171,7 @@ public void CopyTo (Array array, int array_index)
JavaConvert.FromJniHandle (
JNIEnv.GetObjectArrayElement (lrefArray, i),
JniHandleOwnership.TransferLocalRef,
- array.GetType ().GetElementType ()),
+ GetElementType (array)),
array_index + i);
JNIEnv.DeleteLocalRef (lrefArray);
}
@@ -203,7 +210,10 @@ public static IntPtr ToLocalJniHandle (ICollection? items)
}
[Register ("java/util/Collection", DoNotGenerateAcw=true)]
- public sealed class JavaCollection : JavaCollection, ICollection {
+ public sealed class JavaCollection<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ > : JavaCollection, ICollection {
public JavaCollection (IntPtr handle, JniHandleOwnership transfer)
: base (handle, transfer)
diff --git a/src/Mono.Android/Android.Runtime/JavaDictionary.cs b/src/Mono.Android/Android.Runtime/JavaDictionary.cs
index 80656dfc58c..311dbf36ebe 100644
--- a/src/Mono.Android/Android.Runtime/JavaDictionary.cs
+++ b/src/Mono.Android/Android.Runtime/JavaDictionary.cs
@@ -12,6 +12,8 @@ namespace Android.Runtime {
// java.util.HashMap allows null keys and values
public class JavaDictionary : Java.Lang.Object, System.Collections.IDictionary {
+ internal const DynamicallyAccessedMemberTypes Constructors = DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors;
+
class DictionaryEnumerator : IDictionaryEnumerator {
IEnumerator simple_enumerator;
@@ -396,7 +398,12 @@ public static IntPtr ToLocalJniHandle (IDictionary? dictionary)
// it may throw.
//
[Register ("java/util/HashMap", DoNotGenerateAcw=true)]
- public class JavaDictionary : JavaDictionary, IDictionary {
+ public class JavaDictionary<
+ [DynamicallyAccessedMembers (Constructors)]
+ K,
+ [DynamicallyAccessedMembers (Constructors)]
+ V
+ > : JavaDictionary, IDictionary {
[Register (".ctor", "()V", "")]
public JavaDictionary ()
diff --git a/src/Mono.Android/Android.Runtime/JavaList.cs b/src/Mono.Android/Android.Runtime/JavaList.cs
index 980b01f386e..e1877533577 100644
--- a/src/Mono.Android/Android.Runtime/JavaList.cs
+++ b/src/Mono.Android/Android.Runtime/JavaList.cs
@@ -10,6 +10,7 @@ namespace Android.Runtime {
// java.util.ArrayList allows null values
public partial class JavaList : Java.Lang.Object, System.Collections.IList {
+ internal const DynamicallyAccessedMemberTypes Constructors = DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors;
internal static readonly JniPeerMembers list_members = new XAPeerMembers ("java/util/List", typeof (JavaList), isInterface: true);
//
@@ -23,7 +24,10 @@ public partial class JavaList : Java.Lang.Object, System.Collections.IList {
//
// https://developer.android.com/reference/java/util/List.html?hl=en#get(int)
//
- internal unsafe object? InternalGet (int location, Type? targetType = null)
+ internal unsafe object? InternalGet (
+ int location,
+ [DynamicallyAccessedMembers (Constructors)]
+ Type? targetType = null)
{
const string id = "get.(I)Ljava/lang/Object;";
JniObjectReference obj;
@@ -266,6 +270,11 @@ public unsafe bool Contains (object? item)
public void CopyTo (Array array, int array_index)
{
+ [UnconditionalSuppressMessage ("Trimming", "IL2073", Justification = "JavaList constructors are preserved by the MarkJavaObjects trimmer step.")]
+ [return: DynamicallyAccessedMembers (Constructors)]
+ static Type GetElementType (Array array) =>
+ array.GetType ().GetElementType ();
+
if (array == null)
throw new ArgumentNullException ("array");
if (array_index < 0)
@@ -273,7 +282,7 @@ public void CopyTo (Array array, int array_index)
if (array.Length < array_index + Count)
throw new ArgumentException ("array");
- var targetType = array.GetType ().GetElementType ();
+ var targetType = GetElementType (array);
int c = Count;
for (int i = 0; i < c; i++)
array.SetValue (InternalGet (i, targetType), array_index + i);
@@ -673,7 +682,10 @@ public virtual Java.Lang.Object [] ToArray ()
}
[Register ("java/util/ArrayList", DoNotGenerateAcw=true)]
- public class JavaList : JavaList, IList {
+ public class JavaList<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ > : JavaList, IList {
//
// Exception audit:
diff --git a/src/Mono.Android/Android.Runtime/JavaSet.cs b/src/Mono.Android/Android.Runtime/JavaSet.cs
index c141e1058a4..b84b040289a 100644
--- a/src/Mono.Android/Android.Runtime/JavaSet.cs
+++ b/src/Mono.Android/Android.Runtime/JavaSet.cs
@@ -268,7 +268,10 @@ public static IntPtr ToLocalJniHandle (ICollection? items)
[Register ("java/util/HashSet", DoNotGenerateAcw=true)]
// java.util.HashSet allows null
- public class JavaSet : JavaSet, ICollection {
+ public class JavaSet<
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)]
+ T
+ > : JavaSet, ICollection {
//
// Exception audit:
diff --git a/src/Mono.Android/Android.Util/SparseArray.cs b/src/Mono.Android/Android.Util/SparseArray.cs
index 0fcd05f31f6..2a895fb7307 100644
--- a/src/Mono.Android/Android.Util/SparseArray.cs
+++ b/src/Mono.Android/Android.Util/SparseArray.cs
@@ -1,4 +1,5 @@
using System;
+using System.Diagnostics.CodeAnalysis;
using Android.Runtime;
@@ -7,7 +8,10 @@
namespace Android.Util
{
[Register ("android/util/SparseArray", DoNotGenerateAcw=true)]
- public partial class SparseArray : SparseArray
+ public partial class SparseArray<
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)]
+ E
+ > : SparseArray
{
public SparseArray ()
{
diff --git a/src/Mono.Android/Android.Widget/AdapterView.cs b/src/Mono.Android/Android.Widget/AdapterView.cs
index 5ad2293d8e3..7689b0c39e3 100644
--- a/src/Mono.Android/Android.Widget/AdapterView.cs
+++ b/src/Mono.Android/Android.Widget/AdapterView.cs
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
+using System.Diagnostics.CodeAnalysis;
using Android.Views;
using JLO = Java.Lang.Object;
@@ -49,7 +50,10 @@ public event EventHandler ItemSelectionCleared {
}
[Register ("android/widget/AdapterView", DoNotGenerateAcw=true)]
- public abstract class AdapterView : AdapterView where T : IAdapter {
+ public abstract class AdapterView<
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)]
+ T
+ > : AdapterView where T : IAdapter {
public AdapterView (IntPtr handle, JniHandleOwnership transfer)
: base (handle, transfer)
diff --git a/src/Mono.Android/Android.Widget/ArrayAdapter.cs b/src/Mono.Android/Android.Widget/ArrayAdapter.cs
index cf35e67fc07..e54ce8d7c94 100644
--- a/src/Mono.Android/Android.Widget/ArrayAdapter.cs
+++ b/src/Mono.Android/Android.Widget/ArrayAdapter.cs
@@ -8,7 +8,10 @@
namespace Android.Widget {
[Register ("android/widget/ArrayAdapter", DoNotGenerateAcw=true)]
- public partial class ArrayAdapter : ArrayAdapter {
+ public partial class ArrayAdapter<
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)]
+ T
+ > : ArrayAdapter {
public ArrayAdapter (IntPtr handle, JniHandleOwnership transfer)
: base (handle, transfer)
diff --git a/src/Mono.Android/Java.Interop/JavaConvert.cs b/src/Mono.Android/Java.Interop/JavaConvert.cs
index c98bc8cd2f2..24d1eab985d 100644
--- a/src/Mono.Android/Java.Interop/JavaConvert.cs
+++ b/src/Mono.Android/Java.Interop/JavaConvert.cs
@@ -10,6 +10,7 @@
namespace Java.Interop {
static class JavaConvert {
+ const DynamicallyAccessedMemberTypes Constructors = DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors;
static Dictionary> JniHandleConverters = new Dictionary>() {
{ typeof (bool), (handle, transfer) => {
@@ -56,6 +57,17 @@ static class JavaConvert {
static Func? GetJniHandleConverter (Type? target)
{
+ const string justification = "JavaDictionary<,>, JavaList<>, and JavaCollection<> TODO I don't see what preserves a FromJniHandle method";
+ [UnconditionalSuppressMessage ("Trimming", "IL2055", Justification = justification)]
+ [UnconditionalSuppressMessage ("Trimming", "IL2068", Justification = justification)]
+ [return: DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicMethods)]
+ static Type MakeGenericType (Type type, params Type [] typeArguments) =>
+ // FIXME: https://github.com/xamarin/java.interop/issues/1192
+ // IL3050 disabled in source: if someone uses NativeAOT, they will get the warning.
+ #pragma warning disable IL3050
+ type.MakeGenericType (typeArguments);
+ #pragma warning restore IL3050
+
if (target == null)
return null;
@@ -64,19 +76,19 @@ static class JavaConvert {
if (target.IsArray)
return (h, t) => JNIEnv.GetArray (h, t, target.GetElementType ());
if (target.IsGenericType && target.GetGenericTypeDefinition() == typeof (IDictionary<,>)) {
- Type t = typeof (JavaDictionary<,>).MakeGenericType (target.GetGenericArguments ());
+ Type t = MakeGenericType (typeof (JavaDictionary<,>), target.GetGenericArguments ());
return GetJniHandleConverterForType (t);
}
if (typeof (IDictionary).IsAssignableFrom (target))
return (h, t) => JavaDictionary.FromJniHandle (h, t);
if (target.IsGenericType && target.GetGenericTypeDefinition() == typeof (IList<>)) {
- Type t = typeof (JavaList<>).MakeGenericType (target.GetGenericArguments ());
+ Type t = MakeGenericType (typeof (JavaList<>), target.GetGenericArguments ());
return GetJniHandleConverterForType (t);
}
if (typeof (IList).IsAssignableFrom (target))
return (h, t) => JavaList.FromJniHandle (h, t);
if (target.IsGenericType && target.GetGenericTypeDefinition() == typeof (ICollection<>)) {
- Type t = typeof (JavaCollection<>).MakeGenericType (target.GetGenericArguments ());
+ Type t = MakeGenericType (typeof (JavaCollection<>), target.GetGenericArguments ());
return GetJniHandleConverterForType (t);
}
if (typeof (ICollection).IsAssignableFrom (target))
@@ -92,13 +104,19 @@ static Func GetJniHandleConverterForType ([D
typeof (Func), m);
}
- public static T? FromJniHandle(IntPtr handle, JniHandleOwnership transfer)
+ public static T? FromJniHandle<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ >(IntPtr handle, JniHandleOwnership transfer)
{
bool set;
return FromJniHandle(handle, transfer, out set);
}
- public static T? FromJniHandle(IntPtr handle, JniHandleOwnership transfer, out bool set)
+ public static T? FromJniHandle<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ >(IntPtr handle, JniHandleOwnership transfer, out bool set)
{
if (handle == IntPtr.Zero) {
set = false;
@@ -133,7 +151,11 @@ static Func GetJniHandleConverterForType ([D
return (T?) Convert.ChangeType (v, typeof (T), CultureInfo.InvariantCulture);
}
- public static object? FromJniHandle (IntPtr handle, JniHandleOwnership transfer, Type? targetType = null)
+ public static object? FromJniHandle (
+ IntPtr handle,
+ JniHandleOwnership transfer,
+ [DynamicallyAccessedMembers (Constructors)]
+ Type? targetType = null)
{
if (handle == IntPtr.Zero) {
return null;
@@ -206,13 +228,19 @@ static Func GetJniHandleConverterForType ([D
return null;
}
- public static T? FromJavaObject(IJavaObject? value)
+ public static T? FromJavaObject<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ >(IJavaObject? value)
{
bool set;
return FromJavaObject(value, out set);
}
- public static T? FromJavaObject(IJavaObject? value, out bool set)
+ public static T? FromJavaObject<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ >(IJavaObject? value, out bool set)
{
if (value == null) {
set = false;
@@ -245,7 +273,10 @@ static Func GetJniHandleConverterForType ([D
return (T) Convert.ChangeType (value, typeof (T), CultureInfo.InvariantCulture);
}
- public static object? FromJavaObject (IJavaObject value, Type? targetType = null)
+ public static object? FromJavaObject (
+ IJavaObject value,
+ [DynamicallyAccessedMembers (Constructors)]
+ Type? targetType = null)
{
if (value == null)
return null;
diff --git a/src/Mono.Android/Java.Interop/JavaObjectExtensions.cs b/src/Mono.Android/Java.Interop/JavaObjectExtensions.cs
index 5b083487c5b..345c664c61d 100644
--- a/src/Mono.Android/Java.Interop/JavaObjectExtensions.cs
+++ b/src/Mono.Android/Java.Interop/JavaObjectExtensions.cs
@@ -17,7 +17,10 @@ public static JavaCollection ToInteroperableCollection (this ICollection instanc
}
[Obsolete ("Use Android.Runtime.JavaCollection.ToLocalJniHandle()")]
- public static JavaCollection ToInteroperableCollection (this ICollection instance)
+ public static JavaCollection ToInteroperableCollection<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ > (this ICollection instance)
{
return instance is JavaCollection ? (JavaCollection) instance : new JavaCollection (instance);
}
@@ -29,7 +32,10 @@ public static JavaList ToInteroperableCollection (this IList instance)
}
[Obsolete ("Use Android.Runtime.JavaList.ToLocalJniHandle()")]
- public static JavaList ToInteroperableCollection (this IList instance)
+ public static JavaList ToInteroperableCollection<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ > (this IList instance)
{
return instance is JavaList ? (JavaList) instance : new JavaList (instance);
}
@@ -41,7 +47,12 @@ public static JavaDictionary ToInteroperableCollection (this IDictionary instanc
}
[Obsolete ("Use Android.Runtime.JavaDictionary.ToLocalJniHandle()")]
- public static JavaDictionary ToInteroperableCollection (this IDictionary instance)
+ public static JavaDictionary ToInteroperableCollection<
+ [DynamicallyAccessedMembers (Constructors)]
+ K,
+ [DynamicallyAccessedMembers (Constructors)]
+ V
+ > (this IDictionary instance)
{
return instance is JavaDictionary ? (JavaDictionary) instance : new JavaDictionary (instance);
}
diff --git a/src/Mono.Android/Mono.Android.csproj b/src/Mono.Android/Mono.Android.csproj
index 006ebd5eb41..4ed01cacea2 100644
--- a/src/Mono.Android/Mono.Android.csproj
+++ b/src/Mono.Android/Mono.Android.csproj
@@ -3,6 +3,7 @@
+
$(DotNetTargetFramework)
diff --git a/src/Mono.Android/System.Linq/Extensions.cs b/src/Mono.Android/System.Linq/Extensions.cs
index ac555e17949..c8bb0a4a740 100644
--- a/src/Mono.Android/System.Linq/Extensions.cs
+++ b/src/Mono.Android/System.Linq/Extensions.cs
@@ -9,6 +9,8 @@ namespace System.Linq {
public static class Extensions {
+ const DynamicallyAccessedMemberTypes Constructors = DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors;
+
static IntPtr id_next;
static Extensions ()
@@ -40,7 +42,10 @@ internal static IEnumerator ToEnumerator_Dispose (this Java.Util.IIterator sourc
}
}
- public static IEnumerable ToEnumerable (this Java.Lang.IIterable source)
+ public static IEnumerable ToEnumerable<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ > (this Java.Lang.IIterable source)
{
if (source == null)
throw new ArgumentNullException ("source");
@@ -52,7 +57,10 @@ internal static IEnumerator ToEnumerator_Dispose (this Java.Util.IIterator sourc
}
}
- internal static IEnumerator ToEnumerator_Dispose (this Java.Util.IIterator source)
+ internal static IEnumerator ToEnumerator_Dispose<
+ [DynamicallyAccessedMembers (Constructors)]
+ T
+ > (this Java.Util.IIterator source)
{
using (source)
while (source.HasNext) {