Hi,
I am new to this forum and new to the embedded world. My sincere apologies if this is not the right place for posting my query .
I have one AVR AT90CAN128 MCU which drives an MC13192 radio. I want to port one application which was written for freescale HCS08 MCU using SMAC onto my AVR MCU. The following code is developed using AVR Studio 4 and WinAVR.
Here in this code, i am trying to reset the transceiver and then calling one Init_MC13192() function. I have tried to port the MC13192Init(), the one mentioned in MC13192_hw_config.c.
After doing that i am trying to send one register address with read access to read the contents of that register like
SPI_DATA_REGISTER = reg_address; /* place register address on MOSI*/
while(!(SPSR &(1<<SPIF)); /* Wait for transmission to complete */
receive_data = SPI_DATA_REGISTER; /* Read the SPI data register to obtain received data*/
I have to call the above routine three times to obtain the contents of the corresponding register. Am i missing something? I am not able to receive anything from transceiver side.
Thanks.
#include<avr/io.h>
#include<inttypes.h>
#define F_CPU 16000000L /* MCU Clock Speed */
#define SPI_PORT PORTB /* Define SPI port */
#define SS PB0 /* The SPI Slave Select Bit */
unsigned char Rx_SPI[2];
uint16_t delay_count;
uint8_t temp;
void delay(uint8_t ms)
{
uint16_t cnt;
asm volatile (
"\n"
"L_dl1%=:" "\n\t"
"mov %A0, %A2" "\n\t"
"mov %B0, %B2" "\n"
"L_dl2%=:" "\n\t"
"sbiw %A0, 1" "\n\t"
"brne L_dl2%=" "\n\t"
"dec %1" "\n\t"
"brne L_dl1%=" "\n\t"
: "=&w" (cnt)
: "r" (ms), "r" (delay_count)
);
}
void ZB_Reset()
{
DDRD |= (1 << DDD7) | (1 << DDD1) ; //Set Direction register as output
PORTD = (0 << PD7); //Resetting the ZB chip by pulling low RST pin
delay(10);
PORTD = (1 << PD7); //Set to normal mode ZB chip to pulling high
delay(25);
}
void SPI_MasterInit(void)
{
/* Set MISO MOSI and SCK output, all others input */
DDRB |= (0<<DDB3)|(1<<DDB2)|(1<<DDB1)|(1<<DDB0);
/* Enable SPI, Master, set clock rate fck/16 */
SPCR = (1<<SPE)|(1<<MSTR)|(1<<SPR0);
}
uint8_t SPI_SingularTransaction(uint8_t data)
{
SPDR = data;
while(!(SPSR &(1<<SPIF)));
return SPDR;
}
void SPIDrvWrite(uint8_t reg_address, uint16_t reg_data)
{
uint8_t reg_data_high = reg_data >> 8;
uint8_t reg_data_low = reg_data;
SPI_PORT = (1<<SS); /* Pull the slave select line low to start the transmission */
/* 3 SPI Bursts for one transaction */
temp = SPI_SingularTransaction(reg_address);
temp = SPI_SingularTransaction(reg_data_high);
temp = SPI_SingularTransaction(reg_data_low);
SPI_PORT = (0<<SS); /* Pull the slave select line high to end the transaction */
}
void SPIDrvRead(uint8_t reg_address)
{
reg_address |= 0x80; /* set MSB to 1 for read access*/
SPI_PORT = (1<<SS);
temp = SPI_SingularTransaction(reg_address);
Rx_SPI[0] = SPI_SingularTransaction(0xFF); /* Read the received 16 bit data in Rx_SPI */
Rx_SPI[1] = SPI_SingularTransaction(0xFF);
SPI_PORT = (0<<SS);
}
void Init_MC13192()
{
SPIDrvWrite(0x11,0x80FF); /* Eliminate Unlock Conditions due to L01 */
SPIDrvWrite(0x1B,0x8000); /* Disable TC1. */
SPIDrvWrite(0x1D,0x8000); /* Disable TC2. */
SPIDrvWrite(0x1F,0x8000); /* Disable TC3. */
SPIDrvWrite(0x21,0x8000); /* Disable TC4. */
SPIDrvWrite(0x07,0x0E00); /* Enable CLKo in Doze */
SPIDrvWrite(0x0C,0x0300); /* IRQ pull-up disable. */
SPIDrvRead(0x25); /* Sets the reset indicator bit */
SPIDrvWrite(0x04,0xA08D); /* New cal value */
SPIDrvWrite(0x08,0xFFF7); /* Preferred injection */
SPIDrvWrite(0x05,0x8351); /* Acoma, TC1, Doze, ATTN masks, LO1, CRC */
SPIDrvWrite(0x06,0x4720); /* CCA, TX, RX, energy detect */
/* Read the status register to clear any undesired IRQs. */
SPIDrvRead(0x24); /* Clear the status register, if set */
//gu8RTxMode = IDLE_MODE; /* Update global to reflect MC13192 status */
}
void main()
{
uint8_t reg;
delay_count = F_CPU/4000;
reg = 0x30; /* BER_Enable register. The default register value after reset is 0x0004*/
ZB_Reset();
SPI_MasterInit(); /*Initialize the MCU SPI port*/
Init_MC13192();
SPIDrvRead(reg);
asm volatile ("nop" : : );
}