文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

C语言中dlopen和dlsym如何使用

2023-06-29 16:36

关注

这篇文章主要介绍“C语言中dlopen和dlsym如何使用”的相关知识,小编通过实际案例向大家展示操作过程,操作方法简单快捷,实用性强,希望这篇“C语言中dlopen和dlsym如何使用”文章能帮助大家解决问题。

背景

为了是不同的逻辑解耦,一般会把各个业务封装成动态库,然后主逻辑去调用各个插件。这里有个问题是,为什么以前我们都是通过include第三方的头文件,然后通过连接器实现,现在却要利用dlopen呢?考虑以下情况,比如我们要用cublas这个库的sgemm函数。

#include "cublas.h"int main(){cublas:: Mat a, b;cublas::sgemm(a,b);}

我们知道cublas是英伟达提供的,人家每年都要更新动态库的,比如今年更新后,动态库的头文件改了cublas_v2.h, 函数名改为sgemm_v2, 这样一顿操作后,你不仅要升级库,也要修改已经上线的代码,假如这个sgemm函数在你源码中出现了n多次,这将是一个灾难。但是通过下面的方式你就可以避免这个问题:

// func.h#include <stdio.h>#include <stdlib.h>#include <cublas_v2.h> // 如果你知道确切的函数返回信息,这个对应下面的cublas_func可以自己写。#include <dlfcn.h>extern std::once_flag cublas_dso_flag;extern void *cublas_dso_handle;  struct DynLoad__add {                                                    template <typename... Args>                                                 inline auto operator()(Args... args) -> DECLARE_TYPE(add, args...)     {       using cublas_func =  decltype(::add(std::declval<Args>()...)) (*)(Args...);               std::call_once(cublas_dso_flag, []() {                                        cublas_dso_handle = dlopen("./libcublas.so", RTLD_LAZY);             });                                                                         static void *p_add = dlsym(cublas_dso_handle, "add");                return reinterpret_cast<cublas_func>(p_add)(args...);                }                                                                         };                                                                          extern DynLoad__add add;// func.cDynLoad__add add;// main.cc#include <stdio.h>#include <stdlib.h>#include "func.h"int main(){    add(2,7));}根据上面的代码可以看到,只要你每次修改func.h文件的动态库路劲和函数名就可以了,其他用到的add函数根本不需要再去修改。真是很方便,上面的代码参考paddle的源码:paddle/fluid/platform/dynload/cublas.h

demo

生产动态库

int add(int a,int b){    return (a + b);}int sub(int a, int b){    return (a - b);}

gcc -fPIC -shared caculate.c -o libcaculate.so

调用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是加载动态链接库,flag可以设置不同的模式(RTLD_LAZY 暂缓决定,等有需要时再解出符号, RTLD_NOW 立即决定,返回前解除所有未决定的符号。), dlopen可以返回动态库的句柄,dlsym是获取动态库中的具体函数名或者变量名。dlopen是关闭动态库。

#include <stdio.h>#include <stdlib.h>#include <dlfcn.h>typedef int (*FUNC)(int, int);int main(){    void *handle;    char *error;    FUNC func = NULL;    //打开动态链接库    handle = dlopen("./libcaculate.so", RTLD_LAZY);    //获取一个函数    *(void **) (&func) = dlsym(handle, "add");    printf("add: %d\n", (*func)(2,7));    //关闭动态链接库    dlclose(handle);}

gcc -rdynamic -o main main.c -ldl

关于“C语言中dlopen和dlsym如何使用”的内容就介绍到这里了,感谢大家的阅读。如果想了解更多行业相关的知识,可以关注编程网行业资讯频道,小编每天都会为大家更新不同的知识点。

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯