dlopen的用法

article/2025/10/3 3:45:21

1、前言

  为了使程序方便扩展,具备通用性,可以采用插件形式。采用异步事件驱动模型,保证主程序逻辑不变,将各个业务已动态链接库的形式加载进来,这就是所谓的插件。linux提供了加载和处理动态链接库的系统调用,非常方便。本文先从使用上进行总结,涉及到基本的操作方法,关于动态链接库的本质及如何加载进来,需要进一步学习,后续继续补充。如何将程序设计为插件形式,挖掘出主题和业务之间的关系,需要进一步去学习。

2、生产动态链接库

编译参数 gcc -fPIC -shared 

例如将如下程序编译为动态链接库libcaculate.so,程序如下:

复制代码
int add(int a,int b)
{return (a + b);
}int sub(int a, int b)
{return (a - b);
}int mul(int a, int b)
{return (a * b);
}int div(int a, int b)
{return (a / b);
}
复制代码

编译如下: gcc -fPIC -shared caculate.c -o libcaculate.so 

3、dlopen、dlsym函数介绍

      在linux上man dlopen可以看到使用说明,函数声明如下:

复制代码
#include <dlfcn.h>void *dlopen(const char *filename, int flag);char *dlerror(void);void *dlsym(void *handle, const char *symbol);int dlclose(void *handle);
复制代码

  dlopen以指定模式打开指定的动态连接库文件,并返回一个句柄给调用进程,dlerror返回出现的错误,dlsym通过句柄和连接符名称获取函数名或者变量名,dlclose来卸载打开的库。 dlopen打开模式如下:

  RTLD_LAZY 暂缓决定,等有需要时再解出符号 
  RTLD_NOW 立即决定,返回前解除所有未决定的符号。

采用上面生成的libcaculate.so,写个测试程序如下:

复制代码
 1 #include <stdio.h>
 2 #include <stdlib.h>
 3 #include <dlfcn.h>
 4 
 5 //动态链接库路径
 6 #define LIB_CACULATE_PATH "./libcaculate.so"
 7 
 8 //函数指针
 9 typedef int (*CAC_FUNC)(int, int);
10 
11 int main()
12 {
13     void *handle;
14     char *error;
15     CAC_FUNC cac_func = NULL;
16 
17     //打开动态链接库
18     handle = dlopen(LIB_CACULATE_PATH, RTLD_LAZY);
19     if (!handle) {
20     fprintf(stderr, "%s\n", dlerror());
21     exit(EXIT_FAILURE);
22     }
23 
24     //清除之前存在的错误
25     dlerror();
26 
27     //获取一个函数
28     *(void **) (&cac_func) = dlsym(handle, "add");
29     if ((error = dlerror()) != NULL)  {
30     fprintf(stderr, "%s\n", error);
31     exit(EXIT_FAILURE);
32     }
33     printf("add: %d\n", (*cac_func)(2,7));
34 
35     cac_func = (CAC_FUNC)dlsym(handle, "sub");
36     printf("sub: %d\n", cac_func(9,2));
37 
38     cac_func = (CAC_FUNC)dlsym(handle, "mul");
39     printf("mul: %d\n", cac_func(3,2));
40 
41     cac_func = (CAC_FUNC)dlsym(handle, "div");
42     printf("div: %d\n", cac_func(8,2));
43 
44     //关闭动态链接库
45     dlclose(handle);
46     exit(EXIT_SUCCESS);
47 }
复制代码

编译选项如下:gcc -rdynamic -o main main.c -ldl

测试结果如下所示:

 

参考资料:

http://blog.chinaunix.net/uid-26285146-id-3262288.html

http://www.360doc.com/content/10/1213/22/4947005_77867631.shtml


http://chatgpt.dhexx.cn/article/40WBqjrr.shtml

相关文章

织梦上一篇下一篇没有了改为英文

织梦上一篇下一篇没有了改为英文 网站根目录找到 include/arc.archives.class.php 文件 打开找到 上一篇改为 Previous上一篇后面的“没有了” 改为 No Previous原图修改后 接着放下翻&#xff0c;紧贴着下面的“下一篇&#xff0c;没有了” 找到 下一篇改为 在这里插入…

在wordpress文章页中显示上一篇和下一篇文章

查看原文&#xff1a;http://www.hellonet8.com/1162.html 今天博主在看别人博客的时候发现他们的文章末尾会有显示上一篇和下一篇的文章链接&#xff0c;所以也想在自己的博客中添加这个功能。这么做顺便可以增加文章之间的相关性&#xff0c;对搜索引擎的蜘蛛也会友好些。废话…

js 实现 点击上一篇、下一篇功能

列表界面&#xff1a; 详细界面&#xff1a; 思路&#xff1a; 1. 首先目录列表渲染的数据是通过接口调用取到的值&#xff0c;然后点击具体某一条数据的时候&#xff0c;获取到他的 ID&#xff0c;然后通过路由跳转的时候带到详细信息页面。 2. 在详细页面中&#xff0c;先再…

Vue中 实现上一篇下一篇的功能

效果&#xff1a; 看下html页面 <div class"NewsDetails_cont_footer"><!-- 使用三目运算符判断 按钮是否可以点击 --><div click"last" :class"lastNoShow ? noClick : btn"><img src"../assets/img/newsDetail/公共…

java实现上一篇下一篇功能

根据文章类型查询&#xff0c;实现上一篇、下一篇的效果 自定义实体Dto(这里只放出扩展字段) Getter Setter public class OsArticleDto extends BaseDto {/** */private static final long serialVersionUID 1L;/** 上一篇文章id*/private String beforeId;/*** 上一篇文章…

vue实现上一篇下一篇

先来看一下效果图 请求回来所有文章&#xff0c;根据索引进行上一篇下一篇的判断 首先为两个按钮绑定点击事件 <buttonclick"last(lastId, columnId)":disabled"isLast":class"{ disClick: isLast true }">上一篇:{{ lastTitle }}</b…

Django针对上一篇和下一篇文章标题的实现逻辑

1、要求显示效果 2、前端html内容 <div><nav aria-label"..."><ul class"pager"><li><a href"/blog/detail/{{ previous_article.article_id }}">上一篇&#xff1a;{{ previous_article.title }}</a><…

程序员,我们应该如何去学习

IT技术的发展日新月异&#xff0c;新技术层出不穷&#xff0c;具有良好的学习能力&#xff0c;能及时获取新知识、随时补充和丰富自己&#xff0c;已成为程序员职业发展的核心竞争力。本文中&#xff0c;作者结合多年的学习经验总结出了提高程序员学习能力的三个要点。 众所周知…

程序员该如何学习新知识

想必大家都不是张无忌&#xff0c;人家三十年才可以练成的乾坤大挪移&#xff0c;张无忌大侠两个时辰就可以搞定&#xff0c;作为一个普通的程序员&#xff0c;经常遇到很多新技术和新知识&#xff0c;it界就是这样&#xff0c;日新月异&#xff0c; 那么我们如何学习一门技术和…

@程序员,这四个学习建议值得收藏

在我看来&#xff0c;学习能力应该是一个人最重要的能力之一。因为我们赖以生存的所有技能&#xff0c;无一例外都是通过学习获得的。那些优秀的人&#xff0c;也不过是学习能力或者学习效率比一般人强而已。 这样的观点被很多人论证过&#xff0c;商业理论家阿里德赫斯&#…

程序员学习视频教程汇总

转载请注明出处:http://blog.csdn.net/lowprofile_coding/article/details/51059080 在IT这个节凑快的行业&#xff0c;我们每天都需要学习&#xff0c;需要get新技能&#xff0c;才能不被淘汰&#xff0c;成功的人总是贵在坚持&#xff0c;我觉得有一句话说的很好&#xff1a;…

想自学一下程序员,该学些什么?

程序员是一门职业&#xff08;手动滑稽&#xff09;&#xff0c;需要自学的是编程哦。 编程分为一个方向&#xff0c;方向不同需要学习的东西也大不相同 大数据前端开发后端开发移动端开发移动开发市场游戏开发人工智能服务器开发等等 前端开发难度较高&#xff0c;需要人员…

程序员,这四个学习建议值得收藏

大家好&#xff0c;我是本周的值班编辑 江南一点雨 &#xff0c;本周将由我为大家排版并送出技术干货&#xff0c;大家可以在公众号后台回复“springboot”&#xff0c;获取最新版 Spring Boot2.1.6 视频教程试看。 在我看来&#xff0c;学习能力应该是一个人最重要的能力之一。…

做程序员,需要学习哪些专业知识?

一、两大能力 1、学习能力 为什么需要学习能力,因为技术不会一直停着不动,可能当你刚在学校出来的时候,是公司的佼佼者,但是如果你不学习,当别人会HTML6/7/8的时候,你还只是在HTML5上徘徊。而且当你遇到困难的时候,如果是有大牛给你解决了问题,但是你只是照搬并没有真…

AJAX-设置同步

AJAX-设置同步 一.同步方式与异步方式的区别&#xff1a; 1.1.同步方式发送请求&#xff1a;发送一个请求&#xff0c;需要等待响应返回&#xff0c;然后才能够发送下一个请求&#xff0c;如果该请求没有响应&#xff0c;不能发送下一个请求&#xff0c;客户端会一直处于等待…

js设置ajax执行顺序,ajax同步处理(使得JS按顺序执行)

在项目中碰到一个问题: 图一: 图二: 函数1代码:这里是因为有ajax请求,默认的是异步的 //点击分页页码,请求后台返回对应页码的数据 function getdata(fewPage,flag,content){$.getJSON(getUrl()+/myAccount/getMyOrders.do?curPage=+fewPage+&flag=+flag+&conte…

CDH6.2.0部署

CDH6.2.0部署 服务器信息 服务器主机名安装服务密码等信息192.168.66.10mysql.cdh.lczy.comcloudera-manager-server httpd mysql-5.7数据库初始密码和安装路径信息如下: mysql_root_pwd“CDH6.2_lczy” mysql_install_path"/usr/local"192.168.66.11cdh11.lczy.co…

转载:CDH6.2离线安装(整理版)

引用地址&#xff1a;https://www.cnblogs.com/swordfall/p/10816797.html  CDH6.2离线安装&#xff08;整理版&#xff09; 1.概述 CDH&#xff0c;全称Clouderas Distribution, including Apache Hadoop。是Hadoop众多分支中对应中的一种&#xff0c;由Cloudera维护&#…

CDH大数据——cloudera-manager搭建安装集群CDH

目录 一、基础软件版本信息&#xff1a; 1、CDH对CentOS的版本要求&#xff1a; 2、CDH对数据库版本的要求&#xff1a; 3、CDH对jdk版本的要求&#xff1a; 4、CDH对浏览器的要求&#xff1a; 5、CDH对网络配置的要求&#xff1a; 6、CDH对安全传输协议&#xff08;TLS…

CDH6.3.2集群变更IP配置修改

CHD集群在服务器节点的IP改变之后需要修改一些配置&#xff0c;它本身不会如Apache原生软件那样完全依赖服务器的域名映射&#xff0c;我这边本地使用的测试环境是CDH6.3.2的&#xff0c;在启动/关闭上不用担心agent&#xff0c;如果大家用的是其他版本需要注意 1、在修改IP之…