linux系统调用第一篇
系统调用
系统调用,顾名思义,说的是操作系统提供给用户程序调用的一组“特殊”接口。用户程序可以通过这组“特殊”接口来获得操作系统内核提供的服务,比如用户可以通过文件系统相关的调用请求系统打开文件、关闭文件或读写文件,可以通过时钟相关的系统调用获得系统时间或设置定时器等。
从逻辑上来说,系统调用可被看成是一个内核与用户空间程序交互的接口——它好比一个中间人,把用户进程的请求传达给内核,待内核把请求处理完毕后再将处理结果送回给用户空间。
系统服务之所以需要通过系统调用来提供给用户空间的根本原因是为了对系统进行“保护”,因为我们知道 Linux 的运行空间分为内核空间与用户空间,它们各自运行在不同的级别中,逻辑上相互隔离。所以用户进程在通常情况下不允许访问内核数据,也无法使用内核函数,它们只能在用户空间操作用户数据,调用用户空间函数。
实现
系统调用是属于操作系统内核的一部分的,必须以某种方式提供给进程让它们去调用。CPU 可以在不同的特权级别下运行,而相应的操作系统也有不同的运行级别,用户态和内核态。运行在内核态的进程可以毫无限制的访问各种资源,而在用户态下的用户进程的各种操作都有着限制,比如不能随意的访问内存、不能开闭中断以及切换运行的特权级别。显然,属于内核的系统调用一定是运行在内核态下,但是如何切换到内核态呢?
答案是软件中断
。软件中断和我们常说的中断(硬件中断)不同之处在于,它是通过软件指令触发而并非外设引发的中断,也就是说,又是编程人员开发出的一种异常(该异常为正常的异常)。操作系统一般是通过软件中断从用户态切换到内核态。
系统调用(system call)和库函数(library function)是编程中常用的两种调用方式,它们之间有以下几点区别:
- 触发方式:
- 系统调用是由用户程序通过特殊的指令(例如软中断指令或者特定的处理器指令)触发的,以请求操作系统提供服务或执行特定操作。
- 库函数是由用户程序直接调用的函数,这些函数通常封装在库文件中,用户程序通过链接库文件来调用这些函数。
- 特权级别:
- 系统调用执行时会导致用户态和内核态之间的切换,因为系统调用需要访问操作系统的内核空间,具有较高的权限级别。
- 库函数的执行在用户态完成,不需要切换到内核态,因此无需特殊的权限。
- 功能:
- 系统调用通常提供了与操作系统相关的底层功能,例如文件操作、进程管理、网络通信等。
- 库函数提供了各种常用的功能,例如字符串处理、数学运算、内存管理等。
- 性能开销:
- 由于系统调用涉及用户态和内核态之间的切换,因此通常会伴随着较大的性能开销。
- 库函数的调用通常只涉及用户态,因此性能开销较小。
- 跨平台性:
- 系统调用的接口是由操作系统定义的,因此在不同的操作系统上可能存在差异,需要编写特定平台的代码。
- 库函数通常是标准化的接口,在不同的编程语言和平台上都可以使用,具有较好的跨平台性。
C库IO函数工作流程
后续提供具体代码
虚拟地址空间
每个进程都会分配虚拟地址空间,在32位机器上,该地址空间为4G:
代码里体现的都是用户区的数据段。
在进程里平时所说的指针变量,保存的就是虚拟地址。当应用程序使用虚拟地址访问内存时,处理器(CPU)会将其转化成物理地址。
这样做的好处在于:
-
进程隔离,更好的保护系统安全运行
-
屏蔽物理差异带来的麻烦,方便操作系统和编译器安排进程地址
本文来自博客园,作者:ivanlee717,转载请注明原文链接:https://www.cnblogs.com/ivanlee717/p/18135814