Exemplo n.º 1
0
void	Stat_handle_message( sys_scatter *scat )
{
	sp_time		now;
	sp_time		delta;
	packet_header	*pack_ptr;
	proc		p;
	int		ret;

	pack_ptr = (packet_header *)scat->elements[0].buf;
	if( ! ( pack_ptr->memb_id.proc_id == 15051963 && Conf_id_in_conf( Conf_ref(), pack_ptr->proc_id ) != -1 ) )
	{
		Alarm( STATUS, "Stat_handle_message: Illegal monitor request\n");
		return;
	}

	now   = E_get_time();
	delta = E_sub_time( now, Start_time );
	GlobalStatus.sec = delta.sec;

	DL_send( Report_channel, pack_ptr->proc_id, pack_ptr->seq, &Report_scat );
	ret = Conf_proc_by_id( pack_ptr->proc_id, &p );
	if( ret < 0 )
		Alarm( STATUS, 
			"Stat_handle_message: sent status to Monitor at %d\n",
			pack_ptr->proc_id );
	else 	Alarm( STATUS, 
			"Stat_handle_message: sent status to Monitor at %s\n",
			p.name );
}
Exemplo n.º 2
0
void 	E_handle_events(void)
{
static	int			Round_robin	= 0;
static	const sp_time		long_timeout 	= { 10000,    0};
                            /* liyu: 1w seconds? this is really bizzar! */
static  const sp_time           zero_sec        = {     0,    0};
#ifdef  BADCLOCK
static	const sp_time		mili_sec 	= {     0, 1000};
	int			clock_sync;
#endif
	int			num_set;
	int			treated;
	int			fd;
	int			fd_type;
	int			i,j;
	sp_time			timeout;
        struct timeval          sel_timeout, wait_timeout;
	fd_set			current_mask[NUM_FDTYPES];
	time_event		*temp_ptr;
        int                     first=1;
#ifdef TESTTIME
        sp_time         	tmp_late,start,stop,req_time;       /* DEBUGGING */
#endif
#ifdef BADCLOCK
    clock_sync = 0;
#endif
    for( Exit_events = 0 ; !Exit_events ; )
    {
	Alarm( EVENTS, "E_handle_events: next event \n");

	/* Handle time events */
	timeout = long_timeout;
#ifdef TESTTIME
        start = E_get_time();
#endif
	while( Time_queue != NULL )
	{
#ifdef BADCLOCK
		if ( clock_sync >= 0 )
		{
		    E_get_time();
		    clock_sync = -20;
		}
#else
                E_get_time();
#endif
		if ( !first && E_compare_time( Now, Time_queue->t ) >= 0 )
		{
#ifdef TESTTIME
                        tmp_late = E_sub_time( Now, Time_queue->t );
#endif
			temp_ptr = Time_queue;
			Time_queue = Time_queue->next;
			Alarm( EVENTS, "E_handle_events: exec time event \n");
#ifdef TESTTIME 
                        Alarm( DEBUG, "Events: TimeEv is %d %d late\n",tmp_late.sec, tmp_late.usec); 
#endif
			temp_ptr->func( temp_ptr->code, temp_ptr->data );
			dispose( temp_ptr );
#ifdef BADCLOCK
			Now = E_add_time( Now, mili_sec );
			clock_sync++;
#else
                        E_get_time();
#endif
                        if (Exit_events) goto end_handler;
		}else{
			timeout = E_sub_time( Time_queue->t, Now );
			break;
		}
	}
        if (timeout.sec < 0 )
                timeout.sec = timeout.usec = 0; /* this can happen until first is unset */
#ifdef TESTTIME
        stop = E_get_time();
        tmp_late = E_sub_time(stop, start);
        Alarm(DEBUG, "Events: TimeEv's took %d %d to handle\n", tmp_late.sec, tmp_late.usec); 
#endif
	/* Handle fd events   */
	for( i=0; i < NUM_FDTYPES; i++ )
	{
		current_mask[i] = Fd_mask[i];
	}
	Alarm( EVENTS, "E_handle_events: poll select\n");
#ifdef TESTTIME
        req_time = zero_sec;
#endif
        wait_timeout.tv_sec = zero_sec.sec;
        wait_timeout.tv_usec = zero_sec.usec;
	num_set = select( FD_SETSIZE, &current_mask[READ_FD], &current_mask[WRITE_FD], &current_mask[EXCEPT_FD], 
			  &wait_timeout );
	if (num_set == 0 && !Exit_events)
	{
#ifdef BADCLOCK
		clock_sync = 0;
#endif
		for( i=0; i < NUM_FDTYPES; i++ )
		{
			current_mask[i] = Fd_mask[i];
		}
		Alarm( EVENTS, "E_handle_events: select with timeout (%d, %d)\n",
			timeout.sec,timeout.usec );
#ifdef TESTTIME
                req_time = E_add_time(req_time, timeout);
#endif
                sel_timeout.tv_sec = timeout.sec;
                sel_timeout.tv_usec = timeout.usec;
		num_set = select( FD_SETSIZE, &current_mask[READ_FD], &current_mask[WRITE_FD], 
				  &current_mask[EXCEPT_FD], &sel_timeout );
	}
#ifdef TESTTIME
        start = E_get_time();
        tmp_late = E_sub_time(start, stop);
        Alarm( DEBUG, "Events: Waiting for fd or timout took %d %d asked for %d %d\n", tmp_late.sec, tmp_late.usec, req_time.sec, req_time.usec);
#endif
	/* Handle all high and medium priority fd events */
	for( i=NUM_PRIORITY-1,treated=0; 
	     i > LOW_PRIORITY && num_set > 0 && !treated;
	     i-- )
	{
	    for( j=0; j < Fd_queue[i].num_fds && num_set > 0; j++ )
	    {
		fd      = Fd_queue[i].events[j].fd;
		fd_type = Fd_queue[i].events[j].fd_type;
		if( FD_ISSET( fd, &current_mask[fd_type] ) )
		{
		    Alarm( EVENTS, "E_handle_events: exec handler for fd %d, fd_type %d, priority %d\n", 
					fd, fd_type, i );
		    Fd_queue[i].events[j].func( 
				Fd_queue[i].events[j].fd,
				Fd_queue[i].events[j].code,
				Fd_queue[i].events[j].data );
		    treated = 1;
		    num_set--;
#ifdef BADCLOCK
		    Now = E_add_time( Now, mili_sec );
		    clock_sync++;
#else
                    E_get_time();
#endif
                    if (Exit_events) goto end_handler;
		}
	    }
	}
        /* Don't handle timed events until all non-low-priority fd events have been handled 
         * FIXME: This may or may not be right. If continual high priority events occur, then
         * timed events will starve, I'm not sure if that is better then what we have. We 
         * could also set first=0 no matter what after trying the high events once, then
         * they will get a shot first, but after that timed events will also be handled.
         */
        if (!treated)
                first = 0;

#ifdef TESTTIME
        stop = E_get_time();
        tmp_late = E_sub_time(stop, start);
        Alarm(DEBUG, "Events: High & Med took %d %d time to handle\n", tmp_late.sec, tmp_late.usec);
#endif
	/* Handle one low priority fd event. 
           However, verify that Active_priority still allows LOW_PRIORITY events. 
           Active_priority can change because of calls to E_set_threshold() during the current select loop.
        */
	for( i=0; i < Fd_queue[LOW_PRIORITY].num_fds 
                     && num_set > 0
                     && Active_priority == LOW_PRIORITY; 
             i++ )
	{
	    j = ( i + Round_robin ) % Fd_queue[LOW_PRIORITY].num_fds;
	    fd      = Fd_queue[LOW_PRIORITY].events[j].fd;
	    fd_type = Fd_queue[LOW_PRIORITY].events[j].fd_type;
	    if( FD_ISSET( fd, &current_mask[fd_type] ) )
	    {
		Round_robin = ( j + 1 ) % Fd_queue[LOW_PRIORITY].num_fds;

		Alarm( EVENTS , "E_handle_events: exec ext fd event \n");
	 	Fd_queue[LOW_PRIORITY].events[j].func( 
				Fd_queue[LOW_PRIORITY].events[j].fd,
				Fd_queue[LOW_PRIORITY].events[j].code,
				Fd_queue[LOW_PRIORITY].events[j].data );
		num_set--;
#ifdef BADCLOCK
		Now = E_add_time( Now, mili_sec );
		clock_sync++;
#else
                E_get_time();
#endif
                if (Exit_events) goto end_handler;
		break;
	    }
	}	
#ifdef TESTTIME
        start = E_get_time();
        tmp_late = E_sub_time(start, stop);
        Alarm(DEBUG, "Events: Low priority took %d %d to handle\n", tmp_late.sec, tmp_late.usec);
#endif
    }
 end_handler:
    /* Clean up data structures for exit OR restart of handler loop */
    /* Actually nothing needs to be cleaned up to allow E_handle_events()
     * to be called again. The events are still registered (or not registered)
     * and the only state for the actual events loop is Exit_events which is reset
     * in the for loop.
     */

    return;
}