I am having trouble getting my MCU to communicate with the nRF24L01. I attached a copy of my board schematic and all of my code. Here are the things I am absolutely sure of:
The MCU is working properly. I can send and receive bytes just fine over the USART, which leads me to my next fact: the USART is working fine. The LED connected to PORTC also works like it should, so the only feature on the board currently not functioning is the nRF24L01.
Essentially what I am trying to do is set a value in a register and then read it back out. I am just doing this to make sure it works and try something very basic, but so far it doesn’t read out the correct value.
You will see in main I am trying to write the value 0x03 into the EN_AA register (register 0x01). I am then trying to read it out and simply transmit the byte (in binary form for debugging) to my PC over the USART.
“00000000” comes up in hyperterminal regardless of what I send over SPI. I’m not sure if my functions are wrong or if I’m not setting up the nRF24L01 correctly. I’ll go ahead and say I’m not sure if I need to write to the config register first (I tried that - no luck).
Any ideas? Thanks ahead of time.
Top level C file with main and most functions
#include <avr/io.h>
#include <util/delay.h>
#include "USART.h"
//Clock is 16MHz
void CSN_high(void); //Drive the CSN line high
void CSN_low(void); //Drive the CSN line low
void SPI_Send(unsigned char); //Send a byte over SPI
unsigned char SPI_Receive(void); //Receive a byte over SPI
void To_PC(unsigned char); //Send a byte in binary format over USART
void SPI_Init(void); //Init SPI
void Init(void); //Init the MCU
//24L01 Defines
#define CE 6 //PORTA 6
#define CSN 5 //PORTA 5
#define IRQ 4 //PORTA 4
//LED Define (active low)
#define LED 4 //PORTC 4
int main(void)
{
unsigned char ch; //Dummy storage variable
Init(); //Init the MCU
USART0_Transmit('\n'); //Send CRLF pair over USART
USART0_Transmit('\r');
CSN_high(); //Drive CSN high
while(1)
{
CSN_low(); //Pull CSN low to transmit a command
SPI_Send(0x21); //Write to the EN_AA register
SPI_Send(0x03); //Turn on AA on Pipe 0 & 1
CSN_high(); //Signal end of command
CSN_low(); //Signal new command
SPI_Send(0x01); //Issue read command for EN_AA register
ch = SPI_Receive(); //Receive the byte (send dummy byte)
CSN_high(); //Signal end of command
To_PC(ch); //Send the character over USART in binary
USART0_Receive(); //Dummy receive to pause the program
}
return 0;
}
void Init(void)
{
//Only the LED is on PORTC. Set it as output and turn it off.
PORTC = 0xFF;
DDRC = 0xFF;
//24L01 control signals CE, CSN, and IRQ on PORTA.
//Set CE and CSN as output and IRQ as input
PORTA = 0xEF;
DDRA = 0xEF;
USART0_Init();
SPI_Init();
}
//Convert a byte to binary over USART. This is just for debugging.
void To_PC(unsigned char ch)
{
if(ch & 0x80)
USART0_Transmit('1');
else
USART0_Transmit('0');
if(ch & 0x40)
USART0_Transmit('1');
else
USART0_Transmit('0');
if(ch & 0x20)
USART0_Transmit('1');
else
USART0_Transmit('0');
if(ch & 0x10)
USART0_Transmit('1');
else
USART0_Transmit('0');
if(ch & 0x08)
USART0_Transmit('1');
else
USART0_Transmit('0');
if(ch & 0x04)
USART0_Transmit('1');
else
USART0_Transmit('0');
if(ch & 0x02)
USART0_Transmit('1');
else
USART0_Transmit('0');
if(ch & 0x01)
USART0_Transmit('1');
else
USART0_Transmit('0');
USART0_Transmit('\n');
USART0_Transmit('\r');
}
void SPI_Send(unsigned char ch)
{
SPDR = ch; //Load the data register
while( !(SPSR & (1 << SPIF)) ); //Wait for it to finish sending
}
unsigned char SPI_Receive(void)
{
SPI_Send(0x05); //Load with a dummy value
return SPDR; //Return the received byte
}
void CSN_high(void)
{
PORTA |= (1 << CSN); //Pull up PORTA Bit 5
}
void CSN_low(void)
{
PORTA &= ~(1 << CSN); //Pull down PORTA Bit 5
}
void SPI_Init(void)
{
PORTB = 0xFF;
DDRB = 0xBF; //SCK and MOSI are outputs, MISO is input
//Turn on SPI, enable Master mode, Use clk/16. MSB first
SPCR = (1 << SPE) | (1 << MSTR) | (1 << SPR0) | (1 << DORD);
}
USART.c - a file I have used several times so I am positive this is working
#include "USART.h"
void USART0_Init( )
{
UBRR0H = (unsigned char)(BAUD0 >> 8); //Set baud rate
UBRR0L = (unsigned char)(BAUD0);
//Enable receiver and transmitter
UCSR0B = (1 << RXEN0) | (1 << TXEN0) | (1 << RXCIE0);
UCSR0C = (0 << USBS0) | (3 << UCSZ00); //Set frame format: 8data, 2stop bit
}
char USART0_Receive( void )
{
while ( !(UCSR0A & (1 << RXC0)) ); // Wait for data to be received
return UDR0; // Get and return received data from buffer
}
void USART0_Transmit( unsigned char data )
{
while ( !( UCSR0A & (1 << UDRE0)) );// Wait for empty transmit buffer
UDR0 = data; // Put data into buffer, sends the data
}
void USART0_Transmit_ptr( unsigned char data[])
{
unsigned char j = 0;
while(data[j] != '\0')
{
USART0_Transmit( data[j] );
j++;
}
}
[/code]