In Python, using 3rd party Pillow module (pip install pillow) for processing images:
from PIL import Image
import math
def extract_lsbs(data):
'''Extract LSBs from RGB data as a string of 1s and 0s.
'''
s = []
for r,g,b in data:
s.extend([str(r & 1), str(g & 1), str(b & 1)])
return ''.join(s)
def decode00(bits):
'''Decode Header: [0, 0]
Next 16-bits: message length in bits
Followed by the message itself, ASCII characters encoded by groups of 8bit, most-significant bit (MSB) first
Return the decoded string
'''
LENGTH_START = 2
DATA_START = 18
if bits[:LENGTH_START] != '00':
raise ValueError('incorrect header')
length = int(bits[LENGTH_START:18], 2)
if length % 8 != 0: # Assume message length is a multiple of 8 bits given description.
raise ValueError('length not multiple of 8 bits')
reqlen = DATA_START + length
if reqlen > len(bits): # Sanity check
raise ValueError('length exceeds data')
databits = bits[DATA_START:reqlen]
return int(databits, 2).to_bytes(length // 8).decode()
def decode10(bits):
'''Decode Header: [1, 0]
Next 16 bits: image width in pixels
Next 16 bits: image height in pixels
Raw pixels of the binary image
Return the decoded image.
'''
WIDTH_START = 2
HEIGHT_START = 18
DATA_START = 34
if bits[:WIDTH_START] != '10':
raise ValueError('incorrect header')
width = int(bits[WIDTH_START:HEIGHT_START], 2)
height = int(bits[HEIGHT_START:DATA_START], 2)
reqlen = DATA_START + width * height
if reqlen > len(bits):
raise ValueError('length exceeds data')
databits = bits[DATA_START:reqlen]
# Collect row data
pad = 8 - width % 8 # Image requires row data to be multiple of 8 bits.
rowbytes = math.ceil(width / 8) # Number of bytes needed for a row
imdata = bytearray()
for row in range(height):
rowbits = databits[row * width:(row + 1) * width] + '0' * pad
imdata.extend(int(rowbits, 2).to_bytes(length=rowbytes))
return Image.frombytes('1', (width, height), imdata)
for filename in ('black.png', 'contrast.png', 'flower.png', 'cat.png'):
im = Image.open(filename)
data = im.get_flattened_data()
print(decode00(extract_lsbs(data)))
im = Image.open('butterfly.png')
data = im.get_flattened_data()
im2 = decode10(extract_lsbs(data))
im2.show()
Output:
Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test
Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test
Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test Test
The first part of the sentence is "Three may keep a secret, ...".
### Task 2: Decode a binary image
A binary image is hidden in the least significant bits of the butterfly image, the encoding scheme is:
- Simple LSB Encoding**
- Header: `[1, 0]`
- Next 16 bits: image `width` in pixels
- Next 16 bits: image `height` in pixels
- Raw pixels of the binary image
Hint: Create and fill an image array of the derived `width` and `height` with the encoded hidden pixels.
In order to view your image in classic viewers, it might be helpful to map 0 -> 0 and 1 -> 255.
Derive the second part of the sentence and answer the question about the image.
The final image is of Ben Franklin flying a kite and reaching to touch a key.
The first image has the text "Three may keep a secret, ...", and the second:
... if two of them are dead.
Benjamin Franklin