4

Greetings all,

I am calling Type.GetProperties(), but after running Dotfuscator, it is returning zero items, when it returned more than zero before.

public class Test
{
    public int Number { get; set; }

    public void ShowInfo()
    {
        Type type = this.GetType();

        PropertyInfo[] props = type.GetProperties();
        Console.WriteLine("type [" + type.Name + "] props count: " + props.Length);
    }
}

If I exclude the "Number" property from renaming within Dotfuscator, then it works, but otherwise it doesn't. However, it is not possible for me to do this for all properties in my project, as it would lead to possible bugs.

Are there any workarounds for this method? Or even other "free" obfuscation applications I could use?

I have already tried looking on their website to submit a bug, but I am only using the community edition so there doesn't seem to be as much support for it.

T.Coutlakis
  • 2,436
  • 1
  • 19
  • 19
  • Can you please open your obfuscated assembly in ILSpy or Reflector and post the obfuscated code of this class, too? – Daniel Hilgarth Jun 01 '11 at 15:16
  • Gosh that is a good idea... Where must I put the code? sorry i'm new here. – T.Coutlakis Jun 01 '11 at 15:49
  • From looking at the code in ILSpy, it looks like it has converted the properties to two function calls, one for each of get and set! This surely explains why it says there are no properties. But what is the work around then? – T.Coutlakis Jun 01 '11 at 15:56
  • @LonelyCoder: Just edit your question and put it there – Daniel Hilgarth Jun 01 '11 at 15:58
  • @LonelyCoder: Well reflection and obfuscation just don't match... :/ – Daniel Hilgarth Jun 01 '11 at 15:59
  • I know for using Reflection with hard-coded strings it will be a problem, but the way I'm using it, it should work regardless of the Type's name after obfuscation? But how can one prevent the obfuscation process of converting properties to methods? – T.Coutlakis Jun 01 '11 at 16:04

2 Answers2

5

Dotfuscator automatically strips properties (which are just metadata anyway - the real work is done by the get/set pair of methods that are automatically created) during renaming. It also renames the underlying get/set methods as well. Depending on what you are trying to do, you'll need to exclude either the property metadata itself, or the get/set methods (or possibly both) from renaming.

If you need to keep the property metadata intact (for example, to simply list the properties in a Type), you can instruct Dotfuscator to exclude properties from renaming by checking them in the tree view on the Renaming Exclusions tab or using a custom regex property rule. This will only exclude the property metadata - the get/set methods will still be renamed.

If you need to keep the get/set methods (because, for example, you are trying to get or set a property's value by reflection), you can instruct Dotfuscator to exclude those methods from renaming by expanding the property in the tree view and checking the get/set methods underneath, or by using a custom regex method rule.

bsiegel
  • 237
  • 1
  • 9
  • Hi, your answer is very helpful thanks. I need to stop it from converting properties to methods. The property name must still be changed though. What regex would I use to do this? – T.Coutlakis Jun 01 '11 at 16:55
  • The methods are always there, the property is just helpful syntactic sugar. When you write obj.Text = "hello", the compiler translates that to obj.setText("hello"). Because the property syntax is just there as a convenience to the coder, if you want to actually use reflection to access the property in any way I would guess that you are almost certainly going to want to operate on the get/set methods instead of the property metadata. What exactly do you want to do once you have a list of properties? – bsiegel Jun 01 '11 at 17:02
  • So can one see this translation in IL code? In Dotfuscator, if I simply check the property to exclude (eg "Number" in this case) and not the underlying get set, then it works. So it seems I just need to exclude all public properties, within a certain namespace. I am using reflection for custom serialization, but please lets not go there. It is already done and dusted. – T.Coutlakis Jun 01 '11 at 17:16
  • Ah okay, makes sense. In the renaming exclusions window, add a type rule. If the namespace you want to exclude is MyNamespace, set the Name field to MyNamespace\..* (that's MyNamespace, an escaped period, and then 0 or more of any character). Uncheck the Exclude Type checkbox. Next right-click the type rule you just made and select Add Property. Set the Name field to .* to select all properties in that namespace. – bsiegel Jun 01 '11 at 17:28
2

As the process of obfuscation is not limited to renaming your class members, you can't be sure of that. That's the problem with obfuscation: You basically can't make any assumptions about your class anymore regarding the result of reflection. The only way I can think of is to not use reflection but expressions.

Have a look at this question and its answer to know, what I mean with "expressions": How to raise PropertyChanged event without using string name

Community
  • 1
  • 1
Daniel Hilgarth
  • 171,043
  • 40
  • 335
  • 443
  • Thanks, but can you call a Type.GetProperties method with expressions? – T.Coutlakis Jun 01 '11 at 16:26
  • That's not why you use expressions. You replace reflecting on a property with the expression. This obviously only works, if that property is already known at compile time... – Daniel Hilgarth Jun 01 '11 at 16:28
  • My properties are known at compile time, but I still need to enumerate them with the Type.GetProperties class, that's why I'm asking. If it can't be done, then it's pointless, I need reflection for reflection purposes. – T.Coutlakis Jun 01 '11 at 16:34
  • Maybe we can find another way. Why do you need to enumerate the properties? I think you are doing something with the result of the enumeration. What is it? – Daniel Hilgarth Jun 01 '11 at 16:35