View previous topic :: View next topic |
Author |
Message |
xxjoelxx
Joined: 28 Sep 2009 Posts: 5
|
Built-in USART buffer 3 characters? |
Posted: Mon Nov 23, 2009 10:42 am |
|
|
Hey, I was reading this on the CCS reference book. As I'm using a built in USART. Thinking of how do I solve the problem of receiving 3 bytes at a time. Anyone can help to explain? Thanks.
Quote: |
GETC( ) GETCH( ) GETCHAR( ) FGETC( )
Syntax:
value = getc()
value = fgetc(stream)
value=getch()
value=getchar()
Parameters:
stream is a stream identifier (a constant byte)
Returns:
An 8 bit character
Function:
This function waits for a character to come in over the RS232 RCV pin and returns the character. If you do not want to hang forever waiting for an incoming character use kbhit() to test for a character available. If a built-in USART is used the hardware can buffer 3 characters otherwise GETC must be active while the character is being received by the PICĀ®.
If fgetc() is used then the specified stream is used where getc() defaults to STDIN (the last USE RS232).
Availability:
All devices
Requires:
#use rs232 |
|
|
|
dyeatman
Joined: 06 Sep 2003 Posts: 1934 Location: Norman, OK
|
|
Posted: Mon Nov 23, 2009 11:57 am |
|
|
I not sure where they get 3 characters. The datasheet shows the RSR and the RCREG which would be one and a half. The datasheet shows the RCREG as having two locations but I am unable to find anything in the datasheet to back that up. Even if that were the case it would still only be two and a half, not three. _________________ Google and Forum Search are some of your best tools!!!! |
|
|
FvM
Joined: 27 Aug 2008 Posts: 2337 Location: Germany
|
|
Posted: Mon Nov 23, 2009 12:58 pm |
|
|
It's a misleading information, that should be corrected. A few advanced 8-Bit-PIC have an UART with RX-FIFO, e.g. the EUSART of
PIC18F4585. Also all 16-Bit PICs have it, but PCD isn't covered by the said manual (the PCD manual has the same text B.T.W.). |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Mon Nov 23, 2009 2:55 pm |
|
|
I made a test program for this, and it shows that two characters are
buffered. If I release the PIC from reset (with the ICD2 button in MPLAB)
and type in 1234 in TeraTerm, and then press the A4 push-button on
the PicDem2-Plus board, I get this displayed:
That's 1 and 2. This fits the description of a 2-deep receive fifo.
(Results are the same, with or without the ERRORS parameter).
The Microchip 16F-series Reference Manual says:
Quote: |
18.4.2 USART Asynchronous Receiver
The RCREG is a double buffered register, i.e. it is a two deep FIFO. |
The next part explains why we don't get the 3rd byte (in the receive shift
register):
Quote: |
It is possible for two bytes of data to be received and transferred to the
RCREG FIFO and a third byte begin shifting to the RSR register.
On the detection of the STOP bit of the third byte, if the RCREG register
is still full then overrun error bit, OERR (RCSTA<1>), will be set.
The word in the RSR will be lost.
|
16F Reference Manual: Section 18. USART
http://ww1.microchip.com/downloads/en/DeviceDoc/31018a.pdf
Test program:
Code: |
#include <16F877.H>
#fuses XT, NOWDT, NOPROTECT, BROWNOUT, PUT, NOLVP
#use delay(clock = 4000000)
#use rs232(baud = 9600, xmit=PIN_C6, rcv=PIN_C7, ERRORS)
#define BUTTON_PIN PIN_A4
void wait_for_button(void);
//====================================
void main()
{
int8 c;
// Type in 3 or more chars in TeraTerm. Then press the
// push button.
wait_for_button();
// Then this loop will read the UART's buffer and display
// what it got.
while(1)
{
c = getc();
printf("%X ", c);
}
}
//==================================
// FUNCTIONS
void wait_for_button(void)
{
char count;
// Wait for the button to be released.
// The button must be in the "up" state for two
// consecutive samples, at 10 ms intervals.
count = 0;
while(1)
{
if(input(BUTTON_PIN))
count++;
else
count = 0;
if(count == 2)
break;
delay_ms(10);
}
// Now that the button is up, wait until the
// user presses it. For the keypress to be
// considered valid, the button must be held
// down for two consecutive samples, taken at
// 10 ms intervals.
count = 0;
while(1)
{
if(input(BUTTON_PIN) == 0)
count++;
else
count = 0;
if(count == 2)
break;
delay_ms(10);
}
} |
Last edited by PCM programmer on Mon Nov 23, 2009 3:06 pm; edited 2 times in total |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Mon Nov 23, 2009 2:58 pm |
|
|
However, I think all the original poster wanted to do is to get 3 bytes.
Answer:
Just call getc() 3 times. Or do it in a for() loop. Or call kbhit() to see
if you have one or more characters available in the UART's receive buffer
and if so, then call getc().
Or, call the get_string() function (assuming you're receiving text chars).
See these example and driver files for get_string():
Quote: | c:\program files\picc\examples\ex_str.c
c:\program files\picc\drivers\input.c |
|
|
|
dyeatman
Joined: 06 Sep 2003 Posts: 1934 Location: Norman, OK
|
|
Posted: Mon Nov 23, 2009 3:49 pm |
|
|
It's interesting they don't mention the double buffered FIFO except by showing it in the in the diagram in the 18F series PIC datasheets. I hadn't looked at the MidRange Ref Guide in quite a while. So, two and a half is correct then... Thanks for the additional info PCM. _________________ Google and Forum Search are some of your best tools!!!! |
|
|
|