CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to CCS Technical Support

Baud Rate "Conversion"

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
pulurumbuluruciu



Joined: 06 Nov 2013
Posts: 27

View user's profile Send private message

Baud Rate "Conversion"
PostPosted: Mon Dec 02, 2013 3:43 pm     Reply with quote

Hi. Using 18F25k22 ( 2 UART) I'm trying to get data from one UART With a 57600 bps, and send it over the other UART with 9600 bps. The problem is that the data comes too fast from the 57600, and the 9600 bps UART fails to output all the string. How is this done in a correct way? I tried
Code:

fputc(UART9.6,fgetc(UART57.6));

I know that I must implement a buffer but I tried several ways and failed. Please help. Thank you.
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Mon Dec 02, 2013 5:01 pm     Reply with quote

Look in the CCS example files directory for Ex_sisr.c. It shows how to
make a serial receive buffer for the incoming bytes:
Quote:
c:\program files\picc\examples\ex_sisr.c
gpsmikey



Joined: 16 Nov 2010
Posts: 588
Location: Kirkland, WA

View user's profile Send private message

PostPosted: Mon Dec 02, 2013 7:12 pm     Reply with quote

If the average data rate from the 57k source is above 9600 baud, then you can't get there from here. If the source average rate is less than 9600 baud, then you can do it, but will need to look at the "burst" size to determine what size buffer you will need (hopefully less than the available RAM in the chip). The key here is the average rate from the source - if it is too high, you are going to have to look at alternatives.

mikey
_________________
mikey
-- you can't have too many gadgets or too much disk space !
old engineering saying: 1+1 = 3 for sufficiently large values of 1 or small values of 3
temtronic



Joined: 01 Jul 2010
Posts: 9245
Location: Greensville,Ontario

View user's profile Send private message

PostPosted: Mon Dec 02, 2013 8:53 pm     Reply with quote

With proper handshaking it should be possible using the Ex_SISR.C example lightly modified for the 2 serial ports.
Key is handshaking.
I've done similar with 115K200 > 9600 using a 46k22 PIC.been stable for 14-18 months in the lab.

hth
jay
Ttelmah



Joined: 11 Mar 2010
Posts: 19546

View user's profile Send private message

PostPosted: Tue Dec 03, 2013 1:31 am     Reply with quote

Agree with Temtronics comments.
You may need to deal with buffer 'overshoot' when handshaking. So (for instance), if you are running a 256byte buffer, it is no good trying to stop when the buffer is full. You need to send the handshake, some characters _before_ the buffer is full. PC's typically have 16byte of hardware buffering, and using XON/XOFF etc., it takes a character time for this to be sent, and it may then send this many characters after you tell it to 'stop'. So something like 32 characters before the buffer is full, is the point to be telling it to stop....

Best Wishes
asmboy



Joined: 20 Nov 2007
Posts: 2128
Location: albany ny

View user's profile Send private message AIM Address

PostPosted: Tue Dec 03, 2013 5:06 am     Reply with quote

don't forget uni-directional DTR-RTS handshaking as another way to deal with
potential overflow issues - tho this will require a control pin on your PIC to 'wave off" the 57600 source when the receive buffer is within range of it's last character or two. simpler and more efficient than software handshake, which can wreck havoc with binary transfers
pulurumbuluruciu



Joined: 06 Nov 2013
Posts: 27

View user's profile Send private message

PostPosted: Tue Dec 03, 2013 6:48 am     Reply with quote

Thank you for all your inputs. The incoming burst is relativ small ( 100 chars) so it could be easy managed by a buffer. The problem is that when I output the characters with a 50 us delay( needed as a guardtime) between them from the buffer I dont get the correct ones anymore. If I output them whitout that delay it works fine. Used the SISR example modified file for that.

NOT WORKING CODE (NEEDED)
Code:

   do {
        while(bkbhit)
       delay_us(50);
        fputc( bgetc(),UART9.6 );
   } while (TRUE);

WORKING CODE
Code:

   do {
        while(bkbhit)
        fputc( bgetc(),UART9.6 );
   } while (TRUE);
Ttelmah



Joined: 11 Mar 2010
Posts: 19546

View user's profile Send private message

PostPosted: Tue Dec 03, 2013 8:00 am     Reply with quote

Understand that if using a hardware UART, you won't get any delay this way....

There is a couple of characters of hardware buffering on the output. Fputc, will return as soon as the characters transfer to the hardware buffer, since each character (at 9600bps), will take 1.04mSec to send, the delay will be lost in the period it takes the character to physically send.....
If you want a longer pause between characters, set the UART up to send 9 bit characters, and then make sure what you actually send has the ninth bit as a zero.

Best Wishes
pulurumbuluruciu



Joined: 06 Nov 2013
Posts: 27

View user's profile Send private message

PostPosted: Tue Dec 03, 2013 8:26 am     Reply with quote

How do I send 9 bits char? Using 2 stop bits?
Ttelmah



Joined: 11 Mar 2010
Posts: 19546

View user's profile Send private message

PostPosted: Tue Dec 03, 2013 8:59 am     Reply with quote

The _hardware_ only supports 8 or 9bit transmission with one stop bit.
The point is that if you select 9bit, then make sure the MSB (9th bit) is one, this sends effectively an extra stop bit, giving an extra just over 100uSec between the bytes.
Just set bits=9, and the option 'LONG_DATA' in the #use RS232 for the 9600bps stream. Then make sure the value you get from the 8bit UART is put into (or cast into) an int16, and send this in the putc. Putc automatically accepts a 16bit value for the character when 'long_data' is selected. So:
Code:

do {
        while(bkbhit)
        fputc( make16(1,(bgetc()),UART9.6 );
   } while (TRUE);

Correction here (thinking about RS232 levels, not TTL async levels). You need to set the 9th bit as shown.

Best Wishes
pulurumbuluruciu



Joined: 06 Nov 2013
Posts: 27

View user's profile Send private message

PostPosted: Mon Dec 09, 2013 5:40 am     Reply with quote

Hi again. After 2 weeks of strugle..no..I did not solve it..:| How Is possible when I print from a buffer created by INT_RDA2 and put the character on Uart1 and then get it back(echo prevent), to get garbage in my UART1 data...!? if I do not get it back It will work ..but whyy? because is a buffer...is nothing "real time".
Code:

#include <18F25K22.h>
#FUSES NOWDT, WDT128, INTRC_IO, NOFCMEN, NOIESO, NOHFOFST, NOMCLR, NOLVP, NOXINST
#use delay(clock=64000000)
#use rs232(uart1, BITS=8,baud=9600, PARITY=N, STOP=1, STREAM=U1,errors)
#use rs232(uart2, BITS=8,baud=19200, PARITY=N, STOP=1, STREAM=U2,errors)
#define BUFFER_SIZE 128
BYTE buffer[BUFFER_SIZE];
BYTE next_in = 0;
BYTE next_out = 0;



#int_rda
void RDA_isr(void) {
fputc(fgetc(U1),U2);    // lower to higher baud-rate , no need to buffer.
}


#int_RDA2
void  RDA2_isr(void)
{
   int t;
   buffer[next_in]=fgetc(U2);
   t=next_in;
   next_in=(next_in+1) % BUFFER_SIZE;
   if(next_in==next_out)
     next_in=t;           // Buffer full !!
}

#define bkbhit (next_in!=next_out)

BYTE bgetc() {
   BYTE c;
   while(!bkbhit) ;
   c=buffer[next_out];
   next_out=(next_out+1) % BUFFER_SIZE;
   return(c);
}

main(){
setup_comparator(NC_NC_NC_NC);// This device COMP currently not supported by the PICWizard
setup_adc_ports( NO_ANALOGS ); // disable analog inputs 
enable_interrupts(INT_RDA2);
enable_interrupts(INT_RDA2);
enable_interrupts(GLOBAL);
    while(true){
if(bkbhit==1){
DISABLE_interrupts(INT_RDA);
fputc(bgetc(),U1);
FGETC(U1);
ENABLE_interrupts(INT_RDA);
}
}
}

And I send maximum 50 char..not even the full 128 buffer... Sad my hair starts to fall..
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
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