Reverse engineering UART protocol of XCM controllers

46eh01

100 µW
Joined
Oct 23, 2025
Messages
8
Location
Germany
Hi guys,

i'm trying to reverse engineer the UART protocol of an XCM-K based controller.
I have connected an Arduino to the Serial port between Display and Controller for sniffing the data.

Till now (just started about 20mins ago), this is the communication of the display to the controller from turning on and then turning off:

Code:
FF
01 03 F9 5B 03 1B 03 00 32 80 00 00 2E 38 1F
01 03 FA 58 03 1C 03 00 32 80 00 00 2E 38 18
01 03 FB 59 03 81 03 00 32 80 00 00 2E 38 85
01 03 FC 06 03 2A 03 00 32 80 00 00 2E 38 76
01 03 FD 07 03 7F 03 00 32 80 00 00 2E 38 23
01 03 FE 04 03 80 03 00 32 80 00 00 2E 38 DC
01 03 FF 05 03 05 03 00 32 80 00 00 2E 38 59
01 03 00 82 03 7E 03 00 32 80 00 00 2E 38 5A
01 03 01 03 03 03 03 00 32 80 00 00 2E 38 A7
01 03 02 80 03 04 03 00 32 80 00 00 2E 38 20
01 03 03 81 03 29 03 00 32 80 00 00 2E 38 0D
01 03 04 6E 03 32 03 00 32 80 00 00 2E 38 FE
01 03 05 6F 03 27 03 00 32 80 00 00 2E 38 EB
01 03 06 6C 03 28 03 00 32 80 00 00 2E 38 E4
01 03 07 6D 03 2D 03 00 32 80 00 00 2E 38 E1
01 03 08 0A 03 26 03 00 32 80 00 00 2E 38 82
01 03 09 0B 03 2B 03 00 32 80 00 00 2E 38 8F
01 03 0A 08 03 2C 03 00 32 80 00 00 2E 38 88
01 03 0B 09 03 51 03 00 32 80 00 00 2E 38 F5
01 03 0C 36 03 7A 03 00 32 80 00 00 2E 38 E6
01 03 0D 37 03 4F 03 00 32 80 00 00 2E 38 D3
01 03 0E 34 03 50 03 00 32 80 00 00 2E 38 CC
01 03 0F 35 03 55 03 00 32 88 00 00 2E 38 C1
01 03 10 32 03 4E 03 00 32 88 00 00 2E 38 C2
01 03 11 33 03 53 03 00 32 88 00 00 2E 38 DF
01 03 12 30 03 54 03 00 32 88 00 00 2E 38 D8
01 03 13 31 03 79 03 00 32 88 00 00 2E 38 F5
01 03 14 5E 03 82 03 00 32 88 00 00 2E 38 66
01 03 15 5F 03 77 03 00 32 80 00 00 2E 38 9B
01 03 16 5C 03 78 03 00 32 80 00 00 2E 38 94
01 03 17 5D 03 7D 03 00 32 80 00 00 2E 38 91
01 03 18 3A 03 76 03 00 32 80 00 00 2E 38 F2
01 03 19 3B 03 7B 03 00 32 80 00 00 2E 38 FF
01 03 1A 38 03 7C 03 00 32 80 00 00 2E 38 F8
01 03 1B 39 03 61 03 00 32 80 00 00 2E 38 E5
01 03 1C 66 03 0A 03 00 32 80 00 00 2E 38 D6
01 03 1D 67 03 5F 03 00 32 80 00 00 2E 38 83
01 03 1E 64 03 60 03 00 32 80 00 00 2E 38 BC
01 03 1F 65 03 65 03 00 32 80 00 00 2E 38 B9
01 03 20 62 03 5E 03 00 32 80 00 00 2E 38 BA
01 03 21 63 03 63 03 00 32 80 00 00 2E 38 87
01 03 22 60 03 64 03 00 32 80 00 00 2E 38 80
FC

I just turned the bike on, waited 1 second, turned the light on, waited 1 second, turned light off and after this, turned Bike off.

Not sure, why the first (and last) line is just 1 Byte, and why there is some missing from FF to F9.

B01 - Unknown (always 01)
B02 - Unknown (always 03)
B03 - Counter (FF-00, starts again fro FF, when 00 is reached)
B04 - Unknown (always changes)
B05 - Assist Level (see B07)
B06 - Unknown (always changes)
B07 - Assist Level (see B05)
B08 - Speed
B09 - Unknown (always 32)
B10 - Light (80=Off, 88 =On)
B11 - Unknown (always 00)
B12 - Unknown (always 00)
B13 - Unknown (always 2E)
B14 - Unknown (always 38)
B15 - Checksum (B1 XOR B2 XOR B3 ... XOR B14)

The UART connection is 1200bps, 8n1.

I will continuously update this post with new info's about this controller and its communication.

PS: English isn't my native language, so please forgive me spelling errors, etc.
 
Last edited:
I will continuously update this post
Do you have a link to this kind of displays? I wonder why you are putting effort in this stone age system. The most generic cheap controllers like Brainpower, Greentime etc. are using the well known No.2 protocol. The protocol has nothing to do with the processor like the title of this thread might imply.
 
No news anymore - the other Bytes never change under any condition.
I also recorded all frames from a 2 hour driving - no changes.

So nothing more to do here, sadly.
 
Hi guys,

i'm trying to reverse engineer the UART protocol of an XCM-K based controller.
I have connected an Arduino to the Serial port between Display and Controller for sniffing the data.

Till now (just started about 20mins ago), this is the communication of the display to the controller from turning on and then turning off:

Code:
FF
01 03 F9 5B 03 1B 03 00 32 80 00 00 2E 38 1F
01 03 FA 58 03 1C 03 00 32 80 00 00 2E 38 18
01 03 FB 59 03 81 03 00 32 80 00 00 2E 38 85
01 03 FC 06 03 2A 03 00 32 80 00 00 2E 38 76
01 03 FD 07 03 7F 03 00 32 80 00 00 2E 38 23
01 03 FE 04 03 80 03 00 32 80 00 00 2E 38 DC
01 03 FF 05 03 05 03 00 32 80 00 00 2E 38 59
01 03 00 82 03 7E 03 00 32 80 00 00 2E 38 5A
01 03 01 03 03 03 03 00 32 80 00 00 2E 38 A7
01 03 02 80 03 04 03 00 32 80 00 00 2E 38 20
01 03 03 81 03 29 03 00 32 80 00 00 2E 38 0D
01 03 04 6E 03 32 03 00 32 80 00 00 2E 38 FE
01 03 05 6F 03 27 03 00 32 80 00 00 2E 38 EB
01 03 06 6C 03 28 03 00 32 80 00 00 2E 38 E4
01 03 07 6D 03 2D 03 00 32 80 00 00 2E 38 E1
01 03 08 0A 03 26 03 00 32 80 00 00 2E 38 82
01 03 09 0B 03 2B 03 00 32 80 00 00 2E 38 8F
01 03 0A 08 03 2C 03 00 32 80 00 00 2E 38 88
01 03 0B 09 03 51 03 00 32 80 00 00 2E 38 F5
01 03 0C 36 03 7A 03 00 32 80 00 00 2E 38 E6
01 03 0D 37 03 4F 03 00 32 80 00 00 2E 38 D3
01 03 0E 34 03 50 03 00 32 80 00 00 2E 38 CC
01 03 0F 35 03 55 03 00 32 88 00 00 2E 38 C1
01 03 10 32 03 4E 03 00 32 88 00 00 2E 38 C2
01 03 11 33 03 53 03 00 32 88 00 00 2E 38 DF
01 03 12 30 03 54 03 00 32 88 00 00 2E 38 D8
01 03 13 31 03 79 03 00 32 88 00 00 2E 38 F5
01 03 14 5E 03 82 03 00 32 88 00 00 2E 38 66
01 03 15 5F 03 77 03 00 32 80 00 00 2E 38 9B
01 03 16 5C 03 78 03 00 32 80 00 00 2E 38 94
01 03 17 5D 03 7D 03 00 32 80 00 00 2E 38 91
01 03 18 3A 03 76 03 00 32 80 00 00 2E 38 F2
01 03 19 3B 03 7B 03 00 32 80 00 00 2E 38 FF
01 03 1A 38 03 7C 03 00 32 80 00 00 2E 38 F8
01 03 1B 39 03 61 03 00 32 80 00 00 2E 38 E5
01 03 1C 66 03 0A 03 00 32 80 00 00 2E 38 D6
01 03 1D 67 03 5F 03 00 32 80 00 00 2E 38 83
01 03 1E 64 03 60 03 00 32 80 00 00 2E 38 BC
01 03 1F 65 03 65 03 00 32 80 00 00 2E 38 B9
01 03 20 62 03 5E 03 00 32 80 00 00 2E 38 BA
01 03 21 63 03 63 03 00 32 80 00 00 2E 38 87
01 03 22 60 03 64 03 00 32 80 00 00 2E 38 80
FC

I just turned the bike on, waited 1 second, turned the light on, waited 1 second, turned light off and after this, turned Bike off.

Not sure, why the first (and last) line is just 1 Byte, and why there is some missing from FF to F9.

B01 - Unknown (always 01)
B02 - Unknown (always 03)
B03 - Counter (FF-00, starts again fro FF, when 00 is reached)
B04 - Unknown (always changes)
B05 - Assist Level (see B07)
B06 - Unknown (always changes)
B07 - Assist Level (see B05)
B08 - Speed
B09 - Unknown (always 32)
B10 - Light (80=Off, 88 =On)
B11 - Unknown (always 00)
B12 - Unknown (always 00)
B13 - Unknown (always 2E)
B14 - Unknown (always 38)
B15 - Checksum (B1 XOR B2 XOR B3 ... XOR B14)

The UART connection is 1200bps, 8n1.

I will continuously update this post with new info's about this controller and its communication.

PS: English isn't my native language, so please forgive me spelling errors, etc.
I like this topic.

I am also performing data reverse engineering on a few E-bike display panels that operate at 1200 BPS. It's slightly strange that my setup detects it at 1202 BPS.
  • The data type is 8 data bits with 1 stop bit.
  • B1 and B2 are the header, functioning as markers to indicate that the data read has begun.
  • The various unknowns that don't change are likely markers for data boundaries/limits.
  • The checksum at the end is for verifying the data's validity level.
  • B06 is likely some kind of Millis (milliseconds), transfer counter, or something similar.
I attach the logic analyzer screeshot.
 

Attachments

  • ebike panel.jpg
    ebike panel.jpg
    250.9 KB · Views: 6
B01 - Unknown (always 01)
B02 - Unknown (always 03)
B03 - Counter (FF-00, starts again fro FF, when 00 is reached)
B04 - Unknown (always changes)
B05 - Assist Level (see B07)
B06 - Unknown (always changes)
B07 - Assist Level (see B05)
B08 - Speed
B09 - Unknown (always 32)
B10 - Light (80=Off, 88 =On)
B11 - Unknown (always 00)
B12 - Unknown (always 00)
B13 - Unknown (always 2E)
B14 - Unknown (always 38)
B15 - Checksum (B1 XOR B2 XOR B3 ... XOR B14)
Hi, it would be correct to start the numbering from zero. Okay, in your system. For a similar protocol:

B06 - encoded assist level (the key and counter B03 are used).
B07 - bit 3 - soft start, bit 2 - cruize, bit 0 - mil/km
B12 - recovery
 
Back
Top