NEW: Learning electronics? Ask your questions on the new Electronics Questions & Answers site hosted by CircuitLab.
Microcontroller Programming » SPI communication code
May 01, 2011 by uml_12 |
I'm trying to get a SPI communication between two ATMega168 microcontrollers. Please Help! It's not doing much of anything. Here is the code I'm using: define F_CPU 14745600include <avr/io.h>include <inttypes.h>include "../libnerdkits/delay.h"include "../libnerdkits/lcd.h"define DDR_SPI PORTBdefine DD_MOSI PB4define DD_SCK PB5define DD_MISO PB3// PIN DEFINITIONS: // // PC4 -- LED anode void SPI_MasterInit(void); void SPI_SlaveInit(void); char SPI_SlaveReceive(void); void SPI_MasterTransmit(char cData); void configurePortDOutput(void); int main() { //If SlaveSelect (!SS) is high controller is master. if (PB2 == 1) { // Initialize the MASTER Controller SPI_MasterInit();
//END NEW CODE } //END WHILE LOOP } // END ELSE
} void SPI_MasterInit(void) { // Set MOSI and SCK output, all others input DDR_SPI = (1 << DD_MOSI) | (1 << DD_SCK);
} void SPI_SlaveInit(void) { // Set MISO output, all others input DDR_SPI = (1 << DD_MISO);
} char SPI_SlaveReceive(void) { // Wait for reception complete while(!(SPSR & ( 1 << SPIF)));
} void SPI_MasterTransmit(char cData) { // Copy cData byte into data register SPDR = cData;
} void configurePortDOutput(void) { DDRD |= (1 << PD0); DDRD |= (1 << PD1); DDRD |= (1 << PD2); DDRD |= (1 << PD3); DDRD |= (1 << PD4); DDRD |= (1 << PD5); DDRD |= (1 << PD6); DDRD |= (1 << PD7); } |
---|---|
May 01, 2011 by Ralphxyz |
So is this your Master or Slave code? You are not using the LCD making PortD available, again on the Master or Slave? Ralph |
May 02, 2011 by uml_12 |
I just found out that I need separate codes for master and for a slave. and yes I made port D availabe for my slave to light up leds. |
May 02, 2011 by Ralphxyz |
Yeah, that is what I suspected. I think you have the right idea in your code so just split it up and lets see what happens. Ralph |
May 02, 2011 by uml_12 |
Okay so I split it up.. Can you see anything wrong with this? Thanks Master Code: define F_CPU 14745600include <avr/io.h> // For IOinclude <inttypes.h> // For int data typesinclude "../libnerdkits/delay.h"define SPI_PORTB PORTBdefine SPI_DDR DDRBdefine SPI_CS PB2char SPI_ReadWrite(char data_out); int main(void){
return 0; } char SPI_ReadWrite(char data_out){
} Slave Code: define F_CPU 14745600include <avr/io.h> // For IOinclude <inttypes.h> // For int data typesinclude "../libnerdkits/delay.h"define SPI_PORTB PORTBdefine SPI_DDR DDRBdefine SPI_CS PB2char SPI_WriteRead(char data_out); int main(void) {
} char SPI_WriteRead(char data_out){
} |
May 02, 2011 by Hexorg |
uml_12, in master's code SPI_ReadWrite(), why are you toggling the SS pin at all? In master code, set SS pin to ouput, set it to 1, and never change it. In slave code everything seems correct. You only need to use SS pin on SLAVES when you have more then 1 slave. |
May 02, 2011 by uml_12 |
well .. okay, i will change it for now. but the future of our project is to control multiple slaves. Are you saying that ss should be pulled the entire time only when one slave is actually connected ? |
May 03, 2011 by uml_12 |
pulling !ss low (active) for the duration of the program did absolutely nothing. Can anyone see anything ever so slightly wrong with that code ? our next step is to implement debugging leds which should have probably been in there already. but im fairly new to this sort of thing. Basically, I plug it in and nothing at all occurs. I'll post my schematic when I get some spare time .. and my setup as well. but are you sure you can't see anything wrong at all with the above code or general flow? I can't even count the hours I've spent researching, and testing spi code (more than 100 by now). we are at the tipping point. everyone I talk to is suggesting we move to aurdino just to get the project over with. I'm not 100% that will solve our problems without providing us with new ones.. |
May 03, 2011 by Noter |
Could be the SPI is working. Be sure you select the slave before you try to read or write, not after as shown in your code above. Maybe just keep it selected as Hexorg suggests. Otherwise, I think your problem may be declaring data_in as a pointer and then setting it to the value of the received byte. A pointer is not necessary for a single byte but when you do use a pointer you must set it to the correct address. Another problem may be that you mean to test bits in the recieved data byte instead of different bytes in an array. |
May 03, 2011 by uml_12 |
Thanks ! I will look into that. |
May 03, 2011 by Hexorg |
Well, in master mode, SS has to be configured as output, because (ATmega168 datasheet p.167):
And for the slave:
|
Please log in to post a reply.
Did you know that you can read diagnostic data from some cars with a NerdKit? Learn more...
|