系统调用

程序运行的时候,本身是没有权限访问多少系统资源的。系统资源有限,如果操作系统不进行控制,那么各个程序难免会产生冲突。线程操作系统都将可能产生冲突的系统资源保护起来,阻止程序直接访问。比如文件、网络、IO、各种设备等。

系统调用涵盖的功能很广,有程序运行锁必须的支持,如创建和退出进程、线程,进程内存管理,对系统资源的访问等。

Linux系统调用与中断

在x86下,系统调用是通过0x80中断完成,各个通用寄存器用于传递参数。EAX寄存器用于表示系统调用的接口号。

比如:EAX=1表示退出进程,EAX=2表示创建进程,EAX=3表示读文件或IO,EAX=4表示写文件或IO。每个系统调用对应到内核源码中的一个函数,他们都是以sys_开头的,比如exit调用对应内核中的sys_exit函数

如果直接使系统调用会有非常多的问题:

  • 使用不方便,操作系统提供的系统调用接口往往过于原始。程序员需要了解很多跟操作系统相关的细节
  • 各个操作系统之间系统调用不兼容

于是增加一个层来解决,系统调用与程序之间增加一个抽象层。这个层就是前面所说的glibc,或者API.

系统调用原理

这里单单以Linux为例,至于Windows调用原理暂时省略。

用户态、内核态、中断与系统安全

现代操作系统中有两种特权级别,分为用户模式和内核模式。

多个模式存在,那么操作系统就可以让不同代码运行在不同模式下,进而限制代码的权限,提高稳定性、安全性。一般普通程序在用户态,操作会受到限制。系统调用运行在内核态,应用程序基本都是运行在用户态被限制。

用户态的程序通过中断来运行内核态的代码,进而从用户态切换到内核态。

比如Linux中int 0x80为例,系统调用号使用eax来传入,用户将系统调用号保存在eax,然后使用int 0x80调用中断,中断服务传给信号就可以从eax取得系统调用号,进行调用相应的函数。

切换堆栈

在实际执行中断向量表中的第0x80好中断之前,CPU还要进行堆栈的奇幻,在Linx中,用户态和内核态使用的是不同的栈,两者各自负责各自的函数调用,互不干扰。

在执行0x80中断的时候,程序从用户态切换到内核态。这时相应的栈也必须切换到内核栈,从中断处理函数中返回时,程序当前栈需要从内核栈切换到用户栈。

当前栈是指ESP值所在的栈空间,如果ESP的值位于用户栈范围能,那么程序的当前栈就是用户栈。内核栈同理。并且SS的值需要指向当前栈所在的页。所以用户栈切换到内核栈就是:

  • 保存当前ESP、SS的值
  • 将ESP、SS的值设置为内核栈的值

(反过来同理)

  • 恢复原理ESP、SS的值
  • 用户态的ESP和SS的值保存在内核栈上,

当发生中断的时候,CPU除了进入内核态之外还会做如下事情:

  • 找到当前进程的内核栈(每一个进程都有一个内核栈)
  • 在内核栈中一猜压入用户态的寄存器SS、ESP、EFLAGS、CS、EIP

当内核从系统调用中返回,则调动iret指令回到用户态,iret指令会从内核栈里面弹出SS、ESP、EFLAGS、CS、EIP的值。使得栈恢复到用户态的状态。

 

作者:纸简书生
链接:https://www.jianshu.com/p/4b9c40e6b8ae
来源:简书
简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。

《程序员的自我修养》读书笔记——系统调用、API的更多相关文章

  1. 第八周读书笔记(人月神话X月亮与六便士)——到底什么才是一个程序员的自我修养?

    写了这么久的读书笔记,涉及到问题大多是一些如何把软件工程做好,如何把自己的职业生涯做好.但总感觉逻辑链上缺了一环,亦即:我们为什么要把软件工程做好,我们成为一名优秀的职业生涯的意义到底在于什么?我觉得 ...

  2. pwn学习日记Day21 《程序员的自我修养》读书笔记

    Linux内核装载ELF过程 (1)bash进程调用fork()系统调用创建一个新的进程 (2)新的进程调用execve()系统调用执行指定的ELF文件,原先的bash进程继续返回等待刚才启动的新进程 ...

  3. pwn学习日记Day20 《程序员的自我修养》读书笔记

    可执行文件的装载与进程 覆盖装入和页映射是两种典型的动态装载方法 进程建立的三步 1.创建一个独立的虚拟地址空间 2.读取可执行文件头,并且建立虚拟空间与可执行文件的映射关系. 3.将CPU的指令寄存 ...

  4. pwn学习日记Day19 《程序员的自我修养》读书笔记

    windows PE/COFF章总结 本章学习了windows下的可执行文件和目标文件格式PE/COFF.PE/COFF文件与ELF文件非常相似,它们都是基于段的结构的二进制文件格式.Windows下 ...

  5. gcc ld 链接器相关知识,调试指令(程序员的自我修养----链接、装载与库)

    最近解决一个动态链接上的问题,因为以前从来没有接触过这方面的知识,所以恶补了一下,首先要了解gcc编译指令(makefile),ld链接器的选项(还有连接脚本section指定内存位置),熟悉查看连接 ...

  6. 程序员的自我修养(2)——计算机网络(转) good

    相关文章:程序员的自我修养——操作系统篇 几乎所有的计算机程序,都会牵涉到网络通信.因此,了解计算机基础网络知识,对每一个程序员来说都是异常重要的. 本文在介绍一些基础网络知识的同时,给出了一些高质量 ...

  7. 《程序员思维修炼》读书笔记——week4

    <程序员思维修炼>读书笔记——week4 PB16061441 陈昶金 这周读的是Andy Hunt的著作<程序员思维修炼>,这本书对于我这种刚刚入门的新手很友好,大多是讲一些 ...

  8. pwn学习日记Day18 《程序员的自我修养》读书笔记

    知识杂项 obj文件:当前源代码编译成二进制目标文件 exe文件:将.obj文件与库文件.lib等文件链接生成的可执行文件 一个现代编译器的主要工作流程如下: 源程序(source code)→ 预处 ...

  9. Java程序员的自我修养

    一.自我修养路线图 如图,这是笔者所走的路.且不论这路走的对不对,这个过程中行业环境会影响到你,大可不必钻牛角尖.附上这张图的目的是为了说,如果你想成为一个优秀的程序员,那么你一定要有规划.当然,别想 ...

随机推荐

  1. mysql 的show processlist和show full processlist区别

    processlist命令的输出结果显示了有哪些线程在运行,不仅可以查看当前所有的连接数,还可以查看当前的连接状态帮助识别出有问题的查询语句等. 如果是root帐号,能看到所有用户的当前连接.如果是其 ...

  2. mac 相关命令

    安装 adb (用于调试 app) brew install Caskroom/cask/android-platform-tools 文件夹显示隐藏文件命令 defaults write com.a ...

  3. Python 部分系统类的常用方法整理

    下面是常用的几个系统类的常用方法整理: list: 列表[1, 2,...] set: 集合,无重复元素{1, 2,...} str: 字符串 dict: 字典{a:'a', b:'b',...} T ...

  4. virtualbox中设置u盘启动

    1.在磁盘管理中查看u盘的磁盘号X 2.管理员运行cmd,进入virtualbox目录 3.运行命令: VBoxManage internalcommands createrawvmdk -filen ...

  5. SSH框架用法,及作用(在一位菜鸟使用半年之后归纳的总结)

    SSH框架从接触以来改变了我对代码的编写方式,从最初开始学习到勉强掌握可以说得到不少心得,以下内容出自java初学者对SSH的理解,如有不对的地方还请谅解,希望可以提出来与我交流,谢谢! SSH顾名思 ...

  6. BZOJ4559: [JLoi2016]成绩比较(dp 拉格朗日插值)

    题意 题目链接 Sol 想不到想不到.. 首先在不考虑每个人的真是成绩的情况下,设\(f[i][j]\)表示考虑了前\(i\)个人,有\(j\)个人被碾压的方案数 转移方程:\[f[i][j] = \ ...

  7. iphone手机投屏在哪里 手机无线投屏电脑

    Iphone是我们经常使用的一款手机,有时候经常需要将一些文件图片信息等投屏到电脑,那么iphone手机投屏在哪里?可以无线投屏到电脑吗?其实很简单,下面就分享下苹果手机投屏的具体方法给大家,希望对大 ...

  8. java Web三大组件--过滤器

    参考博客:http://www.cnblogs.com/coderland/p/5902878.html https://www.cnblogs.com/HigginCui/p/5772514.htm ...

  9. Loadrunner 脚本优化-事务函数简介

    脚本优化-事务函数简介 by:授客 QQ:1033553122 1.事务的开始和结束名称需要相同 lr_start_transaction(“transaction_name”); …//事务处理 l ...

  10. Android和H5进行数据交互,Android获取H5Input框中的内容

    项目中嵌入了H5 页面,这个时候就需要拿到H5 input中的内容进行数据传递,先看实现的效果图