dotnet学习笔记二 - 运行.net程序的秘密

原创 2003年07月12日 10:45:00

.NET Framework给我们提供了良好的开发平台。有很好的类库,可以跨语言,跨平台等等。但是他的内部实现细节是怎样的呢?.NET编译出来的exe文件并不是机器码,它是怎样和CLR结合起来的呢?下面就让我们揭开这个小秘密。

首先做一个简单的.NET应用,把它编译成EXE文件。然后用Visual Studio 6.0带的工具Depends把它打开。如下图:

<?xml:namespace prefix = v ns = "urn:schemas-microsoft-com:vml" /><?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />CSDN_Dev_Image_2003-7-111817390.jpg

这里可以看到一个很奇怪的现象,我的.net应用程序只直接依赖于一个dll – MSCOREE.DLL。而且这个DLL输出的这么多函数中也只用到了一个_CorExeMain。我的这个APPENDLINE.EXE中还用到了自己做的一个.NET组件,在这里也看不到。

再让我们借助一些PE察看工具来分析一下这个EXE文件。这一步得到的结果是什么呢?在这个PE文件的入口函数上可以看到一条唯一的汇编语句:

JMP  DS:_CorExeMain

经过上面的步骤,我们可以明确的断定所有的.net编译后的EXE文件一旦运行,就执行MSCOREE.DLL输出的一个函数_CorExeMain。而在开发过程中我们使用到的一些外部组件、控件由于是被.net编译器编译成了中间代码,在Depends中是无法看到的,所有使用外部组件的过程全部由CLR处理。

幸运的是微软这次公布了一个CLI实现的代码,我们可以看个究竟。我下载的代码中没有找到_CorExeMain,只找到了一个_CorExeMain2。参数有5个:

PBYTE   pUnmappedPE,                // -> memory mapped code

    DWORD   cUnmappedPE,                // Size of memory mapped code

    LPWSTR  pImageNameIn,               // -> Executable Name

    LPWSTR  pLoadersFileName,           // -> Loaders Name

    LPWSTR  pCmdLine

一目了然,pUnmappedPEcUnmappedPE就是.net编译后的中间代码的内存缓冲和长度。pImageNameIn就是这个EXE的名字,pLoadersFileName是载入者的名字,pCmdLine就是命令参数。有了这几个参数我们就可以猜到.net将中间代码编译后放入到PE文件中,再加入一段代码直接执行MSCOREE.DLL_CorExeMain,参数就是中间代码的内存指针。JIT就把这段中间代码编译成机器代码执行。

_CorExeMain2代码不长,简单总结一些,做了如下的5步工作:

1.         验证签名。

2.         初始化CLR环境

3.         创建了一个代表EXE文件的PEFile对象

4.         使用SystemDomain的静态方法执行这个PEFile

5.         执行后,做一些清除工作,退出。

 

很明显,上面5个步骤里最重要,最关键的就是第4步了,究竟做了什么呢?有兴趣的朋友可以去看微软的CLI代码,我在以后的文章中也会进一步分析。

dotnet学习笔记二 - 运行.net程序的秘密

  • zgqtxwd
  • zgqtxwd
  • 2008年04月24日 15:27
  • 68

2017-03-05 CentOS中配置守护服务(Supervisor)监听dotnet core web程序的运行

我们继续解决上篇博客的问题,我这个人有个毛病,不喜欢遗留什么问题,也不喜欢问题说不明白,具体要怎么解决一定要详尽,因为经常自己遇到问题的时候,去翻别人的博客,就会遇到这样的问题,很苦恼,又说废话了。 ...
  • u010584641
  • u010584641
  • 2017年03月05日 15:25
  • 876

04-dotnetCore博客后台基本功能实现

今天继续上篇博客的内容,在上一篇的时候,已经基本实现了博客列表内容的显示,继续进行添加、编辑、删除等功能。添加和编辑界面共用一个界面,添加界面如图所示: 同样我这里使用的还是layui里面的...
  • u010584641
  • u010584641
  • 2017年03月29日 11:31
  • 726

DotNet平台主要开发技术总结与经验 .

自微软2000年发布.Net战略以来有10年多,世界上有数百万的程序员在.Net Framework上构建了自己的应用产品。从2002年发布.Net1.0开始,先后发布了.Net1.0、1.1、2.0...
  • dongqiang51
  • dongqiang51
  • 2012年07月28日 16:05
  • 1619

ubuntu for win10 里运行net core

花了点时间在ubuntu for win10里运行net core 按官网上ubuntun10.14装的net core指令 ...... ...... sudo apt-get ins...
  • niunan
  • niunan
  • 2016年09月24日 10:29
  • 665

VS2017-无法启动程序dotnet.exe(.NET CORE)

1.可尝试关闭vs,重新启动,以及以admin权限运行 2.检测“我的电脑-属性-高级-环境变量”中 Path变量内是否存在:\Program Files\dotnet C:\Progra...
  • m0_37302219
  • m0_37302219
  • 2017年09月01日 12:05
  • 2973

PHP 5调用DotNet dll

环境:win2003+IIS+php5.2.4+dotnet 2.0+vs2008挪了个窝,最近又跑window下来了。不想asp.net和php两边都实现一个逻辑一样的类库,所以想到了com。。。c...
  • bobo068
  • bobo068
  • 2007年11月09日 16:17
  • 1461

net core 2.0 控制台无法生成exe的解决办法

::通过批处理,打开net core生成的控制台应用程序 start dotnet xxx.dll xxx是你发布出来的DLL的名字...
  • zwc_csd
  • zwc_csd
  • 2017年09月02日 09:16
  • 1576

.Net程序脱离.net framework框架的另一个方法

网上很多让.net 程序脱离.net framework 环境运行的方法: 第一种是基于移动飞信的虚拟器,具体实现是 在 VMDotNet 目录里面会找到一个 FetionVM.exe 。这个是...
  • zchin
  • zchin
  • 2010年08月06日 13:02
  • 7614

dotnet in docker

dotnet environment in docker
  • u013091013
  • u013091013
  • 2016年11月17日 13:49
  • 534
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:dotnet学习笔记二 - 运行.net程序的秘密
举报原因:
原因补充:

(最多只允许输入30个字)