Pages: [1] 2   Go Down
Author Topic: UART(COM port) baud rate converter? Help anyone?  (Read 3674 times)
0 Members and 1 Guest are viewing this topic.
Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Guys, i would really appreciate any help - is there any open sourced baud rate converter implemented in arduino for several com ports? I really need something like 115200 ttl com in, and 38400 + 9600 + 115200 out on several com ports. Anybody done this type of thing before?
Logged

nr Bundaberg, Australia
Offline Offline
Tesla Member
***
Karma: 121
Posts: 8443
Scattered showers my arse -- Noah, 2348BC.
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

You just read from one port and write to another, probably 20 lines of code

Code:
setup () {
   Serial1.begin (115200);
   Serial2.begin (9600);
}

loop () {
   if (Serial1.available())
       Serial2.write(Serial1.read());
}

Make that 8 lines smiley

______
Rob
Logged

Rob Gray aka the GRAYnomad www.robgray.com

Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

But this will not work. More thoughts on the subject

GPS data 10HZ, uses about 32000bps of the com port... Yeah, it will work pushing the stream to 38400, but i'll need probably to discard some data for the low speed 9600.... How?
Logged

Left Coast, CA (USA)
Online Online
Brattain Member
*****
Karma: 331
Posts: 16515
Measurement changes behavior
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Well I don't think you have defined your requirements well enough to say it can be done or not on a arduino. However a arduino mega board does have four serial ports available so under certain conditions serial conversion is certainly possible. But again requirements have to be more clear, such as:

Is this to be a one way conversion, that is there to be one input stream to the arduino converted to one or more streams outputting at other baud rates from the arduino?

Is the one input stream the slowest of the baud rates relative to the output streams? If not then possible additional buffering might be required in your sketch, above what the arduino hardware serial library makes available.

Lefty
Logged

nr Bundaberg, Australia
Offline Offline
Tesla Member
***
Karma: 121
Posts: 8443
Scattered showers my arse -- Noah, 2348BC.
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Yes I was a bit flippant there smiley

If the average input throughput is faster than the output you are screwed. However if the average input is the same or less than what the output can handle you can buffer the data.

Let's say you have an NMEA string of 100 chars occurring every 100mS. That's an average of 1000 chars a second so your output has to match that or better.

There are usually 10 bits per byte when transmitting so 1000 bytes per second == 10000 bits per second so (if we ignore any overheads) your output stream has to have a baud rate of at least 10000bps.

So the actual input baud rate is fairly immaterial, you need to know the number of bytes received per second.

If the above conditions are met you write some simple ring buffer code to hold the characters while they are waiting for transmission.

______
Rob
« Last Edit: August 31, 2012, 11:13:23 am by Graynomad » Logged

Rob Gray aka the GRAYnomad www.robgray.com

Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I'll try to be more thorough

Data IN:
One UART TTL input, GPS, 115200, 10HZ updates, NMEA, the data is sent to the arduino at a rate 10 times per second so the average baud rate is 32000bps.

Data OUT:
Will need(arduino mega will do): 2/3/4/(the more the better) outputs. The data communication is unidirectional (recieve at RX and transmit to those 2/3/4 TX ports)

1) Must have an option to strip the NMEA 10HZ data stream to, lets say 2HZ, or even 1HZ, so that the average baud rate would be sufficient for selected baud rate (lets say in this scenario it's 9600)
2) If the baud rate allows it - no "stripping" neccesary, and all 10HZ data updates can be pushed to those other COM ports..

So that such a config could exist:
Data IN: 115200, NMEA, 10HZ
Data OUT1: 38400, NMEA, 10HZ
DATA OUT2: 14400, NMEA, 5HZ
DATA OUT3: 9600, NMEA, 2HZ

.. I'm a crappy programmer at arduino

So if i am screwed - It seems that the only way is to parse the NMEA data, and discard some of the NMEA "sentences" in case i need to put this data to the port with lower available bandwidth. Ok - is there a library and a parcer for NMEA? )))))
Logged

Left Coast, CA (USA)
Online Online
Brattain Member
*****
Karma: 331
Posts: 16515
Measurement changes behavior
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
One UART TTL input, GPS, 115200, 10HZ updates, NMEA, the data is sent to the arduino at a rate 10 times per second so the average baud rate is 32000bps.

A little confusing as you are using baudrate to define something other then what it measures. A baud rate is a fixed clocking speed that both sides of a comm link agree to use to clock individual bits onto the com link and does not change. Character rate is a variable rate that can be any value up to a maximum rate possible that can be supported by the baudrate being used. So at a 115200 baud rate, a link can support a character rate to a maximum of 11,520 characters a second (divide by 10 because, 8 bit character + one stop bit + one start bit). However that same 1152000 baud rate link can certainly be used to send a one character message only every one second, so the link would be working at an effective rate of one character a second, even though the bits in that single character are clocking at 1152000 bits per second rate.

 So when you say a device like a GPS will be sending a message at a 10hz rate, it doesn't give us a complete picture of the character rate as you don't state how many characters are going to be sent every 10hz, so an effective character rate per second can't be determined. If the GPS message can be of variable character lengths then it's even more difficult to state the effective character rate, only a possible maximum character rate based on the longest possible message.

Baud rate is essential to know as it is used to configure the AVR serial hardware to run at the correct speed you require to support the comm link. Effective character rate is important to know so that one can determine what software support will be required to handle the message traffic from the link, such as possible arrays of a specific length to use to 'buffer' a complete message, and the amount of time your program will have to possibly parse the messages and take action based on the content in the messages.

So your table:

Quote
So that such a config could exist:
Data IN: 115200, NMEA, 10HZ
Data OUT1: 38400, NMEA, 10HZ
DATA OUT2: 14400, NMEA, 5HZ
DATA OUT3: 9600, NMEA, 2HZ

Needs at least one other data value added to each link, what is the maximum number of characters that can happen every xxHz message cycle?

 Also do you see a possible fatal problem with your defined links? If you can receive new messages into the arduino at up to 10 messages per second but have to limit sending them out as slow as 2 messages per second then your input stream will certainly be coming in faster then you can output the messages, so input stream will have to be buffered and there is limited SRAM memory to support that and I think that sooner or later you will 'overflow' the input buffered stream and lose information?


Lefty
« Last Edit: September 01, 2012, 09:39:26 am by retrolefty » Logged

New Jersey
Offline Offline
Faraday Member
**
Karma: 48
Posts: 3412
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Stepping back a little, what are you actually trying to do? Presumably, you have several devices that consume NMEA sentences; is their baud rate limited? Does each need all sentences or a subset? Does it matter if not all sentences are delivered?

Having some more detail about the requirement might get you some more insightful advice; as is, it's hard to see the why.
Logged

Miers 46500 France
Offline Offline
Full Member
***
Karma: 2
Posts: 170
EmbeddedAT .. From Concept to Prototype to Production
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

You just read from one port and write to another, probably 20 lines of code

Code:
setup () {
   Serial1.begin (115200);
   Serial2.begin (9600);
}

loop () {
   if (Serial1.available())
       Serial2.write(Serial1.read());
}

Make that 8 lines smiley

______
Rob



You may want to add the lines that define the pins used in the softserial library too smiley
Logged

EmbeddedAT .. From Concept to Prototype to Production

Electronics and firmware design and project mentoring

Miers 46500 France
Offline Offline
Full Member
***
Karma: 2
Posts: 170
EmbeddedAT .. From Concept to Prototype to Production
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

OK .... so ...

We have two frequencies going on here, and some confusion as to the requirements of the "baud" rate.

The interface speed of the GPS is the baud rate, the rate at which it sends messages is the message rate, the two are not really inter dependent unless you are expecting to be transmitting data at 32 baud smiley

So even if the messages are coming in at 10Hz unless there is a VERY good reason why not then they can also go out at 10 Hz independently of the baud rates.

The very simple serial repeater posted by Rob will do what you want, all you have to do is extend it to have the number of ports you are expecting to repeat to and specify the pins you are intending to use for the soft serial library. Most NMEA sentences are quite short and will not require buffering but can just be squirted directly out.

If you need more guidance with the coding just shout, I am sure there are plenty of people including myself who can knock this up in 5 minutes for you.

If my understanding is too simplistic and you do need to be throttling the NEMA message rate then it all gets much more complicated.

Cheers Pete.
Logged

EmbeddedAT .. From Concept to Prototype to Production

Electronics and firmware design and project mentoring

Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Guys, really, really thx on advices, i am probably describing the task incorrectly.

- NMEA - is the protocol for GPS(NMEA 108 to be exact).
- 10HZ is a must, as the more accurate, the better

10HZ NMEA cannot fit into 9600. That's 100% sure ), although calculating required bandwidth of the NMEA0183 is a bit tricky. And some sort of NMEA parser is needed to discard every 5th NMEA sentence.

The application is RC plane OSD and telemetry. It's really weird using 2-3-4 GPS recievers, instead of just one, but with a splitter, that can split the protocol to the required baudrate(requirment of the end device) and the update rate(also a requirment of the end device)
Logged

nr Bundaberg, Australia
Offline Offline
Tesla Member
***
Karma: 121
Posts: 8443
Scattered showers my arse -- Noah, 2348BC.
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

The longest example of an NMEA0183 sentence I can find is 72 bytes, at 10 transmissions a second that's 720 bytes per second and at 9600bps you can transmit 960 bytes per second.

So on those numbers it should work even with processing overhead.

However we still don't know how long your sentences are and that's the main issue.

______
Rob
Logged

Rob Gray aka the GRAYnomad www.robgray.com

Belgium
Offline Offline
Edison Member
*
Karma: 58
Posts: 1731
Arduino rocks; but with my plugin it can fly rocking the world ;-)
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

My GPS module is setup so it send only 1 message a second
As many people asked before: what are you trying to do?
Best regards
Jantje
Logged

Do not PM me a question unless you are prepared to pay for consultancy.
Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -

Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I've already explained. I'm trying to get my OSD, my Flight controller, my telemetry to get to work with one GPS.

When using MTK utility for setting the GPS, it gives an overhead in procentage, when you set the baud rate. And it doesent allow to set any update rates higher than 2HZ for 9600baud... I'am not sure that the sentence is 72bytes, i do believe it's much, much larger.
Logged

Belgium
Offline Offline
Edison Member
*
Karma: 58
Posts: 1731
Arduino rocks; but with my plugin it can fly rocking the world ;-)
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

olaf
You will probably need to filter your GPS input. You do this by sending messages to your GPS module. This way you reduce the input on your arduino.
For my gps module the code looks like this
Code:
// what to log
#define LOG_RMC 1 // RMC-Recommended Minimum Specific GNSS Data, message 103,04
#define LOG_GGA 0 // GGA-Global Positioning System Fixed Data, message 103,00
#define LOG_GLL 0 // GLL-Geographic Position-Latitude/Longitude, message 103,01
#define LOG_GSA 0 // GSA-GNSS DOP and Active Satellites, message 103,02
#define LOG_GSV 0 // GSV-GNSS Satellites in View, message 103,03
#define LOG_VTG 0 // VTG-Course Over Ground and Ground Speed, message 103,05
void GPSModule::setup()
{
bufferidx = 0;
WDTCSR |= (1 << WDCE) | (1 << WDE);
WDTCSR = 0;

// connect to the GPS at the desired rate
(*m_gpsSerial).begin(m_gpsRate);
pinMode(m_powerPin, OUTPUT);
digitalWrite(m_powerPin, LOW);
//delay(250);
(*m_gpsSerial).print(SERIAL_SET);
delay(250);

#if (LOG_DDM == 1)
(*m_gpsSerial).print(DDM_ON);
#else
(*m_gpsSerial).print(DDM_OFF);
#endif
delay(250);
#if (LOG_GGA == 1)
(*m_gpsSerial).print(GGA_ON);
#else
(*m_gpsSerial).print(GGA_OFF);
#endif
delay(250);
#if (LOG_GLL == 1)
(*m_gpsSerial).print(GLL_ON);
#else
(*m_gpsSerial).print(GLL_OFF);
#endif
delay(250);
#if (LOG_GSA == 1)
(*m_gpsSerial).print(GSA_ON);
#else
(*m_gpsSerial).print(GSA_OFF);
#endif
delay(250);
#if (LOG_GSV == 1)
(*m_gpsSerial).print(GSV_ON);
#else
(*m_gpsSerial).print(GSV_OFF);
#endif
delay(250);
#if (LOG_RMC == 1)
(*m_gpsSerial).print(RMC_ON);
#else
(*m_gpsSerial).print(RMC_OFF);
#endif
delay(250);

#if (LOG_VTG == 1)
(*m_gpsSerial).print(VTG_ON);
#else
(*m_gpsSerial).print(VTG_OFF);
#endif
delay(250);

#if (USE_WAAS == 1)
(*m_gpsSerial).print(WAAS_ON);
#else
(*m_gpsSerial).print(WAAS_OFF);
#endif
}
I'm using a buffer of 90 characters for the RMC mesage

Best regards
Jantje
Logged

Do not PM me a question unless you are prepared to pay for consultancy.
Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -

Pages: [1] 2   Go Up
Jump to: