IronPython 源码剖析系列(1):IronPython 编译器
自 IronPython 正式发布以来,由于对 Python 语言的喜爱所驱使,同时我想藉此去了解一下编程语言的编译器,分析器等程序是什么原理,如何运作的,所以我开始了对 IronPython 源代码的学习过程。但代码也看了有一段时间了,之前是看一些实现细节,结果越看越糊涂。现在我发现需要改变一下策略了,因为我们了解一个系统总是从对它的使用方法去开始了解,如果直接去了解底层的运作原理,则可能会迷失在代码海洋里面。所以我也准备采取自顶而下的分析方法,捡软柿子捏,从简单的,宏观的入手。至于具体的实现细节,可以慢慢再深入研究。
OK,今天被我抓到的看起来像软柿子的是:
IronPython/Hosting/PythonCompiler.cs
首先我们抓住要点,看这个文件中的主要类: PythonCompiler (Python 编译器)
在这个类中,首先有一堆的属性不用去管,表示的无非是编译器将要输出的文件的类型啊(DLL 还是 EXE),输出路径,引用了哪些程序集啊等等东西。
直奔主题,我们看到 Compile() 方法,这是负责编译的主控制方法。
这个方法不难理解,我读了一遍,注释如下:
}
// 最终产生输出的程序集
assemblyGen.Dump();
}
这段代码中,调用到了 PythonCompiler 类自身的私有方法 CompilePythonModule() 来完成编译模块的功能。下面我们来看一下这个方法在做什么:
// 创建一个全局套件??有可能是指 globals() 这个字典对象。有待分析。。。
// 这里面的 Binder 是干什么的也有待研究。
GlobalSuite gs = Compiler.Ast.Binder.Bind(body, context);
string moduleName = GetModuleFromFilename(fileName);
// 这里看到了 TypeGen,该类代表一个类型产生器
// tg 指向了一个模块类型(IronPython 中,每一个模块产生为一个对应的类。)
TypeGen tg = OutputGenerator.GenerateModuleType(moduleName, assemblyGen);
// 编译模块的 __init__ 方法??(猜测)
CodeGen init = CompileModuleInit(context, gs, tg, moduleName);
// 如果需要创建 Main 方法则创建之
if (createMain) {
// 联想前面一个 CodeGen 的例子,观察调用语句可以想到,方法的产生器是
// CodeGen,而类型的产生器是 TypeGen
CodeGen main = OutputGenerator.GenerateModuleEntryPoint(tg, init, moduleName, referencedAssemblies);
// 这里注意到 CodeGen 代码产生器含有一个重要的属性就是代表这个方法
// 的反射信息的 MethodInfo, 可以通过这个来调用产生的方法。
assemblyGen.SetEntryPoint(main.MethodInfo, targetKind);
}
// 因为模块类不是普通的类,需要给他添加一个特殊的标签(Attribute)
assemblyGen.AddPythonModuleAttribute(tg, moduleName);
// 产生类型的动作完毕
tg.FinishType();
}
在上述两个方法中,我们看到,出现了几个重要的类,它们将是我们下面接着分析的重点线索:
Parser: 分析器
Statement: 语句
GlobalSuite: globals() ??
TypeGen: 类型产生器
CodeGen: 代码产生器(用于产生方法的代码)
在另一个私有方法 CompileModuleUnit 中,主要是进行了一些模块的导入工作,代码很容易懂,这里不详细分析。
现在回头看一下,在 IronPython/Hosting/PythonCompiler.cs 这个文件中,还剩下了两个类没有提到:
ResourceFile: 代表一个资源文件的相关属性。
PythonCompilerSink: 按照字面理解就是 PythonCompiler 的编译结果的接受池。至于它到底如何运作,留待后面再分析。
到这里为止,我们大致上看到了 IronPython 编译器的工作流程,从一系列源代码文件,资源文件,以及其他一些配置属性出发,经过 Parser, 各种 Generator 的运作,最终到达 AssemblyGenerator 的 Dump() 方法,输出编译结果程序集。
以上的代码分析难免有错误之处,尚有待继续挖掘和梳理。
出处:http://www.cnblogs.com/RChen/archive/2006/10/09/ipysrcstudy1.html
IronPython 源码剖析系列(1):IronPython 编译器的更多相关文章
- IronPython 源码剖析系列(2):IronPython 引擎的运作流程
http://blog.csdn.net/inelm/article/details/4612987 一.入口点 Python 程序的执行是从 hosting 程序 ipy.exe 开始的,而他的入口 ...
- 【java集合框架源码剖析系列】java源码剖析之TreeSet
本博客将从源码的角度带领大家学习TreeSet相关的知识. 一TreeSet类的定义: public class TreeSet<E> extends AbstractSet<E&g ...
- 【java集合框架源码剖析系列】java源码剖析之HashSet
注:博主java集合框架源码剖析系列的源码全部基于JDK1.8.0版本.本博客将从源码角度带领大家学习关于HashSet的知识. 一HashSet的定义: public class HashSet&l ...
- 【java集合框架源码剖析系列】java源码剖析之TreeMap
注:博主java集合框架源码剖析系列的源码全部基于JDK1.8.0版本.本博客将从源码角度带领大家学习关于TreeMap的知识. 一TreeMap的定义: public class TreeMap&l ...
- 【java集合框架源码剖析系列】java源码剖析之ArrayList
注:博主java集合框架源码剖析系列的源码全部基于JDK1.8.0版本. 本博客将从源码角度带领大家学习关于ArrayList的知识. 一ArrayList类的定义: public class Arr ...
- 【java集合框架源码剖析系列】java源码剖析之LinkedList
注:博主java集合框架源码剖析系列的源码全部基于JDK1.8.0版本. 在实际项目中LinkedList也是使用频率非常高的一种集合,本博客将从源码角度带领大家学习关于LinkedList的知识. ...
- 【java集合框架源码剖析系列】java源码剖析之HashMap
前言:之所以打算写java集合框架源码剖析系列博客是因为自己反思了一下阿里内推一面的失败(估计没过,因为写此博客已距阿里巴巴一面一个星期),当时面试完之后感觉自己回答的挺好的,而且据面试官最后说的这几 ...
- WorldWind源码剖析系列:星球类World
星球类World代表通用的星球类,因为可能需要绘制除地球之外的其它星球,如月球.火星等.该类的类图如下. 需要说明的是,在WorldWind中星球球体的渲染和经纬网格的渲染时分别绘制的.经纬网格的渲染 ...
- WorldWind源码剖析系列:星球球体的加载与渲染
WorldWind源码剖析系列:星球球体的加载与渲染 WorldWind中主函数Main()的分析 在文件WorldWind.cs中主函数Main()阐明了WorldWind的初始化运行机制(如图1所 ...
随机推荐
- SDOI2012 Round1 day2 集合(set)解题报告
//=====================以上为官方题解==============// 数据略水,暴力枚举50. 把边按照升序排一遍,在询问,水过. #include<cstdio> ...
- Nginx结合GeoIP库
1. 编译nginx时带上geoip模块 # wget http://nginx.org/download/nginx-x.x.x.tar.gz # tar zxvf nginx-x.x.x.tar. ...
- "ORA-01012: not logged on"以及"Connected to an idle instance."解决思路
今天测试用的ORACLE服务器出现卡顿情况,于是准备重启一下,在运行shutdown指令关闭数据库的时候意外断开连接,后面想再次进入ORACLE服务器启动时便遇见如下报错: 使用sqlplus /no ...
- 洛谷P3943 星空
洛谷P3943 星空 题目背景 命运偷走如果只留下结果, 时间偷走初衷只留下了苦衷. 你来过,然后你走后,只留下星空. 题目描述 逃不掉的那一天还是来了,小 F 看着夜空发呆. 天上空荡荡的,没有一颗 ...
- windows下安装PyQt4
第一步:确认自己电脑上的Python版本.然后下载对应的.whl文件下载 第二步:https://www.lfd.uci.edu/~gohlke/pythonlibs/#pyqt4上下载对应版本版本的 ...
- C# 串口调试助手源码
本方法,禁用跨进程错误(做法不太好,但是对于单片机出身的人来说,好理解,能用就行). 基本功能: 1.点串口号的下拉菜单自动当前检索设备管理器的COM 2.发送模式可选,hex和string两种 3. ...
- nuget.org 无法加载源 https://api.nuget.org/v3/index.json 的服务索引 不定时抽风
今天添加新项目想添加几个工具包,打开NuGet就这样了 发生错误如下: [nuget.org] 无法加载源 https://api.nuget.org/v3/index.json 的服务索引.响应状 ...
- [原创]java WEB学习笔记03:使用eclipes开发javaWEB项目
本博客为原创:综合 尚硅谷(http://www.atguigu.com)的系统教程(深表感谢)和 网络上的现有资源(博客,文档,图书等),资源的出处我会标明 本博客的目的:①总结自己的学习过程,相当 ...
- 【leetnode刷题笔记】Maximum Depth of binary tree
Given a binary tree, find its maximum depth. The maximum depth is the number of nodes along the long ...
- nova 为何要做互信
1.计算节点为什么要做nova 的互信? nova 做resize 或者冷迁移需要两台计算节点做互信. 原因:resize(冷迁移)实际上是运行scp 文件到另一台主机上,如下的命令 Command: ...