win和linux动静态链接库介绍,以及win下动态库生成和调用方法

news/2024/7/5 4:50:16

目录

参考文献

知识点介绍

linux下动静态库编译简单介绍

win下动静态库使用

win下动态库的生成和隐式链接(静态调用)


参考文献

【基础】动态链接库/静态链接库的区别_叫我东方小巴黎的博客-CSDN博客_动态链接库和静态链接库的区别

Linux动静态库详解_GSX_MI的博客-CSDN博客_linux动态库后缀

动态链接库的显示加载和隐式加载的区别_y13156556538的博客-CSDN博客

使用动态链接为什么还需要静态库lib文件 - 走看看

VS生成自己的DLL并调用_aspiretop的博客-CSDN博客_vs生成dll

知识点介绍

通过gcc编译,将一个.c源文件到可执行文件,要经过

预处理(.c->.i)

$ gcc -E main.c -o main.i

编译(.i->.s) (.s文件为一堆汇编指令)

$ gcc -S main.i

汇编(.s->.o) (汇编得到的.o为可重定位目标文件,包含二进制代码和数据)

$ gcc -c main.s

链接(.o->可执行)

$ gcc -o main.o

这四个步骤。

对于频繁用到的目标文件(.o),我们可以将其进行打包,打包后就成为一个库。在之后要使用这些目标文件时,只要链接库里面的目标文件即可。一个库就是一堆目标文件(.o)的集合,但其中不包含main函数。

其中,链接分为静态链接和动态链接两种。

(linux中静态链接库后缀通常为.a,动态链接库后缀通常为.so,这两种库通常存放在/usr/bin或/bin目录下;win中静态链接库后缀通常为.lib,动态链接库后缀通常为.dll)

静态链接

静态链接以一组可重定位目标文件和命令行参数作为输入,经过符号解析和重定位,输出一个完全链接的可加载和运行的可执行目标文件。

(静态库在链接阶段,会将汇编生成的目标文件.o与引用到的库一起链接打包到可执行文件中。调用静态库函数多少次,就复制多少次代码过去。)

优点:可移植性强;可独立运行,与库函数无关,可在任何环境中运行。

缺点:代码冗余,可执行文件体积大;如果所有使用的静态库发生改变,程序需要重新编译。

动态链接

动态链接方式下,函数定义在动态链接库(也称共享对象目标文件、共享库)中。在链接阶段,动态链接库只提供符号表和其他少量信息用于保证所有符号引用都有定义,使得编译能顺利通过;在运行过程中,动态链接库链接程序根据记录的共享对象的符号定义来加载动态链接库,以完成重定位。

(采用动态链接库实现链接操作时,程序文件中哪里需要库文件的功能模块,GCC 编译器不会直接将该功能模块的代码拷贝到文件中,而是将功能模块的位置信息记录到文件中,直接生成可执行文件。在运行采用动态链接库生成的可执行文件时,GCC 编译器会将对应的动态链接库一同加载在内存中,由于可执行文件中事先记录了所需功能模块的位置信息,所以在现有动态链接库的支持下,也可以成功运行。)

优点:可执行文件体积小;动态库改动更方便,改动后对程序不用重新编译。

缺点:无法独立运行;可移植性差。

linux下动静态库编译简单介绍

linux下使用动静态库编译成可执行程序

$ gcc test.c -o test_d                //动态库编译,test_d为生成的可执行文件名
$ gcc test.c -o test_s -static        //静态库编译,test_s为生成的可执行文件名

// 通过ldd命令查看一个可执行程序所需依赖的库文件
$ ldd test_d
$ ldd test_s        //静态库编译的是查看到不到依赖的库文件的,因为它已经编到可执行文件中了,不需要再依赖其他库文件了。

// 通过file命令可以查看一个可执行文件是静态链接还是动态链接的
$ file test_d
$ file test_s

win下动静态库使用

win中

.h文件包含了库函数声明

.dll文件为.o文件的集合。

.lib文件(这里的lib文件指导入库文件,而不是静态库文件,大小比静态库文件小很多。两者只是恰好使用了相同的后缀)提供地址符号表等信息,可以理解为用来存放.dll文件中各功能模块的位置信息,在加载时先从.lib文件中找到.dll文件中各个功能模块在机器代码中的位置。

win中动态库加载方式

可以通过两种方式加载,隐式链接(隐式加载、静态调用)和显示链接(显示加载、动态调用)。

隐式链接(静态调用)

隐式链接在程序开始执行时,将dll加载到内存中,需要用到.h、.lib、.dll文件。

默认加载到内存中,并始终占用内存。

显示链接(动态调用)

显示链接调用比较麻烦,但可以没有lib库,只需要用到.h、.dll文件。

只在加载时载入内存,用完时(即对该库引用计数为0时)立即释放。

显式和隐式只是对于代码编写时来说的,最后产生的可执行程序,不管是显式和隐式,都是用loadlibrary载入的。

我们大多数情况使用隐式链接比较方便。

win下动态库的生成和隐式链接(静态调用)

可完全参考下面文献,进行动态库的生成和调用

VS生成自己的DLL并调用_aspiretop的博客-CSDN博客_vs生成dll


http://lihuaxi.xjx100.cn/news/9658.html

相关文章

响应式UI组件集DevExtreme v22.1.5,9月全新发布!

DevExtreme拥有高性能的HTML5 / JavaScript小部件集合,使您可以利用现代Web开发堆栈(包括React,Angular,ASP.NET Core,jQuery,Knockout等)构建交互式的Web应用程序。从Angular和Reac&#xff0c…

计算机毕业设计之java+ssm基于个人需求和地域特色的外卖推荐系统

计算机毕业设计之javassm基于个人需求和地域特色的外卖推荐系统 项目介绍 系统权限按管理员,商家和用户这三类涉及用户划分。 (a) 管理员:管理员使用本系统涉到的功能主要有:首页,个人中心,用户管理,商家管理,菜系分类管理,城市管理,系统管理,订单管理等…

csmall-passport(Day14)

1. 使用JWT保存权限 在UserDetailsServiceImpl中,调用的adminMapper.getLoginInfoByUsername()中已经包含用户的权限,则,在返回的UserDetails对象中封装权限信息: UserDetails userDetails User.builder().username(loginAdmin…

Fabric.js 自定义子类,创建属于自己的图形~

theme: smartblue 我报名参加金石计划1期挑战——瓜分10万奖池,这是我的第14篇文章,点击查看活动详情 本文简介 点赞 关注 收藏 学会了 fabric.js 在出厂时就提供了几个基础图形,比如矩形、圆形、三角形等。 但这些图形可能不能满足日常开…

Hive常用语句

创建表 CREATE TABLE if not exists ${database}.ads_dd_s( register_date string COMMENT ‘日期’, order_number string COMMENT ‘流水号’, card_no string COMMENT ‘信用卡号’, rl_bank_acct_no string COMMENT ‘借记卡’, loan_init_prin int COMMENT ‘金额’, loan…

MySQL创建存储过程,事件定时执行

MySQL创建存储过程,事件定时执行 创建存储过程 Procedure格式 CREATE[DEFINER { user | CURRENT_USER }]PROCEDURE procedure_name([[IN |OUT |INOUT ] 参数名 数据类形...]) BEGIN[characteristic ...] routine_body END [end_label]IN 输入参数:调用…

国产RK3399开发板如何在Ubuntu保留文件系统

文章来源:飞凌嵌入式官网http://www.forlinx.com在Ubuntu系统的嵌入式设备开发过程中,保留文件系统或者说备份当前开发板镜像的需求在不断增加。 比如Ubuntu文件系统需要安装库文件的话直接使用apt-get工具就可以下载,但由于需要下载的核心板…

只因程序员写了一段爬虫,公司200人被端,是种什么体验?

​只因程序员写了一段爬虫,公司200人被端是种什么体验,很多人的第一反应可能都是不可能,作为程序员谁还没写过几段爬虫,不过这次可不是乱编的。 事情的起因是这样,某一个知名互联网公司,突然发现公司的服务…