Example #1
0
/*
	fsm driver routine-1, this procedure might be called
	from arbitrary context
*/
LOCAL void peer_event(int code, void * e1, int e2,int e3,int e4)
{
	int c;
	ke_toggle_flag(FKERN_LED_BUSB);
	switch(code){
	case HSE_PEER_COLLISION:
		c=peer_lock();
		set_state(hsp_s_collision);
		peer_unlock(c);
		break;
	case HSE_PEER_RX:
		g_kernel.peer->lastMsgTime = ke_get_time();
		if(e2 < sizeof(struct peer_cmd_t)){
			return;
		}
		peer_rx_event((struct peer_cmd_t*)e1,e2);
		break;
	case HSE_PEER_STATUS_BROADCAST:
		c=peer_lock();
		/*reset watchdog*/
		g_kernel.peer->lastMsgTime=ke_get_time();
#ifdef __VXWORKS__
		memcpy(g_kernel.peer->peerAddress,((struct ether_header*)e1)->ether_shost,6);
#endif
		g_kernel.peer_status = *((struct kstatus_t*)e2);
		if(kernelState == KERN_S_RUNNING && peerState==KERN_S_RUNNING){
			ki_log(&g_kernel, F8_IOBUS_COLLISION,0,0,0);
			set_state(hsp_s_collision);
		}
		peer_unlock(c);
		break;
	}	
}
Example #2
0
/*
	void peer_arbitrate()
	
	setup the initial kernel state by monitoring hot-standby port
	and IO bus activities.
*/
LOCAL void peer_arbitrate() 
{
	int cookie;
	f8_u8 st;
	int i;
	
	struct peer_cmd_t tp;

	for(i=0;i<3;i++){
		cookie = peer_lock();
		set_state(hsp_s_arbitrate);
		tp.cmd = Pr_query_status;
		tp.code = F8_SUCCESS;
		tp.time = ke_get_time();
		//peer_flush();
		peer_write(&tp, sizeof tp);
		peer_unlock(cookie);
		
		miliSleep(HSP_ARBITRATION_TIMEOUT);
		
		/* is there an answer? */
		cookie = peer_lock();
		st = get_state();
		set_state(hsp_s_idle);
		peer_unlock(cookie);
		if(st==hsp_s_complete)
			break;
	}
	// mode_show();
	// logMsg("Peer is %s, state=%s\n", ke_get_mode_name(peerState, state_name(st)));
	
	if(st == hsp_s_complete){
		switch(peerState){
		case KERN_S_RUNNING:
			ki_switch_to(KERN_S_STANDBY);
			return;
		case KERN_S_ARBITRATING:
			if(check_priority())
				ki_switch_to(KERN_S_RUNNING);
			else
				ki_switch_to(KERN_S_STANDBY);
			break;
		default:
			ki_switch_to(KERN_S_RUNNING);
			break;
		}
	}else{
		ki_switch_to(KERN_S_RUNNING);
	}

	hsp_log(("arbitration finished, mode is:%d\n", kernelState));

	// ki_switch_to(KERN_S_HALTED);
}
Example #3
0
void
bgp_adj_out_set (struct bgp_node *rn, struct peer *peer, struct prefix *p,
		 struct attr *attr, afi_t afi, safi_t safi,
		 struct bgp_info *binfo)
{
  struct bgp_adj_out *adj = NULL;
  struct bgp_advertise *adv;

#ifdef DISABLE_BGP_ANNOUNCE
  return;
#endif /* DISABLE_BGP_ANNOUNCE */

  /* Look for adjacency information. */
  if (rn)
    {
      for (adj = rn->adj_out; adj; adj = adj->next)
	if (adj->peer == peer)
	  break;
    }

  if (! adj)
    {
      adj = XCALLOC (MTYPE_BGP_ADJ_OUT, sizeof (struct bgp_adj_out));
      adj->peer = peer_lock (peer); /* adj_out peer reference */
      
      if (rn)
        {
          BGP_ADJ_OUT_ADD (rn, adj);
          bgp_lock_node (rn);
        }
    }

  if (adj->adv)
    bgp_advertise_clean (peer, adj, afi, safi);
  
  adj->adv = bgp_advertise_new ();

  adv = adj->adv;
  adv->rn = rn;
  
  assert (adv->binfo == NULL);
  adv->binfo = bgp_info_lock (binfo); /* bgp_info adj_out reference */
  
  if (attr)
    adv->baa = bgp_advertise_intern (peer->hash[afi][safi], attr);
  else
    adv->baa = baa_new ();
  adv->adj = adj;

  /* Add new advertisement to advertisement attribute list. */
  bgp_advertise_add (adv->baa, adv);

  FIFO_ADD (&peer->sync[afi][safi]->update, &adv->fifo);
}
Example #4
0
void
bgp_adj_in_set (struct bgp_node *rn, struct peer *peer, struct attr *attr)
{
  struct bgp_adj_in *adj;

  for (adj = rn->adj_in; adj; adj = adj->next)
    {
      if (adj->peer == peer)
	{
	  if (adj->attr != attr)
	    {
	      bgp_attr_unintern (adj->attr);
	      adj->attr = bgp_attr_intern (attr);
	    }
	  return;
	}
    }
  adj = XCALLOC (MTYPE_BGP_ADJ_IN, sizeof (struct bgp_adj_in));
  adj->peer = peer_lock (peer); /* adj_in peer reference */
  adj->attr = bgp_attr_intern (attr);
  BGP_ADJ_IN_ADD (rn, adj);
  bgp_lock_node (rn);
}
Example #5
0
/*
	standby_sync()
	- standby phase of the BPC
*/
LOCAL f8_status standby_sync()
{
	int cookie;
	ktime_t t;
	f8_uint i, size;
	long size2;
	f8_status ret = F8_BUSY;
	f8_u8 st;
	static ktime_t syncTime;
	
	t = ke_get_time();

	/* check automata */
	cookie = peer_lock();

	st = get_state();
	switch(st){
	case hsp_s_complete:
		size = 0;
		ke_toggle_flag(FKERN_LED_DBG1);
		syncTime=t;
		ke_set_flag(FKERN_LED_SYNCHRONIZED,1);
		for(i=0; i<KERN_NUM_SECTIONS; i++){
			if(peerHdr.x_mem_sizes[i] != g_kernel.x_mem_sizes[i]){
				ret = F8_VERSION_MISMATCH;
				set_state(hsp_s_idle);
				goto __done;
			}
			size += peerHdr.x_mem_sizes[i];
		}
		size += sizeof(struct marshalled_timer_t) * peerHdr.timer_q_len +
			sizeof(struct marshalled_event_t) * peerHdr.event_q_len +
			peerHdr.i_mem_size;
		if(size + sizeof(struct kpeer_hdr_t) > F8_VOLATILE_MEM_SIZE){
			ret = F8_LOW_MEMORY;
			set_state(hsp_s_idle);
			goto __done;
		}

		size2=sizeof(peerData);
		if(uncompress(peerData, &size2, peerDataZipped, peerHdr.zipped_data_len) != Z_OK){
			ret=F8_INVALID_DATA;
			set_state(hsp_s_idle);
			break;
		}
		
		/* indicate how much memory we can use */
		peerGuardian = peerData + size2;
		ki_load_volatile(&g_kernel);
		
		/* start another session */
		//peer_flush();
		set_state(hsp_s_idle);
		ret = F8_SUCCESS;
		peerCounters[1]++;
		break;

	case hsp_s_idle:
		break;
		
	case hsp_s_active:
		if(!ke_get_flag(FKERN_LED_SYNCHRONIZED)){
			//peer_flush();
			set_state(hsp_s_idle);
		}
		break;

	default:
		/* last error */
		peerCounters[5]++;
		peerCounters[3] = st;
		//peer_flush();
		set_state(hsp_s_idle);
		break;
	}
	
__done:	
	peer_unlock(cookie);

	if(t>syncTime+ki_get_primary_life()*5)
		ke_set_flag(FKERN_LED_SYNCHRONIZED,0);

	if(!ke_get_flag(FKERN_LED_SOFT_STOP)){
		if(t > g_kernel.peer->lastMsgTime + ki_get_primary_life()||
			(peerState!=KERN_S_RUNNING && !ke_get_peer_flag(FKERN_LED_SOFT_LOCK))
		){
			/* primary failure detected */
			/* try switch to primary state */
			if(g_kernel.peer_status.prog_id == g_kernel.status.prog_id && ke_get_flag(FKERN_LED_SYNCHRONIZED)){
				/* adjust kernel clock */
				kern_time_bias += hspTimeOffset;
				ki_log(&g_kernel, F8_PRIMARY_FAILURE,0,0,0);
				ki_switch_to(KERN_S_ARBITRATING);
				set_state(hsp_s_idle);
			}
			/* reset peer to unknown state */
			memset(&g_kernel.peer_status, 0, sizeof g_kernel.peer_status);
		}
	}
	
	return ret;
}
Example #6
0
LOCAL f8_status primary_sync()
{
	struct peer_cmd_t tp;
	int i, cookie;
	enum hsp_state_t st;
	long size2;
	
	st = get_state();
	if(st == hsp_s_collision){
		if(!check_priority()){
			ki_switch_to(KERN_S_STANDBY);
			return F8_SUCCESS;
		}
	}
	
	ki_save_volatile(&g_kernel);

	cookie = peer_lock();

	/* prepare volatile data */
	size2=sizeof(peerDataZipped);
	if(compress(peerDataZipped, &size2, peerData, peerPointer-peerData) == Z_OK){
		peerHdr.zipped_data_len=size2;
	}else{
		/* might continue with un-compressed data */
		return F8_LOW_MEMORY;
	}
	
	/* start automata */
	// set_state(hsp_s_connecting);
	_state = hsp_s_connecting;
	memset(&tp, 0, sizeof(tp));
	tp.cmd = Pr_connect;
	tp.code = F8_SUCCESS;
	tp.time = ke_get_time();
	//peer_flush();
	if(peer_write3(&tp, sizeof(tp), &g_kernel.status, sizeof(g_kernel.status), &peerHdr, sizeof(peerHdr)) < 0){
		set_state(hsp_s_idle);
		peer_unlock(cookie);
		return F8_CONNECTION_LOST;
	}
	peer_unlock(cookie);

	/* wait 5 times to see if connection established */
	for(i=0; i<5; i++){
		if(get_state() == hsp_s_active || get_state() >= 10){
			break;
		}
		miliSleep(hspConnTimeout);
	}
	st = get_state();
	if(st == hsp_s_active){
		/* expected transfer time */
		////i = size2*8/HSP_LINE_SPEED;
		////if(!i) i=1;
		// i is packet count, chenj 2009-3-5
		i=size2/1024+1;
		while(i > 0){
			if(get_state() >= 10){
				break;
			}			
			////miliSleep(hspConnTimeout);
			////i -= hspConnTimeout;
			miliSleep(2);
			i--;
		}
	}
	st = get_state();
	// set_state(hsp_s_idle);
	_state = hsp_s_idle;

	if(st == hsp_s_complete){
		return F8_SUCCESS;
	}else if(st == hsp_s_collision){
		ki_switch_to(KERN_S_ARBITRATING);
	}else{
		peerCounters[3] = st;
		peerCounters[5]++;
		// hsp_log(("primary timeout %d\n", i));
		/* reset peer state */
		memset(&g_kernel.peer_status, 0, sizeof g_kernel.peer_status);
	}
	
	return F8_TIMEOUT;
}