Glitching images with hex editors is fun. We touch a few bytes and the whole image gets screwed up.
But what if we don’t want to screw up the bitstream? I want the resulting bitstream to valid, and just tweak a few values.
I had an idea on how to do that, and I’ve spent a few hours this weekend working on a proof of concept for FFmpeg. The source code is available here:
https://github.com/ramiropolla/ffmpeg/tree/gbm
Basically it’s a three-step process. We first run FFmpeg and ask it to dump the value we’re interested in editing (only DC coefficients for jpeg images is currently implemented). We then tweak the values that were dumped in a text file. And then we re-run FFmpeg and specify the altered dump file as input for those specific values.
The code is a huge hack. I’ve modified the jpeg decoder to dump the DC coefficients on the first run. Then I’ve modified the bitstream reader to duplicate the data it’s reading as it goes along. When we get to the altered DC coefficients, the new values are read from the text file and written to the output bitstream.
$ ./configure --disable-everything --disable-external-libs --disable-doc --disable-programs --enable-ffmpeg --enable-decoder=mjpeg --enable-encoder=mjpeg --enable-encoder=mjpeg_glitch --enable-demuxer=image2 --enable-muxer=image2 $ make $ # generate DC coefficients file $ ./ffmpeg_g -i lena.jpg -f image2 -vcodec mjpeg_glitch -dump_mjpeg_dc dc_in.txt -y temp.jpg $ # now edit dc_in.txt (for example, using the python script provided with the source code) $ python glitch/reverse_dc.py dc_in.txt > dc_out.txt $ # rewrite the bitstream with the new DC coefficients $ ./ffmpeg_g -i lena.jpg -f image2 -vcodec mjpeg_glitch -read_mjpeg_dc dc_out.txt -y lena_out.jpg
Input:
Output: