操作系统概念第三章作业

题目一

使用下图所示的程序,说明 LINE A 的输出是什么。为什么?

#include < sys/types.h >
#include < stdio.h >
#include <unistd.h >
int value =5;
int main()
{
	pid_t pid;
	pid = fork();
	if(pid == 0)
	{
		value += 15;
	}
	else if(pid > 0)
	{
		wait(NULL);
		printf("PARENT: value = %d", value );/*LINE A*/
		exit();
	}
}

答:
LINE A输出为PARENT:value = 5
该程序调用fork()函数创建一个新的运行子进程,该子进程除了PID与父进程不同之外,几乎完全与父进程相同,两者拥有相同却独立的地址空间(即父进程和子进程对value做出的任何改变都不受彼此的影响)。当执行pid = fork()返回时,父进程value为5,子进程value值为20;因为在子进程中fork的返回值为0,父进程中fork的返回值是子进程的pid(即一个非负整数)。故LINE A会输出原来value的值

题目二

下面设计的优点和缺点分别是什么? 分别从操作系统层面和用户层面来阐述。

• 同步和异步通信
• 自动和显式缓冲
• 复制传送和引用传送
• 固定大小和可变大小消息
答:
同步和异步通信: 同步的话,对于发送进程阻塞,直到消息被接收进程或邮箱所接收;对于接收进程阻塞,直到收到一个有效消息或空消息;使用同步通信的设计则无需再关心生产者——消费者问题,但是使用异步通信的话,可以提高系统的效率
自动或显式缓冲: 自动缓冲提供了一个无限长度的队列,从而保证了发送者在复制消息时不会遇到阻塞,如何提供自动缓存的规范,一个方案也许能保存足够大的内存,但许多内存被浪费缓存明确指定缓存区的大小。在这种状况下,发送者不能在等待可用空间队列中被阻塞。然而缓冲明确的内存不太可能被浪费。
复制发送和引用发送: 复制发送不允许接收者改变参数的状态,引用发送是允许的。引用发送允许的优点之一是它允许程序员写一个分布式版本的一个集中的应用程序。如,Java’s RMI公司提供两种发送,但引用传递一个参数需要声明这个参数是一个远程对象。
固定大小和可变大小消息: 如果只能发送定长消息,那么系统级的实现十分简单,但是,却使变成任务变得更加困难;相反的是,可变大小消息要求更复杂的系统级实现,但是编程任务变得简单。

题目三

Fibonacci 序列是一组数: 0 , 1, 1, 2, 3, 5, 8,…,通常它可以表示为:
f i b 0 = 0 , f i b 1 = 1 , f i b n = f i b n − 1 + f i b n − 2 fib_0=0,fib_1=1,fib_n=fib_{n-1}+fib_{n-2} fib0=0,fib1=1,fibn=fibn1+fibn2
使用系统调用 fork() 编写一个 C 程序,使其在子程序中生成 Fibonacci 序列,序列的号码将在命令行中提供。例如,如果提供的是 5,Fibonacci 序列中的前 5 个数将由子进程输出。退出程序前,父进程调用 wait() 调用来等待子进程结束。执行必要的错误检查以保证不会接受命令行传递来的负数号码。
答:

#include <sys/types.h>
#include <stdio.h>
#include <unistd.h>
int main(int argc,char* argv[])
{
	pid_t pid;
	int i;
	int input;
	scanf("%d", &input);
	int f0,f1,f2;
	f0=0;
	f1=1;
	pid=fork();
	if(pid<0){
		printf("We need a nun-negative number");
		exit(-1);
	}
	else if(pid == 0)
	{
		printf("the number We input is %d\n",input);
		printf("0 1 ");
		for(i=2;i<input;i++){
			f2=f0+f1;
			f0=f1;
			f1=f2;
			printf("%d ",f2);
		}
	}
	else{
		wait(NULL);
		printf("end\n");
	}
	return 0;
}

在Linux环境下运行得到如下结果
在这里插入图片描述

题目四

请检索文献了解某一特定操作系统(如 Solaris,Windows 等)所提供的进程状态及其可能的状态转换关系,并与基本的进程状态转换图进行比较。
答:
Linux的进程状态转换图
基本的进程状态转换图
进程状态转换

  • 新的状态: 表示进程正在被创建。
  • 运行状态: 当进程正在被CPU执行,可以是在内核态或用户态运行。
  • 就绪状态: 当系统资源已经可用时,进程就被唤醒而进入准备运行状态或已经准备就绪随时可由调度程序执行。操作系统通过调派算法分派,将就绪状态的进程切换为运行状态。
  • 等待状态: 进程等待某个事件的发生(如I/O完成或收到信号),对应于Linux进程的可中断/不可中断睡眠状态、暂停状态都需要先经过Linux的就绪状态才能到内核态运行。
  • 终止状态: 当进程完成执行时。Linux下的僵死进程是进程已经终止运行,但是父进程还没有询问其状态的情况。
    Linux中的进程状态转换
    TASK_RUNNING(可执行状态): 操作系统概念一书中将正在CPU上执行的进程定义为RUNNING状态、而将可执行但是尚未被调度执行的进程定义为READY状态,这两种状态在linux下统一为 TASK_RUNNING状态
    TASK_INTERRUPTIBLE(可中断睡眠状态): 一般情况下,进程列表中的绝大多数进程都处于TASK_INTERRUPTIBLE状态。当有事件发生时(由外部中断触发、或由其他进程触发),对应的等待队列中的一个或多个进程将被唤醒。
    TASK_UNINTERRUPTIBLE(不可中断睡眠状态): 与TASK_INTERRUPTIBLE状态类似,TASK_UNINTERRUPTIBLE状态为睡眠状态,但是此刻进程是不可中断的。不可中断,指的并不是CPU不响应外部硬件的中断,而是指进程不响应异步信号。处于该状态的进程只有被wake_up函数明确唤醒后才能转换到可运行的就绪态。
    TASK_STOPPED(暂停状态): 当进程收到信号SIGSTOP、SIGTSTP、SIGTTIN或SIGTTOU时就会进入TASK_STOPPED。可向其发送SIGCONT信号让进程转换到可运行状态。在Linux 0.11中,还未实现对该状态的转换处理。处于该状态的进程将被作为进程终止来处理。
    TASK_ZOMBIE(僵死状态): 当进程已停止运行,但其父进程还没有询问其状态时,则称该进程处于TASK_ZOMBIE
    当一个进程的运行时间片用完,系统就会使用调度程序强制切换到其它的进程去执行。另外,如果进程在内核态执行时需要等待系统的某个资源,此时该进程就会调用sleep_on()或sleep_on_interruptible()自愿地放弃CPU的使用权,而让调度程序去执行其它进程。进程则进入睡眠状态。
    只有当进程从“内核运行态”转移到“睡眠状态”时,内核才会进行进程切换操作。在内核态下运行的进程不能被其它进程抢占,而且一个进程不能改变另一个进程的状态。为了避免进程切换时造成内核数据错误,内核在执行临界区代码时会禁止一切中断。

题目五

请详细描述上下文的切换过程,并谈谈你对上下文切换的作用理解
答:

  • 上下文切换 是指,将CPU切换到另一个进程需要保存当前进程的状态并恢复另一个进程的状态。上下文就是内核重新启动一个被抢占的进程所需的状态。进程的上下文用进程的PCB(PCB属于操作系统的内核空间而不属于进程)表示,包括CPU寄存器的值、进程状态和内存管理信息等。进程在进行上下文切换时,需要保存的信息包括PC寄存器的值、CPU寄存器的值和堆栈指针,而不包括全局变量和局部变量
  • 上下文的切换过程: 首先保存当前运行在CPU中的任务的上下文(CPU寄存器和程序计数器)保存起来,然后加载新任务的上下文到这些CPU中的寄存器和程序计数器,最后再跳转到程序计数器所指的新位置,运行新任务;其中,保存的上下文,会存储在系统内核中,并在任务重新调度执行时再次加载进来。
  • 上下文切换的作用:
    当某一进程在系统资源不足、某个进程的时间片耗尽、进程通过睡眠函数sleep将自己主动挂起、发生硬件中断导致CPU上的进程被中断挂起,转而执行内核中的中断服务程序、出现优先级更高的进程运行时,当前进程均会被挂起。这时候上下文切换可以保证任务原来的状态不受影响,让任务看起来是连续运行的;同时,上下文切换提高了CPU的工作效率。

题目六

请简述你对进程的理解,并分析进程与程序的区别和联系。
答:

  • 进程的概念:
    进程是计算机中已运行程序的实体,一个进程就是一个运行中的程序,每个进程在操作系统内用**进程控制块(PCB)来表示,它包含了有关特定进程的信息,如进程状态、进程编号、程序计数器、寄存器、内存界限、打开文件列表等
    进程是具有独立功能的程序关于某个数据集合上的一次运行活动,是系统进行资源分配和调度的独立单位。它又被称为任务。它的特点是:它是程序的一次执行过程;是正在运行程序的抽象;将一个CPU变换成多个虚拟的CPU;系统资源以进程为单位分配,如内存、文件等;每一个进程都具有独立的地址空间。
  • 进程与程序之间的区别和联系: 程序是一堆代码和数据;它可以作为目标模块存在于磁盘上,或者作为段存在于地址空间中。进程是执行中的程序的一个具体实例;程序总是运行在某个进程的上下文中。
参考网址

Linux进程的状态转换图
Linux进程状态解析

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值