Published on

BlueHensCTF 2023 - Least Significant Color

Authors

Least Significant Color

Delving into the depths of the least significant bits of an image to uncover concealed data.

Table of Contents

Introduction

This challenge prompted participants to extract concealed information from an image. The task involved a blend of forensic analysis, image analysis, and steganographic techniques.

Initial Observations

Upon receiving the challenge, the provided image "encoded.png" was displayed to discern any visible hint or anomaly. At a cursory glance, nothing out of the ordinary was observed.

Image file

Deciphering The Hint

The challenge's title, "Least Significant Color", provided an essential hint. This suggested that the image might hide its data within the Least Significant Bits (LSBs) of its color channels, a common steganographic technique. Additionally, the reference to the colors red and green indicated a potential operation involving these color channels.

Technical Exploration

The approach was centered on analyzing the LSBs of the image's color channels. By delving into the depths of the red and green channels, and with the hint suggesting an XOR operation, a solution began to take shape.

Script Explanation

from PIL import Image
import numpy as np

def extract_udctf_from_lsb(image_path):
    # Open the image
    img = Image.open(image_path)

    # Convert the image to an RGB array
    img_array = np.array(img)

    # Extract the LSBs of the red and green channels
    red_lsb = img_array[:,:,0] & 1
    green_lsb = img_array[:,:,1] & 1

    # Perform an XOR operation between the LSBs of the two channels
    xor_result = np.bitwise_xor(red_lsb, green_lsb)

    # Convert the result into a binary sequence
    binary_sequence = ''.join(map(str, xor_result.ravel()))

    # Split the sequence into byte-sized chunks
    byte_chunks = [binary_sequence[i:i+8] for i in range(0, len(binary_sequence), 8)]

    # Convert each chunk to its ASCII representation
    decoded_text = ''.join([chr(int(byte, 2)) for byte in byte_chunks if len(byte) == 8 and 0 <= int(byte, 2) <= 127])

    # Search for the string containing "UDCTF"
    udctf_string = next((s for s in decoded_text.split() if "UDCTF" in s), None)
    return udctf_string

# Using the function to extract the UDCTF string
udctf_data = extract_udctf_from_lsb("encoded.png")
print(udctf_data)

Using the script, we successfully extracted the string containing "UDCTF".

Conclusion

By utilizing forensic analysis and steganographic techniques, we were able to uncover the hidden message in the image, leading to the flag.

Flag : UDCTF{y0u_R_1mag3_wizZarD}