View previous topic :: View next topic |
Author |
Message |
mdares
Joined: 26 Oct 2005 Posts: 19
|
SPI Problem |
Posted: Thu Nov 03, 2005 7:07 pm |
|
|
Hi Everyone,
I am having the following problem with my SPI setup:
I have a TI-DSP master and a slave PIC. I am sending the same 2 bytes from the DSP in a loop with a few seconds between each transmission. On the scope I see the proper data leaving the DSP, and as I do not write anything from my slave pic, I see the previous byte being clocked back out to the dsp from the pic on the MISO line. This is all as expected, the problem is that what is in the SSPBUF is not always the correct data (even when I see the correct data being clocked out on the next cycle).
To try and clairify, my dsp writes 0x55, then 0xA5 in a continous loop with a few seconds between each write. When the DSP writes A5 I will see the previously sent 55 being clocked back on the master in line as I expect. The problem is that the data that was in SSPBUF was not necessarily 0x55, (sometimes it is, but mostly it is some other random hex value). So any ideas on where I could be having a problem between the register that this is shifted into and the SSPBUF register?
This setup works fine when I use two pics, but not when I use the DSP master.
I have not included my code as I am (nearly) sure this is some sort of hardware issue I just can't seem to wrap my head around. The code I am running is simply a loop that calls:
setup_spi(SPI_SLAVE|SPI_L_TO_H);
while (1) {
readdata=spi_read();
printf(readdata);
}
Matthew |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Thu Nov 03, 2005 8:22 pm |
|
|
Change the clock edge in the DSP, or change it in the PIC.
i.e., make sure the DSP is using the same SPI mode as the PIC. |
|
|
mdares
Joined: 26 Oct 2005 Posts: 19
|
|
Posted: Thu Nov 03, 2005 9:22 pm |
|
|
That was my first thought as well, but they are setup as close to the same as their implementetions allow. I have a pic 16 board that works fine with the same SPI settings and the same DSP as I am using here. (I am trying to replace it with a new board and moving to an 18). Also, it appears that the data is shifting into the register properly as the correct bits are being shifted back out of the pic on the next write, they are just not being placed into the SSPBUF register. Fianlly I would expect the data to be consistantly wrong if my clocking scheme was backwards, but this is not the case.
Matt |
|
|
mdares
Joined: 26 Oct 2005 Posts: 19
|
|
Posted: Fri Nov 04, 2005 7:34 am |
|
|
I can't understand how I can have the right data in SSPSR and not in SSPBUF, which is what seems to be the case....
Matt |
|
|
Foppie
Joined: 16 Sep 2005 Posts: 138 Location: The Netherlands
|
|
Posted: Fri Nov 04, 2005 7:55 am |
|
|
I do see where you clock back the previous byte in your example code, you only printf it... is this a copy-paste error and should it be spi_write() or is this intended to be so and did you forget the clock-back part of your code?
Are there any interrupts that might cause the chip to give you a bad/altered output? |
|
|
mdares
Joined: 26 Oct 2005 Posts: 19
|
|
Posted: Fri Nov 04, 2005 8:44 am |
|
|
I'm not writing anything to the SPI from the slave (which means when the next clock comes whatever is still in the shift register will get clocked out). And that is what I see from the DSP side, it will receive from the pic the last byte I sent from the DSP (as those bits will be sitting in SSPSR unmodified).
I have removed all of my interrupt handling but it has made no difference. What I am having the hardest time with is that this works pic-pic but not dsp-pic. I know that the SSPSR is getting the right data as it is clocking the right data back out.
The system clock on my pic is twice as fast as that of the clock on the DSP, could my trouble lie here? I wasn't worried about it because the SSPCLK is essentially bit banging out my signal, but that is the only difference I can see between my working pic-pic setup over my dsp-pic setup. (Both pics run off of the same clock).
Matt |
|
|
DragonPIC
Joined: 11 Nov 2003 Posts: 118
|
|
Posted: Fri Nov 04, 2005 11:45 am |
|
|
mdares wrote: | I'm not writing anything to the SPI from the slave
setup_spi(SPI_SLAVE|SPI_L_TO_H);
while (1) {
readdata=spi_read();
printf(readdata);
}
|
yes you are.
The code you have writes data and waits for return data. _________________ -Matt |
|
|
mdares
Joined: 26 Oct 2005 Posts: 19
|
|
Posted: Fri Nov 04, 2005 12:57 pm |
|
|
The spi_read function should only write data if it is supplied (that is readdata=spi_read(writedata) ).
With nothing in the brackets it should not do a write to the buffer.
(Here is the assembler generated:
.................... readdata = spi_read();
01DC: MOVFF FC9,1D
.................... printf("Read: %X\n\r", readdata);
So, unless I am missing something we are only moving the data from SSPBUF to my variable in 1D.
Matt |
|
|
Ttelmah Guest
|
|
Posted: Fri Nov 04, 2005 3:12 pm |
|
|
SSP, is bi-directional, and _something_ will always be clocked in the other direction. If you don't define what it is, it will probably be something left over from a previous transaction.
The 'read' without data, won't generate any clocks, and will depend on the transaction being clocked by the other end. However if the other end clocks a byte 'to' you, it'll clock 'back' the last byte transferred, if you have not defined another byte to be sent.
Best Wishes |
|
|
mdares
Joined: 26 Oct 2005 Posts: 19
|
|
Posted: Fri Nov 04, 2005 7:05 pm |
|
|
That is what I am saying. The byte clocked out is the previous received byte, this is the point of my argument of why the problem 'appears' to be between the SSPSR and the SSPBUF.
Matthew |
|
|
Ttelmah Guest
|
|
Posted: Sat Nov 05, 2005 5:34 am |
|
|
Have you actually checked what values the setup puts into the SPI configuration register?. Historically, some versions of the compiler have put incorrect values here.
Also is the serial, using the hardware UART, or a software version?. If a software UART is being used, or you are sending more than a couple of characters, the loop may just not be fast enough.
Best Wishes |
|
|
mdares
Joined: 26 Oct 2005 Posts: 19
|
|
Posted: Sat Nov 05, 2005 9:08 am |
|
|
First question: I have checked the setep registers, and it is putting the correct values in (the I have noticed a restriction using setup_spi when trying to put a high to low transition for the clock, but it is setting it up correctly in this case).
Second: The print statement is not an issue in this case as I am running the other processor in debug mode with a breakpoint set. There would be at least a second or more between transitions.
Thank you for the suggestions though... I know I am missing a clue here somewhere, but this problem is killing me! ;-)
Matt |
|
|
DragonPIC
Joined: 11 Nov 2003 Posts: 118
|
|
Posted: Mon Nov 07, 2005 1:35 pm |
|
|
My mistake, I missread. The feature can only be used by the master mode where it will be sending the clock anyways. It also confused me when the manual said to use SPI_READ(0) if nothing is being written (don't know if the 0 is really required).
Are your SSPIF and BF bits set? I would also check the WCOL bit to see if the code is doing anything goofy.
Is readdata being loaded with the correct data? Assuming you are using a debugger to check the SSPBUF register, maybe you are breaking in code before you can get the correct data or maybe the debugger has a bug.
You may be sending one too many clock pulses somewhere to interfer with when the data from SSPSR is loaded into SSPBUF register. then you only get the correct data every 8th write or something. You may also be writing another byte to the slave before it has an opportunity to clear the BF bit (when the SSPBUF is read). _________________ -Matt |
|
|
|