daily pastebin goal
16%
SHARE
TWEET

Untitled

a guest Jun 13th, 2018 60 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. #include "../../h/const.h"
  2.  
  3. #include "../../h/types.h"
  4.  
  5. #include "../../h/vpop.h"
  6.  
  7. #include "../../h/util.h"
  8.  
  9. #include "../../h/procq.e"
  10.  
  11. #include "../../h/asl.e"
  12.  
  13.  
  14.  
  15. #define NUM_DEV 15 /* number of devices */
  16.  
  17. #define QUANTUM 5000 /* 5ms */
  18.  
  19. #define DELAY 100000 /* 100ms */
  20.  
  21. #define MAXLEN 64 /* maximal size of a string */
  22.  
  23.  
  24.  
  25. extern int mem_size;
  26.  
  27. extern proc_link RQ;
  28.  
  29.  
  30.  
  31. /* global variables */
  32.  
  33. HIDDEN devsemtable_t devsemtable[NUM_DEV]; /* device sem table */
  34.  
  35. HIDDEN int pseudoclock;
  36.  
  37. long last_check_time = 0;
  38.  
  39.  
  40.  
  41. void static sleep () {
  42.  
  43.     asm("stop #0x2000");
  44.  
  45. }
  46.  
  47.  
  48.  
  49. void intschedule () {
  50.  
  51.     long timeslice = QUANTUM;
  52.  
  53.     LDIT(&timeslice);
  54.  
  55. }
  56.  
  57.  
  58.  
  59. int check_devsem() {
  60.  
  61.     int i;
  62.  
  63.     for(i=0;i<NUM_DEV;i++) {
  64.  
  65.     if(devsemtable[i].devsem <0)
  66.  
  67.         return TRUE;
  68.  
  69.     }
  70.  
  71.     return FALSE;
  72.  
  73. }
  74.  
  75.  
  76.  
  77. void print_foo(char* buf) {
  78.  
  79.     devreg_t *printer0 = (devreg_t *)0x1450;
  80.  
  81.     printer0->d_amnt = MAXLEN; /* buffer size */
  82.  
  83.     printer0->d_badd = buf; /* address of buf */
  84.  
  85.     printer0->d_op = IOWRITE;
  86.  
  87.     printer0->d_stat = -1;  /* normal state 0-9 */ 
  88.  
  89.     /* wait for the printer to finish printing */
  90.  
  91.     while (printer0->d_stat == -1);
  92.  
  93.     /* shut it down */
  94.  
  95.     HALT();
  96.  
  97. }
  98.  
  99.  
  100.  
  101. /* handle the case of empty RQ */
  102.  
  103. void intdeadlock () {
  104.  
  105.     /* any process blocked on pseudoclock? */
  106.  
  107.     if (pseudoclock < 0) {
  108.  
  109.     intschedule();
  110.  
  111.     sleep();
  112.  
  113.     }
  114.  
  115.     /* any process blocked on I/O? */
  116.  
  117.     else if (check_devsem())
  118.  
  119.     sleep();
  120.  
  121.     /* system shut down normally */
  122.  
  123.     else if (headASL() == FALSE) {
  124.  
  125.     /* print out the termination information */
  126.  
  127.     char buf[MAXLEN] = "normal termination.";
  128.  
  129.     print_foo(buf);
  130.  
  131.     }
  132.  
  133.     /* deadlock */
  134.  
  135.     else {
  136.  
  137.     char buf[MAXLEN] = "deadlock.";
  138.  
  139.     print_foo(buf);
  140.  
  141.     }
  142.  
  143. }
  144.  
  145.  
  146.  
  147. int on_sem(proc_t * p) {
  148.  
  149.     int i=0;
  150.  
  151.     for(;i<SEMMAX;i++) {
  152.  
  153.     if(p->semvec[i] != (int*)NULL ) {
  154.  
  155.         return TRUE;
  156.  
  157.     }
  158.  
  159.     }
  160.  
  161.     return FALSE;
  162.  
  163. }
  164.  
  165.  
  166.  
  167. /* P/V for interrupts */
  168.  
  169. void intsemop (int *semaddr, int semop) {
  170.  
  171.     long currenttime;
  172.  
  173.     *semaddr += semop;
  174.  
  175.     if ( semop == LOCK && *semaddr < 0 ) {
  176.  
  177.     /*remove the head of RQ to the sem queue*/
  178.  
  179.     proc_t *p = removeProc(&RQ);
  180.  
  181.     STCK(&currenttime);
  182.  
  183.     p->acc_time += currenttime - p->start_time;
  184.  
  185.     insertBlocked(semaddr, p);         
  186.  
  187.     /* schedule the new head */
  188.  
  189.     if (headQueue(RQ) != (proc_t *)NULL)
  190.  
  191.         schedule();
  192.  
  193.     else
  194.  
  195.         intdeadlock(); 
  196.  
  197.     }
  198.  
  199.     else if (semop == UNLOCK && *semaddr <= 0) {
  200.  
  201.     proc_t *p = removeBlocked(semaddr);
  202.  
  203.     /* if not on any sem */
  204.  
  205.     if (!on_sem(p)) {
  206.  
  207.         insertProc(&RQ, p);
  208.  
  209.         if(headQueue(RQ) == p)
  210.  
  211.         schedule();
  212.  
  213.     }
  214.  
  215.     }  
  216.  
  217. }
  218.  
  219.  
  220.  
  221. /* interrupt handler */
  222.  
  223. void static inthandler (int devtyp, int devnum) {
  224.  
  225.     /* no wait_for_io happened */
  226.  
  227.     if (devsemtable[devnum].devsem >= 0) { 
  228.  
  229.     devsemtable[devnum].devsem += UNLOCK;
  230.  
  231.     devsemtable[devnum].devinfo.io_len = devsemtable[devnum].devreg_p->d_amnt;
  232.  
  233.     devsemtable[devnum].devinfo.io_sta = devsemtable[devnum].devreg_p->d_stat;
  234.  
  235.     }
  236.  
  237.     /* wait_for_io happened */
  238.  
  239.     else { 
  240.  
  241.     proc_t *p = headBlocked(&(devsemtable[devnum].devsem));
  242.  
  243.     p->p_s.s_r[2] = devsemtable[devnum].devreg_p->d_amnt;
  244.  
  245.     p->p_s.s_r[3] = devsemtable[devnum].devreg_p->d_stat;      
  246.  
  247.     intsemop(&(devsemtable[devnum].devsem), UNLOCK);
  248.  
  249.     }
  250.  
  251. }
  252.  
  253.  
  254.  
  255. /* terminal interrupt handler */
  256.  
  257. void static intterminalhandler () {
  258.  
  259.     int devtyp = TERMINAL;
  260.  
  261.     int devnum = ((state_t *)0x9c8)->s_tmp.tmp_int.in_dno;
  262.  
  263.     inthandler(devtyp, devnum + TERM0);
  264.  
  265.     LDST((state_t *)0x9c8);
  266.  
  267. }
  268.  
  269.  
  270.  
  271. /* printer interrupt handler */
  272.  
  273. void static intprinterhandler () {
  274.  
  275.     int devtyp = PRINTER;
  276.  
  277.     int devnum = ((state_t *)0xa60)->s_tmp.tmp_int.in_dno; 
  278.  
  279.     inthandler(devtyp, devnum + PRINT0);
  280.  
  281.     LDST((state_t *)0xa60);
  282.  
  283. }
  284.  
  285.  
  286.  
  287. /* disk interrupt handler */
  288.  
  289. void static intdiskhandler () {
  290.  
  291.     int devtyp = DISK;
  292.  
  293.     int devnum = ((state_t *)0xaf8)->s_tmp.tmp_int.in_dno; 
  294.  
  295.     inthandler(devtyp, devnum + DISK0);
  296.  
  297.     LDST((state_t *)0xaf8);
  298.  
  299. }
  300.  
  301.  
  302.  
  303. /* floppy interrupt handler */
  304.  
  305. void static intfloppyhandler () {
  306.  
  307.     int devtyp = FLOPPY;   
  308.  
  309.     int devnum = ((state_t *)0xb90)->s_tmp.tmp_int.in_dno; 
  310.  
  311.     inthandler(devtyp, devnum + FLOPPY0);
  312.  
  313.     LDST((state_t *)0xb90);
  314.  
  315. }
  316.  
  317.  
  318.  
  319. /* clock interrupt handler */
  320.  
  321. void static intclockhandler () {
  322.  
  323.     proc_t *head = headQueue(RQ);
  324.  
  325.     long current_time = 0;
  326.  
  327.     STCK(&current_time);   
  328.  
  329.     if (head != (proc_t *)NULL) {
  330.  
  331.     /* restore the current status into the process */
  332.  
  333.     head->p_s = *(state_t *)0xc28;
  334.  
  335.     head->acc_time += current_time - head->start_time;
  336.  
  337.     removeProc(&RQ);
  338.  
  339.     insertProc(&RQ, head);
  340.  
  341.     schedule();
  342.  
  343.     }
  344.  
  345.     /* V the pseudoclock if nessecery */
  346.  
  347.     if (pseudoclock < 0) {
  348.  
  349.     if(current_time - last_check_time >= DELAY) {
  350.  
  351.         intsemop(&pseudoclock, UNLOCK);
  352.  
  353.         last_check_time = current_time;
  354.  
  355.     }
  356.  
  357.     }
  358.  
  359.     LDST((state_t *)0xc28);
  360.  
  361. }
  362.  
  363.  
  364.  
  365. /* initialize interrupt area */
  366.  
  367. void intinit () {
  368.  
  369.     int i;
  370.  
  371.     /* set the new area for terminal interrupt */
  372.  
  373.     ((state_t *)(0x9c8 + sizeof(state_t)))->s_sp = mem_size;
  374.  
  375.     ((state_t *)(0x9c8 + sizeof(state_t)))->s_pc = (int)intterminalhandler;
  376.  
  377.     ((state_t *)(0x9c8 + sizeof(state_t)))->s_sr.ps_s = 1;
  378.  
  379.     ((state_t *)(0x9c8 + sizeof(state_t)))->s_sr.ps_int = 7;   
  380.  
  381.     /* set the new area for printer interrupt */
  382.  
  383.     ((state_t *)(0xa60 + sizeof(state_t)))->s_sp = mem_size;
  384.  
  385.     ((state_t *)(0xa60 + sizeof(state_t)))->s_pc = (int)intprinterhandler;
  386.  
  387.     ((state_t *)(0xa60 + sizeof(state_t)))->s_sr.ps_s = 1;
  388.  
  389.     ((state_t *)(0xa60 + sizeof(state_t)))->s_sr.ps_int = 7;
  390.  
  391.     /* set the new area for disk interrupt */
  392.  
  393.     ((state_t *)(0xaf8 + sizeof(state_t)))->s_sp = mem_size;
  394.  
  395.     ((state_t *)(0xaf8 + sizeof(state_t)))->s_pc = (int)intdiskhandler;
  396.  
  397.     ((state_t *)(0xaf8 + sizeof(state_t)))->s_sr.ps_s = 1; 
  398.  
  399.     ((state_t *)(0xaf8 + sizeof(state_t)))->s_sr.ps_int = 7;
  400.  
  401.     /* set the new area for floppy interrupt */
  402.  
  403.     ((state_t *)(0xb90 + sizeof(state_t)))->s_sp = mem_size;
  404.  
  405.     ((state_t *)(0xb90 + sizeof(state_t)))->s_pc = (int)intfloppyhandler;
  406.  
  407.     ((state_t *)(0xb90 + sizeof(state_t)))->s_sr.ps_s = 1;
  408.  
  409.     ((state_t *)(0xb90 + sizeof(state_t)))->s_sr.ps_int = 7;
  410.  
  411.     /* set the new area for clock interrupt */
  412.  
  413.     ((state_t *)(0xc28 + sizeof(state_t)))->s_sp = mem_size;
  414.  
  415.     ((state_t *)(0xc28 + sizeof(state_t)))->s_pc = (int)intclockhandler;
  416.  
  417.     ((state_t *)(0xc28 + sizeof(state_t)))->s_sr.ps_s = 1;
  418.  
  419.     ((state_t *)(0xc28 + sizeof(state_t)))->s_sr.ps_int = 7;
  420.  
  421.     /* initialize the interrupt table */
  422.  
  423.     for (i = 0; i < NUM_DEV; i++) {
  424.  
  425.     devsemtable[i].devsem = 0;
  426.  
  427.     devsemtable[i].devreg_p = (devreg_t *)(0x1400 + 0x10 * i);
  428.  
  429.     devsemtable[i].devinfo.io_len = 0;
  430.  
  431.     devsemtable[i].devinfo.io_sta = NULL; /* normal status: 0-9 */
  432.  
  433.     }
  434.  
  435.     /* initilize the psudoclock */
  436.  
  437.     pseudoclock = 0;
  438.  
  439. }
  440.  
  441.  
  442.  
  443. /* SYS7: wait on clock */
  444.  
  445. void waitforpclock (state_t *oldzone) {
  446.  
  447.     /* restore the oldzone */
  448.  
  449.     headQueue(RQ)->p_s = *oldzone;
  450.  
  451.     /* p the pseudoclock */
  452.  
  453.     intsemop(&pseudoclock, LOCK);
  454.  
  455. }
  456.  
  457.  
  458.  
  459. /* SYS8: wait on an interrupt */
  460.  
  461. void waitforio (state_t *oldzone) {
  462.  
  463.     int d4 = oldzone->s_r[4]; /* for device number */
  464.  
  465.     int *d2 = &(oldzone->s_r[2]); /* length reg */
  466.  
  467.     int *d3 = &(oldzone->s_r[3]); /* status reg */
  468.  
  469.     /* if an interrupt has already occured */
  470.  
  471.     if (devsemtable[d4].devsem > 0) {      
  472.  
  473.     devsemtable[d4].devsem += LOCK;
  474.  
  475.     *d2 = devsemtable[d4].devinfo.io_len;
  476.  
  477.     *d3 = devsemtable[d4].devinfo.io_sta;
  478.  
  479.     }
  480.  
  481.     /* wait for interrupt */
  482.  
  483.     else {
  484.  
  485.     headQueue(RQ)->p_s = *oldzone;
  486.  
  487.     intsemop(&(devsemtable[d4].devsem), LOCK);     
  488.  
  489.     }
  490.  
  491. }
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
 
Top