|
|
View previous topic :: View next topic |
Author |
Message |
kWoody_uk
Joined: 29 Jan 2015 Posts: 47 Location: United Kingdom
|
Slave select on pic18f4423 |
Posted: Tue Mar 31, 2015 1:19 pm |
|
|
Hi Guys,
I think there is a problem with the Slave Select for Spi on the pic18f4423 and would like another pair of eyes to look at the silicon errata data and confirm the bad news I have come to.
http://ww1.microchip.com/downloads/en/DeviceDoc/80289e.pdf
It's section 1 in this document (Module: MSSP)
My spi interrupt is firing whenever there are 8 clock pulses, whether the slave select line is low or not.
I have checked and confirmed the CCS assembly listing to ensure the Slave select line is in use and not just IO and that it is selected as an input.
Unfortunately, I've only discovered this after the product has been assembled (I should have read the errata more carefully!) Apart from using the SS line as general IO and polling to see if low before awaiting the data, is there a better work-around?
Thanks in advance,
Keith |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Tue Mar 31, 2015 1:39 pm |
|
|
The obvious question is how long your master device allows from the SS dropping to starting to send the data?. This is the problem, but only if this is a very short time (depends on yous CPU clock rate). Needs to be 12 cycles of your PIC master clock, |
|
|
kWoody_uk
Joined: 29 Jan 2015 Posts: 47 Location: United Kingdom
|
|
Posted: Tue Mar 31, 2015 2:58 pm |
|
|
Hi Ttelmah,
I'm waiting about 30 cycles. However, I know it isn't this, as even when the slave select is permanently high, the spi interrupt is still entered whenever there are 8 clock pulses... It's almost like enabling the use of the slave select line is being ignored by the pic.
Keith |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Tue Mar 31, 2015 10:54 pm |
|
|
If you can post small, working SPI master and slave programs, we can
test it. These two programs can be really short (but compilable). |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Wed Apr 01, 2015 1:06 am |
|
|
I have just put this together on a 4423, and it works correctly (at least on a basic test...).
Code: |
#include <18F4423.h>
//Basic setups adjust to suit your device
#device ADC=10
#fuses HS, NOFCMEN, NOWDT, STVREN, NOXINST, NOPROTECT, NODEBUG, BROWNOUT, BORV43
#use delay(crystal=20000000)
//Basic SPI slave test
#use RS232(UART1, baud=9600, ERRORS)
//SPI mode definitions
#define SPI_MODE_0 (SPI_L_TO_H | SPI_XMIT_L_TO_H)
#define SPI_MODE_1 (SPI_L_TO_H)
#define SPI_MODE_2 (SPI_H_TO_L)
#define SPI_MODE_3 (SPI_H_TO_L | SPI_XMIT_L_TO_H)
//Basic buffer code -setup 16byte buffers both ways
int8 btempSPIRX,btempSPITX;
#define SIBUFF (16) //buffer sizes
typedef struct {
int8 in;
int8 out;
int8 buff[SIBUFF];
} buffer;
buffer SPIRX,SPITX; //buffers
//Macros to handle buffers
#define incin(buff) ((buff.in==(SIBUFF-1))?0:buff.in+1)
#define incout(buff) ((buff.out==(SIBUFF-1))?0:buff.out+1)
#define isempty(buff) (buff.in==buff.out)
#define hasdata(buff) (buff.in!=buff.out)
#define isfull(buff) ((incin(buff)==buff.out)
#define tobuff(bname,c) { bname.buff[bname.in]=c;\
bname.in=incin(bname);\
if (bname.in==bname.out) bname.out=incout(bname);\
}
#define frombuff(bname) (btemp##bname=bname.buff[bname.out],\
bname.out=incout(bname), \
btemp##bname)
#define clrbuff(buff) buff.in=buff.out=0
//Because CCS code tests unecessarily just do direct SPI I/O
#byte SSPBUF=getenv("SFR:SSPBUF")
#INT_SSP
void SPI(void)
{
//have seen SPI transfer
tobuff(SPIRX,SSPBUF); //read incoming
if (hasdata(SPITX)) //if data is waiting to send
{
SSPBUF=frombuff(SPITX); //load next outgoing
}
}
void main()
{
int8 chr, ctr=0;
setup_spi(SPI_MODE_0 | SPI_SLAVE);
clrbuff(SPIRX);
clrbuff(SPITX); //clear both buffers
//Now several setups must happen. Analog must be off on A5
setup_adc_ports(NO_ANALOGS); //obviously if using the analog enable other pins
setup_adc(ADC_OFF);
setup_ccp1(CCP_OFF);
//comparator 2 must be off
setup_comparator(NC_NC_NC_NC);
enable_interrupts(GLOBAL);
enable_interrupts(INT_SSP); //enable the slave interrupts
while(TRUE)
{
//Now sit and wait for something on the SSP
if (hasdata(SPIRX)) //something has been received
{
chr=frombuff(SPIRX); //get the received character
//do something - minimum demo
if (chr=='R')
{
tobuff(SPITX,ctr++); //send a byte back
}
}
}
}
|
If I hold the SS high, I can toggle C3, and no interrupt occurs. Drop A5, and toggle C3, and after eight cycles it interrupts.
Remember there needs to be long enough after _every_ byte, to allow time for the slave to have reached the interrupt, serviced it, and returned. As written here, about 20uSec/byte maximum. As written, if the SPI sends the character 'R', then waits, and clocks out a dummy byte, it received back a count.
I wonder if you are forgetting to turn off the analog port on pin A5?. If this is not off, SS does not work. Same with comparator 2. |
|
|
kWoody_uk
Joined: 29 Jan 2015 Posts: 47 Location: United Kingdom
|
|
Posted: Wed Apr 01, 2015 2:17 am |
|
|
You've cracked it Ttelmah!
I am using the analogue pins, and when I disabled this the SS works.
Unfortunately, with my application, I am using the analogue pins ( AN5 upwards) and on this device, I don't think you can individually set which pins are Analogue, but must accept the choices given... Doh!!
Any suggestions would be gratefully accepted.
Thanks,
Keith |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Wed Apr 01, 2015 2:37 am |
|
|
Change the chip......
Unfortunately this was something you needed to spot at the design. 'And upwards', is the exact opposite of how this chip allows the analogs to be selected. You can use AN3 _and down_ as analogs, but not AN5 'and up'.
Unfortunately, most of the chips that offer the same ADC resolution and are completely compatible, have at least one pin different (VddCore on the ones that internally run at a lower voltage, or USB pins for example). The ones that directly slot in place have the same ADC restrictions. The nearest is probably the 45K80, if you can add a capacitor for the VddCore pin, then this allows every ADC pin to be individually selected |
|
|
kWoody_uk
Joined: 29 Jan 2015 Posts: 47 Location: United Kingdom
|
|
Posted: Wed Apr 01, 2015 3:39 am |
|
|
Yeah I know, I would have used the 46k22 as I like this chip and know it's short-comings, but my boss wanted 12bit ADC resolution and we'd used this before, but only in Master SPI mode.
Thanks for the suggestion; I'll consider this in future.
Lesson learnt. Next time, I'll read the data sheet 50 times through :-)
Thanks again,
Keith |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Wed Apr 01, 2015 3:45 am |
|
|
The 45K80, has the same 12bit ADC resolution. That's why I mentioned this one. |
|
|
kWoody_uk
Joined: 29 Jan 2015 Posts: 47 Location: United Kingdom
|
|
Posted: Wed Apr 01, 2015 4:04 am |
|
|
Oh Blimey
That's even better. I don't know how you do it for the money ;-)
- but thank you!
Keith |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9228 Location: Greensville,Ontario
|
|
Posted: Wed Apr 01, 2015 4:56 am |
|
|
yeesh , bosses, 12 bit vs 10 bits...
hope he's paying you lots for those extra 2 bits! Board layout, signal conditioning, wiring, PSU...ALL have to be PERFECT to acquire usable 12bits.
Depending on the application, it might be better and cheaper to go with solid 10 bits than 'hit and miss' 12 bits.
just my 2 cents worth
Jay |
|
|
kWoody_uk
Joined: 29 Jan 2015 Posts: 47 Location: United Kingdom
|
|
Posted: Wed Apr 01, 2015 7:20 am |
|
|
Thanks Jay,
All input is appreciated. Luckily, my boss is great at analogue design (an art which is disappearing) so that's looked after.
Keith |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Wed Apr 01, 2015 7:36 am |
|
|
True.
It's worth also realising that the 'extras' depend a lot on the 'nature' of the actual data.
For things like audio signals, the noise constraints etc., are all there, but the 'accuracy/repeatability' ones are not. It doesn't matter if a value reads as 2623 one day and 2625 another. What matters is that a value that has dropped by a tiny percentage really does read 2 lower each day. However if being used for an actual measurement application, then (of course) you want the same reading each day, so the accuracy required spreads to things like the stability of the Vref etc...
It's actually surprising just how good the 10bit PIC ADC really can be, if used with good design, and a really good reference. I've had systems that give repeatable values to 0.1% over long periods. |
|
|
|
|
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
|