Is your .NET Code Really Safe?
Demeanor is a software product that allows you to protect software applications you have developed in .NET by providing obfuscation. What exactly does that mean? There are many products that can reverse engineer, or decompile, the executable (EXE) or library (DLL) file that is created in .NET. These decompilers take the Intermediary Language (IL) code and convert it back to a .NET programming language that was originally used, such as C#, VB.NET, or managed C++.
Startup
As should be expected, the Demeanor .NET Edition requires the .NET Framework to be installed. The installation of Demeanor went very smoothly on my system. I encountered no problems. Once installed, you can start Demeanor as a standalone application or through Visual Studio .NET. If running Demeanor from Visual Studio .NET, you will also need to install the Demeanor add-in.
Figure: Visual Studio Add-In:
The Interface:
The Interface is very clear and easy to use. Basically, you have just two panes. The left pane lists all the applications or DLLs to obfuscate. If you select one of the items, the right pane will show you the properties for it. You can set these properties or leave them as they are.
You can obfuscate a file by creating a new preset. A preset is an XML file that stores all the information about the obfuscated file. Once a preset is created, you only need to add your application to it and then set the properties according your needs. You can load more than one application or DLL into a preset; however, in the following figure you can see that I have used only one application.
Figure: Demeanor .NET Enterprise
Setting Properties In Demeanor
Several properties can be set with Demeanor. One of the most important properties is Application. You should set this to True; otherwise, Demeanor obfuscates only part of the application. Here is a list of the properties in Demeanor and their meaning:
Property | Default Value | Comment / Meaning |
Exclude | String[]-Array | See help file |
Exclude Regular Expression(s) | String[]-Array | See help file |
Force Parameters | False | Obfuscate all function parameters. |
No Enumerations | False | Disable obfuscation of all enumerations. |
No Events | False | Disable obfuscation of all events. |
No Fields | False | Disable obfuscation of all fields. |
No Methods | False | Disable obfuscation of all methods. |
No Parameters | False | Same as Force Parameters. |
No Properties | False | Disable obfuscation of all methods. |
No Resources | False | Disable obfuscation of all resources. |
Additional Assemblies | String[]-Array | see help file |
Application | False | Set this to True, otherwise only parts of the application are obfuscated. |
Compiler Controlled Accessibility |
False | Changes the accessibility of obfuscated methods |
Config File | – | Here you can enter a previous written report file, which can use the information in the file for the current obfuscation. |
EncryptStrings | False | Encrypt the literal strings. |
Excluded Assemblies |
String[]-Array | Display name of the assembly to exclude from obfuscation. |
File Name | Path of the file name |
File name and full path name of the file to be obfuscated. |
In Situ | False | Obfuscate only the metadata in situ. |
Names | Alpha | Determine the style of the renaming to be done on the target. |
Report Enabled | False | Enable/Disable the report. |
Report name | yourfile.xml | File name and full path of the assembly. |
No Logo | False | Suppress logo display. |
Obfuscate all types |
False | Obfuscate many symbols as possible. |
Obfuscation Enabled |
True | Determines whether or not the project is obfuscated during the build process. |
Out | – | Directory in which to place the assembly. |
Verbose | False | Display obfuscation statistics to the console. |
SN Resign Enabled | False | Re-signs a previously or delay signed assembly. |
SN Resign In-File | – | Specifies the infile containing the key pair. |
A Trial
I created a simple Microsoft Visual C#.NET application to show how Demeanor obfuscates an application. I was surprised at first because Demeanor didn’t obfuscated the application. Using a decompiler, I could still get and see all of the code. I used the following online tool to decompile my application: http://www.remotesoft.com/salamander/.
While you might expect the default settings of Demeanor to work to do the obfuscation, this was not the case. You need to set the property Application to True to obfuscate your entire application. With this one property change, voilà; it works! By doing this, the online decompiler I was using was no longer able to determine how to decompile my application.
To show the result from the decompiler, I have set the Application property to False. My original code looked like this:
using System; using System.Drawing; using System.Collections; using System.ComponentModel; using System.Windows.Forms; using System.Data; namespace DecompileMe { ///<summary> ///Zusammenfassung f|r Form1. ///</summary> publicclass Form1 : System.Windows.Forms.Form { ///<summary> ///Erforderliche Designervariable. ///</summary> privateSystem.ComponentModel.Container components = null; publicForm1() { //// Erforderlich f|r die Windows Form-Designerunterst|tzung
// InitializeComponent(); // // TODO: F|gen Sie den Konstruktorcode nach dem //Aufruf von InitializeComponent hinzu // } /// <summary> ///Die verwendeten Ressourcen bereinigen. /// </summary> protected overridevoid Dispose( booldisposing ) { if( disposing ) { if (components != null) { components.Dispose(); } } base.Dispose( disposing ); }
#region
Vom Windows Form-Designer generierter Code
/// <summary>
///Erforderliche Methode f|r die Designerunterst|tzung.
///Der Inhalt der Methode darf nicht mit dem
///Code-Editor gedndert werden.
/// </summary>
private voidInitializeComponent()
{
//
//Form1
//
this.AutoScaleBaseSize = new System.Drawing.Size(5, 13);
this.ClientSize = new System.Drawing.Size(292, 266);
this.Name = “Form1”;
this.Text = “Form1”;
this.Load += new System.EventHandler(this.Form1_Load);
}#endregion
/// <summary> ///Der Haupteinstiegspunkt f|r die Anwendung.
/// </summary>[STAThread]
static voidMain()
{
Application.Run(new Form1());
} private void Form1_Load(object sender, System.EventArgs e)
{
//Can you decompile me ???
MessageBox.Show(“You decompiled me !!!”);
}
}
}
After I set the property Force to True and Names to Numeric, I received the following result in the decompiler. (I show only the changes.)
public class _1 : Form { privateContainer _1 = null; public_1() { _1(); } protected overridevoid Dispose(booldisposing) { if (disposing && _1 != null) { _1.Dispose(); } base.Dispose(disposing); } privatevoid _1() { AutoScaleBaseSize = new Size(5, 13); base.ClientSize = new Size(292,266); base.Name = "Form1"; Text = "Form1"; base.Load += new EventHandler(this._1); } [STAThreadAttribute()] private static void _2() { Application.Run(new _1()); } privatevoid _1(object , EventArgs ) { MessageBox.Show("You decompiled me !!!"); } }
As you can see, Demeanor has obfuscated the method-names to numeric values and changed the parameters on some of the functions. Even so, the decompiler recognized is still able to decompile the application. You will have to make sure that you have set the correct properties if you want to make sure your code is going to be safe.
One other feature is that Demeanor will remove all unnecessary code from your application. Unfortunately, you don’t have the choice of turning this feature off.
After obfuscation, the size of my sample application was reduced by 10%. Even with this reduction in size and with the obfuscation, the execution time remained the same.
One of the key things that some obfuscators do is to change the flow of the code. This helps to hide the logic in a program. This change is often considered more important than simply changing the variable names to something more cryptic. By changing the flow in the IL code, it is even harder to determine exactly what is being done within the code. Unfortunately, Demeanor does not appear to do this.
Thoughts on Demeanor
This product is not cheap; therefore, you may have to think twice before you buy it. Of course, companies deploying .NET applications should consider buying this as well as people who need to protect their code. If you plan to use Borland’s C#Builder integrated development environment, you’ll find that a version of Demeanor is included.
If you are going to use Demeanor, I suggest you always set the property Application to True; otherwise, the potential is left for your code to still be open. I also recommend that after you obfuscate your application that you try to decompile your own IL code to see what you get. There are a number of freely available tools for doing this. I have used the online decompiler http://www.remotesoft.com/salamander/.
About the Reviewer
Sonu Kapoor is a software developer and network administrator residing in Germany. He is also the site manager for CodeFinger.de. In his free time he is a moderator on CodeGuru.com.
Notes from the editors at Developer.com
We, at Developer.com, wanted to add a few additional comments regarding Demeanor:
Our understanding is that the product is primarily used as a command line tool. Most developers currently using Demeanor obfuscate directly from their makefile/NANT build scripts.
Demeanor includes an Add-In for Visual Studio .NET that adds obfuscation property pages to the Solution Explorer. You can right-click on any project or solution in the Solution Explorer and select Obfuscation Properties. This allows you to control all of the obfuscation settings from within Visual Studio .NET. Changes to the settings are automatically saved within Visual Studio .NET’s configuration files. This allows you to have different settings for your different build configurations (Debug/Release/whatever). When you build a project or solution with obfuscation enabled, Demeanor is ran after the build using the settings you’ve saved.
Software Manufacturer Retail Price Enterprise Annual Support Supported OS |
: : : : : |
Demeanor .NET Enterprise Edition WiseOwl $1,450 per license $435 per additional year Windows |