zoukankan      html  css  js  c++  java
  • Android中的Prelink技术

    1. 原理简介

    (1)Prelink
      Prelink即预链接技术是利用事先链接以代替运行时链接的技术,以加快共享库的加载速度,它不仅能加快程序启动时间,还可以减少部分内存开销(它能使KDE的启动时间减少50%)。每次程序执行时,进行的链接动作都是一样的,链接相对来说开销很大,尤其是嵌入式系统。

    (2)普通Linux系统的Prelink
      Redhat系统中prelink工具(/etc/cron.dialy/prelink)会修改可执行程序,把它与所需库的链接信息加入可执行程序。在程序运行时,使用glibc(glibc > 2.3.1-r2)中的ld-linux.so来进行链接。用此方式,每次更新动态库后,使用它的程序都需要重新prelink,因为新库中的符号信息,地址等很可能与原来不同了。

    (3)Android的Prelink
      Android源码中有一组map文件,其中定义了需要预连接的动态库,其Prelink信息以及对应的逻辑地址(4G地址空间中位置),在动态库编译时,预处理程序apriori根据map文件中的定义,生成预链接信息重定向信息,并加入到这些二进制文件lib*.so的末尾。它主要节约了查询函数地址等工作所用的时间,动态库重定位的开销。在运行程序,动态库加载时,加载程序linker判断动态库是否为Prelink的,如果是的话,就在首次使用时将其加载到指定的内存空间,直接使用预编译信息。

    2. Android上的现状

    (1)prelink-linux-arm.map

    这个文件在Android源码中好像自2009年之后就不存在了,最后的一个见:https://gerrit.unlegacy-android.org/plugins/gitiles/Unlegacy-Android/android_build/+/8f83fce7f1084c5dff2f8fa99d3fdff6e045726b/core/prelink-linux-arm.map

    (2)LOCAL_PRELINK_MODULE

    这个是Android编译时mk文件里面可以指定的,可以决定编译so时是否启用prelink,该值设置为true要生效的前提是要在prelink-link-arm.map中定义so的偏移位置,但是好像Android 4.2之后就没有这个map文件了。(引用:《Android build系统中常用的LOCAL_变量》)

    (3)仅适用于系统应用开发者,原因是这种机制必须要有系统支持才行实现

    适用于Android的系统开发者,用来定制系统级的动态库,加速定制的android的系统的启动及加载速度。由于嵌入式设备尤其是android设备,目前的升级比较频繁,一旦prelink过的库函数修改过了,要求所有引用该库函数的可执行文件也要被重新编译。这就要求系统开发者谨慎的修改系统代码,毕竟每次OTA升级的代价还是很大的。

    (4)主要由于安全性方面的考虑,在最新版本的各个系统中都已经放弃了prelink技术:

      参考PPT内容:《Dynamic-prelink》《Dynamic-prelink yoon esa14 slides

    3. 一点体会

    这种prelink机制的核心原理是由Android系统Linker(或者Linux系统的prelink进程)去帮忙做地址的预先分配与计算,省去一般动态库那种动态so地址分配以及导出符号表的地址查找与计算的过程,这样一来每个so中存储的导出符号都是预先已经计算好的符号绝对地址了,而不是未决的(导出)偏移地址。从而起到提高动态库加载速度的目的。

    正因为如此,必须要系统级的支持才能实现,不可能由某个应用级APP来自行控制。

  • 相关阅读:
    深入理解CSS中的层叠上下文和层叠顺序
    利用CSS3制作淡入淡出动画效果
    <link>标签的rel属性全解析
    解决<pre>标签里的文本换行(兼容IE, FF和Opera等)
    HTML特殊字符大全
    清除浮动4种方法总结下
    打开wamp中的phpmyadmin出现403的错误
    js访问CSS最终计算样式
    js 正则 exec() 和 match() 数据抽取
    函数表达式中,函数名称在函数体内是只读的
  • 原文地址:https://www.cnblogs.com/kuliuheng/p/12195960.html
Copyright © 2011-2022 走看看