进程控制模拟程序

实验目的:

1 理解操作系统内核与应用程序的差别,哪些信号和操作是操作系统内核能捕捉到而应用程序无法捕捉到的?可以用什么样的操作去代替?

2 理解操作系统如何完成进程的控制(创建、撤消、阻塞、唤醒)

3 理解操作系统是如何利用进程控制块来管理和控制进程的?

程序功能:

1 提供触发进程创建、撤销、阻塞、唤醒的界面和操作

2 完成进程的创建、撤销、阻塞、唤醒功能

3 界面能在每次操作后分别显示当前处于就绪态、阻塞态、运行态进程的状态、优先权、进程id

4 实现进程调度的模拟,用基于优先权的调度算法实现进程调度。

程序功能实现:

        通过界面选项选择进程创建、撤销、阻塞、唤醒操作。

        就绪队列,阻塞队列、运行队列通过全局变量的结构体指针实现。

        创建函数通过全局变量分配唯一进程ID,进程需要运行时间,优先级手动输入。时间片大小默认为5。


#include <stdio.h>
#include <stdlib.h>
#include<windows.h>

/*进程控制块结构体*/
struct task_struct
{
    int id; //进程id
    int state; //-1就绪, 0运行, >0 阻塞(本程序默认为1,不区分阻塞队列)
    int priority;   //优先级
    int needtime;  //运行完毕所需时间
    int arrivedtime;    //已运行时间
    int slicetime;      //时间片剩余时间,初始化为5
    struct task_struct* next;
};

/*进程队列*/
struct task_struct* runnableTask;   //运行
struct task_struct* unrunnableTask; //就绪
struct task_struct* stoppedTask;    //阻塞

//进程id控制,每次自增1
int id = 1;

/*函数名声明*/
void taskController();
void createTask();
void stopTask();
void awakeTask();
void runTask();
void showTask();
void scheduleTask();
void getBigPriorityTask();
void deleteTask();

int main()
{
    runnableTask = NULL;
    unrunnableTask = NULL;
    stoppedTask = NULL;
    printf("进程模拟\n");
    while(1)
    {
        taskController();
    }
    return 0;
}

/*
本函数模拟进程控制程序
本函数执行一次运行,当前执行进程时间片减一
本函数创建进程不占当前执行进程时间
*/

void taskController()
{
    char select;
    printf("本函数为进程控制函数\n");
    printf("    1.创建进程\n");
    printf("    2.阻塞当前进程\n");
    printf("    3.唤醒选定进程\n");
    printf("    4.撤销进程\n");
    printf("    5.无操作\n");
    printf("    6.退出\n");
    printf("\n请输入你的选择(1--6):");
    do
    {
        select=getchar();
    }
    while(select!='1'&&select!='2'&&select!='3'&&select!='4' &&select!='5' &&select!='6');
    switch(select)
    {
    case '1':
        createTask();
        break;
    case '2':
        stopTask();
        break;
    case '3':
        awakeTask();
        break;
    case '4':
        deleteTask();
        break;
    case '5':
        break;
    case '6':
        exit(0);
        break;
    default:
        return ;
    }
    runTask();
    showTask();
}

/*
创建进程,新创建进程添加到就绪进程队尾
*/
void   createTask()
{
    printf("\n\n\n\n创建进程开始\n");
    if(unrunnableTask == NULL)  //判断是否已有就绪进程 //判断是否为首指针
    {
        unrunnableTask = malloc(sizeof(struct task_struct));
        unrunnableTask->id = id++;
        printf("进程优先级:\n");
        scanf("%d",&unrunnableTask->priority);
        printf("进程运行需要的时间:\n");
        scanf("%d",&unrunnableTask->needtime);
        unrunnableTask->arrivedtime=0;
        unrunnableTask->state=-1;
        unrunnableTask->slicetime=0;
        unrunnableTask->next = NULL;
    }
    else
    {
        struct task_struct* test = unrunnableTask;
        while(test->next != NULL)
        {
            test = test->next;
        }
        test->next = malloc(sizeof(struct task_struct));
        test->next->id = id++;
        printf("进程优先级:\n");
        scanf("%d",&test->next->priority);
        printf("进程运行需要的时间:\n");
        scanf("%d",&test->next->needtime);
        test->next->arrivedtime=0;
        test->next->state=-1;
        test->next->next = NULL;
        test->next->slicetime=0;
        test = test->next;
    }
}

/*
撤销内存程序
*/
void deleteTask()
{
    //撤销运行进程
    char select;
    printf("撤销运行进程输入Y/y,不撤销输入N/n。\n");
    do
    {
        select=getchar();
    }
    while(select!='y'&&select!='n'&&select!='Y'&&select!='N');
    if(select=='y' || select=='Y')//进行撤销
    {
        free(runnableTask);
        runnableTask = NULL;
        scheduleTask();
        return ;
    }
    //撤销阻塞进程
    printf("撤销阻塞进程输入Y/y,不撤销输入N/n。\n");
    do
    {
        select=getchar();
    }
    while(select!='y'&&select!='n'&&select!='Y'&&select!='N');
    if(select=='y' || select=='Y')//选择撤销
    {
        struct task_struct* test = stoppedTask;
        while(test != NULL) //循环输出阻塞进程信息
        {
            printf("本进程信息为\n");
            printf("\n   进程名    优先级  需要时间    已用时间  剩余时间片 进程状态 \n");
            printf("%8d %8d %8d %10d %10d %10d \n",test->id,test->priority,test->needtime,test->arrivedtime, test->slicetime, test->state);
            printf("撤销本进程输入Y/y,不撤销输入N/n。\n");
            do
            {
                select=getchar();
            }
            while(select!='y'&&select!='n'&&select!='Y'&&select!='N');
            if(select=='y' || select=='Y')  //选择撤销该进程
            {
                //从进程队列删除撤销进程
                if(stoppedTask == test)     //判断是否为队首
                {
                    stoppedTask=test->next;
                }
                else    //撤销进程非队首
                {
                    struct task_struct* test3 = stoppedTask;
                    while(test3->next != test)
                    {
                        test3 = test3->next;
                    }
                    test3->next = test->next;
                }
                free(test);
                scheduleTask();
                return ;
            }
        }
    }
    //撤销就绪进程
    printf("撤销就绪进程输入Y/y,不撤销输入N/n。\n");
    do
    {
        select=getchar();
    }
    while(select!='y'&&select!='n'&&select!='Y'&&select!='N');
    if(select=='y' || select=='Y')//选择撤销
    {
        struct task_struct* test = unrunnableTask;
        while(test != NULL) //循环输出阻塞进程信息
        {
            printf("本进程信息为\n");
            printf("\n   进程名    优先级  需要时间    已用时间  剩余时间片 进程状态 \n");
            printf("%8d %8d %8d %10d %10d %10d \n",test->id,test->priority,test->needtime,test->arrivedtime, test->slicetime, test->state);
            printf("撤销本进程输入Y/y,不撤销输入N/n。\n");
            do
            {
                select=getchar();
            }
            while(select!='y'&&select!='n'&&select!='Y'&&select!='N');
            if(select=='y' || select=='Y')  //选择撤销该进程
            {
                //从进程队列删除撤销进程
                if(unrunnableTask == test)     //判断是否为队首
                {
                    unrunnableTask=test->next;
                }
                else    //撤销进程非队首
                {
                    struct task_struct* test2 = unrunnableTask;
                    while(test2->next != test)
                    {
                        test2 = test2->next;
                    }
                    test2->next = test->next;
                }
                free(test);
                scheduleTask();
                return ;
            }
        }
    }

}

/*
阻塞进程程序
*/
void stopTask()
{
    if(runnableTask == NULL)
    {
        printf("无运行进程!\n");
        return ;
    }
    runnableTask->state = 1;    //阻塞进程状态默认为1,将进程放入阻塞队列由runTask实现
}

/*
唤醒程序,唤醒优先级最大的进程,若有优先级相同进程,唤醒先进入队列的进程
*/
void awakeTask()
{
    //无阻塞进程,退出
    if(stoppedTask == NULL)
    {
        printf("无阻塞进程!\n");
        return ;
    }
    int max = -100;
    struct task_struct* test = stoppedTask;
    while(test != NULL)
    {
        if(max < test->priority)
        {
            max = test->priority;
        }
        test = test->next;
    }
    if(max == stoppedTask->priority)     //判断是否为队首
    {
        //将进程放入就绪队列中
        if(unrunnableTask == NULL)//判断就绪队列是否为空
        {
            unrunnableTask = stoppedTask;
            unrunnableTask->state=0;
            stoppedTask = stoppedTask->next;
            unrunnableTask->next = NULL;
        }
        else//放到就绪队列队尾
        {
            struct task_struct* test2 = unrunnableTask;
            while(test2->next != NULL)
            {
                test2 = test2->next;
            }
            stoppedTask = stoppedTask->next;
            test2->next = stoppedTask;
            test2->next->state=-1;
            test2->next->next=NULL;
        }
    }
    else        //唤醒进程不在队首
    {
        //确定应唤醒进程在阻塞进程队列的位置
        struct task_struct* test3 = stoppedTask;
        while(test3->next->priority != max)
        {
            test3 = test3->next;
        }
        //将进程放入就绪队列中
        if(unrunnableTask == NULL)  //判断就绪队列是否为空
        {
            unrunnableTask = test3->next;
            unrunnableTask->state=-1;
            test3->next = test3->next->next;
            unrunnableTask->next=NULL;
        }
        else        //放到就绪队列队尾
        {
            printf("test3");
            struct task_struct* test2 = unrunnableTask;
            while(test2->next != NULL)
            {
                test2 = test2->next;
            }
            test2->next = test3->next;
            test2->next->state=-1;
            test3->next = test3->next->next;
            test2->next->next=NULL;
        }
    }
    scheduleTask();
}

/*
模拟运行运行状态进程
运行进程时间片时间减1
已用时间加1
判断是否启动进程调度程序
*/
void runTask()
{
    printf("\n\n\n\n运行进程开始\n");
    if(runnableTask != NULL)
    {
        printf("进程运行中……\n");
        runnableTask->arrivedtime += 1;
        runnableTask->slicetime -= 1;
        if(runnableTask->arrivedtime == runnableTask->needtime) //当运行进程完成
        {
            printf("当前运行进程执行完毕\n");
            printToScreen(runnableTask);
            printf("运行进程执行完毕,执行进程调度程序\n");
            free(runnableTask);
            runnableTask = NULL;
            scheduleTask();
        }
        else if(runnableTask->slicetime == 0)    //当运行进程时间片用完
        {
            //改变进程优先级,运行进程优先级-1,阻塞进程优先级+2
            runnableTask->priority -= 1;
            //将运行完进程放回就绪进程
            if(unrunnableTask == NULL)
            {
                unrunnableTask = runnableTask;
                unrunnableTask->state=-1;
            }
            else
            {
                struct task_struct* test = unrunnableTask;
                test->priority += 2;
                while(test->next != NULL)
                {
                    test = test->next;
                    test->priority += 2;
                }
                test->next = runnableTask;
                test->next->state = -1;
                test->next->next=NULL;
            }
            runnableTask = NULL;
            printf("运行进程时间片用完,执行进程调度程序\n");
            scheduleTask();
        }
        else if(runnableTask->state > 0)    //当运行进程被阻塞
        {
            //将被阻塞进程放入阻塞进程
            if(stoppedTask == NULL)
            {
                stoppedTask = runnableTask;
                stoppedTask->state=1;
                stoppedTask->next=NULL;
            }
            else
            {
                struct task_struct* test = stoppedTask;
                while(test->next != NULL)
                {
                    test = test->next;
                }
                test->next = runnableTask;
                test->next->state=1;
                test->next->next=NULL;
            }
            runnableTask = NULL;
            printf("运行进程被阻塞,执行进程调度程序\n");
            scheduleTask();
        }
    }
    else
    {
        printf("无正在运行进程,调用进程调度程序\n");
        scheduleTask();
    }
}

/*
模拟进程调度程序
*/
void scheduleTask()
{
    if(runnableTask==NULL||runnableTask->slicetime==0||runnableTask->needtime==runnableTask->arrivedtime||runnableTask->state>0)    //判断是否符合切换运行进程条件
    {
        printf("\n\n\n\n运行调度开始\n");
        if(unrunnableTask != NULL)  //判断有无就绪进程
        {
            if(runnableTask==NULL||runnableTask->slicetime==0||runnableTask->needtime==runnableTask->arrivedtime||runnableTask->state>0)
            {
                getBigPriorityTask();
            }
            else //运行进程队列不需切换进程但进入
            {
                printf("进程调度程序出现未知错误\n");
            }
        }
        else //无就绪进程
        {
            printf("无就绪进程可供调度\n");
        }
    }
    else
    {
        printf("进入进程调度程序错误\n");
    }
}

/*
对进程排序,并将最大优先级的进程给运行进程
*/
void getBigPriorityTask()
{
    int max = -100;
    struct task_struct* test = unrunnableTask;
    while(test != NULL)
    {
        if(max < test->priority)
        {
            max = test->priority;
        }
        test = test->next;
    }
    if(max == unrunnableTask->priority)     //判断是否为队首
    {
        runnableTask = unrunnableTask;
        runnableTask->state=0;
        unrunnableTask = unrunnableTask->next;
        runnableTask->next = NULL;
        runnableTask->slicetime=5;
    }
    else
    {
        test = unrunnableTask;
        while(test->next != NULL)
        {
            if(test->next->priority == max)
            {
                runnableTask=test->next;
                runnableTask->state=0;
                test->next = test->next->next;
                runnableTask->next = NULL;
                runnableTask->slicetime=5;
            }
            break;
        }
    }
}

/*
显示进程状态
*/
void showTask()
{
    printf("----------运行进程----------\n");
    if(runnableTask != NULL)
    {
        printToScreen(runnableTask);
    }
    printf("----------就绪进程----------\n");
    if(unrunnableTask != NULL)
    {
        printToScreen(unrunnableTask);
    }
    printf("----------阻塞进程----------\n");
    if(stoppedTask != NULL)
    {
        printToScreen(stoppedTask);
    }
}

/*
向屏幕输出进程状态
*/
void printToScreen(struct task_struct* test)
{
    printf("\n   进程名    优先级  需要时间    已用时间  剩余时间片 进程状态 \n");
    while(test != NULL)
    {
        printf("%8d %8d %8d %10d %10d %10d \n",test->id,test->priority,test->needtime,test->arrivedtime, test->slicetime, test->state);
        test = test->next;
    }
}


  • 5
    点赞
  • 35
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
用于进程控制模拟 #include <dos.h> #include <fcntl.h> #include <io.h> #include <malloc.h> #include <stdio.h> #include <time.h> #include <string.h> #include "ggg.h" #include "os.h" #include "menu.h" void draw_bar() { int y,color,yy; setbkcolor(HiColor(BK_COLOR)); rect(0,0,SCREEN_W-1,SCREEN_H-1,HiColor(0xC0C0C0)); for (color = 652, y = 92,yy=1; y <121; ++y, color += 2048,++yy) { hline(1,yy,480,color); } /* rectfill(1, 1, 480, 30,HiColor(0xFFFFFF)); */ line(481,1,481,430,HiColor(0xFFFFFF)); hline(1,434,SCREEN_W-2,HiColor(0xFFFFFF)); } char *input(char *text) { char *in; int i=0; in=calloc(12,sizeof(char)); showMessage(text); in[i]=getch(); while(in[i]!=13) { rectfill(5, 455, 5+(8*10), 455, HiColor(BK_COLOR)); string_out(in,5,450); vsync(); i++; if(i>10){ return 0; } in[i]=getch(); } in[i]=0; return in; } #define PCB_W 60 #define PCB_H 20 #define PCB_LEFT 30 #define LINE_H 10 void draw_PCB(int start_x,int start_y,int end_x,int end_y,int color,PCB *p,int text_color) { set_str_color(HiColor(text_color)); rectfill(start_x+PCB_LEFT,start_y+LINE_H,end_x-PCB_LEFT,end_y,color); line(start_x+PCB_LEFT+(PCB_W/2),start_y,start_x+PCB_LEFT+(PCB_W/2),start_y+LINE_H,0); if(p->hasname==1) textout(p->name,start_x+PCB_LEFT,start_y+LINE_H+5); set_str_color(1); } void draw_PCB_point(PCB_point *p) { int i=0; int start_x,start_y; char c; PCB *temp; rectfill(p->start_x,p->start_y,p->end_x,p->end_y,HiColor(BK_COLOR)); temp=p->next; set_str_color(HiColor(0x00ff00)); string_out(p->name,p->start_x+10,6); for(i=0;i<p->num;i++) { start_x=p->start_x; start_y=p->this_y; draw_PCB(start_x,start_y,p->end_x,start_y+PCB_H+LINE_H,p->color,temp,p->text_color); p->this_y=start_y+PCB_H+LINE_H; temp=temp->link; } set_str_color(1); itoa(p->num,c,10); string_out(c,p->this_x,p->this_y); } char *show_input() { char *n,*p; n=input("请输入进程名:"); p=calloc(100,sizeof(char)); strcpy(p,"输入数据成功,你输入的数据为: "); strcat(p,n); showMessage(p); return n; } void reset_this(PCB_point *p) { p->this_x=p->start_x; p->this_y=p->start_y; } void create_proess() { char *text; scare_mouse(); showMessage("\nplease input text:"); /*text=(char *)malloc(100);*/ text=show_input(); create(text); unscare_mouse(); } void keymode() { char choice; char *msg; /*printf("start:\n"); */ PCB_point_init(); while(1) { reset_this(freelist); reset_this(runlist); reset_this(runablelist); reset_this(blocklist); draw_PCB_point(freelist) ; draw_PCB_point(runlist) ; draw_PCB_point(runablelist) ; draw_PCB_point(blocklist) ; showMessage("请输入操作指令:"); choice=getch(); switch(choice) { case 'c': create_proess(); break; /*case 's': list(); break;*/ case 'p': dispatch(); break; case 't': timeout(); break; case 'b': block(); break; case 'w': wakeup(); break; case 'e': quit_PCB(); break; case 'x': exit(0); } } } void quit() { exit(0); } #define BUTTON_W 80 #define BUTTON_H 30 void init_menu() { button *b; btinsert(createbutton(521,30,521+BUTTON_W,30+BUTTON_H,"创建进程",create_proess)); btinsert(createbutton(521,90,521+BUTTON_W,90+BUTTON_H,"调度进程",dispatch)); btinsert(createbutton(521,150,521+BUTTON_W,150+BUTTON_H,"阻塞进程",block)); btinsert(createbutton(521,210,521+BUTTON_W,210+BUTTON_H,"唤醒进程",wakeup)); btinsert(createbutton(521,270,521+BUTTON_W,270+BUTTON_H,"时间片到",timeout)); btinsert(createbutton(521,330,521+BUTTON_W,330+BUTTON_H,"结束进程",quit_PCB)); btinsert(createbutton(521,390,521+BUTTON_W,390+BUTTON_H,"退出程序",quit)); b=btlist->next; while(b!=NULL) { button_fill(b); b=b->link; } } void update(PCB_point *t) { if(t->changed) { reset_this(t); draw_PCB_point(t) ; t->changed=0; } } void main() { char *n,*p; PCB_point *li; neo_init(); set_vbe_mode(VBE640X480X64K); install_timer(new_1ch_int); /*change_timer(50); */ /*set_cn_size(0); */ install_mouse(); /*设置鼠标移动范围*/ set_mouse_range(0, 0, SCREEN_W, SCREEN_H); draw_bar(); PCB_point_init(); /* keymode(); draw_PCB(0,31,120,31+PCB_H+LINE_H,HiColor(0xFF0000)); li=(PCB_point *)malloc(sizeof(PCB_point)); set_PCB_point(li,NULL,10,10,0,31,120,431,HiColor(0xFF0000)); draw_PCB_point(li) ; */ init_menu(); while(1){ update(freelist); update(runlist); update(runablelist); update(blocklist); mouse_refresh(); chk_mouse(); LOOP_END_OF_TIMER(); } showMessage("按任意键退出!"); getch(); quit(); }

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值