技术开发 频道

颠覆C#王权的“魔比斯环”



    三、偶遇通往MSIL世界的“魔比斯环”,C#王权土崩瓦解


     可能每个人都向往着穿越时空。然而有一群幸运的科学家却做到了。这些科学家在一个深谷中偶然发现了一个可以通往另一个世界的大门,这就是“魔比斯环”。通过“魔比斯环”,不仅能穿越时空,同时也将拥有无穷无尽的力量,尽管这么做会有带来一定的危险。

    上面所描述的只是科幻电影中的场景。然而在现实世界也确实存在着很多的“魔比斯环”。如我们使用的C#就是这样。虽然C#是强大的,但我们必须受到C#语法和约定的限制。如一个重要限制是任何子类在创建其对象实例时,在子类的构造方法中必须调用父类的一个构造方法,如果不调用,C#编译器会自动在子类的构造方法加入调用父类构造方法的语句(无参数的默认构造方法)。我们可以先看看下面两个类:
class ParentClass { public ParentClass() { System.Console.WriteLine("ParentClass"); } } class ChildClass : ParentClass { public ChildClass() { System.Console.WriteLine("ChildClass"); } }
    如果在控制台程序中创建ChildClass对象,将输出如下的结果:
ParentClass ChildClass

    让我们用微软提供的反编译工具ildasm.exe(位置:C:\Program Files\Microsoft Visual Studio 8\SDK\v2.0\Bin\ildasm.exe)来反编译exe,看看为什么会这样。用ildasm.exe打开exe后的界面如图1所示:


图1

    双击图1所选中的部分,将会显示如下的中间语言代码:

.method public hidebysig specialname rtspecialname instance void .ctor() cil managed { .maxstack 8 IL_0000: ldarg.0 IL_0001: call instance void ConsoleApplication1.ParentClass::.ctor() IL_0006: nop IL_0007: nop IL_0008: ldstr "ChildClass" IL_000d: call void [mscorlib]System.Console::WriteLine(string) IL_0012: nop IL_0013: nop IL_0014: ret }

    读者可以不必管这些代码是什么意思,只要注意上面黑体字部分。C#编译器已经自动加入了调用ParentClass的构造方法的代码(.ctor()表示构造方法),这一行是去不掉的。找到问题所在,就意味着离成功又近了一步。从中间代码可以看出,如果不让C#编译器加上这行不就行了吗?但我又不能再设计一个C#编译器,因此,只能利用C#原来的编译器。
    根据上面所述,现在我只要解决一个问题即可,就是要利用C#编译器来改变C#的规则。这就要求不能使用C#的代码,而构造方法的代码必须直接使用中间语言来完成(并不是象编译器一样直接生成dll或exe)。

0
相关文章