Browse Source

Enable trimming in .NET 6 targets (#1906)

Ian Griffiths 2 years ago
parent
commit
e7c81256a4

+ 3 - 0
Rx.NET/Source/Directory.build.targets

@@ -16,6 +16,9 @@
   <PropertyGroup Condition="'$(TargetFramework)' == 'netstandard2.0'">
     <DefineConstants>$(DefineConstants);HAS_WINRT;NO_NULLABLE_ATTRIBUTES</DefineConstants>
   </PropertyGroup>
+  <PropertyGroup Condition="$(TargetFramework.StartsWith('net6.0')) or $(TargetFramework.StartsWith('net7.0'))">
+    <DefineConstants>$(DefineConstants);HAS_TRIMMABILITY_ATTRIBUTES</DefineConstants>
+  </PropertyGroup>
   <PropertyGroup Condition="$(TargetFramework.StartsWith('net6.0-windows')) or $(TargetFramework.StartsWith('net7.0-windows'))">
     <DefineConstants>$(DefineConstants);HAS_WINRT;HAS_WINFORMS;HAS_WPF;HAS_DISPATCHER;DESKTOPCLR;WINDOWS;CSWINRT</DefineConstants>
   </PropertyGroup>

+ 4 - 1
Rx.NET/Source/src/System.Reactive/Internal/Constants.cs

@@ -4,7 +4,7 @@
 
 namespace System.Reactive
 {
-    // We can't make those based on the Strings_Core.resx file, because the ObsoleteAttribute needs a compile-time constant.
+    // We can't make those based on the Strings_Core.resx file, because attributes need a compile-time constant.
 
     internal static class Constants_Core
     {
@@ -15,6 +15,9 @@ namespace System.Reactive
         public const string ObsoleteSchedulerThreadpool = ObsoleteRefactoring + " Consider using Scheduler.Default to obtain the platform's most appropriate pool-based scheduler. In order to access a specific pool-based scheduler, please add a reference to the System.Reactive.PlatformServices assembly for your target platform and use the appropriate scheduler in the System.Reactive.Concurrency namespace.";
 
         public const string ObsoleteSchedulerequired = "This instance property is no longer supported. Use CurrentThreadScheduler.IsScheduleRequired instead.";
+
+        internal const string AsQueryableTrimIncompatibilityMessage = "This type uses Queryable.AsQueryable, which is not compatible with trimming because expressions referencing IQueryable extension methods can get rebound to IEnumerable extension methods, and those IEnumerable methods might be trimmed.";
+        internal const string EventReflectionTrimIncompatibilityMessage = "This member uses reflection to discover event members and associated delegate types.";
     }
 
     // We can't make those based on the Strings_*.resx file, because the ObsoleteAttribute needs a compile-time constant.

+ 4 - 0
Rx.NET/Source/src/System.Reactive/Internal/ReflectionUtils.cs

@@ -2,6 +2,7 @@
 // The .NET Foundation licenses this file to you under the MIT License.
 // See the LICENSE file in the project root for more information. 
 
+using System.Diagnostics.CodeAnalysis;
 using System.Globalization;
 using System.Reflection;
 
@@ -19,6 +20,9 @@ namespace System.Reactive
             return method.CreateDelegate(delegateType, o);
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+    [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static void GetEventMethods<TSender, TEventArgs>(Type targetType, object? target, string eventName, out MethodInfo addMethod, out MethodInfo removeMethod, out Type delegateType, out bool isWinRT)
         {
             EventInfo? e;

+ 36 - 0
Rx.NET/Source/src/System.Reactive/Linq/IQueryLanguage.cs

@@ -433,17 +433,53 @@ namespace System.Reactive.Linq
         IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(Action<EventHandler<TEventArgs>> addHandler, Action<EventHandler<TEventArgs>> removeHandler, IScheduler scheduler);
         IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TDelegate, TSender, TEventArgs>(Action<TDelegate> addHandler, Action<TDelegate> removeHandler);
         IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TDelegate, TSender, TEventArgs>(Action<TDelegate> addHandler, Action<TDelegate> removeHandler, IScheduler scheduler);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<object>> FromEventPattern(object target, string eventName);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<object>> FromEventPattern(object target, string eventName, IScheduler scheduler);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(object target, string eventName);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(object target, string eventName, IScheduler scheduler);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(object target, string eventName);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(object target, string eventName, IScheduler scheduler);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<object>> FromEventPattern(Type type, string eventName);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<object>> FromEventPattern(Type type, string eventName, IScheduler scheduler);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(Type type, string eventName);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(Type type, string eventName, IScheduler scheduler);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(Type type, string eventName);
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(Type type, string eventName, IScheduler scheduler);
 
         IObservable<TEventArgs> FromEvent<TDelegate, TEventArgs>(Func<Action<TEventArgs>, TDelegate> conversion, Action<TDelegate> addHandler, Action<TDelegate> removeHandler);

+ 37 - 0
Rx.NET/Source/src/System.Reactive/Linq/Observable.Events.cs

@@ -2,6 +2,7 @@
 // The .NET Foundation licenses this file to you under the MIT License.
 // See the LICENSE file in the project root for more information. 
 
+using System.Diagnostics.CodeAnalysis;
 using System.Reactive.Concurrency;
 using System.Threading;
 
@@ -538,6 +539,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<object>> FromEventPattern(object target, string eventName)
         {
             if (target == null)
@@ -581,6 +585,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<object>> FromEventPattern(object target, string eventName, IScheduler scheduler)
         {
             if (target == null)
@@ -633,6 +640,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(object target, string eventName)
         {
             if (target == null)
@@ -677,6 +687,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(object target, string eventName, IScheduler scheduler)
         {
             if (target == null)
@@ -730,6 +743,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(object target, string eventName)
         {
             if (target == null)
@@ -775,6 +791,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(object target, string eventName, IScheduler scheduler)
         {
             if (target == null)
@@ -830,6 +849,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<object>> FromEventPattern(Type type, string eventName)
         {
             if (type == null)
@@ -873,6 +895,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<object>> FromEventPattern(Type type, string eventName, IScheduler scheduler)
         {
             if (type == null)
@@ -925,6 +950,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(Type type, string eventName)
         {
             if (type == null)
@@ -969,6 +997,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(Type type, string eventName, IScheduler scheduler)
         {
             if (type == null)
@@ -1022,6 +1053,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(Type type, string eventName)
         {
             if (type == null)
@@ -1067,6 +1101,9 @@ namespace System.Reactive.Linq
         /// </para>
         /// </remarks>
         /// <seealso cref="ToEventPattern"/>
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public static IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(Type type, string eventName, IScheduler scheduler)
         {
             if (type == null)

+ 5 - 0
Rx.NET/Source/src/System.Reactive/Linq/Observable.Queryable.cs

@@ -4,8 +4,13 @@
 
 #pragma warning disable 1591
 
+using System.Diagnostics.CodeAnalysis;
+
 namespace System.Reactive.Linq
 {
+#if HAS_TRIMMABILITY_ATTRIBUTES
+    [RequiresUnreferencedCode(Constants_Core.AsQueryableTrimIncompatibilityMessage)]
+#endif
     public static partial class Qbservable
     {
 #pragma warning disable IDE1006 // Naming Styles: 3rd party code is known to reflect for this specific field name

+ 8 - 0
Rx.NET/Source/src/System.Reactive/Linq/Qbservable.Joins.cs

@@ -45,7 +45,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => And<TLeft, TRight>(default, default)),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()!).MakeGenericMethod(typeof(TLeft), typeof(TRight)),
+#pragma warning restore IL2060
 #endif
                     left.Expression,
                     GetSourceExpression(right)
@@ -80,7 +82,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Then<TSource, TResult>(default, default)),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()!).MakeGenericMethod(typeof(TSource), typeof(TResult)),
+#pragma warning restore IL2060
 #endif
                     source.Expression,
                     selector
@@ -114,7 +118,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => When<TResult>(default, default)),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()!).MakeGenericMethod(typeof(TResult)),
+#pragma warning restore IL2060
 #endif
                     Expression.Constant(provider, typeof(IQbservableProvider)),
                     Expression.NewArrayInit(
@@ -151,7 +157,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => When(default, default(IEnumerable<QueryablePlan<TResult>>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()!).MakeGenericMethod(typeof(TResult)),
+#pragma warning restore IL2060
 #endif
                     Expression.Constant(provider, typeof(IQbservableProvider)),
                     Expression.Constant(plans, typeof(IEnumerable<QueryablePlan<TResult>>))

+ 4 - 0
Rx.NET/Source/src/System.Reactive/Linq/Qbservable.cs

@@ -56,7 +56,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => ToQbservable<TSource>(default)),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()!).MakeGenericMethod(typeof(TSource)),
+#pragma warning restore IL2060
 #endif
                     source.Expression
                 )
@@ -90,7 +92,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => ToQbservable<TSource>(default)),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()!).MakeGenericMethod(typeof(TSource)),
+#pragma warning restore IL2060
 #endif
                     source.Expression,
                     Expression.Constant(scheduler)

+ 60 - 0
Rx.NET/Source/src/System.Reactive/Linq/QbservableEx.NAry.cs

@@ -35,12 +35,14 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond)),
 #endif
                     first.Expression,
                     GetSourceExpression(second)
                 )
             );
+#pragma warning restore IL2060 // Call to 'System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed. It's not possible to guarantee the availability of requirements of the generic method.
         }
 
         /// <summary>
@@ -69,7 +71,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -108,7 +112,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -152,7 +158,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -201,7 +209,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -255,7 +265,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -314,7 +326,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -378,7 +392,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -447,7 +463,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -521,7 +539,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -600,7 +620,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -684,7 +706,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -773,7 +797,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth, TFourteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth), typeof(TFourteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -867,7 +893,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth, TFourteenth, TFifteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth), typeof(TFourteenth), typeof(TFifteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -966,7 +994,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.CombineLatest<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth, TFourteenth, TFifteenth, TSixteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth), typeof(TFourteenth), typeof(TFifteenth), typeof(TSixteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1010,7 +1040,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second)
@@ -1044,7 +1076,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1083,7 +1117,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1127,7 +1163,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1176,7 +1214,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1230,7 +1270,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1289,7 +1331,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1353,7 +1397,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1422,7 +1468,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1496,7 +1544,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1575,7 +1625,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1659,7 +1711,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1748,7 +1802,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth, TFourteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth), typeof(TFourteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1842,7 +1898,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth, TFourteenth, TFifteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth), typeof(TFourteenth), typeof(TFifteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),
@@ -1941,7 +1999,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => Qbservable.Zip<TFirst, TSecond, TThird, TFourth, TFifth, TSixth, TSeventh, TEighth, TNinth, TTenth, TEleventh, TTwelfth, TThirteenth, TFourteenth, TFifteenth, TSixteenth>(default(IQbservable<TSource1>), default(IObservable<TSource2>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodInfo.GetCurrentMethod()!).MakeGenericMethod(typeof(TFirst), typeof(TSecond), typeof(TThird), typeof(TFourth), typeof(TFifth), typeof(TSixth), typeof(TSeventh), typeof(TEighth), typeof(TNinth), typeof(TTenth), typeof(TEleventh), typeof(TTwelfth), typeof(TThirteenth), typeof(TFourteenth), typeof(TFifteenth), typeof(TSixteenth)),
+#pragma warning restore IL2060
 #endif
                     first.Expression,
                     GetSourceExpression(second),

+ 59 - 0
Rx.NET/Source/src/System.Reactive/Linq/QueryLanguage.Events.cs

@@ -7,6 +7,8 @@ using System.Threading;
 
 namespace System.Reactive.Linq
 {
+    using System.Diagnostics.CodeAnalysis;
+
     using ObservableImpl;
 
     //
@@ -133,11 +135,17 @@ namespace System.Reactive.Linq
 
         #region Instance events
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<object>> FromEventPattern(object target, string eventName)
         {
             return FromEventPattern_(target, eventName, GetSchedulerForCurrentContext());
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<object>> FromEventPattern(object target, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_(target, eventName, scheduler);
@@ -145,6 +153,9 @@ namespace System.Reactive.Linq
 
         #region Implementation
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         private static IObservable<EventPattern<object>> FromEventPattern_(object target, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<object, object, EventPattern<object>>(target.GetType(), target, eventName, (sender, args) => new EventPattern<object>(sender, args), scheduler);
@@ -152,11 +163,17 @@ namespace System.Reactive.Linq
 
         #endregion
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(object target, string eventName)
         {
             return FromEventPattern_<TEventArgs>(target, eventName, GetSchedulerForCurrentContext());
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(object target, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<TEventArgs>(target, eventName, scheduler);
@@ -164,6 +181,9 @@ namespace System.Reactive.Linq
 
         #region Implementation
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         private static IObservable<EventPattern<TEventArgs>> FromEventPattern_<TEventArgs>(object target, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<object, TEventArgs, EventPattern<TEventArgs>>(target.GetType(), target, eventName, (sender, args) => new EventPattern<TEventArgs>(sender, args), scheduler);
@@ -171,11 +191,17 @@ namespace System.Reactive.Linq
 
         #endregion
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(object target, string eventName)
         {
             return FromEventPattern_<TSender, TEventArgs>(target, eventName, GetSchedulerForCurrentContext());
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(object target, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<TSender, TEventArgs>(target, eventName, scheduler);
@@ -183,6 +209,9 @@ namespace System.Reactive.Linq
 
         #region Implementation
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         private static IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern_<TSender, TEventArgs>(object target, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<TSender, TEventArgs, EventPattern<TSender, TEventArgs>>(target.GetType(), target, eventName, (sender, args) => new EventPattern<TSender, TEventArgs>(sender, args), scheduler);
@@ -194,11 +223,17 @@ namespace System.Reactive.Linq
 
         #region Static events
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<object>> FromEventPattern(Type type, string eventName)
         {
             return FromEventPattern_(type, eventName, GetSchedulerForCurrentContext());
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<object>> FromEventPattern(Type type, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_(type, eventName, scheduler);
@@ -206,6 +241,9 @@ namespace System.Reactive.Linq
 
         #region Implementation
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         private static IObservable<EventPattern<object>> FromEventPattern_(Type type, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<object, object, EventPattern<object>>(type, null, eventName, (sender, args) => new EventPattern<object>(sender, args), scheduler);
@@ -213,11 +251,17 @@ namespace System.Reactive.Linq
 
         #endregion
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(Type type, string eventName)
         {
             return FromEventPattern_<TEventArgs>(type, eventName, GetSchedulerForCurrentContext());
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TEventArgs>> FromEventPattern<TEventArgs>(Type type, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<TEventArgs>(type, eventName, scheduler);
@@ -225,6 +269,9 @@ namespace System.Reactive.Linq
 
         #region Implementation
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         private static IObservable<EventPattern<TEventArgs>> FromEventPattern_<TEventArgs>(Type type, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<object, TEventArgs, EventPattern<TEventArgs>>(type, null, eventName, (sender, args) => new EventPattern<TEventArgs>(sender, args), scheduler);
@@ -232,11 +279,17 @@ namespace System.Reactive.Linq
 
         #endregion
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(Type type, string eventName)
         {
             return FromEventPattern_<TSender, TEventArgs>(type, eventName, GetSchedulerForCurrentContext());
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         public virtual IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern<TSender, TEventArgs>(Type type, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<TSender, TEventArgs>(type, eventName, scheduler);
@@ -244,6 +297,9 @@ namespace System.Reactive.Linq
 
         #region Implementation
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         private static IObservable<EventPattern<TSender, TEventArgs>> FromEventPattern_<TSender, TEventArgs>(Type type, string eventName, IScheduler scheduler)
         {
             return FromEventPattern_<TSender, TEventArgs, EventPattern<TSender, TEventArgs>>(type, null, eventName, static (sender, args) => new EventPattern<TSender, TEventArgs>(sender, args), scheduler);
@@ -255,6 +311,9 @@ namespace System.Reactive.Linq
 
         #region Helper methods
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.EventReflectionTrimIncompatibilityMessage)]
+#endif
         private static IObservable<TResult> FromEventPattern_<TSender, TEventArgs, TResult>(Type targetType, object? target, string eventName, Func<TSender, TEventArgs, TResult> getResult, IScheduler scheduler)
         {
             ReflectionUtils.GetEventMethods<TSender, TEventArgs>(targetType, target, eventName, out var addMethod, out var removeMethod, out var delegateType, out var isWinRT);

+ 13 - 0
Rx.NET/Source/src/System.Reactive/ObservableQuery.cs

@@ -3,6 +3,7 @@
 // See the LICENSE file in the project root for more information. 
 
 using System.Collections.Generic;
+using System.Diagnostics.CodeAnalysis;
 using System.Globalization;
 using System.Linq;
 using System.Linq.Expressions;
@@ -12,6 +13,9 @@ using System.Reflection;
 
 namespace System.Reactive
 {
+#if HAS_TRIMMABILITY_ATTRIBUTES
+    [RequiresUnreferencedCode(Constants_Core.AsQueryableTrimIncompatibilityMessage)]
+#endif
     internal class ObservableQueryProvider : IQbservableProvider, IQueryProvider
     {
         public IQbservable<TResult> CreateQuery<TResult>(Expression expression)
@@ -91,6 +95,9 @@ namespace System.Reactive
         }
     }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+    [RequiresUnreferencedCode(Constants_Core.AsQueryableTrimIncompatibilityMessage)]
+#endif
     internal class ObservableQuery
     {
         protected object? _source;
@@ -112,6 +119,9 @@ namespace System.Reactive
         public Expression Expression => _expression;
     }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+    [RequiresUnreferencedCode(Constants_Core.AsQueryableTrimIncompatibilityMessage)]
+#endif
     internal class ObservableQuery<TSource> : ObservableQuery, IQbservable<TSource>
     {
         internal ObservableQuery(IObservable<TSource> source)
@@ -159,6 +169,9 @@ namespace System.Reactive
             return _expression.ToString();
         }
 
+#if HAS_TRIMMABILITY_ATTRIBUTES
+        [RequiresUnreferencedCode(Constants_Core.AsQueryableTrimIncompatibilityMessage)]
+#endif
         private class ObservableRewriter : ExpressionVisitor
         {
             protected override Expression VisitConstant(ConstantExpression/*!*/ node)

+ 4 - 0
Rx.NET/Source/src/System.Reactive/Platforms/Desktop/Linq/Observable.Remoting.cs

@@ -74,7 +74,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => RemotingObservable.Remotable<TSource>(default(IQbservable<TSource>))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()).MakeGenericMethod(typeof(TSource)),
+#pragma warning restore IL2060
 #endif
                     source.Expression
                 )
@@ -103,7 +105,9 @@ namespace System.Reactive.Linq
 #if CRIPPLED_REFLECTION
                     InfoOf(() => RemotingObservable.Remotable<TSource>(default(IQbservable<TSource>), default(ILease))),
 #else
+#pragma warning disable IL2060 // ('System.Reflection.MethodInfo.MakeGenericMethod' can not be statically analyzed.) This gets the MethodInfo for the method running right now, so it can't have been trimmed
                     ((MethodInfo)MethodBase.GetCurrentMethod()).MakeGenericMethod(typeof(TSource)),
+#pragma warning restore IL2060
 #endif
                     source.Expression,
                     Expression.Constant(lease, typeof(ILease))

+ 4 - 0
Rx.NET/Source/src/System.Reactive/System.Reactive.csproj

@@ -10,6 +10,10 @@
     <Nullable>enable</Nullable>
   </PropertyGroup>
 
+  <PropertyGroup Condition="$(TargetFramework.StartsWith('net6.0')) or $(TargetFramework.StartsWith('net7.0'))">
+    <IsTrimmable>true</IsTrimmable>
+  </PropertyGroup>
+
   <PropertyGroup Condition="$(TargetFramework.StartsWith('net6.0-windows')) or $(TargetFramework.StartsWith('net7.0-windows'))">
     <UseWPF>true</UseWPF>
     <UseWindowsForms>true</UseWindowsForms>

+ 1 - 0
Rx.NET/Source/tests/Tests.System.Reactive.Uwp.DeviceRunner/Tests.System.Reactive.Uwp.DeviceRunner.csproj

@@ -21,6 +21,7 @@
     <PackageCertificateThumbprint>8570A5641EDE61A2AB21E12809E9E0376A041E8C</PackageCertificateThumbprint>
     <SignAssembly>false</SignAssembly>
     <AppxPackageSigningEnabled>True</AppxPackageSigningEnabled>
+    <AppxBundlePlatforms>x86|x64|arm</AppxBundlePlatforms>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Debug|x86'">
     <DebugSymbols>true</DebugSymbols>