Skip to content

Commit 5fef575

Browse files
grendellojonathanpeppers
authored andcommitted
Support for exempting native libraries from JNI preload (#10787)
Fixes: #10617 Context: cba39dc cba39dc introduced support for preloading of JNI native libraries at application startup. However, it appears that in some scenarios this behavior isn't desired. This PR introduces a mechanism which allows exempting some or all (with exception of the BCL libraries) libraries from the preload mechanism. In order to not preload any JNI libraries it's now possible to set the `$(AndroidIgnoreAllJniPreload)` MSBuild property to `true`. It is also possible to exempt individual libraries from preload by adding their name to the `AndroidNativeLibraryNoJniPreload` MSBuild item group, for instance:
1 parent e0c0236 commit 5fef575

20 files changed

Lines changed: 987 additions & 81 deletions

File tree

‎Documentation/docs-mobile/building-apps/build-items.md‎

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ The following MSBuild metadata are required:
3333
- `%(JavaArtifact)`: The group and artifact id of the Java library matching the specifed POM
3434
file in the form `{GroupId}:{ArtifactId}`.
3535
- `%(JavaVersion)`: The version of the Java library matching the specified POM file.
36-
36+
3737
See the [Java Dependency Resolution documentation](../features/maven/java-dependency-verification.md)
3838
for more details.
3939

@@ -279,9 +279,9 @@ installing app bundles.
279279

280280
## AndroidMavenLibrary
281281

282-
`` allows a Maven artifact to be specified which will
283-
automatically be downloaded and added to a .NET for Android binding project.
284-
This can be useful to simplify maintenance of .NET for Android bindings for artifacts
282+
`` allows a Maven artifact to be specified which will
283+
automatically be downloaded and added to a .NET for Android binding project.
284+
This can be useful to simplify maintenance of .NET for Android bindings for artifacts
285285
hosted in Maven.
286286

287287
```xml
@@ -336,6 +336,20 @@ used to specify the ABI that the library targets. Thus, if you add
336336
ItemGroup>
337337
```
338338

339+
## AndroidNativeLibraryNoJniPreload
340+
341+
Every native library included in this item group will be exempt from the
342+
JNI library preload mechanism. By default, all such libraries will be loaded
343+
by the runtime early during application startup in order to assure their
344+
proper initialization. However, in some cases it might not be the desired
345+
behavior and this item group allows exclusion of libraries from this process
346+
on individual basis.
347+
348+
Some framework libraries which must be loaded at application startup will not
349+
be affected if included in this item group.
350+
351+
See also [`$(AndroidIgnoreAllJniPreload)`](build-properties.md#androidignorealljnipreload)
352+
339353
## AndroidPackagingOptionsExclude
340354

341355
A set of file glob compatible items which will allow for items to be

‎Documentation/docs-mobile/building-apps/build-properties.md‎

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -689,6 +689,20 @@ The most common values for this property are:
689689
> [`@(AndroidEnvironment)`](build-items.md#androidenvironment)
690690
> will take precedence.
691691
692+
## AndroidIgnoreAllJniPreload
693+
694+
A boolean value which, if set to `true`, exempts all the native JNI libraries
695+
from being preloaded at application startup. By default, all such libraries
696+
will be loaded by the runtime early during application startup in order to
697+
assure their proper initialization. However, in some cases it might not be the
698+
desired behavior and this property allows to effectively disable this behavior.
699+
700+
Some framework libraries which must be loaded at application startup will not
701+
be affected by this property.
702+
703+
See also [`@(AndroidNativeLibraryNoJniPreload)`](build-items.md#androidnativelibrarynojnipreload)
704+
for a more fine-grained way to exempt libraries from the preload mechanism.
705+
692706
## AndroidIncludeWrapSh
693707

694708
A boolean value that indicates whether the Android wrapper script

‎build-tools/xaprepare/xaprepare/Application/KnownProperties.cs‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ static class KnownProperties
5656
public const string PkgXamarin_LibZipSharp = "PkgXamarin_LibZipSharp";
5757
public const string ProductVersion = "ProductVersion";
5858
public const string RuntimeRedistDirName = "_RuntimeRedistDirName";
59+
public const string TestOutputDirectory = "TestOutputDirectory";
5960
public const string XABuildToolsFolder = "XABuildToolsFolder";
6061
public const string XABuildToolsVersion = "XABuildToolsVersion";
6162
public const string XABuildToolsPackagePrefixMacOS = "XABuildToolsPackagePrefixMacOS";

‎build-tools/xaprepare/xaprepare/Application/Properties.Defaults.cs.in‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,7 @@ namespace Xamarin.Android.Prepare
6060
properties.Add (KnownProperties.PkgXamarin_LibZipSharp, StripQuotes (@"@PkgXamarin_LibZipSharp@"));
6161
properties.Add (KnownProperties.ProductVersion, StripQuotes ("@ProductVersion@"));
6262
properties.Add (KnownProperties.RuntimeRedistDirName, StripQuotes ("@_RuntimeRedistDirName@"));
63+
properties.Add (KnownProperties.TestOutputDirectory, StripQuotes (@"@TestOutputDirectory@"));
6364
properties.Add (KnownProperties.XABuildToolsFolder, StripQuotes (@"@XABuildToolsFolder@"));
6465
properties.Add (KnownProperties.XABuildToolsVersion, StripQuotes ("@XABuildToolsVersion@"));
6566
properties.Add (KnownProperties.XABuildToolsPackagePrefixMacOS, StripQuotes ("@XABuildToolsPackagePrefixMacOS@"));

‎build-tools/xaprepare/xaprepare/Steps/Step_GenerateFiles.cs‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -127,6 +127,7 @@ GeneratedFile GetCmakePresetsCommon (Context context, string sourcesDir)
127127
{ "@NDK_ARM64_V8A_NONMONO_API_NET@", BuildAndroidPlatforms.NdkMinimumNonMonoAPI },
128128
{ "@NDK_X86_64_NONMONO_API_NET@", BuildAndroidPlatforms.NdkMinimumNonMonoAPI },
129129
{ "@XA_BUILD_CONFIGURATION@", context.Configuration },
130+
{ "@XA_TEST_OUTPUT_DIR@", Utilities.EscapePathSeparators (props.GetRequiredValue (KnownProperties.TestOutputDirectory)) },
130131
};
131132

132133
return new GeneratedPlaceholdersFile (

‎build-tools/xaprepare/xaprepare/xaprepare.targets‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -93,6 +93,7 @@
9393
<Replacement Include="@PkgXamarin_LibZipSharp@=$(PkgXamarin_LibZipSharp)" />
9494
<Replacement Include="@ProductVersion@=$(ProductVersion)" />
9595
<Replacement Include="@_RuntimeRedistDirName@=$(_RuntimeRedistDirName)" />
96+
<Replacement Include="@TestOutputDirectory@=$(TestOutputDirectory)" />
9697
<Replacement Include="@XABuildToolsFolder@=$(XABuildToolsFolder)" />
9798
<Replacement Include="@XABuildToolsVersion@=$(XABuildToolsVersion)" />
9899
<Replacement Include="@XABuildToolsPackagePrefixMacOS@=$(XABuildToolsPackagePrefixMacOS)" />

‎src/Xamarin.Android.Build.Tasks/Tasks/GenerateNativeApplicationConfigSources.cs‎

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ public class GenerateNativeApplicationConfigSources : AndroidTask
2828
public ITaskItem[] ResolvedAssemblies { get; set; } = [];
2929

3030
public ITaskItem[]? NativeLibraries { get; set; }
31+
public ITaskItem[]? NativeLibrariesNoJniPreload { get; set; }
32+
public ITaskItem[]? NativeLibrariesAlwaysJniPreload { get; set; }
3133

3234
public ITaskItem[]? MonoComponents { get; set; }
3335

@@ -253,6 +255,8 @@ public override bool RunTask ()
253255
NumberOfAssembliesInApk = assemblyCount,
254256
BundledAssemblyNameWidth = assemblyNameWidth,
255257
NativeLibraries = uniqueNativeLibraries,
258+
NativeLibrariesNoJniPreload = NativeLibrariesNoJniPreload,
259+
NativeLibrarysAlwaysJniPreload = NativeLibrariesAlwaysJniPreload,
256260
AndroidRuntimeJNIEnvToken = android_runtime_jnienv_class_token,
257261
JNIEnvInitializeToken = jnienv_initialize_method_token,
258262
JNIEnvRegisterJniNativesToken = jnienv_registerjninatives_method_token,
@@ -279,6 +283,8 @@ public override bool RunTask ()
279283
BundledAssemblyNameWidth = assemblyNameWidth,
280284
MonoComponents = (MonoComponent)monoComponents,
281285
NativeLibraries = uniqueNativeLibraries,
286+
NativeLibrariesNoJniPreload = NativeLibrariesNoJniPreload,
287+
NativeLibrarysAlwaysJniPreload = NativeLibrariesAlwaysJniPreload,
282288
HaveAssemblyStore = UseAssemblyStore,
283289
AndroidRuntimeJNIEnvToken = android_runtime_jnienv_class_token,
284290
JNIEnvInitializeToken = jnienv_initialize_method_token,

0 commit comments

Comments
 (0)