LiangDong

Queue

First part

/* q.h - firstid, firstkey, isempty, lastkey, nonempty */

#ifndef _QUEUE_H_
#define _QUEUE_H_

/* q structure declarations, constants, and inline procedures           */

#ifndef NQENT
#define NQENT           2*NPROC + NSEM + NSEM + 4       /* for ready & sleep    */
#endif

struct  qent    {               /* one for each process plus two for    */
/* each list                            */
int     qkey;           /* key on which the queue is ordered    */
int     qnext;          /* pointer to next process or tail      */
int     qprev;          /* pointer to previous process or head  */
};

extern  struct  qent q[];
extern  int     nextqueue;

/* inline list manipulation procedures */

#define isempty(list)   (q[(list)].qnext >= NPROC)
#define nonempty(list)  (q[(list)].qnext < NPROC)
#define firstkey(list)  (q[q[(list)].qnext].qkey)
#define lastkey(tail)   (q[q[(tail)].qprev].qkey)
#define firstid(list)   (q[(list)].qnext)

/* gpq constants */

#define QF_WAIT         0       /* use semaphores to mutex              */
#define QF_NOWAIT       1       /* use disable/restore to mutex         */

/* ANSI compliant function prototypes */

int enqueue(int item, int tail);
int dequeue(int item);
int printq(int head);
int newqueue();
int insertd(int pid, int head, int key);
int insert(int proc, int head, int key);
int getfirst(int head);

#endif

Second part

/* q.h - firstid, firstkey, isempty, lastkey, nonempty */

#ifndef _QUEUE_H_
#define _QUEUE_H_

/* q structure declarations, constants, and inline procedures           */

#ifndef NQENT
#define NQENT           NPROC + NSEM + NSEM + 4 /* for ready & sleep    */
#endif

struct  qent    {               /* one for each process plus two for    */
/* each list                            */
int     qkey;           /* key on which the queue is ordered    */
int     qnext;          /* pointer to next process or tail      */
int     qprev;          /* pointer to previous process or head  */
};

extern  struct  qent q[];
extern  int     nextqueue;

/* inline list manipulation procedures */

#define isempty(list)   (q[(list)].qnext >= NPROC)
#define nonempty(list)  (q[(list)].qnext < NPROC)
#define firstkey(list)  (q[q[(list)].qnext].qkey)
#define lastkey(tail)   (q[q[(tail)].qprev].qkey)
#define firstid(list)   (q[(list)].qnext)

/* gpq constants */

#define QF_WAIT         0       /* use semaphores to mutex              */
#define QF_NOWAIT       1       /* use disable/restore to mutex         */

/* ANSI compliant function prototypes */

int enqueue(int item, int tail);
int dequeue(int item);
int printq(int head);
int newqueue();
int insertd(int pid, int head, int key);
int insert(int proc, int head, int key);
int getfirst(int head);
int getlast(int tail);

#endif

Third part

/* resched.c  -  resched */
#include <conf.h>
#include <kernel.h>
#include <proc.h>
#include <q.h>
#include <lab1.h>
#include <math.h>
unsigned long currSP;   /* REAL sp of current process */
extern int ctxsw(int, int, int, int);
/*-----------------------------------------------------------------------
* resched  --  reschedule processor to highest priority ready process
*
* Notes:       Upon entry, currpid gives current process id.
*              Proctab[currpid].pstate gives correct NEXT state for
*                      current process if other than PRREADY.
*------------------------------------------------------------------------
*/
int skip=0;
int epoch_state;
extern int dbgmod;
dbgmod=1;
int resched()
{

int tmp_head;
int next_pid;
STATWORD ps;
int proc_head=rerdyhead;
register struct pentry  *optr;  /* pointer to old process entry */
register struct pentry  *nptr;  /* pointer to new process entry */
disable(ps);
if (epoch == 0)
{
epoch_state=new_epoch();
optr=&proctab[currpid];
if(currpid!=0&&optr->pstate==PRCURR&&preempt>0){
restore(ps);
return OK;
}
if(epoch_state==EMPTYQUEUE){
if(currpid!=0&&optr->pstate==PRCURR){
if(optr->pprio!=REALTIMEPRIO)
preempt=optr->pprio+optr->counter;
else
preempt=100;
epoch=preempt;
}
else if(currpid==0)
preempt=1;
else{                 /*currpid stops*/
nptr=&proctab[0];
preempt=1;
currpid=0;
ctxsw((int)&optr->pesp, (int)optr->pirmask, (int)&nptr->pesp, (int)nptr->pirmask);
}
restore(ps);
return OK;
}


//get the next process according to their "goodness"
if(epoch_state==REALTIMEMOD)
nptr = &proctab[ (next_pid = getlast(rerdytail)) ];
else
nptr = &proctab[ (next_pid = getlast(rdytail)) ];

if(nptr->goodness==0){
skip=1;
if(optr->pprio==REALTIMEPRIO&&currpid!=-1&&(optr->pstate==PRCURR||optr->pstate==PRREADY))
insert(currpid,rerdyhead,0);
else if(currpid!=-1&&(optr->pstate==PRCURR||optr->pstate==PRREADY))
insert(currpid,rdyhead,0);
else
skip=0;

if(nptr->pprio==REALTIMEPRIO&&next_pid!=-1&&(nptr->pstate==PRCURR||nptr->pstate==PRREADY))
insert(next_pid,rerdyhead,1);
else if(next_pid!=-1&&(nptr->pstate==PRCURR||nptr->pstate==PRREADY))
insert(next_pid,rdyhead,1);

epoch_state=new_epoch();
restore(ps);
return resched();
}

if(currpid==next_pid){
skip=0;
if(epoch_state==REALTIMEMOD)
preempt=100;
else
preempt=floor(nptr->counter/2)+nptr->pprio;
restore(ps);
return OK;
}

if (optr->pstate == PRCURR){
optr->pstate = PRREADY;
optr->counter = preempt;
if (currpid!=0&&skip==0){
optr->goodness = 0;
if(curr_sch==MULTIQSCHED&&optr->pprio==REALTIMEPRIO)
insert(currpid,rerdyhead,0);

}
if(skip!=0)
skip=0;
}


nptr->pstate=PRCURR;
currpid=next_pid;
if(epoch_state==REALTIMEMOD)
preempt=100;
else
preempt=floor(nptr->counter/2)+nptr->pprio;


restore(ps);
ctxsw((int)&optr->pesp, (int)optr->pirmask, (int)&nptr->pesp, (int)nptr->pirmask);
return OK;
}