Skip to content

Commit

Permalink
Update docs and tests
Browse files Browse the repository at this point in the history
Removed documentation about `counters.txt`, since the file is no longer
generated.  Added info on how to get `methods.xml` generated.

TODO: `jit-times`
  • Loading branch information
grendello committed Nov 20, 2024
1 parent 0048d70 commit 56d091e
Show file tree
Hide file tree
Showing 6 changed files with 41 additions and 58 deletions.
75 changes: 28 additions & 47 deletions Documentation/guides/profiling.md
Original file line number Diff line number Diff line change
Expand Up @@ -174,72 +174,53 @@ If profiling a Release build, you'll need to edit your

Debug builds already set this value by default.

In order to save method JIT statistics, the application has to be built
with the `$(_AndroidMethodsStats)` MSBuild property set to `true`.

Next, run the `adb` command:

> adb shell setprop debug.mono.log timing,default

After launching the app, you can find a file that was recorded during
startup:
After launching the app, wait for the desired period of time and then send
an Android intent to the application in order to actually save data into
the `methods.xml` file:

> adb shell am broadcast -a mono.android.app.DUMP_TIMING_DATA com.xamarin.android.helloworld

After this is done, you can find a file that was recorded during startup:

> adb shell run-as com.xamarin.android.helloworld ls files/.__override__
counters.txt
methods.txt
methods.xml

Make sure to use your app's package name instead of
`com.xamarin.android.helloworld`.
Make sure to use your app's package name instead of `com.xamarin.android.helloworld`.

You can pull these files to your machine by doing:

> adb shell run-as com.xamarin.android.helloworld cat files/.__override__/counters.txt > counters.txt
> adb shell run-as com.xamarin.android.helloworld cat files/.__override__/methods.txt > methods.txt
> adb shell run-as com.xamarin.android.helloworld cat files/.__override__/methods.xml > methods.xml

If you ever need to reset/clear these directories, you can
uninstall/reinstall the app or merely:

> adb shell run-as com.xamarin.android.helloworld rm -r files/.__override__/

`counters.txt` has some interesting summary information provided by
Mono:

## Runtime.register: type=HelloWorld.MainActivity, HelloWorld
JIT statistics
Discarded method code : 1
Time spent JITting discarded code : 0.82 ms
Try holes memory size : 896
Dynamic code allocs : 3
Dynamic code bytes : 584
Dynamic code frees : 0
Unwind info size : 5985
Calls to trampolines : 1994
JIT trampolines : 952
Unbox trampolines : 2
Static rgctx trampolines : 7
Async JIT info size : 0
Max native code in a domain : 0
Max code space allocated in a domain: 0
Total code space allocated : 0
Hazardous pointers : 0
Compiled methods : 921
Methods from AOT : 0
Methods JITted using mono JIT : 921
Methods JITted using LLVM : 0
Methods using the interpreter : 0

_NOTE: that `counters.txt` is not available in .NET 6 projects._

`methods.txt` has the individual JIT times of each method:

JIT method begin: System.OutOfMemoryException:.ctor (string) elapsed: 0s:20::136721
JIT method done: System.OutOfMemoryException:.ctor (string) elapsed: 0s:20::605627
> adb shell run-as com.xamarin.android.helloworld rm files/.__override__/methods.xml

`methods.xml` has the individual JIT times of each method:

<method name="Java.Lang.Object:GetObject (intptr,Android.Runtime.JniHandleOwnership,System.Type)" invocation_count="1" jit_time="0:0::20915" jit_status="success" />

If methods statistics were gathered in `Release` mode, the `invocation_count` attribute of most entries
will be `0`. This is due to the fact that the Mono runtime allows us to gather call statistics only
when running with the interpreter instead of JIT. In order to properly count calls to each method, the
application needs to be built with the `$(UseInterpreter)` MSBuild property set to `true` (it works both in
`Debug` and `Release` modes).

This is not particularly readable, so you can use our
[jit-times][jit_times] command-line tool to get better/sorted output:

# Windows / .NET
jit-times.exe methods.txt > methods-sorted.txt
jit-times.exe methods.xml > methods-sorted.txt

# Mac / Mono
mono jit-times.exe methods.txt > methods-sorted.txt
mono jit-times.exe methods.xml > methods-sorted.txt

Which outputs:

Expand Down Expand Up @@ -441,7 +422,7 @@ target:
Project Evaluation Performance Summary:
12 ms samples\HelloWorld\HelloLibrary\HelloLibrary.csproj 1 calls
98 ms samples\HelloWorld\HelloWorld.csproj 1 calls
Target Performance Summary:
275 ms _UpdateAndroidResgen 2 calls
354 ms _GenerateJavaStubs 1 calls
Expand All @@ -450,7 +431,7 @@ target:
865 ms _ResolveSdks 2 calls
953 ms ResolveProjectReferences 2 calls
1219 ms _CompileToDalvikWithD8 1 calls
Task Performance Summary:
681 ms Csc 2 calls
809 ms ValidateJavaVersion 2 calls
Expand Down
6 changes: 4 additions & 2 deletions Documentation/workflow/SystemProperties.md
Original file line number Diff line number Diff line change
Expand Up @@ -169,8 +169,10 @@ categories:
* `timing`
Enable logging of native code performance information, including
method execution timing which is written to a file named
`methods.txt`. `timing=bare` should be used in preference to this
category.
`methods.xml` (see [profiling][profiling] for more information).
`timing=bare` should be used in preference to this category.

[profiling]: ../guides/profiling.md

#### Timing events format

Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
<!--
<!--
***********************************************************************************************
Xamarin.Android.Common.targets
Expand Down Expand Up @@ -1540,7 +1540,7 @@ because xbuild doesn't support framework reference assemblies.
<ItemGroup>
<AndroidManifestOverlay
Include="$(MSBuildThisFileDirectory)\ManifestOverlays\Timing.xml"
Condition=" '$(_AndroidFastTiming)' == 'True' "
Condition=" '$(_AndroidFastTiming)' == 'True' Or '$(_AndroidMethodsStats)' == 'True' "
/>
</ItemGroup>
<ManifestMerger
Expand Down
2 changes: 1 addition & 1 deletion src/native/monodroid/monodroid-glue-internal.hh
Original file line number Diff line number Diff line change
Expand Up @@ -231,7 +231,7 @@ namespace xamarin::android::internal
static void prof_method_begin_invoke (MonoProfiler *prof, MonoMethod *method) noexcept;
static void prof_method_end_invoke (MonoProfiler *prof, MonoMethod *method) noexcept;
static void prof_method_enter (MonoProfiler *prof, MonoMethod *method, MonoProfilerCallContext *context) noexcept;
static void prof_method_leave (MonoProfiler *prof, MonoMethod *method, MonoProfilerCallContext *context) noexcept;
static void prof_method_leave (MonoProfiler *prof, MonoMethod *method, MonoProfilerCallContext *context) noexcept;
static MonoProfilerCallInstrumentationFlags prof_method_filter (MonoProfiler *prof, MonoMethod *method) noexcept;

#if !defined (RELEASE)
Expand Down
4 changes: 2 additions & 2 deletions src/native/monodroid/performance-methods.cc
Original file line number Diff line number Diff line change
Expand Up @@ -35,11 +35,10 @@ namespace {
void
MonodroidRuntime::dump_method_events ()
{
if (!method_event_map) {
if (!method_event_map || !method_event_map_write_lock) {
return;
}

log_debug (LOG_ASSEMBLY, "Dumping method events");
lock_guard<mutex> write_mutex { *method_event_map_write_lock.get () };

mono_profiler_set_jit_begin_callback (profiler_handle, nullptr);
Expand Down Expand Up @@ -71,6 +70,7 @@ MonodroidRuntime::dump_method_events ()
return;
}
Util::set_world_accessable (jit_log_path.get ());
log_info (LOG_DEFAULT, "Saving managed method statistics to: %s", jit_log_path.get ());

dprintf (
jit_log,
Expand Down
8 changes: 4 additions & 4 deletions tests/MSBuildDeviceIntegration/Tests/InstallTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -333,7 +333,7 @@ public void LoggingPropsShouldCreateOverrideDirForRelease ()
Assert.True (didLaunch, "Activity should have started.");
var directorylist = GetContentFromAllOverrideDirectories (proj.PackageName, DeviceAbi);
builder.Uninstall (proj);
StringAssert.Contains ("methods.txt", directorylist, $"methods.txt did not exist in the .__override__ directory.\nFound:{directorylist}");
StringAssert.Contains ("methods.xml", directorylist, $"methods.xml did not exist in the .__override__ directory.\nFound:{directorylist}");
}
}

Expand Down Expand Up @@ -546,7 +546,7 @@ public void IncrementalFastDeployment (string packageFormat)
}

long lib1FirstBuildSize = new FileInfo (Path.Combine (rootPath, lib1.ProjectName, lib1.OutputPath, "Library1.dll")).Length;

using (var builder = CreateApkBuilder (Path.Combine (rootPath, app.ProjectName))) {
builder.Verbosity = LoggerVerbosity.Detailed;
builder.ThrowOnBuildFailure = false;
Expand Down Expand Up @@ -653,7 +653,7 @@ public void AppWithAndroidJavaSource ()
public class TestJavaClass2 {
public String test(){
return ""Java is called"";
}
}",
Expand All @@ -671,7 +671,7 @@ public String test(){
public class TestJavaClass {
public String test(){
return ""Java is called"";
}
}",
Expand Down

0 comments on commit 56d091e

Please sign in to comment.