dotnet / android

.NET for Android provides open-source bindings of the Android SDK for use with .NET managed languages such as C#
MIT License
1.92k stars 526 forks source link

Nothing preserves an assembly reference, if no C# types are used directly #9008

Open jonathanpeppers opened 3 months ago

jonathanpeppers commented 3 months ago

Android framework version

net8.0-android, net9.0-android

Affected platform version

.NET 9

Description

Context:

In the above PR, I had to add a class named Foo and use it for the CustomWidgetTests to succeed.

The situation is:

Possible Solution

I suppose we could do something that would support passing all Android class libraries to the trimmer. Even ones that the C# compiler deems is unused?

We'd then rely on the trimmer to do its job to remove unused code.

Steps to Reproduce

  1. Remove Foo.cs from the changes in #8954
  2. Run the APK tests in Release mode

Did you find any workaround?

Reference some C# class, such as Foo or even the previous code would work:

// usage of typeof(CustomTextView) includes the assembly reference
[DynamicDependency (DynamicallyAccessedMemberTypes.All, typeof (CustomTextView))]

Relevant log output

Mentioned in 9a782d7f404d83240fb7dce9548fccbb0d679e17.

Xamarin.Android.RuntimeTests.CustomWidgetTests failed with:

    (Binary XML file line #1 in Mono.Android.NET_Tests:layout/uppercase_custom: Binary XML file line #1 in Mono.Android.NET_Tests:layout/uppercase_custom: Error inflating class Mono.Android_Test.Library.CustomTextView)
       at Java.Interop.JniEnvironment.InstanceMethods.CallObjectMethod(JniObjectReference , JniMethodInfo , JniArgumentValue* )
       at Java.Interop.JniPeerMembers.JniInstanceMethods.InvokeVirtualObjectMethod(String , IJavaPeerable , JniArgumentValue* )
       at Android.Views.LayoutInflater.Inflate(Int32 , ViewGroup )
       at Xamarin.Android.RuntimeTests.CustomWidgetTests.<>c.<UpperCaseCustomWidget_ShouldNotThrowInflateException>b__0_0()
       at NUnit.Framework.Constraints.VoidInvocationDescriptor.Invoke()
       at NUnit.Framework.Constraints.ExceptionInterceptor.Intercept(Object )
    --- End of managed Java.Lang.RuntimeException stack trace ---
    android.view.InflateException: Binary XML file line #1 in Mono.Android.NET_Tests:layout/uppercase_custom: Binary XML file line #1 in Mono.Android.NET_Tests:layout/uppercase_custom: Error inflating class Mono.Android_Test.Library.CustomTextView
    Caused by: android.view.InflateException: Binary XML file line #1 in Mono.Android.NET_Tests:layout/uppercase_custom: Error inflating class Mono.Android_Test.Library.CustomTextView
    Caused by: java.lang.ClassNotFoundException: Mono.Android_Test.Library.CustomTextView
       at java.lang.Class.classForName(Native Method)
       at java.lang.Class.forName(Class.java:454)
       at android.view.LayoutInflater.createView(LayoutInflater.java:815)
       at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:1006)
       at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:961)
       at android.view.LayoutInflater.rInflate(LayoutInflater.java:1123)
       at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:1084)
       at android.view.LayoutInflater.inflate(LayoutInflater.java:682)
       at android.view.LayoutInflater.inflate(LayoutInflater.java:534)
       at android.view.LayoutInflater.inflate(LayoutInflater.java:481)
       at crc643df67da7b13bb6b1.TestInstrumentation_1.n_onStart(Native Method)
       at crc643df67da7b13bb6b1.TestInstrumentation_1.onStart(TestInstrumentation_1.java:32)
       at android.app.Instrumentation$InstrumentationThread.run(Instrumentation.java:2189)
    Caused by: java.lang.ClassNotFoundException: Didn't find class "Mono.Android_Test.Library.CustomTextView" on path

In this case, Mono.Android_Test.Library.CustomTextView was used from an Android layout, but not used anywhere in managed code.