Background
There are currently 2 ILLink warnings left in System.Linq.Expressions that both boil down to the same pattern.
When you create a Binary or Unary Expression, and don't specify a MethodInfo, System.Linq.Expressions will try to find an operator on the Type corresponding to the ExpressionType you specified.
For example, if you call Expression.Equal(left, right), will call the following code
public static BinaryExpression Equal(Expression left, Expression right, bool liftToNull, MethodInfo? method)
{
ExpressionUtils.RequiresCanRead(left, nameof(left));
ExpressionUtils.RequiresCanRead(right, nameof(right));
if (method == null)
{
return GetEqualityComparisonOperator(ExpressionType.Equal, "op_Equality", left, right, liftToNull);
}
GetEqualityComparisonOperator will look for the op_Equality operator on both the left and right types. This cannot be expressed in the existing trimming annotations because we don't have a System.Type parameter to annotate. left and right are System.Linq.Expressions.Expression instances.
This same pattern applies to pretty much all Binary and Unary expressions:
- Equal
- NotEqual
- Add
- Subtract
- Divide
- Modulo
- Multiply
- Power
- LeftShift
- RightShift
- And
- Or
- Not
- Convert
- Increment
- Decrement
- etc
Proposal
We should add a new rule in the mono/linker that when System.Linq.Expressions is used in an app, it should preserve all user defined operators on Types that are being preserved. This will allow the above Expression code to keep working in a trimmed application.
In the System.Linq.Expressions library, we can then suppress the remaining warnings saying "The trimmer won't trim operators on preserved Types when Expressions are involved. It is safe to try to find these operator methods."
cc @vitek-karas @MichalStrehovsky @marek-safar
Background
There are currently 2 ILLink warnings left in System.Linq.Expressions that both boil down to the same pattern.
When you create a
BinaryorUnaryExpression, and don't specify aMethodInfo,System.Linq.Expressionswill try to find an operator on the Type corresponding to the ExpressionType you specified.For example, if you call
Expression.Equal(left, right), will call the following codeGetEqualityComparisonOperatorwill look for theop_Equalityoperator on both theleftandrighttypes. This cannot be expressed in the existing trimming annotations because we don't have aSystem.Typeparameter to annotate.leftandrightareSystem.Linq.Expressions.Expressioninstances.This same pattern applies to pretty much all Binary and Unary expressions:
Proposal
We should add a new rule in the
mono/linkerthat whenSystem.Linq.Expressionsis used in an app, it should preserve all user defined operators on Types that are being preserved. This will allow the above Expression code to keep working in a trimmed application.In the
System.Linq.Expressionslibrary, we can then suppress the remaining warnings saying "The trimmer won't trim operators on preserved Types when Expressions are involved. It is safe to try to find these operator methods."cc @vitek-karas @MichalStrehovsky @marek-safar