Nachos实验实现线程id、限制线程数和更改调度算法(按优先级调度)

Nachos实验1实现线程id、限制线程数和更改调度算法(按优先级调度)

一、理解Nachos线程的运行及调度原理

Nachos实验主要是为了使我们深入的理解操作系统结构,Nachos也是一个操作系统,但是它很简便,我们可以很容易的对它进行改动;通过对Nachos的实验来增加我们对操作系统的理解,当前这个实验主要是通过我们实现Nachos线程id和优先级调度来对操作系统进程和线程的理解。Nachos里面主要分为内核线程(例如main线程)和用户线程,主要通过主线程来操作,例如新建和调度线程。其实对于增加线程id和限制最大线程数,只要了解进程的实现原理,看代码也会非常的容易理解,这样就会非常简单了。
对于理解这次实验代码,我认为,需要看thread.h、thread.cc、scheduler.h、scheduler.cc、List.h、List.cc、main.h、main.cc,对于main.h和main.cc,只需要知道在运行Nachos的时候加-K命令(“./nachos -K”)就会进入线程测试就行了。

二、增加线程ID和最大线程数

在增加实现线程id和最大线程数时,thread类的构造函数尽量不要改动,只需再重构一个构造方法,因为之前的构造函数可能在Nachos的其他类里会调用它,所以我们不能再之前的构造函数里构造,这样才不会打乱原系统的正确性,所以需要增加一个构造函数Thread(char* debugName,int priority);至于int priority先不用管,这是之后优先级调度需要用到的参数,不影响我们使用这个构造函数

1.增改class thread,增加线程id成员和一些需要用到的成员方法

#define MAX_SIZE  128//最大线程数
//pk数组主要记录线程号被使用的状态
//下标位线程号,数组对应值位线程号状态
//对应值为0时,表示该线程号没有线程占用
//对应值为1时,表示该线程号被占用
static int pk[MAX_SIZE]={
   0};
static int threadMAX = 0;//记录线程数

class Thread {
   
  private:
    // NOTE: DO NOT CHANGE the order of these first two members.
    // THEY MUST be in this position for SWITCH to work.
    int *stackTop;			 // the current stack pointer
    void *machineState[MachineStateSize];  // all registers except for stackTop

	int tid;
  public:
    Thread(char* debugName);//原构造函数		// initialize a Thread 
    ~Thread(); //析构函数				// deallocate a Thread
					// NOTE -- thread being deleted
					// must not be running when delete 
					// is called

    // basic thread operations
	Thread(char* debugName,int priority);//新构造函数
	int getTid(){
   return this->tid;};//获得线程id

    void Fork(VoidFunctionPtr func, void *arg); //将线程加入就绪队列
    				// Make thread run (*func)(arg)
    void Yield();  //打断当前线程,运行就绪队列里的线程
					// Relinquish the CPU if any 
				// other thread is runnable
    void Sleep(bool finishing);//将当前线程阻塞
								 // Put the thread to sleep and 
				// relinquish the processor
    void Begin();	// Startup code for the thread	
    void Finish();  //线程运行结束	
						// The thread is done executing
    
    void CheckOverflow();   	// Check if thread stack has overflowed
    void setStatus(ThreadStatus st) {
    status = st; }//设置线程状态
    char* getName() {
    return (name); }//获取线程名字
    void Print() {
    cout << name; }//打印线程名字
    void SelfTest();	//测试方法	// test whether thread impl is working

  private:
    // some of the private data for this class is listed above
    
    int *stack; 	 	// Bottom of the stack 
				// NULL if this is the main thread
				// (If NULL, don't deallocate stack)
    ThreadStatus status;	// ready, running or blocked
    char* name;

    void StackAllocate(VoidFunctionPtr func, void *arg);
    				// Allocate a stack for thread.
				// Used internally by Fork()

// A thread running a user program actually has *two* sets of CPU registers -- 
// one for its state while executing user code, one for its state 
// while executing kernel code.

    int userRegisters[NumTotalRegs];	// user-level CPU register state

  public:
    void SaveUserState();		// save user-level register state
    void RestoreUserState();		// restore user-level register state

    AddrSpace *space;			// User code this thread is running.
};

2.在thread.cc里面增加我们需要的功能,切记,我们是新增构造函数,不是在原构造函数更改!!

Thread::Thread(char* threadName)//原构造函数,不要更改它
{
   
    name = threadName;
    stackTop = NULL;
    stack = NULL;
    status = JUST_CREATED;
    for (int i = 0; i < MachineStateSize; i++) {
   
	machineState[i] = NULL;		// not strictly necessary, since
					// new thread ignores contents 
					// of machine registers
    }
    space = NULL;
}
Thread::Thread(char* threadName,int priority)//新构造函数
{
   

	if(++threadMAX > MAX_SIZE){
   //限制线程数
		cout<<"最大线程数:"<<MAX_SIZE<<"!!!"<<endl;
		ASSERT(threadMAX<=MAX_SIZE);
	}
	int j;
	for(j=0;j<MAX_SIZE;j++){
   //设置id
		if(pk[j]==0){
   
			this->tid = j+1;
			pk[j] = 1;
			break;
		}
	}

    name = threadName;
    stackTop = NULL;
    stack = NULL;
    status = JUST_CREATED;
    for (int 
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值