Esempio n. 1
0
void rf_parse_rx_packet(void)
{
    uint16_t frameControlField;
    uint8_t length, i;
    
    // Disable Rx while parsing packet
    rf_rx_off();
    
    length = mrf_read_long(RXFIFO);
		//printf("\nrx_length=%d\r\n",length);
    
    if((length - RF_PACKET_OVERHEAD_SIZE - 2) <= rfSettings.pRxInfo->max_length) {
        // Note: 2 bytes for footer are included in Rx length
        rfSettings.pRxInfo->length = length - RF_PACKET_OVERHEAD_SIZE - 2;
        frameControlField = mrf_read_long(RXFIFO+1);
        frameControlField |= (mrf_read_long(RXFIFO+2) << 8);
        rfSettings.pRxInfo->ackRequest = !!(frameControlField & RF_FCF_ACK_BM);
        rfSettings.pRxInfo->seqNumber = mrf_read_long(RXFIFO+3);
        rfSettings.pRxInfo->srcAddr = mrf_read_long(RXFIFO+8);
        rfSettings.pRxInfo->srcAddr |= (mrf_read_long(RXFIFO+9) << 8);
    
        for(i = 0; i < rfSettings.pRxInfo->length; i++) {
            rfSettings.pRxInfo->pPayload[i] = mrf_read_long(RXFIFO+10+i);
        }
    
        rfSettings.pRxInfo->rssi = mrf_read_long(RXFIFO+1+length+1);
        rx_data_ready = 1;
    }
    
    // Re-enable Rx when done parsing
    rf_rx_on();
    
}
Esempio n. 2
0
void bmac_nw_task()
{
	int8_t v;
	int8_t e;
	uint8_t backoff;
	nrk_sig_mask_t event;
	
	while(bmac_started() == 0) {
		nrk_wait_until_next_period();
	}
	
	while(1) {
		
		if(is_enabled)
		{
		v = 1;
		rf_rx_on();
		if(rx_buf_empty) {
				v = _bmac_channel_check();
		} else {
			e = nrk_event_signal(bmac_rx_pkt_signal); // Mb
			// Should signal user task here as a "reminder"
		}
		
		if(v == 0) {
				// Channel detected as busy, attept to Rx
			_bmac_rx();
				// Should signal user task here to notify of Rx 
		}
		else if(tx_data_ready) {
			// Only try to Tx if the channel is free
			rf_rx_off(); // Mb
			_bmac_tx();
		}
		
		//rf_rx_off(); // Mb
		nrk_wait(_bmac_check_period);
		
		}
	else
	{
			event =0;
			do
			{
				v = nrk_signal_register(bmac_enable_signal);
				event = nrk_event_wait(SIG(bmac_enable_signal));
			}
			while((event & SIG(bmac_enable_signal))==0);
	}
			
		
	}
}
Esempio n. 3
0
int8_t _bmac_channel_check ()
{
  int8_t val = 0;

  rf_rx_on ();
  val += rf_cca_check ();
  val += rf_cca_check ();
  val += rf_cca_check ();
  if (val > 1)
    val = 1;
  rf_rx_off ();
  return val;
}
Esempio n. 4
0
// This function will put the node into a low-duty checking mode to save power
void tdma_snooze()
{
    int8_t v;
    uint8_t i;

// stop the software watchdog timer so it doesn't interrupt
    nrk_sw_wdt_stop(0);
// This flag is cleared only by the button interrupt
    snoozing=1;
// Setup the button interrupt
    nrk_ext_int_configure( NRK_EXT_INT_1,NRK_LEVEL_TRIGGER, &wakeup_func);
// Clear it so it doesn't fire instantly
    EIFR=0xff;
    nrk_ext_int_enable( NRK_EXT_INT_1);
// Now loop and periodically check for packets
    while(1)
    {
        nrk_led_clr(RED_LED);
        nrk_led_clr(GREEN_LED);
        rf_power_up();
        rf_rx_on ();
// check return from button interrupt on next cycle
        if(snoozing==0 ) return;
        tmp_time.secs=0;
        tmp_time.nano_secs=10*NANOS_PER_MS;
        nrk_led_set(RED_LED);
        // Leave radio on for two loops of 10ms for a total of 20ms every 10 seconds
        for(i=0; i<2; i++ )
        {
            v = _tdma_rx ();
            if(v==NRK_OK) {
                nrk_led_set(RED_LED);
                nrk_ext_int_disable( NRK_EXT_INT_1);
                nrk_sw_wdt_update(0);
                nrk_sw_wdt_start(0);
                return NRK_OK;
            }
            nrk_wait(tmp_time);
        }
        nrk_led_clr(RED_LED);
        rf_power_down();
        tmp_time.secs=10;
        tmp_time.nano_secs=0;
        nrk_sw_wdt_stop(0);
        nrk_wait(tmp_time);

    }

}
Esempio n. 5
0
// Assuming that CCA returned 1 and a packet is on its way
// Receive the packet or timeout and error
int8_t _bmac_rx ()
{
  int8_t n;
  uint8_t cnt;

  rf_rx_on ();
  cnt = 0;
//printf( "calling rx\r\n" );
  dummy_t.secs = 0;
  dummy_t.nano_secs = 5 * NANOS_PER_MS;
  nrk_wait (dummy_t);

  n = rf_rx_packet_nonblock ();

  if (n != NRK_OK) {
    if (rx_failure_cnt < 65535)
      rx_failure_cnt++;
    rf_rx_off ();
    return 0;
  }

/*while ( rf_rx_packet_nonblock() != NRK_OK )
	{
	cnt++;
	nrk_wait(_bmac_check_period);
	if(cnt>2) { 
			#ifdef DEBUG
			printf( "rx timeout 1 %d\r\n",cnt );
			#endif
			if(rx_failure_cnt<65535) rx_failure_cnt++;
			rf_rx_off();
			return 0;
			} 
	}
*/


  rx_buf_empty = 0;
#ifdef DEBUG
  printf ("BMAC: SNR= %d [", bmac_rfRxInfo.rssi);
  for (uint8_t i = 0; i < bmac_rfRxInfo.length; i++)
    printf ("%c", bmac_rfRxInfo.pPayload[i]);
  printf ("]\r\n");
#endif
  rf_rx_off ();
  return 1;
}
Esempio n. 6
0
int8_t _bmac_rx()
{
	int8_t result;
	uint8_t cnt;
	
	rf_rx_on();
	
	cnt = 0;
	while((result = rf_rx_check_cca()) != 0) {
		cnt++;
		nrk_wait(_bmac_check_period);
		if(cnt > 2) {
			if(rx_failure_cnt < 65535) rx_failure_cnt++;
			rf_rx_off();
			//printf("failure1=%d\r\n",rx_failure_cnt);
			return 0;
		}
	}
	

	// Packet on its way
	cnt = 0;
	while((result = rf_rx_packet()) == 0) {
		cnt++;
		nrk_wait(_bmac_check_period);
		//nrk_spin_wait_us(100);
		if(cnt > 1) {
			if(rx_failure_cnt < 65535) rx_failure_cnt++;
				rf_rx_off();
			//printf("failure2=%d\r\n",rx_failure_cnt);
				return 0;	
			}
		}
	//printf("failure3=%d\r\n",rx_failure_cnt);
	rf_rx_off();
	rx_buf_empty = 0;
	return 1;
	// Note: CRC is checked in hardware
	
}
Esempio n. 7
0
void Task1 ()
{
  uint16_t cnt;
  uint8_t len,i;
  //printf ("My node's address is %d\r\n", NODE_ADDR);

  //printf ("Task1 PID=%d\r\n", nrk_get_pid ());


  rfRxInfo.pPayload = rx_buf;
  rfRxInfo.max_length = RF_MAX_PAYLOAD_SIZE;
  nrk_int_enable();
  rf_init (&rfRxInfo, 13, 0x2420, 0x1214);

  cnt = 0;
  slip_init (stdin, stdout, 0, 0);
	rf_rx_on();
  while (1) {
    


    while (rf_rx_packet_nonblock () != NRK_OK) {
      nrk_wait_until_next_period();

    }
		
		
    rx_packet_len = rfRxInfo.length;
    for(i=0; i<rfRxInfo.length; i++ ) slip_tx_buf[i]=rfRxInfo.pPayload[i];
		slip_tx_buf[10] = rfRxInfo.rssi;
		
    while(uart_tx_busy==1) nrk_wait_until_next_period();
    uart_tx_busy=1;
    slip_tx (slip_tx_buf, rx_packet_len);
    uart_tx_busy=0;
		

  }
}
Esempio n. 8
0
uint8_t rf_tx_packet(RF_TX_INFO *pRTI)
{
    uint16_t frameControlField;
    uint8_t packetLength;
    uint8_t success, i;
    // Note: checksum is automatic in HW
	
		LPC_GPIO1->FIOPIN ^= 1<<31;
    
    packetLength = pRTI->length + RF_PACKET_OVERHEAD_SIZE;
    
    frameControlField = RF_FCF_NOACK;
    if(auto_ack_enable || pRTI->ackRequest) frameControlField |= RF_ACK_BM;
    if(security_enable) frameControlField |= 0x0000; // TODO: Paul Gurniak, add security
    
    mrf_write_long(TXNFIFO, RF_PACKET_OVERHEAD_SIZE);    // No checksum, overhead is all header
    mrf_write_long(TXNFIFO+1, packetLength);
    
    // Write header bytes
    mrf_write_long(TXNFIFO+2, frameControlField & 0xFF);
    mrf_write_long(TXNFIFO+3, frameControlField >> 8);
	  mrf_write_long(TXNFIFO+4, rfSettings.txSeqNumber);
    mrf_write_long(TXNFIFO+5, rfSettings.panId & 0xFF);
    mrf_write_long(TXNFIFO+6, rfSettings.panId >> 8);
    mrf_write_long(TXNFIFO+7, pRTI->destAddr & 0xFF);
    mrf_write_long(TXNFIFO+8, pRTI->destAddr >> 8);
    mrf_write_long(TXNFIFO+9, rfSettings.myAddr & 0xFF);
    mrf_write_long(TXNFIFO+10, rfSettings.myAddr >> 8);
    
    // Write payload
    for(i = 0; i < pRTI->length; i++) {
        mrf_write_long(TXNFIFO+11+i, pRTI->pPayload[i]); // pPayload is the user defined part of data packet right ?
    }
    
    if(pRTI->cca) {
        uint8_t cnt = 0;
        if(!rfSettings.receiveOn) {
            rf_rx_on();
        }
				while(!rf_rx_check_cca()) {
					cnt++;
					if(cnt > 100) {
						return FALSE;
					}
					halWait(100);
				}
    }
    
    tx_status_ready = 0;
    mrf_write_short(TXNCON, auto_ack_enable ? 0x05 : 0x01);  // Send contents of TXNFIFO as packet
    //putchar(auto_ack_enable);
    // Wait for Tx to finish
    while(!tx_status_ready);
    wait_ms(50);
    success = 1;
		//putchar(auto_ack_enable);
    if(auto_ack_enable || pRTI->ackRequest) {
        uint8_t k = mrf_read_short(TXSTAT);
				success = !(k & 0x01);
			//printf("ACK%c",k);
    }
    
		//printf("tx_pkt success = %d\r\n",success);
		// Transmission works fine : Checked by Madhur, success = 1only when the receiver is enabled
		
    // Increment sequence, return result
    rfSettings.txSeqNumber++;
    return success;
}
Esempio n. 9
0
void tdma_nw_task ()
{
  int8_t v, i;
  uint16_t slot, tmp,sync;
  nrk_sig_mask_t event;

  do {
    nrk_wait_until_next_period ();
  } while (!tdma_started ());
  _tdma_slot_time.nano_secs = TDMA_DEFAULT_SLOT_MS * NANOS_PER_MS;
  _tdma_slot_time.secs = 0;

//register the signal after bmac_init has been called
  v = nrk_signal_register (tdma_enable_signal);
  if (v == NRK_ERROR)
    nrk_kprintf (PSTR ("Failed to register signal\r\n"));
  slot = 0;
//rf_set_rx (&tdma_rfRxInfo, tdma_chan);



  while (1) {
    if (tdma_mode == TDMA_HOST) {
	    sync_status=1; // HOST is always synced
      // This is the downstream transmit slot
      if (slot == 0) {

        //rf_rx_off();
        // If there is no pending packet, lets make an empty one
        if (tx_data_ready == 0) {
          tdma_rfTxInfo.pPayload = tdma_tx_buf;
          // Setup the header data
          tdma_rfTxInfo.pPayload[TDMA_DST_LOW] = 0xff;  // dst
          tdma_rfTxInfo.pPayload[TDMA_DST_HIGH] = 0xff;
          tdma_rfTxInfo.pPayload[TDMA_SRC_LOW] = 0x00;  // src
          tdma_rfTxInfo.pPayload[TDMA_SRC_HIGH] = 0x00;
          tdma_rfTxInfo.pPayload[TDMA_SEQ_NUM_LOW] = 0x00;      // seq num
          tdma_rfTxInfo.pPayload[TDMA_SEQ_NUM_HIGH] = 0x00;
          tdma_rfTxInfo.length = TDMA_PCF_HEADER;
        }
        tdma_rfTxInfo.pPayload[TDMA_CYCLE_SIZE_LOW] = tdma_slots_per_cycle & 0xff;      // cycle size 
        tdma_rfTxInfo.pPayload[TDMA_CYCLE_SIZE_HIGH] =
          tdma_slots_per_cycle >> 8;
        tdma_rfTxInfo.pPayload[TDMA_SLOT_LOW] = 0;      // slot
        tdma_rfTxInfo.pPayload[TDMA_SLOT_HIGH] = 0;
        tdma_rfTxInfo.pPayload[TDMA_SLOT_SIZE] = tdma_slot_len_ms;
        nrk_time_get (&_tdma_next_wakeup);
        tdma_rfTxInfo.destAddr = 0xffff;
        tdma_rfTxInfo.ackRequest = 0;
        tdma_rfTxInfo.cca = 0;
        _tdma_tx ();
        rf_rx_on ();
      }
      else {
        // Upstream data slot
        v = _tdma_rx ();
        if (v == 1)
          tdma_last_tx_slot = slot;
      }
      slot++;
      if (slot >= tdma_slots_per_cycle + 1)
        slot = 0;
      nrk_time_add (&_tdma_next_wakeup, _tdma_next_wakeup, _tdma_slot_time);
      nrk_time_compact_nanos (&_tdma_next_wakeup);
      nrk_wait_until (_tdma_next_wakeup);

    }
Esempio n. 10
0
int8_t _bmac_tx ()
{
  uint8_t v, backoff, backoff_count;
  uint16_t b;

#ifdef DEBUG
  nrk_kprintf (PSTR ("_bmac_tx()\r\n"));
#endif
  if (cca_active) {

// Add random time here to stop nodes from synchronizing with eachother
    b = _nrk_time_to_ticks (&_bmac_check_period);
    b = b / ((rand () % 10) + 1);
//printf( "waiting %d\r\n",b );
    nrk_wait_until_ticks (b);
//nrk_wait_ticks(b);

    backoff_count = 1;
    do {
#ifdef BMAC_MOD_CCA
	v=_bmac_rx();
	v=!v;
        if (v == 1) { 
		break; 
	}
        nrk_event_signal (bmac_rx_pkt_signal);
#else
      v = _bmac_channel_check ();
      if (v == 1)
        break;
#endif
      // Channel is busy
      backoff = rand () % (_b_pow (backoff_count));
#ifdef DEBUG
      printf ("backoff %d\r\n", backoff);
#endif
//      printf( "backoff %d\r\n",backoff );
      nrk_wait_until_next_n_periods (backoff);
      backoff_count++;
      if (backoff_count > 6)
        backoff_count = 6;      // cap it at 64    
      b = _nrk_time_to_ticks (&_bmac_check_period);
      b = b / ((rand () % 10) + 1);
//      printf( "waiting %d\r\n",b );
      nrk_wait_until_ticks (b);
//      nrk_wait_ticks(b);

    }
    while (v == 0);
  }

  // send extended preamble
  bmac_rfTxInfo.cca = 0;
  bmac_rfTxInfo.ackRequest = 0;

  uint16_t ms = _bmac_check_period.secs * 1000;
  ms += _bmac_check_period.nano_secs / 1000000;
  //printf( "CR ms: %u\n",ms );
  //target_t.nano_secs+=20*NANOS_PER_MS;
  rf_rx_on ();
  pkt_got_ack = rf_tx_packet_repeat (&bmac_rfTxInfo, ms);

  // send packet
  // pkt_got_ack=rf_tx_packet (&bmac_rfTxInfo);
  rf_rx_off ();                 // Just in case auto-ack left radio on
  tx_data_ready = 0;
  nrk_event_signal (bmac_tx_pkt_done_signal);
  return NRK_OK;
}