2021-2022-1 20212804《Linux内核原理与分析》第五周作业

系统调用的三层机制(上)

一、知识积累

1、
内核态:高执行级别下,代码可以执行特权指令,访问任意物理地址,CPU执行级别就对应内核态。
用户态:低级别指令,只能在对应级别允许的范围内活动。
中断处理是从用户态进入内核态主要的方式
2、寄存器上下文

  • 从用户态切换到内核态时,必须保存用户态的寄存器上下文。
  • 中断/int指令会在堆栈上保存一些寄存器的值,如:用户态栈顶地址、当时的状态字、当时的CS:eip的值。
    3、应用编程接口API和系统调用是不同的
    API只是一个函数定义。
    系统调用通过软中断向内核发出明确请求。
    4、系统调用的三层皮
    API XYZ,中断向量system_call,中断服务程序sys_xyz

在这里插入图片描述

二、实验楼实验

使用库函数 API 和 C 代码中嵌入汇编代码两种方式使用同一个系统调用

1、查看系统调用号信息
在这里插入图片描述

在这里插入图片描述
选择getuid进行此次实验,其系统调用号为102,即0x66。
2、通过man getuid查看getuid系统调用相关信息,可以看到其功能是返回当前调用进程的用户ID:
在这里插入图片描述
3、库函数API的方式进行系统调用
编写getuid.c文件,通过getuid()方法获取用户ID:

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
int main()
{
    int usrid;
    usrid=getuid();
    printf("The user id is %d\n",usrid);
    return 0;
}

在这里插入图片描述
编译执行
在这里插入图片描述
4、C 代码中嵌入汇编代码方式进行系统调用
修改getuid.c,嵌入汇编代码,将系统调用号0x66赋给eax寄存器,系统调用后将返回值赋给变量usrid

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
int main()
{
    int usrid;
    asm volatile(
        "mov $0,%%ebx\n\t"
        "mov $0x66,%%eax\n\t"
        "int $0x80\n\t"
        "mov %%eax,%0\n\t"
        :"=m"(usrid)
    );
    printf("The user id is %d\n",usrid);
    return 0;
}

在这里插入图片描述
编译执行
在这里插入图片描述
这里出错了,查询资料后发现,linux系统中64位汇编和32位汇编的系统调用主要有以下不同:
(1)系统调用号不同.linux系统调用号实际上定义在/usr/include/asm/unistd_32.h和/usr/include/asm/unistd_64.h中。
(2)系统调用所使用的寄存器不同,x86_64中使用与eax对应的rax传递系统调用号,但是 x86_64中分别使用rdi/rsi/rdx传递前三个参数,而不是x86中的ebx/ecx/edx。
(3)系统调用使用“syscall”而不是“int 80”。
修改成32位汇编系统下的调用

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
int main()
{
    int usrid;
    asm volatile(
        "mov $0,%%ebx\n\t"
        "mov $0x18,%%eax\n\t" #getuid在32位系统下系统调用号为24,即0x18
        "int $0x80\n\t"
        "mov %%eax,%0\n\t"
        :"=m"(usrid)
    );
    printf("The user id is %d\n",usrid);
    return 0;
}

在这里插入图片描述

三、总结

本节主要学习了系统调用机制,通过分别使用库函数 API 和 C 代码中嵌入汇编代码两种方式使用同一个系统调用,来进行练习。
系统调用流程:第一步,代码调用系统调用( xyz ),该函数是一个包装系统调用的库函数;库函数 ( xyz )负责准备向内核传递的参数,并触发软中断,切换到内核;CPU被软中断打断后,执行中断处理函数 ,即系统调用处理函数 ( system_call);系统调用处理函数调用系统调用服务例程 (sys_xyz ),真正开始处理该系统调用。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值