MIT6.828LAB4 (4)

LAB3_Part C: Preemptive Multitasking and Inter-Process communication (IPC)

文章目录

  • LAB3_Part C: Preemptive Multitasking and Inter-Process communication (IPC)
  • 前言
  • 练习13
  • 练习14
  • 练习15
  • 总结


前言

记录一下自己的学习过程
实验内容翻译:
https://gitee.com/cherrydance/mit6.828
该翻译仅供参考

练习13

修改 kern/trapentry.S 和 kern/trap.c,初始化 IDT 中相应的条目,并为 IRQ 0 到 15 提供处理程序。然后,在 kern/env.c 中的 env_alloc() 函数中修改代码,确保用户环境始终以启用中断的方式运行。
同时取消注释 sched_halt() 函数中的 sti 指令,以便空闲的 CPU 解除中断屏蔽。
处理器在调用硬件中断处理程序时不会推送错误代码。您可能希望此时重新阅读 80386 参考手册的第 9.2 节,或者 IA-32 Intel 架构软件开发者手册第 3 卷的第 5.8 节。
完成此练习后,如果您使用任何运行时间较长的测试程序(例如 spin)运行内核,您应该会看到内核打印出硬件中断的陷阱帧。虽然处理器现在启用了中断,但 JOS 还没有处理它们,所以您应该会看到它错误地将每个中断归属于当前正在运行的用户环境并将其销毁。最终,它将用尽环境并进入监视器模式。

先查看inc/trap.h,里面给出了需要设置的IRQ。

#define IRQ_OFFSET	32	// IRQ 0 corresponds to int IRQ_OFFSET
// Hardware IRQ numbers. We receive these as (IRQ_OFFSET+IRQ_WHATEVER)
#define IRQ_TIMER        0
#define IRQ_KBD          1
#define IRQ_SERIAL       4
#define IRQ_SPURIOUS     7
#define IRQ_IDE         14
#define IRQ_ERROR       19

在kern/trapentry.S中设置

TRAPHANDLER_NOEC(irq_timer, IRQ_OFFSET + IRQ_TIMER)
TRAPHANDLER_NOEC(irq_kbd, IRQ_OFFSET + IRQ_KBD)
TRAPHANDLER_NOEC(irq_serial, IRQ_OFFSET + IRQ_SERIAL)
TRAPHANDLER_NOEC(irq_spurious, IRQ_OFFSET + IRQ_SPURIOUS)
TRAPHANDLER_NOEC(irq_ide, IRQ_OFFSET + IRQ_IDE)
TRAPHANDLER_NOEC(irq_error, IRQ_OFFSET + IRQ_ERROR)

在kern/trap.c中加入函数声明

void irq_timer();
void irq_kbd();
void irq_serial();
void irq_spurious();
void irq_ide();
void irq_error();

然后在idt中注册

SETGATE(idt[IRQ_OFFSET + IRQ_TIMER], 0, GD_KT, irq_timer, 0);
SETGATE(idt[IRQ_OFFSET + IRQ_KBD], 0, GD_KT, irq_kbd, 0);
SETGATE(idt[IRQ_OFFSET + IRQ_SERIAL], 0, GD_KT, irq_serial, 0);
SETGATE(idt[IRQ_OFFSET + IRQ_SPURIOUS], 0, GD_KT, irq_spurious, 0);
SETGATE(idt[IRQ_OFFSET + IRQ_IDE], 0, GD_KT, irq_ide, 0);
SETGATE(idt[IRQ_OFFSET + IRQ_ERROR], 0, GD_KT, irq_error, 0);

在inc/mmu.c中我们可以得到#define FL_IF 0x00000200 // Interrupt Flag因此我们在env_alloc中设置启用中断 e->env_tf.tf_eflags |= FL_IF;最后注释掉sched_halt() 函数中的 sti 指令。

练习14

修改内核的 trap_dispatch() 函数,使其在发生时钟中断时调用 sched_yield() 来查找并运行另一个环境。
现在,您应该能够使 user/spin 测试正常工作:父环境应该派生出子环境,对其使用 sys_yield() 函数几次,但在每次时间片后都能重新获得 CPU 的控制权,最后杀死子环境并正常终止。

先判断是否是时间中断,然后使用lapic_eoi确认中断,用sched_yield运行一个新环境。

	if (tf->tf_trapno == IRQ_OFFSET + IRQ_TIMER){
		lapic_eoi();
		sched_yield();
		return;
	}

实验结果如图:
在这里插入图片描述

练习15

在 kern/syscall.c 中实现 sys_ipc_recv 和 sys_ipc_try_send。在实现之前,请阅读它们的注释,因为它们需要一起工作。在这些例程中调用 envid2env 时,应将 checkperm 标志设置为 0,表示允许任何环境向任何其他环境发送 IPC 消息,并且内核除了验证目标 envid 是否有效外,不进行特殊的权限检查。
然后在 lib/ipc.c 中实现 ipc_recv 和 ipc_send 函数。
使用 user/pingpong 和 user/primes 函数来测试您的 IPC 机制。user/primes 会生成每个素数一个新的环境,直到 JOS 用尽环境为止。您可能会发现阅读 user/primes.c 很有趣,以了解其背后的分支和 IPC 过程。

sys_ipc_recv函数:
阻塞,直到接收一个值。其实就是所谓的缺少资源放弃cpu进入阻塞队列,直到资源准备好进入就绪队列,而后获得cpu运行。

1,判断dstva是否小于UTOP且业对齐
2,使用 struct Env 的 env_ipc_recving 和 env_ipc_dstva 字段记录您希望接收的信息,将自己标记为不可运行,然后放弃 CPU。

代码如下

	if((uint32_t)dstva < UTOP && PGOFF(dstva)){
		return -E_INVAL;
	}
	curenv->env_ipc_recving = true;
	curenv->env_ipc_dstva = dstva;
	curenv->env_status = ENV_NOT_RUNNABLE;
	sys_yield();

sys_ipc_try_send函数:
尝试将 ‘value’ 发送到目标环境 ‘envid’。

1,获取目标环境并判断该环境是否在等待接收信息
2,判断srcva是否是要映射一个页面
3,对相关参数进行合法性检查
4,获取要映射的页内容,插入到目标环境
5,更新目标的ipc字段

代码如下:

	struct Env *renv = NULL;
	if(envid2env(envid, &renv, 0) < 0){
		return -E_BAD_ENV;
	}
	if(!renv->env_ipc_recving){
		return -E_IPC_NOT_RECV;
	}
	if((uint32_t)srcva < UTOP){
		if(PGOFF(srcva)){
			return -E_INVAL;
		}
		if(!(perm & PTE_P) || !(perm & PTE_P)){
			return -E_INVAL;
		}
		if (perm & (~PTE_SYSCALL)){
			return -E_INVAL;
		}
		pte_t *src_pte;
		struct PageInfo *src_page = page_lookup(curenv->env_pgdir, srcva, &src_pte);
		if(!src_page){
			return -E_INVAL;
		}
		if((perm & PTE_W) && !(*src_pte & PTE_W)){
			return -E_INVAL;
		}
		if((uint32_t)renv->env_ipc_dstva < UTOP){
			if(page_insert(renv->env_pgdir, src_page, renv->env_ipc_dstva, perm) < 0){
				return -E_NO_MEM;
			}
		}
		renv->env_ipc_perm = perm;
	}
    renv->env_ipc_recving = 0; // 获得数据后 取消接受ing状态
    renv->env_ipc_value = value;
    renv->env_status = ENV_RUNNABLE;
    renv->env_ipc_from = curenv->env_id;
    renv->env_tf.tf_regs.reg_eax = 0;//参数为0
	return 0;

ipc_rev函数:
通过ipc接收一个值并返回它

1,如果pg为空,向 sys_ipc_recv 传递一个特殊的值,表示“没有页面”。
2,如果 from_env_store 非空,则将 IPC 发送方的 envid 存储在 *from_env_store 中,如果 perm_store 非空,则将 IPC 发送方的页面权限存储在 *perm_store 中。
3,如果系统调用失败,则将 0 存储在 *fromenv 和 *perm 中(如果它们非空),然后返回错误。
否则,返回发送方发送的值。

代码如下:

	if(!pg){
		pg = (void *)UTOP;
	}
	size_t ret = sys_ipc_recv(pg);
	if(ret < 0){
		if(from_env_store){
			*from_env_store = 0;
		}
		if(perm_store){
			*perm_store = 0;
		}
		return ret;
	}else{
		if(from_env_store){
			*from_env_store = thisenv->env_ipc_from;
		}
		if(perm_store){
			*perm_store = thisenv->env_ipc_perm;
		}
		return thisenv->env_ipc_value;
	}

ipc_send函数:
将 ‘val’(如果 ‘pg’ 非空,则包括 ‘pg’ 和 ‘perm’)发送给 ‘toenv’。
该函数会一直尝试直到成功为止。

1,pg为空,则给予特殊值表示没有页面
2,循环调用sys_ipc_try_send函数,直至成功或出现特殊错误
3,是要sys_yield()防止一直占用cpu

代码如下:

	if(!pg){
		pg = (void *)UTOP;
	}
	size_t ret;
	while(1){
		ret = sys_ipc_try_send(to_env, val, pg, perm);
		if(ret == -E_IPC_NOT_RECV){
			sys_yield();
		}else{
			break;
		}
	}
	if(ret != 0){
        panic("ipc_send Error: %e", ret);
    }

运行结果:
在这里插入图片描述

总结

完成了lab4的所有部分!!!!!
该部分为了防止cpu独占实现了时钟中断,还实现了最基本的进程间通信。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/447737.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Python 导入Excel三维坐标数据 生成三维曲面地形图(体) 5-3、线条平滑曲面且可通过面观察柱体变化(三)

环境 python:python-3.12.0-amd64 包: matplotlib 3.8.2 pandas 2.1.4 openpyxl 3.1.2 scipy 1.12.0 import pandas as pd import matplotlib.pyplot as plt from mpl_toolkits.mplot3d import Axes3D from scipy.interpolate import griddata from matplotlib.c…

Vue-Router路由介绍和使用

vue属于单页面应用&#xff0c;路由就是根据浏览器路径不同&#xff0c;用不同的试图组件替换这个页面内容 开启路由功能 如图在创建项目时候勾选rouler 这样创建好的项目就有路由功能 下一步 不同的访问路径 展示不同的页面内容 路由配置 路由连接组件 浏览器会解析为超链接 …

OpenCV开发笔记(七十六):相机标定(一):识别棋盘并绘制角点

若该文为原创文章&#xff0c;转载请注明原文出处 本文章博客地址&#xff1a;https://blog.csdn.net/qq21497936/article/details/136535848 各位读者&#xff0c;知识无穷而人力有穷&#xff0c;要么改需求&#xff0c;要么找专业人士&#xff0c;要么自己研究 红胖子(红模仿…

爬虫练习:获取某网站的房价信息

一、相关网站 二、相关代码 import requests from lxml import etree import csv with open(房天下数据.csv, w, newline, encodingutf-8) as csvfile:fieldnames [名称, 地点,价格,总价,联系电话]writer csv.DictWriter(csvfile, fieldnamesfieldnames)writer.writeheader…

MySQL临时表创建出错(OS errno 13 - Permission denied)

一个客户向我抱怨&#xff1a;在MySQL查询小表没有问题&#xff0c;查询大表出错&#xff0c;下面是他发给我的出错的部分截屏&#xff08;客户的表名被我隐藏了&#xff09;。 这里的给出的信息已经比较明显了&#xff0c;是向/tmp目录中创建临时表失败&#xff08;临时表的路…

在用Java写算法的时候如何加快读写速度

对于解决该方法我们一般如下操作&#xff0c;不需要知道为什么&#xff0c;有模板&#xff08;个人观点&#xff09; 使用BufferedReader代替Scanner&#xff1a;Scanner类在读取大量输入时性能较差&#xff0c;而BufferedReader具有更高的读取速度。可以使用BufferedReader的r…

B端系统:漂亮就行。扯淡,漂亮仅占五分之一!

Hi&#xff0c;我是贝格前端工场&#xff0c;接触N多B端系统&#xff0c;也优化升级过N多。在这个过程中&#xff0c;仅仅美观是不够的&#xff0c;所以我拓展出来的B端系统五度评价指标&#xff0c;本篇着重讲易用性指标&#xff0c;欢迎老铁们评论点赞转发&#xff0c;有需求…

安卓studio安装

安卓studio安装 2024.3.11官网的版本&#xff08;有些翻墙步骤下载东西也解决了&#xff09; 这次写的略有草率&#xff0c;后面会更新布局的&#xff0c;因为截图量太大了&#xff0c;有需要的小伙伴可以试着接受一下哈哈哈哈 !(https://gitee.com/jiuzheyangbawjf/img/raw/ma…

Node.Js编码注意事项

Node.js 中不能使用 BOM 和 DOM 的 API&#xff0c;可以使用 console 和定时器 APINode.js 中的顶级对象为 global&#xff0c;也可以用 globalThis 访问顶级对象 浏览器端js的组成 Node.js中的JavaScript组成 相比较之下发现只有console与定时器是两个API所共有的&#xff…

【CLIP综述】CLIP在医学影像中的应用(二)

原文传递&#xff1a;CLIP in Medical Imaging: A Comprehensive Survey 其他综述篇&#xff1a;   【SAM综述】医学图像分割的分割一切模型&#xff1a;当前应用和未来方向   【CLIP综述】CLIP在医学影像中的应用&#xff08;一&#xff09; 4、基于CLIP的应用&#xff08…

OD_2024_C卷_200分_10、部门人力分配【JAVA】【二分法 + 双指针】

说明 输入数据两行&#xff0c;第一行输入数据3表示开发时间要求&#xff0c;第二行输入数据表示需求工作量大小&#xff0c;输出数据一行&#xff0c;表示部门人力需求。当选择人力为6时&#xff0c;2个需求量为3的工作可以在1个月里完成&#xff0c;其他2个工作各需要1个月完…

​​​​​​​ARCGIS API for Python进行城市区域提取

ArcGIS API for Python主要用于Web端的扩展和开发&#xff0c;提供简单易用、功能强大的Python库&#xff0c;以及大数据分析能力&#xff0c;可轻松实现实时数据、栅格数据、空间数据等多源数据的接入和GIS分析、可视化&#xff0c;同时提供对平台的空间数据管理和组织管理功能…

Visual C++ 2005 可以生成清单信息了

在 Visual C 2005 中&#xff0c;我们可以通过 #pragma 指令来生成你想要的清单信息&#xff0c;这项功能可以简化新版本通用控件的使用。 例如&#xff0c;下面的代码可以指示链接器&#xff0c;将通用控件的新版本(6.0.0.0)链接到应用程序中。 // do not use – see discussi…

01 数据结构引入 和 顺序表

阅读引言&#xff1a; 从本文开始给大家带来我在复习过程中写的数据结构的代码&#xff0c; 分享给需要的同学 一、数据结构引入 1.数据结构解决什么问题 数据结构可以将杂乱无章的数据管理起来&#xff0c; 提高数据的访问效率 计算机处理的对象&#xff08;数据&#xff09…

2022 年广西职业院校技能大赛高职组《云计算》赛项赛卷

#需要资源或有问题的&#xff0c;可私博主&#xff01;&#xff01;&#xff01; #需要资源或有问题的&#xff0c;可私博主&#xff01;&#xff01;&#xff01; #需要资源或有问题的&#xff0c;可私博主&#xff01;&#xff01;&#xff01; 某企业拟使用 OpenStack 搭建一…

YOLOv8独家改进:backbone改进 | 最新大卷积核CNN架构UniRepLKNet,ImageNet 88% | CVPR2024

💡💡💡本文独家改进:大核卷积一统多种模态!RepLK正统续作UniRepLKNet,代替YOLOv8 Backbone 改进结构图如下: 收录 YOLOv8原创自研 https://blog.csdn.net/m0_63774211/category_12511737.html?spm=1001.2014.3001.5482 💡💡💡全网独家首发创新(原创),适…

基于智慧灯杆的智慧城市解决方案(2)

功能规划 智慧照明功能 智慧路灯的基本功能仍然是道路照明, 因此对照明功能的智慧化提升是最基本的一项要求。 对道路照明管理进行智慧化提升, 实施智慧照明, 必然将成为智慧城市中道路照明发展的主要方向之一。 智慧照明是集计算机网络技术、 通信技术、 控制技术、 数据…

WordPress高端后台美化WP Adminify Pro优化版

后台UI美化WP Adminify Pro修改自定义插件&#xff0c;适合建站公司和个人使用&#xff0c;非常高大上&#xff0c;下载地址&#xff1a;WP Adminify Pro优化版 修复记录&#xff1a; 1、修复已知BUG 2、修复手机版兼容问题 3、修复打开速度&#xff0c;原版打开速度太慢 4…

华为数通方向HCIP-DataCom H12-821题库(多选题:121-140)

第121题 以下哪些事件会导致IS-IS产生一个新的LSP? A、引入的IP路由发送变化 B、周期性更新 C、接口开销发生了变化 D、邻接Up或Down 【参考答案】ABCD 【答案解析】 第122题 以下哪些协议既支持网络配置管理又支持网络监控管理? A、Telemetry B、NETCONF C、SNMP D、LLDP …

STM32CubeIDE基础学习-STM32CubeIDE软件偏好设置

STM32CubeIDE基础学习-STM32CubeIDE软件偏好设置 文章目录 STM32CubeIDE基础学习-STM32CubeIDE软件偏好设置前言第1章 设置字体颜色第2章 设置字体大小第3章 设置代码区背景颜色总结 前言 编程软件环境最好就设置一个自己喜欢的界面进行显示&#xff0c;这样看起来会比较舒服些…