.Net RuntimeExplorer开发日志(六) IL to C# - 重来

  曾有朋友问我为什么不使用现成的框架做流水工,我说那太没劲,抄来抄去的没有成就感,可实际情况是无桥可走,无处可抄,找不着能参考的代码,只能自己摸石头过河。就是这样一点一点的,时至今日已经一年多了,这个“软件”还处在遥遥无期的状态,如果有雇主的话,一定早就把我开除了吧。显然,造成现在局面的主要原因是我过高估计了自己的水平,自不量力的开始开荒。

  表达式与语法糖解析这部分代码,改来改去不知多少次了,228个IL的opcode简单改一遍就得一两天,虽然有时很享受这种开荒的感觉,但这不知道浪费了多少时间。所以,利用国庆这几天假期将整个框架重来了一次,主要目的是提升代码的性能和可重塑性,简单说就是让以后修改代码更容易,把重复的代码与类似的调用都统一调度,整合参数与类成员都放入上下文。

  整体重写主要是增加了rewrite部分,将类型转换和地址与地址值转换变成后期处理,再根据不同的opcode选择性输出。举个例子,如果方法返回值是object,那么就不显示值类型的装箱操作,也就是将return (object)i 显示为 return i 这样,同样的还有unsafe下也需要隐去数值变指针的uint的转换等等。从rewrite这个部分来看,整体表达式的解析与dnspy系列是完全不同的,dnspy似乎是依靠当前与下一句opcode,而我的方法则没有上句下句的相互依赖性,让代码的可读性与复杂程度大大的减少。

  这次改动,将228个opcode按堆栈操作类型重新分成了25块(原来是40+块),大大的缩小了我在一千多行里上下翻找内容的时间,将前缀opcode全部无视,将值类型字段的地址操作与变量和参数的值操作合并处理,增加了对扩展方法的处理,增加了继承后对base方法的调用处理等等。

  在输出方面,对subBlockWriter也进行整体重塑,将与opcode有关联的元素全部扔进了context,同时在结构上也进行了拆分,将所有的writer都与其内容分离,彻底结构化。IWriter为最底层,负责向窗口控制输出内容,ICodeWriter为语言类型,目前有IL、C#和IL块,其对应着三个Writer,还有语句符号拼接的BlockWriter和SubBlockWriter。

  大体上的改动就是这些了,以后想起来再补充。

posted @ 2020-10-13 03:36  ccddnet  阅读(115)  评论(0)    收藏  举报