Message Edited by pittbull on 02-25-200601:58 PM
... But when other people use my SPI slave, they can make a mistake and this would confuse the device if not handled. The main reason that I need to detect change of /SS is to bring the software protocol to its initial state (Begin with e.g. packet header, token, lenght at next connection).
From what you say, I assume that the slave is not permanently connected to the master, and may be powered up separately from the master. So the master would need to ascertain when the slave was actually connected and operating, before initiating a packet transfer, and the slave will not return anything until its /SS input becomes low.
Here is a suggested possibility:
I think this sort of approach avoids the problems that you anticipate with possibly incomplete initial data byte.
Because my slave device and the master have to send an arbitrary number of bytes and SPI can't send without receiving (and also vice versa), I must define a byte value that represents an 'invalid byte'.
I am inclined to rename your "invalid" byte as an "idle" byte or token. So this byte would also have a unique value, not replicated by any data packet header. I would consider a suitable value $55 or $AA (alternating 0's and 1's), that cannot be replicated in the event of an incomplete byte.
I would not be too concerned if any of the data bytes within a packet were to have the same value as the idle byte, or the packet header byte. This is because the master (or slave) already knows how many data bytes it expects to receive, and would not be looking for further headers (tokens) until after it has received the required packet data.
... I first put the 'invalid byte' into SPI0DR, then setting SPTIE to ensure that the first byte transmitted is not a zero but my 'invalid byte'.
I don't think this would really be a problem since the master would need to treat both $00 and $FF values as invalid header values.
I monitor the /SS to reset the 'byte stuffer' when /SS goes high. I do this by reading the PORTS input register (PTIS_PTIS7). I don't know if it makes a difference to use PTS_PTS7 instead.
I still cannot understand why this complication is necessary. I think I would simply not put any packet data into the slave send buffer until I had received an idle byte from the master, and would also expect at least one idle byte as acknowledgment, before placing subsequent packets.
The only situation I can't detect until now is when someone switched the slave off and on again while the master is continously clocking. Although, that doesn't confuse the slave but it would be nice if the master can recognize it.
Perhaps if the master does not receive at least one idle byte immediately following a received packet, it should discard that packet data. Another special token to request a resend of the prior packet might prove useful.
If the slave can lose power whilst connected to the master, you may need to consider separate open collector (drain) buffers on the MOSI, /SS and clock lines at the master, with resistive pull-ups at the slave. If the interconnection between master and slave is potentially subject to static discharge, buffers on all lines, for both master and slave, are probably a good idea anyway.
"I can safely say that it is tedious" is the understatement of the year!
i've been working on a 6 processor scada system for over a year now. the communications protocol issues have dominated about 10% to 15% of the design time. i't more choreography than programming.