So I want to use an Arduino to process a serial data stream from a motorcycle's ECU (Suzuki SV650). The data stream is what the ECU sends to the dashboard. I already know that the stream looks like:
10 messages/second @ 30ms apart
each message is 8 bytes @ 10ms apart
I need to process the 8 bytes together (last byte is CRC) and do some quick parsing to illuminate an LED/7 segment display. No big deal.
So far the best idea I've come up with is using SoftwareSerial (I have an Uno and I want to use the USB serial for debugging) to read the bytes and just measure the time by calling micros() each time to measure the delta between bytes to figure out where I am. Seems kinda hackish, so I figured I'd ask here if there are better ways.
One thing I'd like to add in the future is to process a 2nd analog line and output on a 3rd analog line. Basically I want to fake the ECU into thinking that there still is an electric motor and it's position sensor are still attached. Not sure how quickly I need to respond to it's inputs to keep the ECU happy (technically there shouldn't be any lag, but I'm sure it would be OK with some), but 10-30ms might be too much???
I've heard about programming via interrupts before- maybe that would allow me to do both on the same Arduino elegantly? Not sure what kind of limitations that has?
Anyways, looking for advice on how to proceed and any links to things I should read about. Thanks!
Yeah, it's not LINBUS or CANBUS. It's single wire, uni-directional and point-to-point. The message format is very simple. First two bytes are water temp, followed by a bit mask for various error codes and the last byte is a simple CRC. Even the tachometer is on a separate line and is a different protocol.
So I did more reading on interrupts... sounds like they only work for digital pins, so probably not viable to deal with both inputs asynchronously. Guess the easiest thing is to just do something like this:
int last_ms = millis();
void loop() {
if (ecu.available()) {
ms = millis();
delta = ms - last_ms;
if (delta < 20) {
synfinatic:
Guess the easiest thing is to just do something like this:
As long as the rest of your sketch follows the same blink-without-delay / state machine pattern then, yes, that is most certainly the easiest thing to do.
I tried hooking it up to the ECU and no luck at all... doesn't see any packets at all. If I hook it up to another Arduino running the simulator code I saw on the SV forum, it sees data; but only if I change it to 9600 baud (the emulator is running at 7800?) Even then though, things are broken- seems like I'm missing occasional bytes on the wire and looks like the data is corrupted.
Not sure if this is a limitation of the SoftwareSerial library or if my code is subtly broken. I looked at the limitations about the library on it's web page, but since I'm using an Uno and only one pin for serial, it doesn't sound like either apply to me.
Anyways, hopefully the logic analyzer I ordered shows up tomorrow and I can see the ECU protocol for myself rather then relying on some descriptions by other people.
michinyon:
Can you have any speed you like with serial ? is 7800 a permissible number ?
Look at the documentation for Serial.begin(). You can specify any speed you like (within limits) and also have control over the other connection parameters. However, I seem to remember reading that the underlying hardware has some limitations on the supported line speed (for example, it can produce 9600 bps but might not be able to produce 9601 bps) so you may find that if you specify an arbitrary frequency it may produce something that is close, but not exactly what you requested. Give it a try - what do you have to lose?
Good news. Fully able to read the ECU data stream. Have to set the SoftwareSerial to 9600 baud (nothing else works at all), and I'm getting some odd timing errors, but I've been able to work around them so far and I'm so far able to parse the messages.
USPS wanted a signature for the logic analyzer and I was at work so didn't get it yet- so not able to compare the actual data stream to what the arduino is reading, but so far so good. Thanks!
synfinatic, how did you get on with this? I'm looking to decode the data from a GEN2 ECU to display on an OLED display, cna you share your latest code?