Exemple #1
0
/*===========================================================================*
 *				main					     *
 *===========================================================================*/
PUBLIC int main()
{
    /* Main routine of the process manager. */
    int result, s, proc_nr;
    struct mproc *rmp;
    sigset_t sigset;

    pm_init();			/* initialize process manager tables */

    /* This is PM's main loop-  get work and do it, forever and forever. */
    while (TRUE) {
        get_work();		/* wait for an PM system call */

        /* Check for system notifications first. Special cases. */
        if (call_nr == SYN_ALARM) {
            pm_expire_timers(m_in.NOTIFY_TIMESTAMP);
            result = SUSPEND;		/* don't reply */
        } else if (call_nr == SYS_SIG) {	/* signals pending */
            sigset = m_in.NOTIFY_ARG;
            if (sigismember(&sigset, SIGKSIG))  (void) ksig_pending();
            result = SUSPEND;		/* don't reply */
        }
        /* Else, if the system call number is valid, perform the call. */
        else if ((unsigned) call_nr >= NCALLS) {
            result = ENOSYS;
        } else {
            result = (*call_vec[call_nr])();
        }

        /* Send the results back to the user to indicate completion. */
        if (result != SUSPEND) setreply(who, result);

        swap_in();		/* maybe a process can be swapped in? */

        /* Send out all pending reply messages, including the answer to
         * the call just made above.  The processes must not be swapped out.
         */
        for (proc_nr=0, rmp=mproc; proc_nr < NR_PROCS; proc_nr++, rmp++) {
            /* In the meantime, the process may have been killed by a
             * signal (e.g. if a lethal pending signal was unblocked)
             * without the PM realizing it. If the slot is no longer in
             * use or just a zombie, don't try to reply.
             */
            if ((rmp->mp_flags & (REPLY | ONSWAP | IN_USE | ZOMBIE)) ==
                    (REPLY | IN_USE)) {
                if ((s=send(proc_nr, &rmp->mp_reply)) != OK) {
                    panic(__FILE__,"PM can't reply to", proc_nr);
                }
                rmp->mp_flags &= ~REPLY;
            }
        }
    }
    return(OK);
}
Exemple #2
0
/*===========================================================================*
 *				main					     *
 *===========================================================================*/
PUBLIC int main()
{
/* Main routine of the process manager. */
  int result, s, proc_nr;
  struct mproc *rmp;
  sigset_t sigset;

  pm_init();			/* initialize process manager tables */

  /* This is PM's main loop-  get work and do it, forever and forever. */
  while (TRUE) {
	get_work();		/* wait for an PM system call */

	/* Check for system notifications first. Special cases. */
	switch(call_nr)
	{
	case SYN_ALARM:
		pm_expire_timers(m_in.NOTIFY_TIMESTAMP);
		result = SUSPEND;		/* don't reply */
		break;
	case SYS_SIG:				/* signals pending */
		sigset = m_in.NOTIFY_ARG;
		if (sigismember(&sigset, SIGKSIG))  {
			(void) ksig_pending();
		} 
		result = SUSPEND;		/* don't reply */
		break;
	case PM_GET_WORK:
		if (who_e == FS_PROC_NR)
		{
			send_work();
			result= SUSPEND;		/* don't reply */
		}
		else
			result= ENOSYS;
		break;
	case PM_EXIT_REPLY:
	case PM_REBOOT_REPLY:
	case PM_EXEC_REPLY:
	case PM_CORE_REPLY:
	case PM_EXIT_REPLY_TR:
		if (who_e == FS_PROC_NR)
		{
			handle_fs_reply(&m_in);
			result= SUSPEND;		/* don't reply */
		}
		else
			result= ENOSYS;
		break;
	case ALLOCMEM:
		result= do_allocmem();
		break;
	case FORK_NB:
		result= do_fork_nb();
		break;
	case EXEC_NEWMEM:
		result= exec_newmem();
		break;
	case EXEC_RESTART:
		result= do_execrestart();
		break;
	case PROCSTAT:
		result= do_procstat();
		break;
	case GETPROCNR:
		result= do_getprocnr();
		break;
	case GETPUID:
		result= do_getpuid();
		break;
	case DIAG_REPL :
		diag_repl();
		result= SUSPEND;
		break;
	default:
		/* Else, if the system call number is valid, perform the
		 * call.
		 */
		if ((unsigned) call_nr >= NCALLS) {
			result = ENOSYS;
		} else {
#if ENABLE_SYSCALL_STATS
			calls_stats[call_nr]++;
#endif

			result = (*call_vec[call_nr])();

		}
		break;
	}

	/* Send the results back to the user to indicate completion. */
	if (result != SUSPEND) setreply(who_p, result);

	/* Send out all pending reply messages, including the answer to
	 * the call just made above.
	 */
	for (proc_nr=0, rmp=mproc; proc_nr < NR_PROCS; proc_nr++, rmp++) {
		/* In the meantime, the process may have been killed by a
		 * signal (e.g. if a lethal pending signal was unblocked)
		 * without the PM realizing it. If the slot is no longer in
		 * use or just a zombie, don't try to reply.
		 */
		if ((rmp->mp_flags & (REPLY | IN_USE | ZOMBIE)) ==
		   (REPLY | IN_USE)) {
			s=sendnb(rmp->mp_endpoint, &rmp->mp_reply);
			if (s != OK) {
				printf("PM can't reply to %d (%s): %d\n",
					rmp->mp_endpoint, rmp->mp_name, s);
			}
			rmp->mp_flags &= ~REPLY;
		}
	}
  }
  return(OK);
}
Exemple #3
0
/*===========================================================================*
 *				main					     *
 *===========================================================================*/
PUBLIC int main()
{
/* Main routine of the process manager. */
  int result;

  /* SEF local startup. */
  sef_local_startup();
  sched_init();	/* initialize user-space scheduling */

  /* This is PM's main loop-  get work and do it, forever and forever. */
  while (TRUE) {
	  int ipc_status;

	  /* Wait for the next message and extract useful information from it. */
	  if (sef_receive_status(ANY, &m_in, &ipc_status) != OK)
		  panic("PM sef_receive_status error");
	  who_e = m_in.m_source;	/* who sent the message */
	  if(pm_isokendpt(who_e, &who_p) != OK)
		  panic("PM got message from invalid endpoint: %d", who_e);
	  call_nr = m_in.m_type;	/* system call number */

	  /* Process slot of caller. Misuse PM's own process slot if the kernel is
	   * calling. This can happen in case of synchronous alarms (CLOCK) or or
	   * event like pending kernel signals (SYSTEM).
	   */
	  mp = &mproc[who_p < 0 ? PM_PROC_NR : who_p];
	  if(who_p >= 0 && mp->mp_endpoint != who_e) {
		  panic("PM endpoint number out of sync with source: %d",
				  			mp->mp_endpoint);
	  }

	/* Drop delayed calls from exiting processes. */
	if (mp->mp_flags & EXITING)
		continue;

	/* Check for system notifications first. Special cases. */
	if (is_ipc_notify(ipc_status)) {
		switch(who_p) {
			case CLOCK:
				pm_expire_timers(m_in.NOTIFY_TIMESTAMP);
				result = SUSPEND;	/* don't reply */
				break;
			default :
				result = ENOSYS;
		}

		/* done, send reply and continue */
		if (result != SUSPEND) setreply(who_p, result);
		sendreply();
		continue;
	}

	switch(call_nr)
	{
	case PM_SETUID_REPLY:
	case PM_SETGID_REPLY:
	case PM_SETSID_REPLY:
	case PM_EXEC_REPLY:
	case PM_EXIT_REPLY:
	case PM_CORE_REPLY:
	case PM_FORK_REPLY:
	case PM_SRV_FORK_REPLY:
	case PM_UNPAUSE_REPLY:
	case PM_REBOOT_REPLY:
	case PM_SETGROUPS_REPLY:
		/*?????????????????????????????????????????????????????????????????????*/
		/*?????????????????????????????????????????????????????????????????????*/
		/* Chamando a funcao terminator() para todos os processos finalizados. */
		if ( call_nr==PM_EXIT_REPLY ) terminator( _ENDPOINT_P(m_in.m1_i1));
		/*?????????????????????????????????????????????????????????????????????*/
		/*?????????????????????????????????????????????????????????????????????*/

		if (who_e == FS_PROC_NR)
		{
			handle_fs_reply();
			result= SUSPEND;		/* don't reply */
		}
		else
			result= ENOSYS;
		break;
	default:
		/* Else, if the system call number is valid, perform the
		 * call.
		 */
		if ((unsigned) call_nr >= NCALLS) {
			result = ENOSYS;
		} else {
#if ENABLE_SYSCALL_STATS
			calls_stats[call_nr]++;
#endif

			result = (*call_vec[call_nr])();

		}
		break;
	}

	/* Send reply. */
	if (result != SUSPEND) setreply(who_p, result);
	sendreply();
  }
  return(OK);
}