当前位置: 首页 > 编程日记 > 正文

在ApacheHTTPD服务器中使用DSO完全分析

Apache HTTP 服务器是一个模块化(或说积木式)的程序,管理员可以选择一些模块来增加服务器的某些功能。这些模块,可以在创建服务器程序时静态地编译到httpd服务器的二进制代码中,也可以编译成一些独立于服务器程序的Dynamic Shared Objects (DSOs)文件。DSO 文件可以在编译服务器程序时创建,也可以在以后利用Apache扩展工具apxs来单独创建。  这篇文档,将描述如何使用DSO 模块,以及其背后的原理。
  
  实现
  Apache HTTPD对DSO 的支持,即对单个模块的动态加载,是基于一个叫mod_so的模块来实现的,此时mod_so必须被静态地编译到HTTP服务器内核中。这是除了core以外唯一不能以dso方式编译的模块。实际操作时,其它的Apache模块可以在编译服务器程序时通过单独指定来将其编译为DSO文件,正如安装文档中讲述的,此时configure的设置参数应为--enable-xxxx=shared(xxxx为模块的名字,如rewrite等)。 当一个模块被编译为一个名为mod_foo.so的DSO文件后,就可以在httpd.conf文件中用mod_so的LoadModule命令,告诉服务器在启动或重新启动时将此模块加载。
  
  为了简化创建Apache模块(尤其是第三方模块)的DSO文件的过程,apache提供了一个新工具名叫apxs(APache eXtenSion)。它可以脱离apache的源码将模块编译成DSO文件。它的实现思路非常简单: 在安装Apache时,configure脚本的 make install 过程会安装Apache的C头文件,并在apxs程序(apxs是一个perl脚本)中对依赖于具体平台的编译器和连接器设置一些标志(Flag),以供创建DSO文件。通过这种方式,用户就可以利用apxs在没有Apache源码树且无需针对当前平台的编译器和连接器进行配置(以生成DSO格式目标文件)的情况下编译Apache模块了。
  
  使用概要说明
  创建和安装一个 Apache发布的(distributed) 模块,比方说将mod_foo.c编译成mod_foo.so:
  
  $ ./configure --prefix=/path/to/install --enable-foo=shared
  $ make install
  
  创建和安装一个第三方的Apache模块,比方说将mod_foo.c编译成mod_foo.so:
  
  $ ./configure --add-module=module_type:/path/to/3rdparty/mod_foo.c --enable-foo=shared
  $ make install
  
  为以后安装(非HTTPD编译时安装)模块配置Apache:
  
  $ ./configure --enable-so
  $ make install
  
  (要编译全部Aapache模块,用./configure --enable-mods-shared=all --with-egd --with-devrandom --enable-so,但对experimental一类的模块,需要特别指定,如./configure --enable-mods-shared=all --with-egd --with-devrandom --enable-so --enable-cache=shared --enable-disk_cache=shared --enable-mem_cache=shared --enable-proxy=shared --enable-proxy_connect=shared --enable-proxy_ftp=shared --enable-proxy_http=shared --enable-file_cache=shared --enable-charset_lite=shared --enable-case_filter=shared --enable-case_filter_in=shared --enable-ssl=shared 。具体有哪些模块可以编译而没有打开编译开关,可在前面的那个configure运行的最后看看哪一个是no.)
  
  利用apxs在没有Apache源码树的情况下,创建和安装第三方的Apache模块:
  
  $ cd /path/to/3rdparty
  $ apxs -c mod_foo.c
  $ apxs -i -a -n foo mod_foo.la
  
  在所有的情况下,当一个模块编译完成后,必须在httpd.conf使用LoadModule命令在告诉 Apache激活这个模块.
  
  背景知识
  在现代的Unix的派生版本中,有一种非常好的机制,叫做Dynamic Shared Objects (DSO) 的动态连接/和加载,它提供了一种方法,将一段代码编译成一种特殊格式后可在一个可执行程序运行时将这段程序加载到它的地址空间中。
  
  这种加载通过可以通过两种方式做到: 在一个可执行程序开始运行后通过一个叫ld.so的系统程序自动加载,或在可执行程序内部通过Unix加载器(loader)的系统编程接口的系统调用dlopen()/dlsym()来手工加载。
  
  在第一种方式中,DSO通常被叫作共享库或DSO库,以libfoo.so或libfoo.so.1.2的形式命名。它们被存放在系统目录中(通常是/usr/lib),它们与可执行程序的联系是在编译这个可执行程序时,通过传递给连接器一个-lfoo参数来建立的。这里对库的引用直接编码在可执行程序中,因而在程序运行时,Unix加载器会通过以下途径寻找libfoo.so:在系统目录/usr/lib下,在通过-R连接参数传递给连接器后被编码在可执行程序中的路径中,在通过环境变量LD_LIBRARY_PATH指定的目录中。加载器会解析出来那些在可执行程序中使用但是在DSO定义的标志(symbol)。
  
  可执行程序中的标志,通常不会被DSO引用(因为它是一个可重用的基本代码库),因而就不再进行进一步的解析。可执行程序自己不需要做任何事情就可以使用来自DSO的标志,因为Unix加载器已经做了相关的解析工作。(实际上,加载ld.so的代码是使用动态库的可执行程序启动代码的一部分). 动态加载基本代码库的优点是很明显的:库的代码只需在一个系统库(如libc.so)中保存一次,这样可以节省每个程序的磁盘空间。
  
  在第二种方式中,DSO通常被叫作共享对象或DSO文件,命名它们时可以使用任意的扩展名,虽然规范的命名是foo.so的样子。这些文件通常存放在程序所在的目录(或子目录)中,它们与执行它们的程序没有自动建立的联系。相反,可执行程序在运行时通过dlopen手工将DSO加载。此时,来自DSO供执行程序用的标志没有被解析。相反,Unix加载器自动解析所有DSO中使用的来自可执行程序和它已经加载的DSO 库的标志(尤其是来自无处不在的libc.so的所有标志)。在这种方式中,DSO取得可执行程序的标志集合的信息,就象是被静态地连接到可执行程序中一样。
  
  最后,为利用DSO's API,可执行程序须通过dlsym()来解析来自DSO的特定标志,供在以后的分派表等处使用。也就是说:可执行程序要想使用来自DSO的标志,须手工解析它。这样一种机制的优点,不需要的程序段不必加载(因而可以节省内存的使用) ,直到我们讨论的程序需要它时。当需要时,这些程序段可以被动态的加载,来扩展基本程序的功能。
  
  虽然DSO机制听起来简单,用起来只少有一个比较困难的步骤,就是当用DSO来扩展程序的功能时(第二种方式)时,对来自可执行程序、供DSO使用的标志的解析。为什么呢? 因为"反向解析" DSO 使用的来自可执行程序标志集合的标志是与函数库的设计相逆的 (函数库没有任何关于那些使用它的程序的信息),而且没有平台提供这种功能,这也不是一个标准化的功能。实际上,可执行程序的全局标志常常不能再次输出,因而也无法供DSO使用。要利用DSO来动态扩展一个程序的功能,找到一种方法来强制连接器输出所有全局标志是必须解决的主要问题。
  
  共享库的方法就是一个典型,因为它是DSO机制最初设计的目标,因而它被用于操作系统提供的几乎所有类型的函数库中。从另一方面来说,利用共享对象来扩展功能的程序并不是很多。
  
  到1998年,只有很少的软件包在程序运行时利用DSO机制来扩展它们的功能:Perl 5(通过它的XS机制和DynaLoader模块), Netscape Server,等。从版本1.3开始, Apache 也加入了这个群体,因为Apache早就用模块的概念来扩展它的功能,且在内容利用基于分派链(dispatch-list-based )的方法来将外部的模块连接到Apache的核心功能中。因此,Apache实际上注定要用DSO来在运行时加载模块的。
  
  长处和不足
  上述的基于DSO的功能有以下优点
  
  服务器在运行时更加灵活,因为实际的服务器进程可以通过配置文件的LoadModule命令动态的组配,而不必在编译时通过配置参数指定。例如,通过这种方式,虽然只安装了一次,但服务器可以以多种形态运行(如标准版本或SSL版本,简化版本或增强版本[含mod_perl,php3等])
  
  即使在安装完成后,服务器仍可以很方便地用第三方的模块进行功能扩展。这至少对销售商的软件支持有帮助,他们可以创建一个apache的核心程序包,和一个包含PHP3, mod_perl, mod_fastcgi等扩展功能的扩展包。
  
  更容易地开发 Apache模块原型,因为借用DSO和apxs,你可以脱离Apache的源码而只需apxs -i命令就可以开发和编译模块,利用apachectl restart 命令,就可以让新开发的模块在在apache服务器中运行。
  
  DSO 也有下列不足
  DSO并不是在任何平台都可以使用,因为有一些平台不支持动态将一段代码加载到另一个程序的地址空间中
  
  服务器在启动时慢大约20%,因为加载器要作标志解析。
  
  在运行时,在有些平台上服务器大约慢5%,因为PIC( position independent code )代码需要更复杂的组配技巧来解决相对地址的问题,而对绝对地址的情况没有这种开销所以会快一些。
  
  因为并不是所有的平台都支持DSO模块连接(ld -lfoo)其它基于DSO的库(如基于out的平台通常不提供这个功能而基于ELF的平台则可以),所以不能将DSO机制用于所有类型的模块。换句话说,可以编译为DSO文件的模块限制为那些:引用的标志只来自apache内核、来自C函数库(libc)、来自其它的Aapche内核使用的动态或静态库、或含有PIC代码的静态库文件(libfoo.a)。使用其它代码的唯一机会,要么确定apache内核已经对此引用,要能自己通过dlopen()加载代码。

相关文章:

apache 2.4.12 + tomcat 7.0.61 + jk connectors 1.2.40实现tomcat负载均衡集群

实验环境: CentOS 5.11 final hostname:T1.getg.com IP地址:192.168.50.138软件准备: CentOS Linux 5.*系统光盘中的“Development tools”工具包组 jdk-8u45-linux-x64.tar.gz pcre-8.36.tar.gz apr-util-1…

有哪些新手程序员不知道的小技巧?

提到新手程序员,大家想到的第一个词可能就是:刷题。尤其是通过LeetCode刷题,想必新手程序员们都经历过这一步,甚至不少人认为只要在LeetCode上刷的题目够多,就一定能够进阶为大神。但是,不难发现&#xff0…

cocostudio UI编辑器中UITextField输入框控件光标

http://www.cocoachina.com/bbs/read.php?tid194533

在apache中使用 memcache 来作 session 存储

session.save_handler memcache session.save_path "tcp://127.0.0.1:11211" 使用多个 memcached server 时用逗号","隔开,并且和 Memcache::addServer() 文档中说明的一样,可以带额外的参数"persistent"、"weigh…

Android WebView访问SSL证书网页(onReceivedSslError)

Android WebView访问https SSL证书网页,如淘宝,需要在onReceivedSslError添加SSL支持 webview.setWebViewClient(new WebViewClient() {Overridepublic void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {// 不要使用su…

改名 Meta,打元宇宙牌,老龄化的 Facebook 能否再换新颜

编译 | 禾木木 出品 | AI科技大本营(ID:rgznai100) 美东时间10月28日周四,在名为 Facebook Connect 的年度大会上,Facebook 宣布,Facebook 将公司名称更改为“Meta”,这个新名字反映了该公司在社交媒体之外…

Android NDK开发之旅31 FFmpeg音频解码

###前言 #####基于Android NDK开发之旅30--FFmpeg视频播放这篇文章,我们已经学会视频解码基本过程。这篇文章就对音频解码进行分析。 #####音频解码和视频解码的套路基本是一样的, 否则怎么会做到音视频同步播放呢? ###1.FFmpeg音视解码过程分…

整理了 65 个 Matplotlib 案例,这能不收藏?

作者|周萝卜来源|萝卜大杂烩Matplotlib 作为 Python 家族当中最为著名的画图工具,基本的操作还是要掌握的,今天就来分享一波文章很长,高低要忍一下,如果忍不了,那就收藏吧,总会用到的。启用和检查交互模式在…

负载均衡工具haproxy安装,配置,使用

一,什么是haproxy HAProxy提供高可用性、负载均衡以及基于TCP和HTTP应用的代 理,支持虚拟主机,它是免费、快速并且可靠的一种解决方案。HAProxy特别适用于那些负载特大的web站点,这些站点通常又需要会话保持或七层处理。HAProxy运…

【文章】本站收集与转载文章目录

1.关于推荐系统中的特征工程 2.Java程序员最喜欢的11款免费IDE编辑器 3.人工智能和机器学习领域的一些有趣的开源项目 4.微软发布Project Oxford,供Azure户免费集多项功能 5.微软推Azure机器学习工具:Algorithm Cheat Sheet

L09-10老男孩Linux运维实战培训-Nginx服务生产实战应用指南05(架构解决方案)

nginx的多实例设置首先说一下nginx后面加的参数的说明 -s 后面加reload 就是重新加载的意思和apache的graceful同样的效果 -v 小写的v显示版本号后退出 -V大写的V显示nginx的版本号和配置环境 -t 就是test的意思,检查配置文件是否正确 -c 后面配置文件的地址&#x…

linux中的apachectl是什么命令

apachectl是Apache HTTP服务器的前端程序。其设计意图是帮助管理员控制Apache httpd后台守护进程的功能。apachectl脚本有两种操作模式。首先,作为简单的httpd的前端程序,设置所有必要的环境变量,然后启动httpd ,并传递所有的命令…

数据库性能优化1——正确建立索引以及最左前缀原则

1. 索引建立的原则用于索引的最好的备选数据列是那些出现在WHERE子句、join子句、ORDER BY或GROUP BY子句中的列。仅仅出现在SELECT关键字后面的输出数据列列表中的数据列不是很好的备选列SELECTcol_a <- 不是备选列FROMtbl1 LEFT JOIN tbl2ON tbl1.col_b tbl2.col_c <-…

深度学习发展下的“摩尔困境”,人工智能又将如何破局?

前不久&#xff0c;微软和英伟达推出包含5300亿参数的语言模型MT-NLG&#xff0c;这是一款基于 Transformer 的模型被誉为“世界上最大、最强的生成语言模型”。 毫无疑问&#xff0c;这是一场令人印象深刻的机器学习工程展示。 然而&#xff0c;我们是否应该对这种大型模型趋势…

Kotlin学习笔记-基础语法

去年学习过一遍Kotlin&#xff0c;相比java而言&#xff0c;Kotlin确实有许多方便的地方&#xff0c;但是学习之后一直没有真正拿来写项目&#xff0c;很久不用很多东西都已经忘记了。最近Google宣布Kotlin成为Android开发的官方语言之后&#xff0c;Kotlin突然变得火热起来&am…

英特尔王锐:软硬件并驾齐驱,开发者是真英雄

北京时间10月28日&#xff0c;英特尔On技术创新峰会在北京举办。在此次峰会上&#xff0c;英特尔公司高级副总裁、英特尔中国区董事长王锐对外宣告了英特尔拥抱开发者&#xff0c;回归技术创新的决心和信心。 英特尔此前提出&#xff0c;四大超级技术力量赋能数字化的变革&…

基于html5海贼王单页视差滚动特效

分享一款基于html5海贼王单页视差滚动特效是一款流行滑落网页特效代码。效果图如下&#xff1a; 在线预览 源码下载 实现的代码&#xff1a; <div class"top"><div class"top_main center"><ul id"scene" class"scene&quo…

切换apache的prefork和worker模式

Apache HTTP服务器被设计为一个强大的、灵活的能够在多种平台以及不同环境下工作的服务器。 不同的平台和不同的环境经常产生不同的需求&#xff0c;或是为了达到同样的最佳效果而采用不同的方法。 Apache凭借它的模块化设计很好的适应了大量不同的环境。 这一设计使得网站管理…

使用adb devices命令无法识别夜神模拟器的解决方法

模拟器不喜欢原生态的&#xff0c;喜欢简单好用的&#xff0c;这里用的是夜神模拟器现象夜神模拟器启动成功&#xff0c;此时用adb devices命令查看&#xff0c;居然啥都不显示&#xff0c;也就是没识别出来分析很大可能是因为adb的版本不一致导致的&#xff0c;心中无数个草泥…

Apache的prefork模式和worker模式

prefork模式 这个多路处理模块(MPM)实现了一个非线程型的、预派生的web服务器&#xff0c;它的工作方式类似于Apache 1.3。它适合于没有线程安全库&#xff0c;需要避免线程兼容性问题的系统。它是要求将每个请求相互独立的情况下最好的MPM&#xff0c;这样若一个请求出现问题就…

AI 与小学生的做题之战,孰胜孰败?

现在小学生的数学题不能用简单来形容&#xff0c;有的时候家长拿到题也需要思考半天&#xff0c;看看是否有其他隐含的解题方法。市面上更是各种拍题搜答案的软件&#xff0c;也是一样的套路&#xff0c;隐含着各种氪金的信息。 就像网络上说的“不写作业母慈子孝&#xff0c;一…

AIDL方向指示

2019独角兽企业重金招聘Python工程师标准>>> AIDL使用简单的语法来定义接口, 该接口定义了可供客户端访问的方法和属性&#xff0c;并且描述其方法以及方法的参数和返回值。这些参数和返回值可以是任何类型&#xff0c;甚至是其他AIDL生成的接口。 其中对于Java编程…

Techshack Weekly 第 0002 期

Techshack Weekly 专注于后端技术阅读&#xff0c;目前有上百位订阅者&#xff0c;欢迎加入 Telegram Channel &#xff0c;或关注推特 techshackweekly&#xff0c;或订阅 RSS&#xff01; 点击查看本期 本期比较关注的几个领域有&#xff1a;TSDB, 系统设计&#xff0c;推荐的…

像数据分析一样写 Web 页面,这个 Python 库做到了!

作者|刘早起来源|早起Python提起用 Python 写一个 web 页面&#xff0c;总是会想起Django/Flask等这样的大家伙。他们确实好用&#xff0c;但就是流程繁琐&#xff0c;比如有时就想写一个简单的页面&#xff0c;比如问卷调查&#xff0c;拿 Django 来说吧总要经过安装、启动、配…

loadrunner 如何做关联

在页面中为了防止CRSF攻击&#xff0c;每次访问登录页面时&#xff0c;在浏览器器端生成一个token。 在提交时检验这个token是否有效&#xff0c;提交后token自动失效。 如果使用loadrunner来测试此系统话需要做一个关联&#xff0c;把这个token作为一个参数进行提交。 做关联有…

让你的数据离CPU更近一些

让你的数据离CPU更近一些 Jim Gray&#xff1a;RAM是硬盘,硬盘是磁带 永远只做自己最擅长的事情 不是所有的任务都需要同步执行

现在很火的答题赢钱游戏,让我来简单教你怎么做自动答题器

一、前言&#xff1a; 现在最火的直播游戏&#xff0c;那就是答题赢钱直播了&#xff0c;如百万英雄、芝士超人、花椒直播、冲顶大会等等&#xff0c;这些游戏的玩法都很简单&#xff0c;答对12题即可瓜分奖金了。玩法虽然简单&#xff0c;但是要能完全答对12题难度还是挺高的&…

OAuth认证协议原理分析及使用方法

twitter或豆瓣用户一定会发现&#xff0c;有时候&#xff0c;在别的网站&#xff0c;点登录后转到 twitter登录&#xff0c;之后转回原网站&#xff0c;你会发现你已经登录此网站了&#xff0c; 这种网站就是这个效果。其实这都是拜 OAuth所赐。 OAuth是什么&#xff1f; OAuth…

一次图文并茂的***完整测试二

任务&#xff1a;某公司授权你对其服务器进行******。对某核心服务器进行***测试&#xff0c;据了解目标机为Windows 2003 Server系统&#xff0c;ip地址为10.1.1.191&#xff0c;在C盘的根目录下存储有两个敏感文件这里就用&#xff08;key1.txt,key2.txt&#xff09;表示&…

神经网络学习到的是什么?(Python)

作者|泳鱼来源|算法进阶神经网络&#xff08;深度学习&#xff09;学习到的是什么&#xff1f;一个含糊的回答是&#xff0c;学习到的是数据的本质规律。但具体这本质规律究竟是什么呢&#xff1f;要回答这个问题&#xff0c;我们可以从神经网络的原理开始了解。一、 神经网络的…