-
Notifications
You must be signed in to change notification settings - Fork 5k
[Android] Support static linking of CoreCLR on Android #114629
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
[Android] Support static linking of CoreCLR on Android #114629
Conversation
Tagging subscribers to this area: @hoyosjs |
src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props
Outdated
Show resolved
Hide resolved
@@ -26,4 +26,4 @@ set (VXSORT_SOURCES | |||
do_vxsort.h | |||
) | |||
|
|||
add_library(gc_vxsort STATIC ${VXSORT_SOURCES}) | |||
add_library(gc_vxsort OBJECT ${VXSORT_SOURCES}) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it would be nice to use the same style, either this one in src/coreclr/gc/unix/CMakeLists.txt
or the other way around.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you mean to conditionally add gc_vxsort objects if android host?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That or change static to object in gc/unix as well.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I added gc_vxsort_objects for the android host. I could also switch it from static to an object library, but I’m not sure if archive is actually being used in other scenarios.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we need both, static and objects, for Android? If not, we can use an if-else block.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
BTW: vxsort is a ton of code for relatively small performance gain. We may want to disable it on mobile. It is implemented on x64 only for now, but arm64 implementation is in the works #110692 .
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Personally, I'd prefer to switch from static to object library here instead of introducing the conditional object for Android. At least for gc_pal
and gc_vxsort
, since they are pretty isolated (used for coreclr and standalone gc) and I think the conditional object build makes it more complicated that just switching - as opposed to something like coreclrminipal
, which would fit better as a separate change per #114629 (review).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree. I haven’t applied these changes to the other libraries in this PR, since I’m not sure whether they’re required as archives on other platforms.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks reasonable to me in the current incarnation. I assume we will eventually want to extend this to all mobile platforms but it's fine to do that separately.
I agree with @am11 here: I'd like to know what errors were being seen with the current system. Also, for the various new "OBJECT" libraries, I'd like the "static library" flavors that are defined in the build system to be based on the object libraries (ie My biggest concern with this work (and work in this general direction) is that the CMake scripts for Mono are extremely confusing today (even for me) and it's really difficult to iterate on them. I really don't want the scripting for CoreCLR to get that confusing as well. |
Below are the linking failures for the object libraries. coreclrminipal_objects
eventprovider_objects
nativeresourcestring_objects
coreclrpal_objects
Yes, I like that approach. I’ve updated the build files to define the static libraries based on the object files.
The object files are no longer conditioned on Android, they now always build the object files first, then package them into the .a archives. What did you have in mind here? |
These are due to missing coreclr minipal linkage (
These are due to missing event provider. Same solution, the archive containing dummy or LTTng etc. provider is missing in the final linkage. If we can make archives link with NDK properly without modifying the output type (objects for Android vs. static lib for every other platform configuration..), that's a win. |
Personally, I'd rather not move everything to object libraries and instead ship each of the static libs that we produce, as well as a listing of them in the correct link order (and then the Android tooling would grab all of them instead of just However, if we decide to use object libraries, I'm fine with the provided approach (linking into static libs and using |
My personal preference is to have single library. This is not going to be consumed just by Android but also by iOS workloads. We have to deal with at least 3 different linkers (lld, ld64, ld-prime) and any additional complexity is going to be PITA long term. |
We can use
to get the combined |
I’ve summarized the main differences to help us make an informed decision. Please share your thoughts so we can iterate fast toward a solution. Option 1: Multiple static libsPros:
Cons:
Option 2: Single static lib via object libsPros:
Cons:
|
Is there a limitation preventing this, or is it already set up this way? Is the complexity you're referring to on the consumer/ SDK side? My take -- multiple static libraries with explicit link order offers better maintainability and modularity. |
I fail to see how is this harder to maintain. I am arguing against leaking the internal details of CoreCLR product composition to downstream consumers (dotnet/android and dotnet/macios). CoreCLR build system itself has to know these details already. I am not arguing for never spliting any separate modules into their .a libraries, similar to MonoVM components. I think it's fine to split diagnostics, custom GC, event tracing or whatever else we see fit in the future. These splits should be meaningful though - ie. the downstream consumer makes a conscious decision about including or not including some component, possibly based on a user-facing option.
The supported linkers are enforced by their respective platforms and their SDK versions. We need to support the three aforementioned linkers due to these constraints. I would very much prefer not to shift any complexity downstream. |
I don't see how it would be harder with |
We must ensure that the runtime includes the same source or object files in both the component libraries and the coreclr_static.a archive. This complexity has to be managed somewhere, and it depends on how we view the runtime: as a modular package that makes no decisions about linking, or as a complete archive bundling all components.
This sounds like reasonable tradeoff. Do we already have clear split? If yes, I suggest proceeding that way. If not, I suggest keeping the single archive file and working on modularization in the future. |
No, we don't have modularization in CoreCLR yet. At some point we will likely end up with base + JIT + interpreter libraries (both static and dynamic) where some workloads will optionally skip JIT, interpreter or both. I'd worry about it when we get there. |
That needs to be ensured anyway regardless of single or multiple archives. The granularity for dynamic libs is: % find '.dotnet/shared' -name '*so'
<prefix>/libmscordbi.so
<prefix>/libSystem.Native.so
<prefix>/libmscordaccore.so
<prefix>/libclrjit.so
<prefix>/libcoreclrtraceptprovider.so
<prefix>/libclrgcexp.so
<prefix>/libSystem.IO.Compression.Native.so
<prefix>/libcoreclr.so
<prefix>/libclrgc.so
<prefix>/libSystem.Security.Cryptography.Native.OpenSsl.so
<prefix>/libSystem.Globalization.Native.so
<prefix>/libhostpolicy.so
<prefix>/libSystem.Net.Security.Native.so static libs can use the same to keep things self explanatory. Notice the two GC flavors, that's pretty much the customization needed for coreclr thus far (nativeaot has more options which is a separate discussion). The rest is internal detail. |
I think it's reaonable expectation to have the same granularity for static and dynamic libs, thus allowing the build scripts to just append |
My vote is to produce one static lib using this approach. |
I think it's almost the same suggestion as aligning it with shared framework. e.g. we can bundle libcoreclr.a and libclrjit.a, while keeping GC flavors separate; unless we don't want to support multiple flavors (ServerGC vs. WorkstationGC distinction), then we can merge that in libcoreclr as well. Then debugging components: libmscordbi.a and libmscordaccore.a could be bundled together. Eventing Singlefilehost uses coreclr_static today:
|
I'd vote for starting with just one static lib I don't think anything we do for single
|
Looking over the conversation and the code, I think I'm okay with one static lib. Here's my preferences for the CMake/infra side of it:
The only alternative that I think would be worthwhile would be to use CMake exports to generate a CMake module that the AppleAppBuilder and AndroidAppBuilder templates would consume (and as such would allow the runtime to control the complexity and the various templates just say "link against this target"). With that option, we'd limit the amount of knowledge that consuming repos would need to have. As this is more work though, I'm fine with the single static-lib approach. |
Thanks @elinor-fung @jkoritzinsky @am11 @filipnavara for chiming in. Seems like we have good alignment. |
That's a pretty good idea for us to do at some point now that you mention it. |
Created a tracking issue: #115362 @jkoritzinsky Are we good to proceed with the current changes? |
Yes, we're good to proceed. |
Description
This PR adds support for static linking of CoreCLR on Android. It includes static libraries in the runtime pack and updates the APK builder to enable static linking of the sample app.
Changes
Validation
Added a functional test in the runtime pipeline to validate static linking.
Out-of-scope
Runtime modularization is tracked in #114737
CMake export module is tracked in #115362