void post_receive(void) {
	last_post = RX_POST;
	/* this sets the rxlen field */
	/* this is undocumented but very important */
	/* you will not receive anything without setting it */
	*MACA_TXLEN = (MAX_PACKET_SIZE << 16);
	if(dma_rx == 0) {
		dma_rx = get_free_packet();
		if (dma_rx == 0) {
			PRINTF("trying to fill MACA_DMARX in post_receieve but out of packet buffers\n\r");		
			/* set the sftclock so that we return to the maca_isr */
			*MACA_SFTCLK = *MACA_CLK + RECV_SOFTIMEOUT; /* soft timeout */ 
			*MACA_TMREN = (1 << maca_tmren_sft);
			/* no free buffers, so don't start a reception */
			enable_irq(MACA);
			return;
		}
	}
	BOUND_CHECK(dma_rx);
	BOUND_CHECK(dma_tx);
	*MACA_DMARX = (uint32_t)&(dma_rx->data[0]);
	/* with timeout */		
	*MACA_SFTCLK = *MACA_CLK + RECV_SOFTIMEOUT; /* soft timeout */ 
	*MACA_TMREN = (1 << maca_tmren_sft);
	/* start the receive sequence */
	*MACA_CONTROL = ( (1 << maca_ctrl_asap) | 
			  ( 4 << PRECOUNT) |
			  ( fcs_mode << NOFC ) |
			  (1 << maca_ctrl_auto) |
			  (1 << maca_ctrl_prm) |
			  (maca_ctrl_seq_rx));
	/* status bit 10 is set immediately */
        /* then 11, 10, and 9 get set */ 
        /* they are cleared once we get back to maca_isr */ 
}
Example #2
0
/*------------------------------------------------------------------------
 * radioWrite - write a packet from an Radioernet device
 *------------------------------------------------------------------------
 */
devcall	radioWrite (
	struct	dentry	*devptr,	/* entry in device switch table	*/
	void	*buf,			/* buffer to hold packet	*/
	uint32	len			/* length of buffer		*/
		)
{
	volatile packet_t *p;
	struct radio *rptr;
	uint32 i;
	char *from, *to;

	rptr = &radiotab[devptr->dvminor];

	/*
	 * Return immediately if a buffer is available
	 */

	p = get_free_packet();

	if(p) {
		kprintf("radioWrite preparing 0x%08x\n", p);
		p->length = len;
		p->offset = 0;
		for (from = buf, to = (char *)p->data, i = 0; i < len; i++)
		  *to++ = *from++;
		//kprintf("radioWrite semcount %d\n", semcount(rptr->osem));
		//wait(rptr->osem);
		tx_packet(p);
		return len;
	} else {
        	kprintf("radioWrite: can't get free packet\n");
		return SYSERR;
	}
}
Example #3
0
File: maca.c Project: 1uk3/contiki
void post_tx(void) {
	/* set dma tx pointer to the payload */
	/* and set the tx len */
	disable_irq(MACA);
	last_post = TX_POST;
	dma_tx = tx_head; 
#if PACKET_STATS
	dma_tx->post_tx++;
#endif
	*MACA_TXSEQNR = dma_tx->data[2];
	*MACA_TXLEN = (uint32_t)((dma_tx->length) + 2) | (3 << 16); /* set rx len to ACK length */
	*MACA_DMATX = (uint32_t)&(dma_tx->data[ 0 + dma_tx->offset]);
	if(dma_rx == 0) {
		dma_rx = get_free_packet();
		if (dma_rx == 0) { 
			dma_rx = &dummy_ack;
			PRINTF("trying to fill MACA_DMARX on post_tx but out of packet buffers\n\r");
		}
		
	}	
	BOUND_CHECK(dma_rx);
	BOUND_CHECK(dma_tx);
	*MACA_DMARX = (uint32_t)&(dma_rx->data[0]);
	/* disable soft timeout clock */
	/* disable start clock */
	*MACA_TMRDIS = (1 << maca_tmren_sft) | ( 1<< maca_tmren_cpl) | ( 1 << maca_tmren_strt ) ;
	
        /* set complete clock to long value */
	/* acts like a watchdog in case the MACA locks up */
	*MACA_CPLCLK = *MACA_CLK + CPL_TIMEOUT;
	/* enable complete clock */
	*MACA_TMREN = (1 << maca_tmren_cpl);
	
	enable_irq(MACA);
	*MACA_CONTROL = ( ( 4 << PRECOUNT) |
			  ( prm_mode << PRM) |
			  (maca_ctrl_mode_no_cca << maca_ctrl_mode) |
			  (1 << maca_ctrl_asap) |
			  (maca_ctrl_seq_tx));	
	/* status bit 10 is set immediately */
        /* then 11, 10, and 9 get set */ 
        /* they are cleared once we get back to maca_isr */ 
}
Example #4
0
void main(void) {
	volatile packet_t *p;
	char c;
	uint16_t r=30; /* start reception 100us before ack should arrive */
	uint16_t end=180; /* 750 us receive window*/

	/* trim the reference osc. to 24MHz */
	trim_xtal();

	uart_init(UART1, 115200);

	vreg_init();

	maca_init();

	set_channel(0); /* channel 11 */
//	set_power(0x0f); /* 0xf = -1dbm, see 3-22 */
//	set_power(0x11); /* 0x11 = 3dbm, see 3-22 */
	set_power(0x12); /* 0x12 is the highest, not documented */

        /* sets up tx_on, should be a board specific item */
	GPIO->FUNC_SEL_44 = 1;	 
	GPIO->PAD_DIR_SET_44 = 1;	 

	GPIO->FUNC_SEL_45 = 2;	 
	GPIO->PAD_DIR_SET_45 = 1;	 

	*MACA_RXACKDELAY = r;
	
	printf("rx warmup: %d\n\r", (int)(*MACA_WARMUP & 0xfff));

	*MACA_RXEND = end;

	printf("rx end: %d\n\r", (int)(*MACA_RXEND & 0xfff));

	set_prm_mode(AUTOACK);

	print_welcome("rftest-tx");

	while(1) {		
	    		
		/* call check_maca() periodically --- this works around */
		/* a few lockup conditions */
		check_maca();

		while((p = rx_packet())) {
			if(p) {
				printf("RX: ");
				print_packet(p);
				free_packet(p);
			}
		}

		if(uart1_can_get()) {
			c = uart1_getc();

			switch(c) {
			case 'z':
				r++;
				if(r > 4095) { r = 0; }
				*MACA_RXACKDELAY = r;
				printf("rx ack delay: %d\n\r", r);
				break;
			case 'x':
				if(r == 0) { r = 4095; } else { r--; }
				*MACA_RXACKDELAY = r;
				printf("rx ack delay: %d\n\r", r);
				break;
			case 'q':
				end++;
				if(r > 4095) { r = 0; }
				*MACA_RXEND = end;
				printf("rx end: %d\n\r", end);
				break;
			case 'w':
				end--;
				if(r == 0) { r = 4095; } else { r--; }
				*MACA_RXEND = end;
				printf("rx end: %d\n\r", end);
				break;
			default:
				p = get_free_packet();
				if(p) {
					fill_packet(p);
					
					printf("autoack-tx --- ");
					print_packet(p);
					
					tx_packet(p);				
				}
				break;
			}
		}
		
	}

}
void main(void) {
  volatile packet_t *p;
#ifdef CARRIER_SENSE
  volatile uint32_t i;
#endif
  uint16_t r=30; /* start reception 100us before ack should arrive */
  uint16_t end=180; /* 750 us receive window*/

  /* trim the reference osc. to 24MHz */
  trim_xtal();
  uart_init(INC, MOD, SAMP);
  vreg_init();
  maca_init();

  ///* Setup the timer */
  *TMR_ENBL = 0;                     /* tmrs reset to enabled */
  *TMR0_SCTRL = 0;
  *TMR0_LOAD = 0;                    /* reload to zero */
  *TMR0_COMP_UP = 18750;             /* trigger a reload at the end */
  *TMR0_CMPLD1 = 18750;              /* compare 1 triggered reload level, 10HZ maybe? */
  *TMR0_CNTR = 0;                    /* reset count register */
  *TMR0_CTRL = (COUNT_MODE<<13) | (PRIME_SRC<<9) | (SEC_SRC<<7) | (ONCE<<6) | (LEN<<5) | (DIR<<4) | (CO_INIT<<3) | (OUT_MODE);
  *TMR_ENBL = 0xf;                   /* enable all the timers --- why not? */

  set_channel(CHANNEL); /* channel 11 */
  set_power(0x12); /* 0x12 is the highest, not documented */

  /* sets up tx_on, should be a board specific item */
  GPIO->FUNC_SEL_44 = 1;	 
  GPIO->PAD_DIR_SET_44 = 1;	 
  GPIO->FUNC_SEL_45 = 2;	 
  GPIO->PAD_DIR_SET_45 = 1;	 
  *MACA_RXACKDELAY = r;
  *MACA_RXEND = end;

  set_prm_mode(AUTOACK);

  while(1) {		

    if((*TMR0_SCTRL >> 15) != 0) 
      tick();

    /* call check_maca() periodically --- this works around */
    /* a few lockup conditions */
    check_maca();

    while((p = rx_packet())) {
      if(p) free_packet(p);
    }

    p = get_free_packet();
    if(p) {
      fill_packet(p);

#ifdef CARRIER_SENSE
      for(i=0; i<POWER_DELAY; i++) {continue;}
      while(get_power()>74) {}
#endif

#ifdef BLOCKING_TX
      blocking_tx_packet(p);
#else
      tx_packet(p);
#endif

      current_pkts++;

#if defined(RANDOM_WAIT_TIME) || defined(FIXED_WAIT)
      random_wait();
#endif
    }
  }
}
Example #6
0
File: maca.c Project: 1uk3/contiki
void maca_isr(void) {

//	print_packets("maca_isr");

	maca_entry++;

	if (bit_is_set(*MACA_STATUS, maca_status_ovr))
	{ PRINTF("maca overrun\n\r"); }
	if (bit_is_set(*MACA_STATUS, maca_status_busy))
	{ PRINTF("maca busy\n\r"); } 
	if (bit_is_set(*MACA_STATUS, maca_status_crc))
	{ PRINTF("maca crc error\n\r"); }
	if (bit_is_set(*MACA_STATUS, maca_status_to))
	{ PRINTF("maca timeout\n\r"); }

	if (data_indication_irq()) {
		*MACA_CLRIRQ = (1 << maca_irq_di);

		if (dma_rx != &dummy_ack && dma_rx != &dummy_rx)
		{
			dma_rx->length = *MACA_GETRXLVL - 2; /* packet length does not include FCS */
			dma_rx->lqi = get_lqi();
			dma_rx->rx_time = *MACA_TIMESTAMP;

			/* check if received packet needs an ack */
			if(prm_mode == AUTOACK && (dma_rx->data[1] & 0x20)) {
				/* this wait is necessary to auto-ack */
				volatile uint32_t wait_clk;
				wait_clk = *MACA_CLK + 200;
				while(*MACA_CLK < wait_clk) { continue; }
			}

			if(maca_rx_callback != 0) { maca_rx_callback(dma_rx); }

			add_to_rx(dma_rx);
		}
		dma_rx = 0;
	}
	if (filter_failed_irq()) {
		PRINTF("maca filter failed\n\r");
		ResumeMACASync();
		*MACA_CLRIRQ = (1 << maca_irq_flt);
	}
	if (checksum_failed_irq()) {
		PRINTF("maca checksum failed\n\r");
		ResumeMACASync();
		*MACA_CLRIRQ = (1 << maca_irq_crc);
	}
	if (softclock_irq()) {
		*MACA_CLRIRQ = (1 << maca_irq_sftclk);
	}
	if (poll_irq()) {		
		*MACA_CLRIRQ = (1 << maca_irq_poll);
	}
	if(action_complete_irq()) {
		/* PRINTF("maca action complete %d\n\r", get_field(*MACA_CONTROL,SEQUENCE)); */
		if(last_post == TX_POST) {
			tx_head->status = get_field(*MACA_STATUS,CODE);

#if MACA_INSERT_ACK
/* Having sent a message with the acknowledge request flag set the
 * MACA hardware will only give a tx success indication if the message
 * was acknowledged by the remote node. We need to detect this
 * condition and inject an ACK packet into the internal receive stream
 * as the higher layers are expecting to see an ACK packet.*/

			if(tx_head->status == SUCCESS && (tx_head->data[0] & MAC_ACK_REQUEST_FLAG)) {

				/* Create the dummy ack packet */

				static volatile packet_t *ack_p;
				if(ack_p = get_free_packet()) {
					ack_p->length = 3;
					ack_p->offset = 1;
					ack_p->data[0] = 3;
					ack_p->data[1] = 0x02;
					ack_p->data[2] = 0;
					ack_p->data[3] = *MACA_TXSEQNR;
					insert_at_rx_head(ack_p);
				}

			}
#endif

			if(maca_tx_callback != 0) { maca_tx_callback(tx_head); }
			dma_tx = 0;
			free_tx_head();
			last_post = NO_POST;
		}
		ResumeMACASync();
		*MACA_CLRIRQ = (1 << maca_irq_acpl);		
	}

	decode_status();

	if (*MACA_IRQ != 0)
	{ PRINTF("*MACA_IRQ %x\n\r", (unsigned int)*MACA_IRQ); }

	if(tx_head != 0) {
		post_tx();
	} else {
		post_receive();
	} 
}