pic_rf_24l01.h File Reference

RF routines for the Nordic nRF24L01 chip. More...

Include dependency graph for pic_rf_24l01.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  rf_config

Defines

#define CONFIG_CRCO   2
#define CONFIG_EN_CRC   3
#define CONFIG_MASK_MAX_RT   4
#define CONFIG_MASK_RX_DR   6
#define CONFIG_MASK_TX_DS   5
#define CONFIG_PRIM_RX   0
#define CONFIG_PWR_UP   1
#define FIFO_STATUS_RX_EMPTY   0
#define FIFO_STATUS_RX_FULL   1
#define FIFO_STATUS_TX_EMPTY   4
#define FIFO_STATUS_TX_FULL   5
#define FIFO_STATUS_TX_REUSE   6
#define OP_ENABLE_1_MBPS   5
#define OP_ENABLE_CH2   7
#define OP_ENABLE_CRC   2
#define OP_ENABLE_RECEIVE   0
#define OP_ENABLE_SHOCKBURST   6
#define OP_LONG_CRC   1
#define pic_rf_get_status()   pic_rf_read_register(RF_NOP, 0, 0)
#define pic_rf_receive_mode()   pic_rf_set_mode(RECEIVE_MODE)
#define pic_rf_set_status(status)   pic_rf_send_command(RF_WR_REG_STATUS, status, 1)
#define pic_rf_transmit_mode()   pic_rf_set_mode(TRANSMIT_MODE)
#define RECEIVE_MODE   1
#define RF_FLUSH_RX   0b11100010
#define RF_FLUSH_TX   0b11100001
#define RF_NOP   0b11111111
#define RF_R_RX_PAYLOAD   0b01100001
#define RF_RD_REG_CD   0b00001001
#define RF_RD_REG_CONFIG_REG   0b00000000
#define RF_RD_REG_FIFO_STATUS   0b00010111
#define RF_RD_REG_RX_PW_P0   0b00010001
#define RF_RD_REG_STATUS   0b00000111
#define RF_W_TX_PAYLOAD   0b10100000
#define RF_WR_REG_CONFIG_REG   0b00100000
#define RF_WR_REG_EN_AA   0b00100001
#define RF_WR_REG_RF_CH   0b00100101
#define RF_WR_REG_RF_SETUP   0b00100110
#define RF_WR_REG_RX_ADDR_P0   0b00101010
#define RF_WR_REG_RX_PW_P0   0b00110001
#define RF_WR_REG_SETUP_AW   0b00100011
#define RF_WR_REG_SETUP_RETR   0b00100100
#define RF_WR_REG_STATUS   0b00100111
#define RF_WR_REG_TX_ADDR   0b00110000
#define STATUS_MAX_RT   4
#define STATUS_RX_DR   6
#define STATUS_TX_DS   5
#define STATUS_TX_FULL   0
#define TRANSMIT_MODE   0

Functions

void pic_rf_init (rf_config *my_config)
 Initialise nRF24L01 chip with config.
void pic_rf_quick_init (char *my_config, uns8 my_channel, bit my_receive_on)
 Initialise nrf2401a chip with quick config.
uns8 pic_rf_read_register (uns8 cmd, uns8 *data, uns8 data_len)
 Read nRF24L01 register.
uns8 pic_rf_read_register_inline (uns8 cmd, uns8 *data, uns8 data_len)
 Read nRF24L01 register (inline).
uns8 pic_rf_receive (uns8 *data, uns8 bytes_to_receive)
 Receive data from nRF24L01.
void pic_rf_receive_inline (uns8 *data, uns8 bytes_to_receive)
 Receive data from nRF24L01.
uns8 pic_rf_send_byte (uns8 b)
 Clock a byte into the nRF24L01.
uns8 pic_rf_send_byte_int (uns8 b)
 Clock a byte into the nRF24L01.
uns8 pic_rf_send_command (uns8 cmd, uns8 *data, uns8 data_len)
 Send command to the nrf24l01.
uns8 pic_rf_send_command_inline (uns8 cmd, uns8 *data, uns8 data_len)
 Send command to the nrf24l01 (inline).
uns8 pic_rf_send_command_single (uns8 cmd, uns8 data)
 Send a single data byte command to the nrf24l01.
void pic_rf_set_channel (uns8 channel)
 Receive data from nRF24L01 (inline).
void pic_rf_set_mode (uns8 mode)
 Set rf mode to transmit or receive.
void pic_rf_setup ()
 Setup ports and pins for communication with nRF24L01.
void pic_rf_transmit (uns8 *data, uns8 bytes_to_transmit)
 Transmit data from nRF24L01.

Variables

static uns8 rf_current_channel = 2
static bit rf_current_mode_receive = 0

Detailed Description

RF routines for the Nordic nRF24L01 chip


Define Documentation

#define CONFIG_CRCO   2
#define CONFIG_EN_CRC   3
#define CONFIG_MASK_MAX_RT   4
#define CONFIG_MASK_RX_DR   6
#define CONFIG_MASK_TX_DS   5
#define CONFIG_PRIM_RX   0
#define CONFIG_PWR_UP   1
#define FIFO_STATUS_RX_EMPTY   0
#define FIFO_STATUS_RX_FULL   1
#define FIFO_STATUS_TX_EMPTY   4
#define FIFO_STATUS_TX_FULL   5
#define FIFO_STATUS_TX_REUSE   6
#define OP_ENABLE_1_MBPS   5

rf_config options - enable 1 MPS transmition (otherwise 250Kbps)

#define OP_ENABLE_CH2   7

rf_config options - enable channel 2 reception

#define OP_ENABLE_CRC   2

rf_config options - enable CRC (recommended!)

#define OP_ENABLE_RECEIVE   0

rf_config options - enable receive

#define OP_ENABLE_SHOCKBURST   6

rf_config options - enable shockburst transmition

#define OP_LONG_CRC   1

rf_config options - enable 16 bit CRC (otherwise 8 bit CRC if 0)

 
#define pic_rf_get_status (  )     pic_rf_read_register(RF_NOP, 0, 0)
 
#define pic_rf_receive_mode (  )     pic_rf_set_mode(RECEIVE_MODE)
#define pic_rf_set_status ( status   )     pic_rf_send_command(RF_WR_REG_STATUS, status, 1)
 
#define pic_rf_transmit_mode (  )     pic_rf_set_mode(TRANSMIT_MODE)
#define RECEIVE_MODE   1

Mode selection - receive

#define RF_FLUSH_RX   0b11100010
#define RF_FLUSH_TX   0b11100001
#define RF_NOP   0b11111111
#define RF_R_RX_PAYLOAD   0b01100001
#define RF_RD_REG_CD   0b00001001
#define RF_RD_REG_CONFIG_REG   0b00000000
#define RF_RD_REG_FIFO_STATUS   0b00010111
#define RF_RD_REG_RX_PW_P0   0b00010001
#define RF_RD_REG_STATUS   0b00000111
#define RF_W_TX_PAYLOAD   0b10100000
#define RF_WR_REG_CONFIG_REG   0b00100000
#define RF_WR_REG_EN_AA   0b00100001
#define RF_WR_REG_RF_CH   0b00100101
#define RF_WR_REG_RF_SETUP   0b00100110
#define RF_WR_REG_RX_ADDR_P0   0b00101010
#define RF_WR_REG_RX_PW_P0   0b00110001
#define RF_WR_REG_SETUP_AW   0b00100011
#define RF_WR_REG_SETUP_RETR   0b00100100
#define RF_WR_REG_STATUS   0b00100111
#define RF_WR_REG_TX_ADDR   0b00110000
#define STATUS_MAX_RT   4
#define STATUS_RX_DR   6
#define STATUS_TX_DS   5
#define STATUS_TX_FULL   0
#define TRANSMIT_MODE   0

Mode selection - transmit


Function Documentation

void pic_rf_init ( rf_config my_config  ) 

Sends the configuration to the Nordic nRF24L01 chip ready to begin communication. This routine assumes you have already set my_config to the correct values.

Initialise nRF24L01 chip with config.

Sends the configuration to the Nordic nrf2401a chip ready to begin communication. This routine assumes you have already set my_config to the correct values.

00084 {
00085 uns8 temp;
00086 uns8 options;
00087 
00088     make_output(rf_data_port, rf_data_pin); // make data pin output
00089     clear_pin(rf_clk1_port, rf_clk1_pin);       // make sure it's 0
00090 
00091     pic_rf_chip_enable(0);
00092     pic_rf_chip_select(1);  // config mode
00093     
00094     pic_rf_send_byte(my_config->payload_width_ch2);
00095     pic_rf_send_byte(my_config->payload_width_ch1);
00096     pic_rf_send_bytes(my_config->address_ch2, 5);
00097     pic_rf_send_bytes(my_config->address_ch1, 5);
00098     
00099     options = my_config->options;
00100 
00101     temp = my_config->address_width << 2;
00102     temp.1 = options.OP_LONG_CRC; // |= my_config->long_crc << 1;
00103     temp.0 = options.OP_ENABLE_CRC; // |= my_config->enable_crc;
00104 
00105     pic_rf_send_byte(temp);
00106 
00107     temp = options & 0b11100000;  //pull off top three bits
00108     //temp.7 = options.ENABLE_CH2; // |= my_config->enable_ch2 << 7;
00109     //temp.6 = options.ENABLE_SHOCKBURST; // |= my_config->enable_shockburst << 6;
00110     //temp.5 = options.ENABLE_1_MBPS; //my_config->enable_1_mbps << 5;
00111     temp |= (my_config->crystal & 0b00000111) << 2; // bits 4,3,2 - mask 3 bit range
00112     temp |= (my_config->output_power & 0b00000011); // bits 1,0 - mask 2 bit range
00113     
00114     pic_rf_send_byte(temp);
00115         
00116     temp = my_config->channel << 1;
00117     rf_current_channel = my_config->channel;
00118     
00119     temp |= options.OP_ENABLE_RECEIVE; // my_config->enable_receive;
00120     rf_current_mode_receive = options.OP_ENABLE_RECEIVE;
00121     
00122     pic_rf_send_byte(temp);
00123     
00124     pic_rf_chip_select(0);  // config mode ended
00125     pic_rf_chip_enable(1);  // on the air!
00126     
00127   }

Here is the call graph for this function:

void pic_rf_quick_init ( char *  my_config,
uns8  my_channel,
bit  my_receive_on 
)

While the usual pic_rf_init() routine is excellent when you want to programatically change the 2401a config, if you're only doing this once (at the start) then it's likely you're burning a lot of instructions (154 words on a PIC16 device) just to send some bytes of config out to the 2401a. If you know your config in advance, then you can just send the byte-stream config using this routine. Use the nrf2401a_config.pl script in the tools directory to generate this string.

00062                                                                             {
00063 
00064 uns8 byte_counter;
00065     make_output(rf_data_port, rf_data_pin); // make data pin output
00066     clear_pin(rf_clk1_port, rf_clk1_pin);       // make sure it's 0
00067 
00068     pic_rf_chip_enable(0);
00069     pic_rf_chip_select(1);  // config mode
00070 
00071     for(byte_counter = 0 ; byte_counter < 15 ; byte_counter++) {
00072         pic_rf_send_byte(my_config[byte_counter]);
00073     }
00074     rf_current_channel = my_channel;
00075     rf_current_mode_receive = my_receive_on;
00076 
00077     pic_rf_chip_select(0);  // config mode ended
00078     pic_rf_chip_enable(1);  // on the air!
00079 
00080 }   

Here is the call graph for this function:

uns8 pic_rf_read_register ( uns8  cmd,
uns8 *  data,
uns8  data_len 
)

Internal routine to read a particular nRF24L01 register. Clocks out data_len bytes from the chip. Internal routine.

Parameters:
cmd Read register command, eg RF_RD_REG_STATUS
data Pointer to array of bytes where data will be put
data_len Number of bytes to clock out

00092                                                                { // returns status
00093 
00094 uns8 byte_counter, status;
00095 
00096     clear_pin(rf_csn_port, rf_csn_pin);
00097     status = pic_rf_send_byte(cmd); 
00098     for(byte_counter = 0 ; byte_counter < data_len ; byte_counter++) {
00099         data[byte_counter] = pic_rf_send_byte(0);
00100     }                            
00101     
00102     set_pin(rf_csn_port, rf_csn_pin);
00103     return status;
00104 }

Here is the call graph for this function:

Here is the caller graph for this function:

uns8 pic_rf_read_register_inline ( uns8  cmd,
uns8 *  data,
uns8  data_len 
) [inline]

Internal routine to read a particular nRF24L01 register. Clocks out data_len bytes from the chip. Internal routine. Inline version.

Parameters:
cmd Read register command, eg RF_RD_REG_STATUS
data Pointer to array of bytes where data will be put
data_len Number of bytes to clock out
Returns:
nRF24L01 status

00326                                                                              {
00327 
00328 uns8 byte_counter, status;
00329 
00330     clear_pin(rf_csn_port, rf_csn_pin);
00331 
00332     status = pic_rf_send_byte_int(cmd);
00333      
00334     for(byte_counter = 0 ; byte_counter < data_len ; byte_counter++) {
00335         data[byte_counter] = pic_rf_send_byte_int(0); // dummy send to get byte back
00336     }
00337     
00338     set_pin(rf_csn_port, rf_csn_pin);
00339     
00340     return status;
00341 }   

Here is the call graph for this function:

Here is the caller graph for this function:

uns8 pic_rf_receive ( uns8 *  data,
uns8  bytes_to_receive 
)

Having been notified that there is data available, call this routine to clock the data in from the nRF24L01.

Receive data from nRF24L01.

Having been notified that there is data available, call this routine to clock the data in from the nrf2401a.

!pic_rf_chip_enable(0); // save power

pic_rf_chip_enable(1); // turn chip back on

!pic_rf_chip_enable(0); // save power

pic_rf_chip_enable(1); // turn chip back on

00130                                                        {
00131 uns8 byte_count, bit_count, temp;
00132 
00134     bit  my_store_gie = intcon.GIE;        
00135     kill_interrupts();
00136 
00137     make_input(rf_data_port, rf_data_pin); // make data pin input
00138     
00139     for (byte_count = 0; byte_count < bytes_to_receive; byte_count++) {
00140         
00141         for (bit_count = 0; bit_count < 8; bit_count++) {
00142             temp <<= 1;
00143             temp.0 = test_pin(rf_data_port, rf_data_pin);
00144             set_pin(rf_clk1_port, rf_clk1_pin);         // clock it out 
00145             clear_pin(rf_clk1_port, rf_clk1_pin);       // ready for next bit
00146         }
00147         data[byte_count] =  temp;
00148     }       
00149 
00151     intcon.GIE = my_store_gie;
00152 }   

Here is the call graph for this function:

void pic_rf_receive_inline ( uns8 *  data,
uns8  bytes_to_receive 
) [inline]

Having been notified that there is data available, call this routine to clock the data in from the nRF24L01.

00348                                                                      {
00349         pic_rf_read_register_inline(RF_R_RX_PAYLOAD, data, bytes_to_receive);
00350 }

Here is the call graph for this function:

Here is the caller graph for this function:

uns8 pic_rf_send_byte ( uns8  b  ) 

Clock one byte into the nRF24L01. Internal routine.

Parameters:
b The byte to send
Returns:
nRF24L01 status

Clock a byte into the nRF24L01.

Internal routine to send a byte to the nrf2401a. Generally you shouldn't need to use this, see pic_rf_transmit instead

See also:
pic_rf_transmit

00042 {
00043 uns8 bit_counter;
00044     for(bit_counter = 0 ; bit_counter < 8 ; bit_counter++) {
00045         change_pin(rf_data_port, rf_data_pin, b.7); // Put data on data pin
00046         set_pin(rf_clk1_port, rf_clk1_pin);         // clock it in (positive edge)
00047         clear_pin(rf_clk1_port, rf_clk1_pin);       // ready for next bit
00048             
00049         b <<= 1;    // Move all the bits left
00050     }   // repeat until finished
00051     
00052 }   // pic_rf_send_byte

Here is the caller graph for this function:

uns8 pic_rf_send_byte_int ( uns8  b  ) 

Clock one byte into the nRF24L01. Internal routine.

Parameters:
b The byte to send
Returns:
nRF24L01 status

00141 {
00142 uns8 bit_counter, status;
00143     // - For debug: print_int_hex(b); putc(' ');
00144     for(bit_counter = 0 ; bit_counter < 8 ; bit_counter++) {
00145         change_pin(rf_mosi_port, rf_mosi_pin, b.7); // Put data on data pin
00146         set_pin(rf_sck_port, rf_sck_pin);           // clock it in (positive edge)
00147         status <<= 1;
00148         status.0 = test_pin(rf_miso_port, rf_miso_pin);
00149         clear_pin(rf_sck_port, rf_sck_pin);     // ready for next bit
00150             
00151         b <<= 1;    // Move all the bits left
00152     }   // repeat until finished
00153     return status;
00154 }   // pic_rf_send_byte

Here is the caller graph for this function:

uns8 pic_rf_send_command ( uns8  cmd,
uns8 *  data,
uns8  data_len 
)

Send a command and associated data to the nRF24L01

Parameters:
cmd Command to send, eg, RF_WR_REG_SETUP_RETR
data Pointer to an array of bytes to send as data for the command
data_len Number of bytes in the array
Returns:
nRF24L01 status

00066                                                               {
00067 
00068 uns8 byte_counter, status;
00069 
00070     clear_pin(rf_csn_port, rf_csn_pin);
00071     status = pic_rf_send_byte(cmd); 
00072     for(byte_counter = 0 ; byte_counter < data_len ; byte_counter++) {
00073         pic_rf_send_byte(data[byte_counter]);
00074     }                            
00075     
00076     set_pin(rf_csn_port, rf_csn_pin);
00077     return status;
00078 }   

Here is the call graph for this function:

Here is the caller graph for this function:

uns8 pic_rf_send_command_inline ( uns8  cmd,
uns8 *  data,
uns8  data_len 
) [inline]

Send a command and associated data to the nRF24L01. Internal routine. Inline version.

Parameters:
cmd Command to send, eg, RF_WR_REG_SETUP_RETR
data Pointer to an array of bytes to send as data for the command
data_len Number of bytes in the array
Returns:
nRF24L01 status

00354                                                                             {
00355 
00356 uns8 byte_counter, status;
00357 
00358     clear_pin(rf_csn_port, rf_csn_pin);
00359     status = pic_rf_send_byte_int(cmd); 
00360     for(byte_counter = 0 ; byte_counter < data_len ; byte_counter++) {
00361         pic_rf_send_byte_int(data[byte_counter]);
00362     }                            
00363     
00364     set_pin(rf_csn_port, rf_csn_pin);
00365     return status;
00366 }   

Here is the call graph for this function:

Here is the caller graph for this function:

uns8 pic_rf_send_command_single ( uns8  cmd,
uns8  data 
)

Send a command and 1 byte of data to the nRF24L01

Parameters:
cmd Command to send, eg, RF_WR_REG_SETUP_RETR
data One byte of data for the command
Returns:
nRF24L01 status

00080                                                      {
00081 
00082 uns8 byte_counter, status;
00083 
00084     clear_pin(rf_csn_port, rf_csn_pin);
00085     status = pic_rf_send_byte(cmd);
00086     pic_rf_send_byte(data);
00087     set_pin(rf_csn_port, rf_csn_pin);
00088     return status;
00089 }   

Here is the call graph for this function:

void pic_rf_set_channel ( uns8  channel  ) 

Having been notified that there is data available, call this routine to clock the data in from the nRF24L01. Change channel on the nRF24L01 Changes the current channel used by the nRF24L01.

Receive data from nRF24L01 (inline).

Reclocks the essential config to change the current channel used by the nrf2401a.

00200 {
00201     bit  my_store_gie = intcon.GIE;        
00202     kill_interrupts();
00203 
00204     clear_bit(tris_array[rf_data_port - PORTA], rf_data_pin); // make data pin output
00205 
00206     pic_rf_chip_enable(0);
00207     pic_rf_chip_select(1);  // config mode
00208     
00209     rf_current_channel = channel;
00210     channel <<= 1;
00211     channel |= rf_current_mode_receive;
00212     
00213     pic_rf_send_byte(channel);  
00214     
00215     pic_rf_chip_select(0);  // config mode ended
00216     pic_rf_chip_enable(1);
00217 
00218     intcon.GIE = my_store_gie;
00219 }

Here is the call graph for this function:

void pic_rf_set_mode ( uns8  mode  ) 

Pass RECEIVE_MODE or TRANSMIT_MODE to change current mode. Generally, you shouldn't need to call this routine. The library assumes you want to receive until you transmit, in which case it switches automatically to transmit mode and back to receive afterwards.

00179 {
00180     bit  my_store_gie = intcon.GIE;        
00181     kill_interrupts();
00182 
00183     make_output(rf_data_port, rf_data_pin); // make data pin output
00184     pic_rf_chip_enable(0);
00185     pic_rf_chip_select(1);  // config mode
00186     
00187     change_pin(rf_data_port, rf_data_pin, mode);    // send a zero
00188     set_pin(rf_clk1_port, rf_clk1_pin);         // clock it in (positive edge)
00189     clear_pin(rf_clk1_port, rf_clk1_pin);       // ready for next bit
00190     
00191     pic_rf_chip_select(0);  // config mode ended
00192     pic_rf_chip_enable(1);
00193     
00194     rf_current_mode_receive = mode;
00195 
00196     intcon.GIE = my_store_gie;
00197 }

Here is the call graph for this function:

Here is the caller graph for this function:

void pic_rf_setup (  ) 

Set up ports and pins to correct input/output for communication with Nordic nRF24L01

Setup ports and pins for communication with nRF24L01.

Set up ports and pins to correct input/output for communication with Nordif nrf2401a

00221                     {
00222 
00223     make_output(rf_data_port, rf_data_pin); // make data pin output
00224     make_output(rf_cs_port, rf_cs_pin); // make cs pin output
00225     make_output(rf_ce_port, rf_ce_pin); // make ce pin output
00226     make_input (rf_dr1_port, rf_dr1_pin); // make dr1 pin input
00227     make_output(rf_clk1_port, rf_clk1_pin); // make clk1 pin output
00228         
00229 }

void pic_rf_transmit ( uns8 *  data,
uns8  bytes_to_transmit 
)

Changes to transmit mode, clocks data into the nrf24L01 and hits the shockburst button. Returns to receive mode when finished.

00326                                                          {
00327 
00328 uns8 byte_count, bit_count, temp, cd;
00329     start_crit_sec();
00330     
00331     pic_rf_set_mode(TRANSMIT_MODE);
00332     
00333     //pic_rf_send_command (RF_FLUSH_TX, 0, 0    );  
00334     pic_rf_read_register_inline(RF_RD_REG_CD, &cd, 1);
00335     serial_print_str("\n cd=");
00336     serial_print_int(cd);
00337     serial_print_nl();
00338     pic_rf_send_command(RF_W_TX_PAYLOAD, data, bytes_to_transmit);
00339 
00340     set_pin(rf_ce_port, rf_ce_pin);
00341     delay_us(10);   // 10us pulse - send packet out on airways
00342     clear_pin(rf_ce_port, rf_ce_pin);
00343     delay_us(130);  // TX settling
00344     pic_rf_set_mode(RECEIVE_MODE);  // go back to receive mode
00345 
00346     end_crit_sec();
00347 }   

Here is the call graph for this function:


Variable Documentation

uns8 rf_current_channel = 2 [static]

Maintain state of current channel

bit rf_current_mode_receive = 0 [static]

Maintain state of current mode (1 = receive mode)


Generated on Fri Aug 19 09:08:14 2011 for Pic Pack Library by  doxygen 1.6.1