Windows 程序启动性能优化(先载入EXE,后载入DLL,只取有限的代码载入内存,将CPU的IP指向程序的入口点)

时间:2021-10-20 14:48:17

一、重定位
链接时重定位:
目标文件一般由多个节组成,编译器在编译每个目标文件时一般都是从0地址开始生成代码。当多个代码节合成一个代码段时,需要根据其在最终代码段中的位置做出调整。同时,链接器需要对已经解析的符号分配运行时地址。这个过程就是重定位。

加载时重定位:
程序中可能调用了DLL,由于EXE是最先被加载的,所以一般都能加载到其想要的内存地址上;而DLL的加载一般在EXE之后,就需要对DLL中的地址进行重定位了。

二、程序的启动过程
WIN32程序启动过程包括:

(1)操作系统把程序加载到内存,并建立相应的运行环境
(2)应用程序自身的初始化过程

备注:应用程序必须符合PE格式,主要包含:data(数据段),.text(代码段)。数据和代码加载到内存中后(内存中,应用程序的代码表现为一系列有序的指令集),CPU从程序入口处按顺序取出每一条指令并执行。

加载器:操作系统加载器的任务是,把磁盘中可执行程序的物理文件读入内存,并转换成程序在内存中的表示。

三、编译链接和启动
编译链接:

(1)预编译展开宏
(2)为每个.cxx文件生成一个.obj文件,目标文件至少包含数据段和代码段;目标文件还包含一个符号表,用于记录自己引用          的符号,以及提供给外部引用的符号。
(3)编译器合成这些目标文件成一个库文件(.lib),同时解析可以找到的符号引用
(4)链接器把目标库文件和所有需要引用的静态、动态库进行链接,生成最终的可执行文件。(首先需要把依赖的静态库合            成到可执行文件中,其次要保证依赖的动态库文件的符号都存在)可执行文件的符号表只需要记录导入符号表。

启动:
不依赖DLL的程序:

(1)操作系统创建进程并分配私有的进程空间;
(2)加载器把可执行文件的数据段和代码段映射到进程虚拟内存中;
(3)预取有限的代码段进入实际内存,把CPU的IP指向程序入口点,即可开始执行

依赖DLL的程序:

(1)同上,创建进程、映射虚拟内存;
(2)加载器读取可执行文件的导入符号表,由此找到依赖的DLL
(3)加载器对依赖的每个DLL调用LoadLibrary,LoadLibrary中处理的事情如下:

a,加载器为该DLL确定一个合适的基地址(地址重定位)

b,读取导入和导出符号表,比较应用程序的导入符号与DLL的导出符号是否匹配

c,通过DLL导入符号表确定该DLL所依赖的其他DLL,同样加载起来

d,调用DLL的初始化函数

(4)初始化应用程序的全局变量
(5)进入应用程序入口点函数开始执行

四、影响启动性能的因素:
(1) 程序冷启动的性能大部分取决于IO操作消耗的时间;
(2) DLL导出过多符号,会引起加载器耗费过多的CPU事件和IO来处理这个符号表;
(3) 磁盘碎片问题:理想状态下,顺序读取一个文件,不需要磁头寻道操作。但操作系统的文件系统,以块为单位管理物理磁盘空间,当磁盘经过不断的增删改操作后,可能不再具有连续的存储空间。导致一个逻辑上连续的文件,在磁盘上由很多不连续的碎片组成,导致执行IO时需要过多的寻道时间。

五、优化启动过程的方法:
(1) 减少动态库数量;
(2) 减小动态库的尺寸:可以通过编译优化选项;清除冗余代码;
(3) 优化可执行文件和库文件的代码布局:把库文件中的函数排的更紧密,从而达到减少IO的目的;
        步骤:获得函数调用的顺序文件(.PRF);把这些PRF传给链接器,链接器会自动按照PRF文件把文件在动态库中的位置重新排序(可以尝试一下)
(4)延迟初始化:可以把一些启动初期不需要的初始化工作延迟到启动后,增强启动体验;延迟的时机:可以在程序空闲时进行处理,在消息循环空闲时处理。
(5) 多线程化启动:具有以下特点,适合多线程化启动
        启动时需要加载大量动态库,引发大量IO操作;同时这些动态库初始化函数需要执行密集型操作,占用CPU时间。这时候可以将IO等待时间和CPU运行时间交错处理,缩短启动时间。

备注:IO的实现,是CPU发出命令后,由主板DMP完成,完成后触发中断,然后CPU继续处理,所以IO占用的CPU时间很少。

https://blog.csdn.net/hellokandy/article/details/70676563

Windows 程序启动性能优化(先载入EXE,后载入DLL,只取有限的代码载入内存,将CPU的IP指向程序的入口点)的更多相关文章

  1. Go 程序的性能优化及 pprof 的使用

    Go 程序的性能优化及 pprof 的使用 程序的性能优化无非就是对程序占用资源的优化.对于服务器而言,最重要的两项资源莫过于 CPU 和内存.性能优化,就是在对于不影响程序数据处理能力的情况下,我们 ...

  2. 使用pprof及Go 程序的性能优化

    使用Golang 程序的性能优化及 Pprof 程序的性能优化无非就是对程序占用资源的优化.对于服务器而言,最重要的两项资源莫过于 CPU 和内存.性能优化,就是在对于不影响程序数据处理能力的情况下, ...

  3. 小程序Canvas性能优化实战

    以下内容转载自totoro的文章<小程序Canvas性能优化实战!> 作者:totoro 链接:https://blog.totoroxiao.com/canvas-perf-mini/ ...

  4. JS Window对象 计时器setInterval&lpar;&rpar; 在执行时&comma;从载入页面后每隔指定的时间执行代码。

    计时器setInterval() 在执行时,从载入页面后每隔指定的时间执行代码. 语法: setInterval(代码,交互时间); 参数说明: 1. 代码:要调用的函数或要执行的代码串. 2. 交互 ...

  5. Windows Server2008 R2性能优化方法

    经常使用的是Windows 2008R2企业版的服务器,简单总结一下性能优化的方法 ========================================================== ...

  6. iOS App 启动性能优化

    1. App启动过程 解析Info.plist 加载相关信息,例如如闪屏 沙箱建立.权限检查 Mach-O加载 如果是胖二进制文件,寻找合适当前CPU类别的部分 加载所有依赖的Mach-O文件(递归调 ...

  7. Python 和 C&sol;C&plus;&plus; 拓展程序如何性能优化?看这一篇文就够

    作者:王璐璐 | 旷视 MegEngine 架构师 一. 背景 在 MegEngine imperative runtime 的早期开发中,我们面临着一些的性能优化问题.除了一些已知需要重构的地方(早 ...

  8. &lbrack;daily&rsqb;&lbrack;optimize&rsqb; 一个小python程序的性能优化 (python类型转换函数引申的性能优化)

    前天,20161012,到望京面试.第四个职位,终于进了二面.好么,结果人力安排完了面试时间竟然没有通知我,也没有收到短信邀请.如果没有短信邀请门口的保安大哥是不让我进去大厦的.然后,我在11号接到了 ...

  9. 微信小程序之性能优化

    如果做前端仅仅停留在编码和实现业务功能上面,可能进步速度会有些慢,但是如果经历了对页面的性能优化之后而且有所成绩的话那就不同了,因为你对他背后的机制进行了研究,才能做好性能优化. 做微信小程序也是一样 ...

随机推荐

  1. Raspberry Pi(树莓派)上安装Raspbian(无路由器,无显示器)

    一. 准备工作 1. 树莓派主板 型号:树莓派3 B型 处理器:四核64位ARM Cortex-A53 CPU 内核架构:ARMv8 2. 一张大于8G的TF卡(本人用的是32G的,也作为PiLFS用 ...

  2. &lbrack;Python&rsqb; Python中的一些特殊函数

    1. 过滤函数filter 定义:filter 函数的功能相当于过滤器.调用一个布尔函数bool_func来迭代遍历每个列表中的元素:返回一个使bool_func返回值为true的元素的序列. a=[ ...

  3. fontcreator制作iconfont&lpar;包含两个教程&rpar;

    第一步 在AI中画好矢量图,或者是在PS中将纯色的图片存成PNG格式,最好是放大很多倍的纯色图片.因为导入到fontcreator中会显得很小,如果不是矢量,图片拉大后就会有锯齿状. 第二步 选中AI ...

  4. Android流量监控 思路,想法

    1,开启一个服务,每5分钟跑动一次更新流量,用于能够准确记录流量         每一个小时,更新一次流量,用于清除非本月的流量 2,保存流量的时候,进行判断         a,若是数据库中保存的 ...

  5. java提高篇(十)-----强制类型转换

    在java中强制类型转换分为基本数据类型和引用数据类型两种,这里我们讨论的后者,也就是引用数据类型的强制类型转换. 在Java中由于继承和向上转型,子类可以非常自然地转换成父类,但是父类转换成子类则需 ...

  6. leetcode&lbrack;89&rsqb; Merge Sorted Array

    合并两个有序数组,放在A中,A中的空间足够. Given two sorted integer arrays A and B, merge B into A as one sorted array. ...

  7. SQL SERVER——CPU问题定位与解决

        CPU问题定位基本流程: 性能计数器诊断 主要用到的性能计数器 %Process Time 全实例 (主要用于查看当前服务器的CPU 情况) %Process Time sqlservr (主 ...

  8. python笔记—循环控制

    1.print可以打印多个参数,在括号内用,号区分,显示时一个,号显示一个空格 2.import导入时可以用as别名代替,方便两个模块中有相同函数时使用 3.序列解包:将一个序列(或任何可迭代对象)解 ...

  9. SQL中的字母的大小写转换

    http://blog.csdn.net/dxb601/article/details/52086830 update 表名 set 字段名a= Lower(字段a)   2.将小写字母转化成大写字母 ...

  10. 在C&plus;&plus;中调用DLL中的函数(3)

    1.dll的优点 代码复用是提高软件开发效率的重要途径.一般而言,只要某部分代码具有通用性,就可将它构造成相对独立的功能模块并在之后的项目中重复使用.比较常见的例子是各种应用程序框架,ATL.MFC等 ...