📄 radioclient.c
字号:
RadioClient_EnterReceive();
setState(STATE_WAIT_FOR_RECEIVE);
}
break;
case STATE_WAIT_FOR_SERVER:
#ifdef TO_DEBUG
SCI0_OutChar('S');
#endif
/* server is now in receive mode */
if(tickCounter >= WAIT_FOR_SERVER_TICK_COUNT) {
RadioClient_Transmit();
setState(STATE_WAIT_FOR_EOT);
}
break;
}
/* restart the timer */
RadioClient_RestartTick();
}
#pragma CODE_SEG DEFAULT
/* end of the interrupt service routine ================================= */
unsigned char RadioClient_Init(unsigned char baudRate,
unsigned char rfChannel,
unsigned long serverAddressHeader,
unsigned long clientAddressHeader,
unsigned char client) {
/* declare space for rx and tx addresses */
unsigned char rx1_address_array[ADDRESS_LENGTH];
unsigned char tx_address_array[ADDRESS_LENGTH];
// space to test the first the receive address was correctly written
unsigned char test[ADDRESS_LENGTH];
/* configure CE pin as an output */
CE_DDR = 1;
/* Enter Standby-I Mode */
CE = 0;
/* initialise the SPI */
SPI_Init(baudRate);
/* Select the first flagged client as the current client, and
simultaneously check for the no client flag set error.
If a client's flag is not set, it will not be polled. */
if(client == CLIENT_FLAG_0) {
rx1_address_array[0] = tx_address_array[0] = CLIENT_TAIL_0;
} else if(client == CLIENT_FLAG_1) {
rx1_address_array[0] = tx_address_array[0] = CLIENT_TAIL_1;
} else if(client == CLIENT_FLAG_2) {
rx1_address_array[0] = tx_address_array[0] = CLIENT_TAIL_2;
} else if(client == CLIENT_FLAG_3) {
rx1_address_array[0] = tx_address_array[0] = CLIENT_TAIL_3;
} else if(client == CLIENT_FLAG_4) {
rx1_address_array[0] = tx_address_array[0] = CLIENT_TAIL_4;
} else {
// no clients are active, return error
return INIT_ERROR_NO_CLIENT_SET;
}
/* set the first four bytes of the receive address of pipe 1
as serverAddress */
rx1_address_array[1] = clientAddressHeader & 0xff;
rx1_address_array[2] = (clientAddressHeader >> 8) & 0xff;
rx1_address_array[3] = (clientAddressHeader >> 16) & 0xff;
rx1_address_array[4] = (clientAddressHeader >> 24) & 0xff;
/* set the first four of the client transmit bytes */
tx_address_array[1] = serverAddressHeader & 0xff;
tx_address_array[2] = (serverAddressHeader >> 8) & 0xff;
tx_address_array[3] = (serverAddressHeader >> 16) & 0xff;
tx_address_array[4] = (serverAddressHeader >> 24) & 0xff;
cc = &commState;
cc->id = 0;
/* init the transmit ring buffers */
RB_INIT(&cc->outRB, cc->outBuf);
/* init the receive ring buffers */
RB_INIT(&cc->inRB, cc->inBuf);
/* lastTID is 0x00 */
cc->lastTID = 0x00;
/* notify clients that the server has been reset */
cc->reset = HEADER_RESET_MASK;
/* seems to be required? May be an artifact of original buggy SPI code... */
SPI_OutChar(NOP);
/*
bit EN_AA Register
7:6 00 Reserved : Must be zero
5 1 : Enable auto-ACK on data pipe 5
4 1 : Enable auto-ACK on data pipe 4
3 1 : Enable auto-ACK on data pipe 3
2 1 : Enable auto-ACK on data pipe 2
1 1 : Enable auto-ACK on data pipe 1
0 1 : Enable auto-ACK on data pipe 0
*/
SPI_OutChar2(W_EN_AA, 0x3f);
/*
bit EN_RXADDR Register
7:6 0 Reserved : Must be zero
5 0 ERX_P5 : Disable
4 0 ERX_P4 : Disable
3 0 ERX_P3 : Disable
2 0 ERX_P2 : Disable
1 1 ERX_P1 : Enable server
0 1 ERX_P0 : Reserved for ACKs
*/
SPI_OutChar2(W_EN_RXADDR, 0x03);
/*
bit SETUP_AW Register
7:2 0 Reserved : Must be zero
1:0 11 AW : RX/TA Address field width = 5
*/
SPI_OutChar2(W_SETUP_AW, 0x03);
/*
bit SETUP_RETR Register
7:4 01 ARD (Auto re-transmit delay)
3:1 15 ARC (Auto re-transmit count)
*/
SPI_OutChar2(W_SETUP_RETR, 0x0f);
/*
Set the RF_CH, which RF channel to receive/transmit on
*/
SPI_OutChar2(W_RF_CH, (rfChannel & RF_CH_MASK));
/*
bit RF_SETUP Register
7:5 0 Reserved
4 0 PLL_LOCK : Use Default
3 X RF_DR : RF baud rate, depends on RF_BAUD_RATE
2:1 11 RF_PWR : 0dBm output power in TX mode (max)
0 1 LNA_HCURR : Setup LNA gain
*/
#ifdef SLOW_RF_BAUD_RATE
SPI_OutChar2(W_RF_SETUP, 0x07);
#else // FAST_RF_BAUD_RATE
SPI_OutChar2(W_RF_SETUP, 0x0f);
#endif
/*
RX_ADDR_P0 Register
Receive address for current client (for ACK).
*/
SPI_OutChar3(W_RX_ADDR_P0, tx_address_array, ADDRESS_LENGTH);
/*
RX_ADDR_P1 Register
Receive address for client 0.
*/
SPI_OutChar3(W_RX_ADDR_P1, rx1_address_array, ADDRESS_LENGTH);
/*
Perform a simple read to make sure that memory is being
correctly written.
*/
SPI_Read(R_RX_ADDR_P1, test, ADDRESS_LENGTH);
/*
Will return NO_POWER if the read RX1 address does not match
the address written, meaning that there's no power to the
module.
*/
if(test[0] != rx1_address_array[0]
|| test[1] != rx1_address_array[1]
|| test[2] != rx1_address_array[2]
|| test[3] != rx1_address_array[3]
|| test[4] != rx1_address_array[4]) {
return INIT_ERROR_NO_POWER;
}
/*
TX_ADDR Register
Transmit address for current client.
*/
SPI_OutChar3(W_TX_ADDR, tx_address_array, ADDRESS_LENGTH);
/*
RW_PW_0 Register
Set the width of data pipe 0 (Reserved for ACKs)
*/
SPI_OutChar2(W_RX_PW_0, 0);
/*
RW_PW_1 Register
Set the width of the RX payload on pipe 1
*/
SPI_OutChar2(W_RX_PW_1, PAYLOAD_LEN);
/* clear all previous interrupts */
SPI_OutChar2(W_STATUS, 0x70);
/* flush buffers */
SPI_OutChar(FLUSH_TX);
SPI_OutChar(FLUSH_RX);
/* start in receive mode */
RadioClient_EnterReceive();
setState(STATE_WAIT_FOR_RECEIVE);
/* start the ticker */
RadioClient_RestartTick();
return INIT_NO_ERROR;
}
/*
Diagnostic to check for carriers (jammed signal). Infinite loop.
Cycle through all 128 channels. If Carrier is detected on a channel,
increment its corresponding element in the carrier_detect array.
See radioClient.h for more info.
*/
void RadioClient_CheckCarrier(void) {
unsigned char i,j,k,cd;
unsigned short carrier_detect[128];
while(1) {
for(i = 127; i != 0; i++) {
CE = 0;
/*
bit CONFIG Register
7 0 Reserved
6 1 MASK_RX_DR : Don't reflect RX_DR on IRQ pin
5 1 MASK_TX_DS : Don't reflect TX_DS on IRQ pin
4 1 MASK_MAX_RT : Don't reflect MAX_RT on IRQ pin
3 1 EN_CRC : Enable CRC
2 1 CRCO : 2 byte CRC
1 1 PWR_UP : Power Up
0 1 PRIM_RX : PRX
Enter receive mode
*/
SPI_OutChar2(W_CONFIG, 0x7f);
/* select a new RF channel */
SPI_OutChar2(W_RF_CH, i);
CE = 1;
for(j=255; j!=0; j--) {
for(k=255; k!=0; k--) {
/* Specification seems to imply 258us delay is required here.
This will delay for quite a bit longer than that. */
}
}
/* read the one byte long CD register */
SPI_Read(R_CD, &cd, 1);
/* if carrier is detected, increment carrier_detect[i] */
if(cd) {
/* protect against overflow */
if(carrier_detect[i] != 0xffff) {
carrier_detect[i]++;
}
}
}
/*
Each time all channels have been tested, output the results to date.
The longer this is left to run, a better average of the results should
be obtained.
*/
#if (DEBUG2SCI0 > 0)
for(i = 127; i != 0; i--) {
SCI0_OutUDec(i);
SCI0_OutString(", ");
SCI0_OutUDec(carrier_detect[i]);
SCI0_OutChar(CR);
SCI0_OutChar(LF);
}
#endif /* DEBUG2SCI0 */
}
}
unsigned char RadioClient_OutChar(unsigned char val) {
return RB_TX_PUSH(&cc->outRB, val);
}
void RadioClient_OutCharArray(unsigned char *pt,
unsigned char len) {
unsigned char i;
for(i=0; i<len; i++) {
while(RadioClient_OutChar(pt[i]));
}
}
void RadioClient_OutString(unsigned char *pt) {
while(*pt) {
while(RadioClient_OutChar(*pt++));
while(RadioClient_OutChar(0x00));
}
}
unsigned char RadioClient_IsOutFull() {
return RB_TX_FULL(&cc->outRB);
}
unsigned char RadioClient_IsOutEmpty() {
return RB_EMPTY(&cc->outRB);
}
unsigned char RadioClient_IsInFull() {
return RB_FULL(&cc->inRB);
}
unsigned char RadioClient_IsInEmpty() {
return RB_EMPTY(&cc->inRB);
}
unsigned char RadioClient_HasElements() {
return RB_ELEMENTS(&cc->inRB);
}
void RadioClient_CleanIn() {
RB_CLEAN(&cc->inRB);
}
void RadioClient_CleanOut() {
RB_CLEAN(&cc->outRB);
}
unsigned char RadioClient_InChar() {
unsigned char toReturn;
while(RB_POP(&cc->inRB, &toReturn));
return toReturn;
}
void RadioClient_InCharArray(unsigned char *charArray,
unsigned char len) {
unsigned char i;
for(i = 0; i<len; i++) {
while(RB_POP(&cc->inRB, &charArray[i]));
}
}
unsigned short RadioClient_GetFailureCount() {
return commState.failureCount;
}
#endif /* HAS_COMMS */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -