Protecting Xamarin-based applications against reverse-engineering, cloning and cracking

Xamarin is one of the most popular frameworks used for cross-platform mobile app development. It allows software developers to share about 90 percent of code across major platforms (Android, iOS, Windows Phone).

DexProtector, the most advanced mobile app protection solution, supports the protection of Xamarin applications (available in the enterprise version) and today we will tell you how to use DexProtector to protect your Xamarin-based applications.

Code Protection, Content Protection, Integrity Control, Environment Checks - all the features can be used for Xamarin apps. As well as that, you can use DexProtector SEE/CryptoModule just like for any other Android/iOS application.

Xamarin Applications contain Dalvik bytecode, Resources and Native libraries. Among the resources there are Mono Runtime native libraries and Xamarin Assemblies. Xamarin Assemblies consist of Xamarin Runtime and Xamarin Program Code.

Applying DexProtector Protection mechanisms to Xamarin Android Applications

1. Code Protection

You can use all the standard protection mechanisms for Dalvik bytecode which in this case contains Android Wrapper Classes (Activity, ContentProvider, Receiver, Service), Xamarin/Mono support classes and third-party library classes:

  • String Encryption
  • Class Encryption
  • Hide Access

For native libraries, you can use:

  • Native code obfuscation (excluding Mono Runtime)
  • Native code encryption
  • Native code anti-debugging (gdb).

DexProtector is capable of interacting with Mono Runtime which allows you to encrypt Xamarin assemblies. You can use the <xamarinAssemblies/> node to enable the encryption of the assemblies and to configure the filters. For example:

        <xamarinAssemblies dir="custom assemblies location">

Please see the full description of the settings in the documentation.

2. Content Protection

All the mechanisms DexProtector provides are applicable for protection of Xamarin-based applications:

  • Encryption of resources and assets
  • Resource name obfuscation (resources.arsc)
  • Obfuscation of AndroidManifest: Applications/ActivityNames/ContentProviders/Receivers class names mangling

3. Integrity Control

You know that DexProtector provides the most reliable integrity control (tamper-proofing) among other obfuscators and protectors. The integrity control works out of the box and enabled by default for Xamarin applications just like for other Android or iOS applications.

4. Environment Checks

We recommend to use Android Callable Wrappers for integration with Environment Checks.

First of all, it is needed to configure Xamarin so that it uses Android-style naming for the Activity class in which you will place Probe and Callback methods.

[Activity(Name = "environmentChecksXamarin.MainActivity", ...]
    public class MainActivity : Activity

Note: The first symbol in the exported name must of low case.

Then we must export all the required methods:

        public static void doProbe(Context ctx)
            System.Console.WriteLine("doProbe: "+ctx);

        public static void positiveRootCheck(Object data)
            System.Console.WriteLine("positiveRootCheck data: " + data);
            envChecks.Set((int)EnvCheckType.Root, true);

As a result, Xamarin will generate the Android Wrapper code that looks like this:

package environmentChecksXamarin;

public class MainActivity extends Activity implements IGCUserPeer {
    public static final String __md_methods = "n_onCreate:(Landroid/os/Bundle;)V:GetOnCreate_Landroid_os_Bundle_Handler\nn_doProbe:(Landroid/content/Context;)V:__export__\nn_positiveRootCheck:...";

    private ArrayList refList;

    private static native void n_doProbe(Context context);

    private static native void n_positiveRootCheck(Object obj);


    static {
        Runtime.register("EnvironmentChecksXamarin.MainActivity, EnvironmentChecksXamarin", MainActivity.class, __md_methods);

    public void onCreate(Bundle bundle) {

    public static void doProbe(Context context) {

Now goes the most interesting trick. We have to invoke the Probe method correctly. At first glance, the following C# code will be enough:

        protected override void OnCreate(Bundle savedInstanceState)

But in this case, a different method will be invoked. Not the doProbe of the generated Java class, but a C# method n_doProbe(context) from Xamarin.

Just a little bit of JNI magic and the correct method is being invoked:

            IntPtr class_ref = JNIEnv.FindClass("environmentChecksXamarin/MainActivity");
            IntPtr method_ref = JNIEnv.GetStaticMethodID(class_ref,
                                                         "doProbe", "(Landroid/content/Context;)V");
            JNIEnv.CallStaticVoidMethod(class_ref, method_ref,new JValue(this));

From the security point of view, it is important that the Java class that contains doProbe and positive/negative callbacks is protected with String Encryption, HideAccess, ClassEncryption.

5. Secure Execution Environment

Secure Execution Environment is the self-defending secure native VM. It is capable of running cryptographic operations inside via the CryptoModule. It also has a HSM-like application pre-installed with WhiteBox Crypto key management system. You can easily integrate your application with SEE via native API. If you are interested in SEE/CryptoModule, please request details via email -

As you see, all the mechanisms work perfectly for Xamarin-based applications, including Environment Checks (root, debug, emulator, hooks, ...) and CryptoModule. If you have any questions, just drop us a line via the contact form or email.