I think someone is getting confused with sending and receiving serial data. When you send, you send the start bit, wait one bit period, send the lsb, wait one bit period etc...
When you use a simple software uart to receive, you should sample the serial data in the middle of a bit period. So after detecting the start bit, then you wait 1 1/2 bit periods so that you sample in the middle of the first bit, then wait one bit period to sample the next bit etc. The 1 1/2 bit period is only valid as the first delay after receiving the start bit.
Mike
-----Original Message-----
From: Byron A Jeff [SMTP:byron@CC.GATECH.EDU]
Sent: Monday, March 27, 2000 1:48 PM
To: PICLIST@MITVMA.MIT.EDU
Subject: Re: rs232 works - should it?
>
> >Your start bit is currently half a bit-time long; make it a full bit-
> >time (in other words, replace the "call Delay50uS" with a "call
> >Delay100uS") and everything will work MUCH better.
> >
> >-Andy
>
> Well, this is confusing - your suggestion doesn't work.
>
> The frustrating part for me is that I still don't have a definitive
>reference for whether the start bit is 1.5t, 1t or 0.5t,
It's 1t, the same size as every other bit in the serial stream.
> and of what polarity
>relative to the stop bit.
The opposite of the stop bit.
> Does anyone have a pointer to an actual rs232
>standard that shows these relationships? I know the voltages and pinouts -
>but what *exactly* is supposed to take place from the start of transmission
>to the very end? Even an ugly ASCII art diagram would be great.
Instead of ASCII art I'll use letters L for low and H for high. Say you wanted
to send an ASCII 'A' (01000001). This would be the sequence:
HHHHLHLLLLLHLHHHH
1 23 4
Notes:
1. The serial line idles in a high state and must be in a high state
for at least 1 bit time before the start bit.
2. The start bit. Note that that it must be the opposite polarity of the idle
state. It is one bit time. Not 1.5 bit times.
3. This is the least significant bit. the other bits follow in sequence.
4. This is the stop bit. Note that it just idles the line but must be present
because the line must be idle for at least 1 bit time before a start bit.
>
> Is this supposed to be right for sending H'28' at 9600/n/8/1?
>
> 1 156uS <start bit
Nope. First of all a start bit is a 0, not a 1. Also it's the same length as
all the other bits.
> 0 104uS <bit0
> 1 104uS
> 0 104uS
> 0 104uS
> 0 104uS
> 0 104uS
> 0 104uS
> 1 104uS <bit7
This sequence sends a H'82', not H'28'. For H'28' it would be
0
0
1
0
0
1
0
0
> 0 104uS <stop bit
Stop bit is a 1. Same length as all the others.
>
> The above doesn't seem to work in my case. Reversing start/stop polarity also
> doesn't work. Only when I shorten the start bit to 50uS does it work
>somewhat reliably,
It's 104uS, just like all other others.
> and only when I lengthen the stop bit 3x-5x does it seem solid.
Now that's possible depending on the receiver. However nothing should require
more than 2 stop bits.
> Like so:
>
> 0 52uS ;start bit
Nope. Still 104uS. The start bit is the same length as all the others.
> bit0 104uS
> bit1 104uS
> ...
> bit7 104uS
> 0 104uS ;stop bit
> 0 104uS ;stop bit
> 0 104uS ;stop bit
> 0 104uS ;stop bit
What's the receiver. It's probably getting confused by the 0.5 length start
bit. Many implementations will check the start (and every other bit) in the
middle of the cell. In both these instances above you've set the start bit
so that it changes in the middle of the cell, making all subsequent bits
spurious. The start bit is the same length as every other bit. Once you do
this then it should stabilize.
>
> Code follows (delays are properly adjusted to give very close to correct bit times in this routine):
>
> Sendbyte:
> movwf MYBYTE
> bsf PORTA,dataout ;startbit 1/2t logic low
> call Delay50uS
call Delay104uS
> movlw D'8'
> movwf BITCNT
> bitlp:
> rrf MYBYTE,f ;lsb first
> btfss STATUS,C
> goto sendlow
> sendhigh:
> bcf PORTA,dataout ;direct-connect so invert
> goto bitset
> sendlow:
> bsf PORTA,dataout
> goto bitset ;this would fall through, but
> ;keeps bit timing symmetrical
> bitset:
> call Delay100uS ;1t each bit
> decfsz BITCNT,f
> goto bitlp
> bcf PORTA,dataout ;stop bit 1t logic high
> call Delay100uS
> call Delay100uS
> call Delay100uS
> call Delay100uS
> call Delay100uS
Should need two at the max once you set the start bit correctly.
BAJ