Maker Pro
Maker Pro

Decoding Chinese UART Protocol

Rohan_Jadhav

Apr 6, 2023
5
Joined
Apr 6, 2023
Messages
5
Hello Everyone, I am currently working on a EV project which has a Chinese UART based Protocol. which is used to transmit various data like speed, RPM, Errors etc to display. So my aim is to decode this data, but i am unable to decode that protocol i have tried reading data from uart but garbage values are coming.... how to read this data?......
 

Attachments

  • 1.png
    1.png
    96.2 KB · Views: 11

danadak

Feb 19, 2021
751
Joined
Feb 19, 2021
Messages
751
If you have a scope with UART decode capability you can typically look
at the stream as ASCII or binary, and capture it for further examination.


Typically data like that has a frame sequence of some sort that essentially
allows receive end to complete the protocol.


Regards, Dana.
 

Rohan_Jadhav

Apr 6, 2023
5
Joined
Apr 6, 2023
Messages
5
If you have a scope with UART decode capability you can typically look
at the stream as ASCII or binary, and capture it for further examination.


Typically data like that has a frame sequence of some sort that essentially
allows receive end to complete the protocol.


Regards, Dana.
Thanks @Dandak

But its not a regular UART as u can see that we have low and High sequence for logic 1 as well as 0. So we cant read it directly. I tried reading it serially but no data... also tried measuring peaks but again lots of rubbish data....
 

Harald Kapp

Moderator
Moderator
Nov 17, 2011
13,700
Joined
Nov 17, 2011
Messages
13,700
its not a regular UART
This is not only not a regular UART, this is not a UART at all. Looks more like the protocol for WS2812B LEDs. Or something similar. Note that in your diagram the first bit is to the right, meaning it starts with a short high pulse followed by a long low puls (equiv. to a logic low for a WS2812B).
1680800435645.png
To read this data you will have to write your own code and it needs to be fast. I did a quick check by big G... but could not find code for this purpose. At least consensus seems to be that an Arduino UNO is not fast enough :(
Possibly a Raspberry Pi Pico with suitably programmed state machine for one of the GPIOs? But don't ask me how to do it.
 

Rohan_Jadhav

Apr 6, 2023
5
Joined
Apr 6, 2023
Messages
5
th
This is not only not a regular UART, this is not a UART at all. Looks more like the protocol for WS2812B LEDs. Or something similar. Note that in your diagram the first bit is to the right, meaning it starts with a short high pulse followed by a long low puls (equiv. to a logic low for a WS2812B).
View attachment 58649
To read this data you will have to write your own code and it needs to be fast. I did a quick check by big G... but could not find code for this purpose. At least consensus seems to be that an Arduino UNO is not fast enough :(
Possibly a Raspberry Pi Pico with suitably programmed state machine for one of the GPIOs? But don't ask me how to do it.
Thanks for suggestion

i have used following code


[Mod edit: put code into code box for better readability]

C:
int pin = 7;
unsigned long duration_H = 0;
unsigned long duration_L = 0;

void setup() {
Serial.begin(9600);
pinMode(pin, INPUT);
}

void loop() {
duration_H = pulseIn(pin, HIGH);
duration_L = pulseIn(pin, LOW);
if (1500 <= duration_H && duration_H <= 2000) {
Serial.print("1");
} else if (1500 <= duration_L && duration_L <= 2000) {
Serial.print("0");
} else if (3200<=duration_L) {
Serial.println("NEXT DATA");
}
}



here are some results but these are not correct yet need to improve accuracy
 
Last edited by a moderator:

Harald Kapp

Moderator
Moderator
Nov 17, 2011
13,700
Joined
Nov 17, 2011
Messages
13,700
here are some results but these are not correct yet need to improve accuracy
No results shown ?

Looks like Arduino code, is it?
This code is way too slow.

I take it these two lines are supposed to return the length of the first High pulse and the following Low pulse.
C:
duration_H = pulseIn(pin, HIGH);
duration_L = pulseIn(pin, LOW);

But what actually happens is:
  1. The first line waits for pin 7 to become high, then starts a timer and waits for pin 7 to become low again and stops the timer. The time indicated by the timer is the duration of the High pulse (label 1 in the diagram).
  2. But the next line will not do what you expect:
    From your code I take it you want to measure the duration of the Low pulse immediately following the High pulse (label 3 in the diagram). But when you look at the documentation of the PulseIn() routine, you will find that it waits for the pin to go from High to Low and then starts the timer. However, the pin is already Low (label 3 in the diagram) - that was the condition for the first line to terminate and return the High duration. Therefore the second line will wait for the next High -> Low transition (label 2 in the diagram) and will return the duration of the 2nd Low pulse after the first High pulse.
1681232739828.png
Apart from that the Serial.print() statements take up way too much time to prepare the loop for the next pulse.
 

Harald Kapp

Moderator
Moderator
Nov 17, 2011
13,700
Joined
Nov 17, 2011
Messages
13,700
Without going into the details of coding: You don't have to measure both LOW and HIGH period. The duration of a bit is constant, What varies is the ducty cycle, the ratio of HIGH to LOW wthin a bit. Therefore it suffices to measure thelength of the HIGH signal using e.g.
C:
duration_H = pulseIn(pin, HIGH);
If the duration is short, the bit is 0. If the duration is long, the bit is 1.
 

Sunnysky

Jul 15, 2016
541
Joined
Jul 15, 2016
Messages
541
This isn't Chinese , rather it looks more like RZ delay modulation or Manchester or Bi-phase encoding of clock and data. There are 3 methods. Mark, Level and space.
First identify the baseband code, then if async or sync type, and then byte format, length, endian order, then parity, checksums, CRC ECC might not be included.
Second change known control methods with result data to correlate functions with the expected output.
Third search for obvious answers on the web with clues.
A Baseband decoder is necessary before feeding UARTs if in fact it is async. it could be burst addressable packets.
 
Last edited:

Rohan_Jadhav

Apr 6, 2023
5
Joined
Apr 6, 2023
Messages
5
Without going into the details of coding: You don't have to measure both LOW and HIGH period. The duration of a bit is constant, What varies is the ducty cycle, the ratio of HIGH to LOW wthin a bit. Therefore it suffices to measure thelength of the HIGH signal using e.g.
C:
duration_H = pulseIn(pin, HIGH);
If the duration is short, the bit is 0. If the duration is long, the bit is 1.
Thanks for suggestion let me try tomorrow and update you....
 

Rohan_Jadhav

Apr 6, 2023
5
Joined
Apr 6, 2023
Messages
5
Thank you @Sunnysky It is a Chinese EV controller with display and all chips are Chinese SC92F7323 microcontroller is used. I have manually decoded data by using DSO it is using little ending order with 96 bits excluding start bit.
 
Top