【问题标题】:Workaround for Reflection Bug in Dotfuscator?Dotfuscator 中反射错误的解决方法?
【发布时间】:2011-09-06 09:40:18
【问题描述】:

大家好,

我正在调用 Type.GetProperties(),但是在运行 Dotfuscator 之后,它返回了零个项目,而之前它返回了多个零。

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);
    }
}

如果我在 Dotfuscator 中将“数字”属性排除在重命名之外,那么它会起作用,否则不会。但是,我不可能对项目中的所有属性都执行此操作,因为这可能会导致错误。

这种方法有什么解决方法吗?甚至是我可以使用的其他“免费”混淆应用程序?

我已经尝试在他们的网站上提交错误,但我只使用社区版,所以似乎没有那么多支持。

【问题讨论】:

  • 能否请您在 ILSpy 或 Reflector 中打开您的混淆程序集并发布该类的混淆代码?
  • 天哪,这是个好主意...我必须把代码放在哪里?对不起,我是新来的。
  • 从 ILSpy 中的代码来看,它似乎已将属性转换为两个函数调用,一个用于 get 和 set!这无疑解释了为什么它说没有属性。但是接下来的工作是什么呢?
  • @LonelyCoder:只需编辑您的问题并将其放在那里
  • @LonelyCoder:反射和混淆就是不匹配...:/

标签: c# .net reflection obfuscation


【解决方案1】:

Dotfuscator 在重命名期间自动剥离属性(无论如何它们只是元数据 - 真正的工作由自动创建的 get/set 方法对完成)。它还重命名了底层的 get/set 方法。根据您要执行的操作,您需要从重命名中排除属性元数据本身或 get/set 方法(或可能两者)。

如果您需要保持属性元数据完整(例如,简单地列出类型中的属性),您可以指示 Dotfuscator 通过在重命名排除选项卡上的树视图中检查属性或使用自定义正则表达式属性规则。这只会排除属性元数据 - get/set 方法仍将被重命名。

如果您需要保留 get/set 方法(例如,因为您试图通过反射获取或设置属性的值),您可以指示 Dotfuscator 通过扩展树中的属性来将这些方法排除在重命名之外查看和检查下面的 get/set 方法,或者使用自定义正则表达式方法规则。

【讨论】:

  • 您好,您的回答非常有帮助,谢谢。我需要阻止它将属性转换为方法。但仍必须更改属性名称。我会使用什么正则表达式来做到这一点?
  • 方法总是存在的,属性只是有用的语法糖。当您编写 obj.Text = "hello" 时,编译器会将其转换为 obj.setText("hello")。因为属性语法只是为了方便编码器,如果你想以任何方式实际使用反射来访问属性,我猜你几乎肯定会想要操作 get/set 方法而不是属性元数据。拥有属性列表后,您到底想做什么?
  • 那么可以在 IL 代码中看到这个翻译吗?在 Dotfuscator 中,如果我只是检查要排除的属性(例如,在这种情况下为“数字”)而不是底层的 get 设置,那么它就可以工作。所以看来我只需要排除某个命名空间内的所有公共属性。我正在使用反射进行自定义序列化,但请不要去那里。它已经完成并除尘了。
  • 嗯,有道理。在重命名排除窗口中,添加类型规则。如果您要排除的命名空间是 MyNamespace,请将 Name 字段设置为 MyNamespace\..*(即 MyNamespace,一个转义句点,然后是 0 个或多个任意字符)。取消选中排除类型复选框。接下来右键单击您刚刚创建的类型规则并选择添加属性。将 Name 字段设置为 .* 以选择该命名空间中的所有属性。
【解决方案2】:

由于混淆过程不仅限于重命名您的班级成员,因此您无法确定这一点。这就是混淆的问题:对于反射的结果,您基本上不能再对您的类做出任何假设。我能想到的唯一方法是不使用反射,而是使用表达式。

看看这个问题及其答案,就知道我所说的“表达式”是什么意思:How to raise PropertyChanged event without using string name

【讨论】:

  • 谢谢,但是你能用表达式调用 Type.GetProperties 方法吗?
  • 这不是你使用表达式的原因。您用表达式替换对属性的反射。这显然只有在编译时已经知道该属性时才有效...
  • 我的属性在编译时是已知的,但我仍然需要使用 Type.GetProperties 类来枚举它们,这就是我问的原因。如果做不到,那就没有意义了,我需要反思来反思。
  • 也许我们可以找到另一种方法。为什么需要枚举属性?我认为你正在对枚举的结果做一些事情。这是什么?
猜你喜欢
  • 2021-03-13
  • 2018-06-29
  • 1970-01-01
  • 2012-01-04
  • 1970-01-01
  • 2016-02-15
  • 2011-12-18
  • 2012-01-11
  • 2011-01-19
相关资源
最近更新 更多