|
|
|
@ -0,0 +1,396 @@
|
|
|
|
|
实验五存储管理
|
|
|
|
|
#include <stdio.h>
|
|
|
|
|
#include <stdlib.h>
|
|
|
|
|
#include <malloc.h>
|
|
|
|
|
#include <time.h>
|
|
|
|
|
#define LEN sizeof(MEMORY_BLOCK)
|
|
|
|
|
#define NUM 5
|
|
|
|
|
struct MEMORY_BLOCK
|
|
|
|
|
{
|
|
|
|
|
int name;
|
|
|
|
|
int address;
|
|
|
|
|
int length;
|
|
|
|
|
int flag;
|
|
|
|
|
struct MEMORY_BLOCK *next;
|
|
|
|
|
};
|
|
|
|
|
typedef struct MEMORY_BLOCK MEMORY_BLOCK;
|
|
|
|
|
void allocation(MEMORY_BLOCK *Header,int name,int length_p);
|
|
|
|
|
void reclaim(int processname, MEMORY_BLOCK *Header);
|
|
|
|
|
void main()
|
|
|
|
|
{
|
|
|
|
|
|
|
|
|
|
int length_p,i;
|
|
|
|
|
int processname;
|
|
|
|
|
MEMORY_BLOCK *Header,*t;
|
|
|
|
|
Header=(MEMORY_BLOCK*)malloc(LEN);//初始化存储空间
|
|
|
|
|
Header->name=-1;
|
|
|
|
|
Header->address=0;
|
|
|
|
|
Header->length=100;
|
|
|
|
|
Header->flag=0;
|
|
|
|
|
Header->next=NULL;
|
|
|
|
|
srand((int)time(0));
|
|
|
|
|
for(i=1;i<=NUM;i++)
|
|
|
|
|
{
|
|
|
|
|
length_p=rand()%20+1; //随机产生进程所需存储空间,至少为1;
|
|
|
|
|
allocation(Header,i,length_p);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
printf("内存分配情况: \n");
|
|
|
|
|
t=Header;
|
|
|
|
|
while(t!=NULL)
|
|
|
|
|
{
|
|
|
|
|
printf("process name %d, address=%d, length=%d,flag=%d\n",t->name,t->address,t->length,t->flag);
|
|
|
|
|
t=t->next;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
printf("请输入回收的进程号(输入0结束):\n");
|
|
|
|
|
scanf("%d",&processname);
|
|
|
|
|
while(processname!=0)
|
|
|
|
|
{
|
|
|
|
|
|
|
|
|
|
printf("回收 process name %d\n",processname);
|
|
|
|
|
reclaim(processname,Header);
|
|
|
|
|
t=Header;
|
|
|
|
|
while(t!=0)
|
|
|
|
|
{
|
|
|
|
|
printf("process name %d, address=%d, length=%d,flag=%d\n",t->name,t->address,t->length,t->flag);
|
|
|
|
|
t=t->next;
|
|
|
|
|
}
|
|
|
|
|
if (Header->next==NULL) break;
|
|
|
|
|
printf("请输入回收的进程号(输入0结束):\n");
|
|
|
|
|
scanf("%d",&processname);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
printf("当前内存分配情况:\n");
|
|
|
|
|
t=Header;
|
|
|
|
|
while(t!=0)
|
|
|
|
|
{
|
|
|
|
|
printf("process name %d, address=%d, length=%d,flag=%d\n",t->name,t->address,t->length,t->flag);
|
|
|
|
|
t=t->next;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void reclaim(int processname, MEMORY_BLOCK *Header)
|
|
|
|
|
{
|
|
|
|
|
MEMORY_BLOCK *temp,*t,*tt;
|
|
|
|
|
t=Header;
|
|
|
|
|
temp=t;
|
|
|
|
|
while(t->name!=processname)
|
|
|
|
|
{
|
|
|
|
|
temp=t;
|
|
|
|
|
t=t->next;
|
|
|
|
|
}
|
|
|
|
|
if(t->next!=NULL)//t非尾结点
|
|
|
|
|
if(temp->flag==0&&t->next->flag==0)//左右为空
|
|
|
|
|
{
|
|
|
|
|
temp->name=-1;
|
|
|
|
|
temp->length=temp->length+t->length+t->next->length;
|
|
|
|
|
tt=t->next;
|
|
|
|
|
temp->next=tt->next;
|
|
|
|
|
}
|
|
|
|
|
else if(temp->flag==0) //左为空
|
|
|
|
|
{
|
|
|
|
|
temp->name=-1;
|
|
|
|
|
temp->length=temp->length+t->length;
|
|
|
|
|
temp->next=t->next;
|
|
|
|
|
}
|
|
|
|
|
else if(t->next->flag==0) //右为空
|
|
|
|
|
{
|
|
|
|
|
t->length=t->length+t->next->length;
|
|
|
|
|
tt=t->next;
|
|
|
|
|
t->next=tt->next;
|
|
|
|
|
}
|
|
|
|
|
else // 左右不为空
|
|
|
|
|
{
|
|
|
|
|
t->name=-1;
|
|
|
|
|
t->flag=0
|
|
|
|
|
}
|
|
|
|
|
else//t是尾结点
|
|
|
|
|
{
|
|
|
|
|
if(temp->flag==0) //左为空
|
|
|
|
|
{
|
|
|
|
|
temp->length = temp->length + t->length;
|
|
|
|
|
temp->next = NULL;
|
|
|
|
|
free(t);
|
|
|
|
|
}
|
|
|
|
|
else // 左不为空
|
|
|
|
|
{
|
|
|
|
|
t->name=-1;
|
|
|
|
|
t->flag=0;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void allocation(MEMORY_BLOCK *Header,int name,int length_p)
|
|
|
|
|
{
|
|
|
|
|
MEMORY_BLOCK *temp,*t,*tt;
|
|
|
|
|
int minsize=2; //不可切割的分区阈值
|
|
|
|
|
t=Header;
|
|
|
|
|
while(t!=0)
|
|
|
|
|
{
|
|
|
|
|
if(t->length>length_p&&t->flag==0) break;
|
|
|
|
|
t=t->next;
|
|
|
|
|
}
|
|
|
|
|
if(t->length-length_p>minsize) //分割
|
|
|
|
|
{
|
|
|
|
|
temp=(MEMORY_BLOCK*)malloc(LEN);//temp=new MEMORY_BLOCK;
|
|
|
|
|
temp->name=-1;
|
|
|
|
|
temp->flag=0;
|
|
|
|
|
temp->length=t->length-length_p;
|
|
|
|
|
temp->address=t->address+length_p;
|
|
|
|
|
t->name=name;
|
|
|
|
|
t->flag=1;
|
|
|
|
|
t->length=length_p;
|
|
|
|
|
temp->next=t->next;
|
|
|
|
|
t->next=temp;
|
|
|
|
|
}
|
|
|
|
|
else //直接分配
|
|
|
|
|
{
|
|
|
|
|
t->name=name;
|
|
|
|
|
t->flag=1
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
实验三进程调度
|
|
|
|
|
#include <stdio.h>
|
|
|
|
|
#include <stdlib.h>
|
|
|
|
|
#include <malloc.h>
|
|
|
|
|
#include <time.h>
|
|
|
|
|
#define NUM 8
|
|
|
|
|
#define LEN sizeof(PCB)
|
|
|
|
|
struct PCB
|
|
|
|
|
{
|
|
|
|
|
int name;
|
|
|
|
|
int runtime;
|
|
|
|
|
int runedtime;
|
|
|
|
|
int killtime;
|
|
|
|
|
struct PCB *next;
|
|
|
|
|
};
|
|
|
|
|
typedef struct PCB PCB;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void main()
|
|
|
|
|
{
|
|
|
|
|
int timeslice=5;
|
|
|
|
|
PCB *runqueue;
|
|
|
|
|
PCB *top,*tail,*temp;
|
|
|
|
|
int i;
|
|
|
|
|
srand((int)time(0));
|
|
|
|
|
for(i=0;i<NUM;i++)
|
|
|
|
|
{
|
|
|
|
|
temp=(PCB*)malloc(LEN);
|
|
|
|
|
temp->name=i;
|
|
|
|
|
temp->runtime=rand()%15+1;
|
|
|
|
|
temp->runedtime=0;
|
|
|
|
|
temp->killtime=0;
|
|
|
|
|
temp->next=NULL;
|
|
|
|
|
if(i==0)
|
|
|
|
|
{
|
|
|
|
|
top=temp;
|
|
|
|
|
tail=temp;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
tail->next=temp;
|
|
|
|
|
tail=temp;
|
|
|
|
|
}
|
|
|
|
|
printf("START:process name %d, runtime=%d, runedtime=%d,killtime=%d\n",tail->name,tail->runtime,tail->runedtime,tail->killtime);
|
|
|
|
|
}
|
|
|
|
|
printf("******************************\n");
|
|
|
|
|
while(top!=NULL)
|
|
|
|
|
{
|
|
|
|
|
runqueue=top;
|
|
|
|
|
top=top->next;
|
|
|
|
|
runqueue->next=NULL;
|
|
|
|
|
runqueue->runtime=runqueue->runtime-timeslice;
|
|
|
|
|
if(runqueue->runtime<=0)
|
|
|
|
|
{
|
|
|
|
|
runqueue->killtime=runqueue->killtime+timeslice;
|
|
|
|
|
runqueue->runedtime=runqueue->runedtime+runqueue->killtime;
|
|
|
|
|
runqueue->runtime=0;
|
|
|
|
|
printf("process name %d, runtime=%d, runedtime=%d,killtime=%d...END...\n",runqueue->name,runqueue->runtime,runqueue->runedtime,runqueue->killtime);
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
runqueue->runedtime += timeslice;
|
|
|
|
|
runqueue->runtime -= timeslice;
|
|
|
|
|
printf("process name %d, runtime=%d, runedtime=%d,killtime=%d\n",runqueue->name,runqueue->runtime,runqueue->runedtime,runqueue->killtime);
|
|
|
|
|
if (tail != NULL)
|
|
|
|
|
{
|
|
|
|
|
tail->next = runqueue;
|
|
|
|
|
} else {
|
|
|
|
|
top = runqueue;
|
|
|
|
|
}
|
|
|
|
|
tail = runqueue;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
实验二进程控制下
|
|
|
|
|
|
|
|
|
|
#include<stdlib.h>
|
|
|
|
|
#include<unistd.h>
|
|
|
|
|
#include<sys/types.h>
|
|
|
|
|
#include<sys/wait.h>
|
|
|
|
|
#include<stdio.h>
|
|
|
|
|
int main()
|
|
|
|
|
{
|
|
|
|
|
int fpid,fpid2,cpid1,cpid2;
|
|
|
|
|
int status,i,j;
|
|
|
|
|
fpid=fork();
|
|
|
|
|
if(fpid<0)
|
|
|
|
|
{
|
|
|
|
|
perror("fork failed\n");
|
|
|
|
|
exit(0);
|
|
|
|
|
}
|
|
|
|
|
else if(fpid==0)
|
|
|
|
|
{
|
|
|
|
|
printf("I am son, my PID is %d, parent PID is %d\n",
|
|
|
|
|
getpid(),getppid());
|
|
|
|
|
printf("I am working\n");
|
|
|
|
|
sleep(1);
|
|
|
|
|
printf("I am done\n");
|
|
|
|
|
exit(4);
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
else if (fpid>0)
|
|
|
|
|
{
|
|
|
|
|
/* 创建第二个子进程(女儿) */
|
|
|
|
|
fpid2=fork();
|
|
|
|
|
if (fpid2==0)
|
|
|
|
|
{
|
|
|
|
|
// 女儿进程执行代码
|
|
|
|
|
printf("I am daughter, my PID is %d, parent PID is %d\n",
|
|
|
|
|
getpid(),getppid());
|
|
|
|
|
printf("I am working\n");
|
|
|
|
|
sleep(1);
|
|
|
|
|
printf("I am finished\n");
|
|
|
|
|
exit(5);
|
|
|
|
|
}
|
|
|
|
|
else if (fpid2<0)
|
|
|
|
|
{
|
|
|
|
|
perror("Second fork failed");
|
|
|
|
|
return 1;
|
|
|
|
|
}
|
|
|
|
|
else if(fpid2>0)
|
|
|
|
|
{/* 父进程执行代码 */
|
|
|
|
|
printf("I am father, my PID is %d, son PID is %d, daughter PID is %d\n",
|
|
|
|
|
getpid(),fpid,fpid2);
|
|
|
|
|
//WEXITSTATUS(status)可以得到调用程序的返回值
|
|
|
|
|
cpid1=wait(&status);
|
|
|
|
|
if(WIFEXITED(status))
|
|
|
|
|
i=WEXITSTATUS(status);
|
|
|
|
|
cpid2=wait(&status);
|
|
|
|
|
if(WIFEXITED(status))
|
|
|
|
|
j=WEXITSTATUS(status);
|
|
|
|
|
printf("Child %d exited with status %d\n",cpid1,i);
|
|
|
|
|
printf("Child %d exited with status %d\n", cpid2,j);
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
实验二上1
|
|
|
|
|
#include<stdlib.h>
|
|
|
|
|
#include<unistd.h>
|
|
|
|
|
#include<stdio.h>
|
|
|
|
|
#include <sys/wait.h>
|
|
|
|
|
#include <stdlib.h>
|
|
|
|
|
//-------begin---------
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
int main() {
|
|
|
|
|
pid_t son_pid, daughter_pid;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
son_pid = fork();
|
|
|
|
|
if (son_pid == 0) {
|
|
|
|
|
|
|
|
|
|
printf("I am son, my pid is %d, parent pid is %d\n", getpid(), getppid());
|
|
|
|
|
exit(0);
|
|
|
|
|
} else if (son_pid < 0) {
|
|
|
|
|
perror("fork failed");
|
|
|
|
|
exit(1);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
daughter_pid = fork();
|
|
|
|
|
if (daughter_pid == 0) {
|
|
|
|
|
|
|
|
|
|
printf("I am daughter, my pid is %d, parent pid is %d\n", getpid(), getppid());
|
|
|
|
|
exit(0);
|
|
|
|
|
} else if (daughter_pid < 0) {
|
|
|
|
|
perror("fork failed");
|
|
|
|
|
exit(1);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (son_pid > 0 || daughter_pid > 0) {
|
|
|
|
|
printf("I am father, my pid is %d, son's pid is %d, daughter's pid is %d\n",
|
|
|
|
|
getpid(), son_pid, daughter_pid);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2
|
|
|
|
|
|
|
|
|
|
#include <stdio.h>
|
|
|
|
|
#include <unistd.h>
|
|
|
|
|
#include <sys/types.h>
|
|
|
|
|
#include <sys/wait.h>
|
|
|
|
|
#include <stdlib.h>
|
|
|
|
|
|
|
|
|
|
int main() {
|
|
|
|
|
pid_t son_pid, daughter_pid;
|
|
|
|
|
|
|
|
|
|
// 创建儿子进程
|
|
|
|
|
son_pid = fork();
|
|
|
|
|
|
|
|
|
|
if (son_pid < 0) {
|
|
|
|
|
// 创建子进程失败
|
|
|
|
|
perror("Fork for son failed");
|
|
|
|
|
return 1;
|
|
|
|
|
} else if (son_pid == 0) {
|
|
|
|
|
// 儿子进程
|
|
|
|
|
printf("I am son, my PID is %d, my father's PID is %d. Executing 'ls'...\n", getpid(), getppid());
|
|
|
|
|
fflush(stdout);
|
|
|
|
|
execlp("ls", "ls", NULL);
|
|
|
|
|
// 如果exec调用失败,会执行到这里
|
|
|
|
|
perror("execlp for ls failed");
|
|
|
|
|
exit(EXIT_FAILURE);
|
|
|
|
|
} else {
|
|
|
|
|
// 创建女儿进程
|
|
|
|
|
daughter_pid = fork();
|
|
|
|
|
|
|
|
|
|
if (daughter_pid < 0) {
|
|
|
|
|
// 创建子进程失败
|
|
|
|
|
perror("Fork for daughter failed");
|
|
|
|
|
return 1;
|
|
|
|
|
} else if (daughter_pid == 0) {
|
|
|
|
|
// 女儿进程
|
|
|
|
|
printf("I am daughter, my PID is %d, my father's PID is %d. Executing 'pwd'...\n", getpid(), getppid());
|
|
|
|
|
fflush(stdout);
|
|
|
|
|
execlp("pwd", "pwd", NULL);
|
|
|
|
|
// 如果exec调用失败,会执行到这里
|
|
|
|
|
perror("execlp for pwd failed");
|
|
|
|
|
exit(EXIT_FAILURE);
|
|
|
|
|
} else {
|
|
|
|
|
// 父进程
|
|
|
|
|
printf("I am father, my PID is %d, my son's PID is %d, my daughter's PID is %d\n", getpid(), son_pid, daughter_pid);
|
|
|
|
|
fflush(stdout);
|
|
|
|
|
// 等待儿子进程结束
|
|
|
|
|
waitpid(son_pid, NULL, 0);
|
|
|
|
|
// 等待女儿进程结束
|
|
|
|
|
waitpid(daughter_pid, NULL, 0);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
|
}
|
|
|
|
|
|