一、概述
之所以要写这个,是因为发现了一个很有趣的问题:我在SecureCRT开了两个终端登陆系统,一个是串口,一个是telnet,
无论我在哪个终端调用printk,信息都会被打印在串口终端,巴特无论在哪个终端调用printf信息都会被打印在这个终端
上(类似的还有echo命令,但没去研究这个命令的源码),为什么会产生这种现象,printf最后调用了什么。
首先要引入glibc的概念
二、glibc
2.1 什么是glibc?
glibc是GNU发布的libc库,是标准C的gnu实现,基于GPL的。glibc库提供了系统调用和标准C函数库,所有动态连接的
程序都要用到它。说白了就是它提供了linux用户编程所用到的所有库函数(自己定义的除外)。但它并不直接实现系统调用,而是把标准C库和系统调用全部封装成API提供给用户,比如用户调用read
函数的时候,会直接调用glibc的read函数(API),这个read函数里会封装一个同名的read系统调用。
它linux系统中最底层的api,几乎其它任何运行库都会依赖于glibc,linux下的gcc默认使用glibc。
在linux下面可以通过“rpm -q glibc”查看有没有安装glibc以及版本号
2.2 glibc的内容
分享函数库群:
这是 glibc 的主体,分布 /lib 与 /usr/lib 中,包括 libc 标准 C 函数库、libm 数学函数库、libcrypt 加密与编码
函数库、libdb 资料库函数库、libpthread 行程多执行绪函数库、libnss 网路服务函数库 .... 等等。这些都是可分享
函数库,档名都以 .so 做结尾。其中,/lib/ld*.so 是程序与函数库连结的工具。简而言之就是,平时你在linux环境中
编程用到的.so和.a文件都是属于glibc库。
函数库头文件:
全部在 /usr/include/ 底下
函式库说明文件:
在一般的 UNIX 系统下,这些说明文件是放在 /usr/man 或 /usr/share/man 底下,统称为 man pages,其底下还分若干章节,
其中第二章 (man2) 讲的是系统调用,而第三章 (man3) 讲的就是 libc 标准函数库,这些都是系统开发者重要的参考资料。
例如:我们可以用 man ls 查看系统命令的资料,用 man 2 open 查看系统调用函数的资料,用 man 3 printf 查看标准C
库函数的资料
其他:就不一一列举了
三、 glibc、系统调用和C库函数
先来区分一下概念,C库函数指的是glibc提供的函数库,它是API的主要部分(API包含C库函数、OpenGL 编程接口等)。
而标准C函数库是C语言提供的一组标准库,不止在linux上面可以使用,windows上面也会使用,例如fopen函数。
我们知道glibc包含了系统调用和标准C函数库,当我们在编写linux应用程序的时候,既可以用标准C函数库,也可以用系统调用,
那么系统调用和标准C函数库有什么关系呢?下面是网上的别人的观点
1.系统调用是为了方便应用使用操作系统的接口,而库函数是为了方便人们编写应用程序而引出的,比如你自己编写一个
函数其实也可以说就是一个库函数。
2.系统调用可以理解为内核提供给我们在用户态用的接口函数,可以认为是某种内核的库函数。
3.read就是系统调用,而fread就是标准C库函数.
4.很多c函数库中的函数名与系统调用的名称一样是因为该函数本身其实就是调用系统调用,放到c函数库就是为了用户态的使用
5.写程序直接使用的是库函数,而库函数内部可能就是调用的同名系统调用
以下是我的理解:
算了还是先来说说系统调用吧
什么是系统调用?
先来一个标准一点的定义,用户应用程序访问并使用内核所提供的各种服务的途径即是系统调用。我们知道,linux系统是分为
内核空间和用户空间的,用户空间不能直接访问内核空间(内核空间可以访问用户空间),如果它想使用内核提供的功能,
怎么办呢?很简单啊,内核给用户空间提供很多个不同的门,这些门就是内核提供的系统调用函数,用户空间通过这些函数
陷入到内核里。所以说它是用户空间与内核空间直接的桥梁。
那么系统调用和C库函数又是什么关系呢?
这里标准C函数库是C库函数的一类,把它划到C库里讲解。
既然这样,先说标准C函数库吧。有的标准C库函数是通过调用系统调用来实现的,它最终会调用系统调用。但这些函数却是通用的,
无论是windows还是linux都可以使用,标准C函数库是不依赖于特定的环境和硬件的。其实,都是编译器来负责库函数到系统调用
之间的转换的。比如说VC可能通过把fopen()对应到windows的打印系统调用XXX(不知道具体是哪个)上去了,而linux的
编译器gcc通过把fopen()对应到linux的系统调用open上去了。
有的标准C库函数不会调用系统调用,因为这类函数不操作硬件,只是用户层的程序实现。例如strcpy函数。
最后就是标准系统调用函数库,它封装了系统调用函数
再看一下系统调用与系统命令
系统命令其实就相当于一个可执行程序,它使用了C库函数,如ls、cd等命令。那么这些被称为系统命令的应用程序是谁提供的呢,
当然是busybox了。
开始提出的那个问题还没解决,这个答案要在分析完下一节才能给出
阅读(2209) | 评论(0) | 转发(0) |