How to speed up MonoTouch compilation time?
Asked Answered
Z

3

46

It is well known that

If compiling takes even 15 seconds, programmers will get bored while the compiler runs and switch over to reading The Onion, which will suck them in and kill hours of productivity.

Our MonoTouch app takes 40 seconds to compile on Macbook Air in Debug/Simulator configuration.

We have about 10 assemblies in the solution.
We're also linking against some native libraries with gcc_flags.

I'm sure there are ways to optimize compilation time that I'm not aware of, which might have to do with references, linker, whatever.

I'm asking this question in hope that someone with better knowledge than me will compile (no pun intended) a list of tips and things to check to reduce MonoTouch compilation time for debug builds.

Please don't suggest hardware optimizations or optimizations not directly related to MonoTouch.

Zorine answered 19/12, 2012 at 22:47 Comment(2)
SSD, more RAM, more cores, set up ram disk and compile from there think ccache used for android building for example... what OS are you running, it is admittedly too broad a question...Septempartite
@t0mm13b: Thanks for coming by. The question includes “MonoTouch” in title and I tagged it so as well. MonoTouch is OS X-only product for building iOS apps with C#. Hence I was asking about MonoTouch-specific optimizations, not about hardware / general things.Zorine
R
47

Build Time Improvements in Xamarin.iOS 6.4

Xamarin.iOS 6.4 has significant build time improvements, and there is now an option to only send updated bits of code to the device. See for yourself:

Built time improvements
(source: xamarin.com)

Read more and learn how to enable incremental build in Rolf's post.

Evolve 2013 Video

An updated and expanded version of this content can be seen in the video of the Advanced iOS Build mechanics talk I gave at Evolve 2013.

Original Answer

There are several factors affecting build speed. However most of them have more impact on device builds, including the use of the managed linker that you mentioned.

Managed Linker

For devices then Link all is the fastest, followed by Link SDK and (at the very end) Don't link. The reason is that the linker can eliminate code faster than the AOT compiler can build it (net gain). Also the smaller .app will upload faster to your devices.

For simulator Don't link is always faster because there's no AOT (the JIT is used). You should not use other linking options unless you want to test them (it's still faster than doing a device build).

Device tricks

  • Building a single architecture (e.g. ARMv7) is faster than a FAT binary (e.g. ARMv7 + ARMV7s). Smaller applications also means less time to upload to device;

  • The default AOT compiler (mono) is a lot faster than using LLVM compilers. However the later will generate better code and also supports ARMv7s, Thumb2;

  • If you have large assets bundled in your .app then it will take time to deploy/upload them (every time since they must be signed) with your app. I wrote a blog post on how you can workaround this - it can save a lot of time if you have large assets;

  • Object file caching was implemented in MonoTouch 5.4. Some builds will be a lot faster, but others won't be (when the cache must be purged) faster (but never slower ;-). More information why this often happens here).

  • Debug builds takes longer because of symbols, running dsymutil and, since it ends up being larger, extra time to upload to devices.

  • Release builds will, by default (you can turn it off), do a IL strip of the assemblies. That takes only a bit of time - likely gained back when deploying (smaller .app) to the device.

Simulator tricks

  • Like said earlier try to avoid linking since it will take more time and will require copying assemblies (instead of symlinking them);

  • Using native libraries is slower because we cannot reuse the shared simlauncher main executable in such cases and need to ask gcc to compile one for the application (and that's slow).

Finally whenever in doubt time it! and by that I mean you can add --time --time to your project extra mtouch arguments to see a timestamp after each operation :-)

Rabid answered 20/12, 2012 at 2:14 Comment(8)
That's the kind of answer I was hoping for :-). Thank you Seb!Zorine
I'm glad if it can shave a few seconds from your builds!Rabid
just wanted to say, fantastic answer.Mulderig
@Rabid If you don't mind, I edited your answer to include a link to Rolf's post on the recent improvements.Zorine
@DanAbramov nice addition, thanks! It reminded me that I wanted to update it with a link to my Evolve talk.Rabid
It's 2016 now and still it takes me 4-5 minutes to get the app to the device. Just wondering how many hours it would've taken in 2012 then. It's not a small one, granted, but the same application for Android compiles in 30 seconds on the same machine.Ringe
I have an app that has 21 MB in the Android Version (according to Google Play). The time it takes to build is around 30s. In Xamarin IOS, the size is around the same, but it clocks at around 5'33, which is outrageous. Every time a build happens, and not even a complete overhaul of it.Unkenned
I'm surprised to know link all is actually faster (due to AOT). It saved me 3 minutes every time I rebuild (from 5 minutes to 1.5 minutes)Footman
Z
4

This is not really meant as an answer, rather a temporary placeholder until there is a better one.
I found this quote by Seb:

Look at your project's build options and make sure the "Linker behavior" is at the default "Link SDK assemblies".

If it's showing "Don't link" then you'll experience very long build time (a large part of it in dsymutil).

I don't know if it is still relevant though, because MonoDevelop shows a warning sign when I choose this option, and it doesn't seem to affect performance much.

Zorine answered 19/12, 2012 at 23:18 Comment(0)
A
2

You cannot expect your compiler to be lightninng quick without understanding everything that it is required to do. Larger applications will naturally take longer. Different languages or different compilers of the same language can make a huge difference on how long it takes to compile your code.

We have a project that will take almost 2 minutes to compile. Your best solution is to figure out a way to reduce the number of times you compile your code.

Instead of trying to fix 1 line of code and rebuilding, over and over again. Get a group of people together to discuss the problem. Or create a list of 3 or 4 things you want to work on, complete them all then test.

These are just some suggestions and they will not work in all cases.

Afterclap answered 19/12, 2012 at 23:35 Comment(1)
I do understand that compilation takes time. But I don't know enough about MonoTouch ahead-of-time compiler and linker design to tell what takes the most time. Is generating Mono soft debugger instructions time consuming? No? What about running dsymutil? Linking against native libraries? Which of the three options should I use for the linker? Does increasing the number of trampolines affect build time? These are the things that make me curious, and I didn't want to test all configurations myself if someone knows the answer. And they are specific to MonoTouch, and therefore, are answerable.Zorine

© 2022 - 2024 — McMap. All rights reserved.