Chauvet Motionset hacking

Published: 2019

Note: This was originally posted as a Twitter thread. It can be read in full at https://threadreaderapp.com/thread/1099406624077332481.html.

I don’t get to talk about my work projects, so I’m gonna “live” tweet my weekend hacking project (Well, on breaks between cleaning).

I have a name-brand LED facade and backdrop for DJing that I want to put custom animations on.

This is not a supported feature.

Here we go.

The visuals you see projected on the wall are separate. That’s an example of the visuals we have going at #SecKC every month. I custom create each scene with Magic Music Visuals. mentions Oops, untagging after this. Sorry about that!

So anyway, after some quick searching, I found this:

https://www.eevblog.com/forum/microcontrollers/reverse-engineering-led-dat-file-communicating-with-stc-micro-controller/

One of the people in the thread provided some interesting quick analysis that gets me a little further ahead than where I was. The bitmap trick was a great trick to visualize the data. Gotta go vacuum the kitchen now. Then I’ll keep catching you up. After looking at the photos they provided, I decided to crack this one open to make sure we’re looking at the same thing. I also wanted to see if there was any obvious way to dump the firmware.

Well, we are looking at the same thing and I don’t see any obvious programming pins.

Images of the processor board

Moving on to nail down the data structure, there are a few details I know that the person doing the initial analysis didn’t:

  1. The DMX controller allows me to choose from 30 programs
  2. The backdrop is in fact 16x11 but there is also an optional facade that is 6x11

Doing a bit more digging I came up with:

  1. The bitmap image shows two obvious horizontal segments. Could this be backdrop and facade?
  2. There are appear to be 30ish vertical “scenes” in the bitmap which seems to correlate with 30 programs

Okay, time to clean the toilets (ahem, @mkr_ultra 😉), and then I’ll dig some more.

Okay, all of the bathroom surfaces can be eaten off of once again. Did I mention that I like the smell of chlorine bleach?

Anyway, back to the project.

So my next goal is to try to map what I’m seeing in the data to how the LEDs behave.

This is what Program 1 looks like. (Cloud is helping)

Video of program 1

And this is what Program 7 looks like.

Video of program 7

None of those bitmaps really look like either of these. So while it’s a cool data viz technique, I don’t think it’s going to give us what we want.

Time to start digging into the hexdump.

So given what we know... the frames seem to be 512 bytes... we can look at the nicely formatted hex by issuing this command:

xxd -p -c 512 LED.dat | vim -R -

Image of xxd output

And if you zoom waaaaaaay out, you can see those patterns emerge.

Image of zoomed out patterns

So what can we derive from this?

I didn't count the first scene because it looks like it might wrap from the bottom of the file.

But is the second "scene" seems to be defined between lines 134 and 268. The next scene seems to go to line 385. Then 497. They're not equal sized.

My two hypothesis at this point are:

  1. These "scenes" are not the actual "programs" at all (most likely)
  2. The programs can be variable-length

I wonder which it'll be!

But it's about time to start planning dinner, so we'll have to look at this more later.

So after digging into the data sheet for the main chip (STC 12C5A60S2), it turns out that those two traces that end in nothing on the board, are the programming pins.

Maybe I’ll poke at those tomorrow.

Image of datasheet and processor

So after a bit more research on this chip, it looks like there isn’t an easy way to dump the firmware.

Image of GitHub issue on processor

I’m not giving up on that avenue yet. But right now, I’m more interested in playing with bits and feeding them into the controller to see what happens.

Progress! I have my first confirmed control of pixels!

Image of pixel control

What we now know for certain:

  1. Each frame is, in fact, 512 bytes
  2. Each frame starts with a an 8-byte counter
  3. Then every 2 bytes controls a pixel
  4. Pixel order is in columns and starts closest to the cable
  5. The next column starts where the LED cable physically wraps around

Image of hexdump diff

What we now know for certain (cont):

  1. The drape is controlled by the bytes immediately following the 8 byte counter
  2. The facade is controlled starting at byte 368 and works the same way as the drape

Image of hexdump

And now we have colors! The colors seem to be standard 16-bit hex values.

I used this table: https://demmel.com/ilcd/help/16BitColorValues.htm

Image showing pixel color control

For anyone wondering about the toolset I used for this:

  1. To convert LED.dat to editable hex: xxd KEEP/LED.dat > LED.dat.hex.1
  2. To convert the edited hex back into binary: xxd -r LED.dat.hex.1 > LED.dat
  3. To verify conversion: vimdiff <(xxd KEEP/LED.dat) <(xxd LED.dat)

And now that I've figured out the data structure, I'm probably going to write a program that takes in ascii art and re-orders the bytes because this physical wrapping v.s. matrix position thing is making my head hurt.

And now, the entire reason I posted this was to show the process. For me, hacking is about learning how something works and then bending it to my will.

There were a number of times when I saw something that made me develop a hypothesis but I wouldn't let myself believe it until I could prove it.

Keep that in mind when you're attacking something. If you're guessing at what's happening while you're doing it, you're not done.

Oh, and by the way... I may have pulled this off during breaks while cleaning my house over the weekend, but I've failed the OSCP exam three times.

Don't let anything tell you you're not good enough.

Happy hacking!

My dot art sucks but you get the picture ;) Time to add some color!

Image showing "pwnd" written in ascii art

That’s better.

Image showing colorized "pwnd" written in ascii art