哈工大操作系统lab2(添加系统调用)

2024-01-07 22:59

本文主要是介绍哈工大操作系统lab2(添加系统调用),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

lab2添加系统调用

前言

对于实验一,由于基本上按照实验册来就可以成功,故我就没有写博客。同时对于此博客更多的是纪念自己所学,如要实验参考:推荐博客:love6’s blog
首先先梳理一下系统调用:首先对于内存我们需要知道是分为用户态和内核态的,其中用户态不可直接访问内核态,而内核态是可以访问任何内存的,然后如何通过用户态来访问内核态呢,即利用API来访问,通过API来找到对应内核函数,然后来实现系统调用。
然后再讲一下本实验中具体系统调用过程:首先是通过API(应用程序接口)将系统调用号存入edx寄存器,然后调用int0x80号中断实现进入内核,内核中的中断处理程序通过系统调用号调用对应的内核函数,然后将其返回值存入edx寄存器中,然后返回到中断处理函数,中断处理程序返回到API中,然后API将edx返回给应用程序。

实验

首先是要复原原来的情况

#删除原来的文件
$ cd ~/oslab
$ sudo rm -rf ./*
#重新拷贝
$ cp -r /home/teacher/oslab/* ./

首先我们先要知道我们要做的两个函数:

int iam(const char * name);
#完成的功能是将字符串参数 name 的内容拷贝到内核中保存下来
要求 name 的长度不能超过 23 个字符。返回值是拷贝的字符数。
如果 name 的字符个数超过了 23,则返回 “-1”,并置 errno 为 EINVAL。
int whoami(char* name, unsigned int size);
#它将内核中由 iam() 保存的名字拷贝到 name 指向的用户地址空间
中,同时确保不会对 name 越界访存(name 的大小由 size 说
明)。返回值是拷贝的字符数。如果 size 小于需要的空间,则返回“-1”,并置 errno 为 EINVAL。
这两个函数都是在kernal/who.c下创建。 

对于实验步骤顺序而言我自己也是不太记得,就从我先想到开始吧,首先是先在linux-0.11下的include/unistd.h下修改必要信息,添加系统调用号,如下:
在这里插入图片描述
然后不要忘记在user下的unistd.h也添加系统调用号,关于如何进入则需要上个实验学的,采用sudo ./mount-hdc即可,当然再**./run之前需要采用sudo umount hdc**将挂载消除掉,然后就可以实现更改了
在这里插入图片描述

实现API

首先AP都是在linux-0.11下的lib路径下实现,我们需要实现iam函数API以及whoami函数API,其结果如下:
在这里插入图片描述
在这里插入图片描述
其中**LIBRARY**是为了标识 _syscall_syscalln是代表n个参数,然后_syscall是一个宏,起到了对API的定义。

修改kernal/system_call.s

对于system_call.s 进行修改
在这里插入图片描述
系统调用的函数增加了,所以需要增加两个。

修改include/linux/sys.h

对于这里也要修改,添加函数引用
在这里插入图片描述
同时在sys_call_table中也要添加,且添加的顺序必须与其系统调用号一致。如图:
在这里插入图片描述

在内核中实现sys_iam()和sys_whoami()

其实现是在kernal/who.c中实现
代码如下:

#include<unistd.h>
#include<errno.h>
#include<asm/segment.h>
#include<string.h>
char msg[24];
int sys_whoami(char*name,unsigned int size){int len=strlen(msg);int i;if(len>size){errno=EINVAL;return -EINVAL;}for(i=0;i<len;i++)put_fs_byte(msg[i],name+i);return len;
}
int sys_iam(const char*name){errno=0;memset(msg,'\0',sizeof(msg));int count=0;char ch;while((ch=get_fs_byte(name+count))!='\0'){if(count>23){errno=EINVAL;return -EINVAL;}msg[count++]=ch;}if(count>23){//这里是为了防止当第二十四个字符为'\0'不会return -EINAVALerrno=EINVAL;return -EINVAL;}return count;
}

其中要注意的是put_fs_byte() 函数和 get_fs_byte() 函数,其中put_fs_byte()函数原型为void put_fs_byte(char ch,const char*name) 是把字符ch拷贝到name对应的地址上去,其中get_fs_byte() 函数原型为 char get_fs_byte(const char * name) 返回 name地址上对应的字符,由于指针参数传递的为用户逻辑地址,如果内核态函数访问的话是不能访问到数据真正的地址的,get_fs_byte()函数和put_fs_byte()函数便是专门在用户态和内核态中进行数据访问设置的。

修改kernal/Makefile

makefile一共要修改两次,第一次为:
在这里插入图片描述
增加一个who.o即可
在这里插入图片描述
第二处为:
在这里插入图片描述
将其修改为:
在这里插入图片描述
然后就可以make all编译一遍就可以把who.c加入到内核中了,没有错误的话一般就代表成功了。

编写测试应用程序

由于我们进入的bochs模拟器中的路径为其root路径,所以为其方便性将其程序编写在root路径下,再此之前需要先sudo ./mount-hdc 挂载,然后就可以通过hdc进入bochs中的root中了,其函数如下:
iam.c

// iam.c的
#define __LIBRARY__ //必须加
#include <unistd.h> //必须加 __NR_iam 在里面72调用号_syscall1(int,iam,const char*,name);//声明iam函数 call后面的数表示有几个参数//argc是读入参数个数
//argv指针数组是 argv[0]是文件名字符串 之后的1 2 3就是你依次输入
//依次输入的字符串了 详情解析可以去百度或者csdn 搜一下
//因为我们运行的时候是需要把字符串读进去的
// ./iam lizhijun 相等于把后面的字符串作为参数给进去了 argv[1]表示的就是那个字符串的地址
int main(int argc,char* argv[])
{iam(argv[1]);return 0;
}

whoami.c的·

#define __LIBRARY__ //必须有
#include <unistd.h> //必须有
#include <stdio.h> //printf
#include <string.h> //memset_syscall2(int,whoami,char*,pos,unsigned int,size);//声明whoami函数int main(int argc,char* argv[])
{char tempstr[24];//用户区字符地址memset(tempstr,'\0',sizeof(tempstr));//初始化whoami(tempstr,24);//调用函数printf("%s\n",tempstr);//输出 此时位于用户层return 0;
}

然后将其在bochs上利用gcc -o xxx xxx.c编译之后,就可以测试数据了
在这里插入图片描述
同时将testlab2.c 和testlab2.sh文件加入bochs模拟器中的usr/root中去便可以测试自己的分数了,可以自己到蓝桥实验楼那下载数据,只要自己创建一个Code文件夹,然后将所需文件加入那里,然后在下载文件那点击下载即可。编译完testlab2.c 文件后,测试:
在这里插入图片描述
其中testlab2代表测试的是内核函数,满分50%,testlab2.sh测试的是应用程序满分30%,有点遗憾自己并未得到满分,也确实不知道自己那里错了。但是为了接下来的实验,自己也就这样过了。

这篇关于哈工大操作系统lab2(添加系统调用)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/581524

相关文章

基于Python实现一个简单的题库与在线考试系统

《基于Python实现一个简单的题库与在线考试系统》在当今信息化教育时代,在线学习与考试系统已成为教育技术领域的重要组成部分,本文就来介绍一下如何使用Python和PyQt5框架开发一个名为白泽题库系... 目录概述功能特点界面展示系统架构设计类结构图Excel题库填写格式模板题库题目填写格式表核心数据结构

Linux系统中的firewall-offline-cmd详解(收藏版)

《Linux系统中的firewall-offline-cmd详解(收藏版)》firewall-offline-cmd是firewalld的一个命令行工具,专门设计用于在没有运行firewalld服务的... 目录主要用途基本语法选项1. 状态管理2. 区域管理3. 服务管理4. 端口管理5. ICMP 阻断

Java调用C#动态库的三种方法详解

《Java调用C#动态库的三种方法详解》在这个多语言编程的时代,Java和C#就像两位才华横溢的舞者,各自在不同的舞台上展现着独特的魅力,然而,当它们携手合作时,又会碰撞出怎样绚丽的火花呢?今天,我们... 目录方法1:C++/CLI搭建桥梁——Java ↔ C# 的“翻译官”步骤1:创建C#类库(.NET

Windows 系统下 Nginx 的配置步骤详解

《Windows系统下Nginx的配置步骤详解》Nginx是一款功能强大的软件,在互联网领域有广泛应用,简单来说,它就像一个聪明的交通指挥员,能让网站运行得更高效、更稳定,:本文主要介绍W... 目录一、为什么要用 Nginx二、Windows 系统下 Nginx 的配置步骤1. 下载 Nginx2. 解压

如何确定哪些软件是Mac系统自带的? Mac系统内置应用查看技巧

《如何确定哪些软件是Mac系统自带的?Mac系统内置应用查看技巧》如何确定哪些软件是Mac系统自带的?mac系统中有很多自带的应用,想要看看哪些是系统自带,该怎么查看呢?下面我们就来看看Mac系统内... 在MAC电脑上,可以使用以下方法来确定哪些软件是系统自带的:1.应用程序文件夹打开应用程序文件夹

windows系统上如何进行maven安装和配置方式

《windows系统上如何进行maven安装和配置方式》:本文主要介绍windows系统上如何进行maven安装和配置方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不... 目录1. Maven 简介2. maven的下载与安装2.1 下载 Maven2.2 Maven安装2.

C/C++和OpenCV实现调用摄像头

《C/C++和OpenCV实现调用摄像头》本文主要介绍了C/C++和OpenCV实现调用摄像头,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一... 目录准备工作1. 打开摄像头2. 读取视频帧3. 显示视频帧4. 释放资源5. 获取和设置摄像头属性

使用Python实现Windows系统垃圾清理

《使用Python实现Windows系统垃圾清理》Windows自带的磁盘清理工具功能有限,无法深度清理各类垃圾文件,所以本文为大家介绍了如何使用Python+PyQt5开发一个Windows系统垃圾... 目录一、开发背景与工具概述1.1 为什么需要专业清理工具1.2 工具设计理念二、工具核心功能解析2.

Linux系统之stress-ng测压工具的使用

《Linux系统之stress-ng测压工具的使用》:本文主要介绍Linux系统之stress-ng测压工具的使用,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录一、理论1.stress工具简介与安装2.语法及参数3.具体安装二、实验1.运行8 cpu, 4 fo

使用Python实现调用API获取图片存储到本地的方法

《使用Python实现调用API获取图片存储到本地的方法》开发一个自动化工具,用于从JSON数据源中提取图像ID,通过调用指定API获取未经压缩的原始图像文件,并确保下载结果与Postman等工具直接... 目录使用python实现调用API获取图片存储到本地1、项目概述2、核心功能3、环境准备4、代码实现