|
|
View previous topic :: View next topic |
Author |
Message |
geolover
Joined: 08 Feb 2011 Posts: 18
|
SPI Slave read problem with PIC24FJ128GA010 |
Posted: Fri Mar 11, 2011 8:34 am |
|
|
Hi! I'm using a PIC24FJ128GA010 to interface with an ADC.
The PIC is using SPI slave is used to read from the ADC. The serial clock of both ADC and PIC is provided by a free-running external clock generated by another PIC's OC2 port.
SPI 1 is used to send data to a USB virtual com port.
Although the Oscilloscope shows outputting data from the ADC.
However, the testing shows that these data has not been read into the PIC, as the hyperterminal freezes itself.
The reason might be spi slave is not clocking in data because:
if I set serial clock of spi2 as master then it will output data although it will be entirely rubbish -- since ADC's master clock and serial clock must be synchronised.
Could anyone take a look at my code and point out a solution to me, another thing I already know is the retared development board does not have OSC2 output port so i cant utilise the clock out pin of the PIC24FJ128GA010.
Code: | #include <24FJ128GA010.h>
#include "stdio.h"
#include "string.h"
#FUSES NOWDT //No Watch Dog Timer
#FUSES NOJTAG //JTAG disabled
#FUSES NOPROTECT //Code not protected from reading
#FUSES NOWRT //Program memory not write protected
#FUSES NODEBUG //No Debug mode for ICD
#FUSES NOCOE //Device will reset into operational mode
#FUSES NOIESO //Internal External Switch Over mode disabled
#FUSES PR //Primary Oscillator
#FUSES CKSNOFSM //Clock Switching is enabled, fail Safe clock monitor is disabled
#FUSES NOOSCIO //OSC2 is clock output
#FUSES XT
#use delay(clock=8000000)
#use rs232(UART1,baud=9600,parity=N,bits=8)
#bit frmen=0x0244.15
#define AD_SYNC PIN_A0
#define DRDY PIN_A4
void main()
{
delay_ms(100);
int8 colon=58;
int8 i,j;
int8 ad_samples1,ad_samples2,ad_samples3;
set_tris_a(0x10); //A0,A7 output while A4 is input(/DRDY)
setup_spi(spi_master | spi_clk_div_4);
setup_spi2(spi_slave | spi_l_to_h | spi_ss_disabled);
output_low(AD_SYNC);
delay_us(2);
output_high(AD_SYNC);
while(1)
{
while((DRDY==1)); //Data ready pin of ADC is actively low
while(!spi_data_is_in2());
ad_samples1=spi_read2();
ad_samples2=spi_read2();
ad_samples3=spi_read2();
spi_write(colon);
delay_ms(1);
spi_write(ad_samples1);//write 8-bit data into spi
delay_ms(1);
spi_write(ad_samples2);
delay_ms(1);
spi_write(ad_samples3);
delay_ms(1);
}
} |
|
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19550
|
|
Posted: Fri Mar 11, 2011 9:08 am |
|
|
OK.
You have an external clock, synchronous with a data stream. The clock comes from another PIC, and clocks data out of a shift register in an ADC.
You can see this clock, and the data stream being generated?.
You are attempting to use this clock to receive the data stream using the SPI hardware.
The read code is hanging.
Is my summary correct?.
Now, the PIC SPI read, on a slave device, will _only_ hang, if it does not see a clock. Pulse the SCK line up and down 8 times, and a byte will be available, even if garbage. Data line levels do not matter.
So, to get the hang, implies the PIC is not seeing the clock.
So, first, triple check that the clock is arriving at the correct pin on the PIC. Pin4, for a 64pin device, 6 for an 80pin, and 10 for 100pin.
Then, look at the actual voltage level. Note that the SCK input buffer, is marked as 'ST'. Implies it needs to get up to 0.8* the supply voltage to be seen as a '1'. This would be my 'most likely' cause for the problem....
If the signal is getting high enough, then simplify. Make a program that _only_ attempts to receive one byte. Does no output, except to toggle an I/O pin when the byte is received. Then try manually toggling the SCK pin 8 times, and see if the pin toggles.
Other possibilities - what is your compiler version?. Obviously there may be something silly like an issue with the SPI configuration. Have you tested that you can send data from SPI1?. If not, do so. Send a 'dummy' output pattern, without trying to read SPI1. Have you verified that your CPU is actually running?. Simple pin toggle test.
If nothing appears on the SPI1 output, just try checking the SPI2 output instead. There has been an issue on some chips in the past with the compiler 'reversing' the ports.
Best Wishes |
|
|
FvM
Joined: 27 Aug 2008 Posts: 2337 Location: Germany
|
|
Posted: Fri Mar 11, 2011 11:15 am |
|
|
I agree, that the SPI slave shouldn't hang but receive some data. But I don't expect, that it will receive the correct data, because the extrenally generated SCK isn't synchronized with AD_SYNC (or is it?). Can you explain, when SCK is activated? Generally I don't understand, why you're using slave mode.
To determine, if there are possibly PCD bugs involved, we would need to know the compiler version. |
|
|
geolover
Joined: 08 Feb 2011 Posts: 18
|
|
Posted: Sun Mar 13, 2011 1:32 pm |
|
|
Thank you! Problem was solved after putting 1ms delay after before spi1 begin to write data out.
However, in my ADC datasheet, it says the device shifts data out on the falling edge and the use shifts this data in on the rising edge. Im getting quite confused about how to setup CKP, CKE to match with this device? |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|