zoukankan      html  css  js  c++  java
  • linux及安全第四周总结——20135227黄晓妍

    总结部分:

    用户态和内核态:

             前提知识:cpu有几种不同指令执行的级别

             用户态:代码的掌控范围受限制

             内核态:高级别,代码课执行特权指令,访问任意物理地址。

    权限设置的意义:没有的话,系统容易啊崩溃,应用程序代码没有内核代码可靠

    Linux有两种执行级别:0级(内核态)3级(用户态)

    Cs寄存器的最低两位表明当前代码的特权级别(一共可以表示四种)

    CPU每条指令的读取都是通过当前CS:eip这两个寄存器

    逻辑地址空间,可以显著地分开用户态和内核态

             0xc0000000以上只有内核态

             0x00000000~0xbfffffff用户态和内核态

    中断处理:用户态进入内核态的主要方式

                       用户也可以通过系统调用陷入内核,系统调用是特殊的中断。

    寄存器上下文

             用户切换到内核,必须保存用户态的寄存器上下文

             中断int指令会在堆栈上保存:

                                         用户态栈顶地址,当时的状态字,当时的cs:eip值

                                         内核态栈顶地址,当时的状态字,中断处理程序入口。

    中断服务程序:

                       首先保护现场(SAVE_ALL:保存需要用到的寄存器数据)。

                       退出恢复现场(RESTORE_ALL:退出中断程序,恢复保存寄存器的数据)。

    用户态进程和硬件设备的交互:系统调用

    1. 把用户态从底层的硬件设备编程中解放出来
    2. 极大地提升了系统安全性
    3. 有利于程序的可移植性

    应用程序接口API :仅是函数定义

    系统调用:是进程明确的请求

    每一个系统调用对应一个封装例程,封装例程再被API引用。但是API和系统调用没有明确的对应关系,可能一对一,一对多,多对多,多对一。

    系统调用“三层皮”

      API

      中断向量

      中断服务程序

    当用户态进程调用一个系统调用时,CPU切换到内核态并开始执行一个内核函数。

    Linux中是通过执行int $0x80来执行系统调用,这条汇编指令产生向量为128的编程异常;即中断向量0x80与System_call绑定起来。

    系统调用号将函数xyz()和中断服务程序sys_xyz关联起来。

    参数传递

    进程用系统调用号指明哪个系统调用。

    system_call是linux中所有系统调用的入口点,每个系统调用至少有一个参数,使用eax寄存器传递系统调用号。

    寄存器传递参数有限制,每个参数的长度不能超过寄存器的长度,即32位;在系统调用号(eax)之外,参数的个数不能超过6个(ebx,ecx,edx,esi,edi,ebp;-超过6个的情况下,使用某一个寄存器作为指针,进入内核态之后可以访问所有的地址空间,通过某一片区域传递参数。

    实验部分:

    我选取了50号函数getegid

    首先查看它包含的库和返回值

    /*getegid1.c*/

    #include<unistd.h>

    #include<stdio.h>

    int main()

    {

             gid_t gid;

             gid = getegid ();

             printf(“the group ID is %d”,gid);

             return 0;

    }

    运行结果

    该程序的嵌入式汇编代码版

    /*getegid2.c*/

    #include<unistd.h>

    #include<stdio.h>

    int main()

    {

             gid_t gid;

             gid = getegid ();

             asm volatile(

             “mov $0x32,%%eax ”//50号系统调用用eax传递

             “int $0x80 ”//中断向量,执行中断服务程序

             “mov %%eax,%0 ”//返回值保存在gid中

             :”=m”(gid)

    );

             printf(“the group ID is %d”,gid);

             return 0;

    }

    运行结果

    分析:

    系统调用的过程:先将系统调用号放在%eax里,相当于API和中断服务程序连接的桥梁,然后执行中断指令int$0x80,在堆栈上保存用户态栈顶地址,当时的状态字,当时的cs:eip值;内核态栈顶地址,当时的状态字,中断处理程序入口。然后系统调用的函数开始在内核执行,执行的结果(返回值)保存在%eax里,再由%eax传入gid,然后弹栈恢复现场。

  • 相关阅读:
    购物菜单
    增删改查
    第七次Android
    第七次作业
    第四次作业
    第二次作业
    第七次
    第二次作业
    第三次作业
    第六周安卓作业
  • 原文地址:https://www.cnblogs.com/angelahxy/p/5296700.html
Copyright © 2011-2022 走看看