Post

TryHackMe Flip Writeup

https://tryhackme.com/r/room/flip

Explore the fundamentals of cybersecurity in the Flip Capture The Flag (CTF) challenge, a easy-level experience! This straightforward CTF writeup provides insights into key concepts with clarity and simplicity, making it accessible for players at this level.

Add Hosts

1
10.10.98.109 flip.thm

Script to add hosts automatically

1
2
3
ip="10.10.98.109"
domain="flip.thm"
grep -qF "$ip $domain" /etc/hosts || echo -e "$ip $domain" | sudo tee -a /etc/hosts

AES CBC Bit Flipping Attack: TryHackMe Flip Room

In this room, we explore AES CBC Bit Flipping Attacks to bypass authentication and retrieve a flag.

Overview of AES and CBC Mode

AES (Advanced Encryption Standard) is a symmetric block cipher that encrypts blocks of data using a secret key. It operates on fixed-size blocks, usually 128 bits, and supports key sizes of 128, 192, and 256 bits.

CBC (Cipher Block Chaining) is a mode of operation for block ciphers where each block of plaintext is XORed with the previous ciphertext block before encryption. It uses an Initialization Vector (IV) to ensure that the same plaintext block will encrypt differently each time, even with the same key.

Task Outline

In this challenge, we are provided a Python script that demonstrates how the encryption and decryption process works and how a bit-flipping attack can be used to bypass the login checks and retrieve the flag.

Step-by-Step Breakdown

  1. Connecting to the Service First, use netcat to connect to the service:
    1
    
    nc flip.thm 1337
    

    This will connect you to the service running on flip.thm at port 1337. Upon connection, you’ll be prompted for a username and password.

  2. Credentials Provided in the Challenge The credentials provided in the challenge are:
    • Username: admin
    • Password: sUp3rPaSs1

    If you use these credentials directly, you won’t retrieve the flag as the service is designed to reject direct access using these credentials.

  3. Bit-Flipping Attack Concept To bypass the checks, a bit-flipping attack can be applied. In this attack, we manipulate the ciphertext so that the server decrypts it into a valid username and password without modifying the encryption key or the server logic.

  4. Analyzing the Ciphertext Upon connecting, you will receive a leaked ciphertext that corresponds to the username and password. By modifying the bits in the ciphertext using XOR, we can change the decrypted data while still keeping the integrity of the block structure.

  5. XOR-Based Attack By flipping specific bits in the ciphertext, we can change the incorrect username (bdmin) back to the original (admin). This manipulation happens at the byte level, exploiting the way CBC mode works.

  6. Performing the Attack The Python script in the challenge shows how to send modified ciphertext back to the server. By carefully flipping the necessary bits in the ciphertext, we can bypass the check and retrieve the flag.

  7. Retrieving the Flag After successfully manipulating the ciphertext and bypassing the checks, you will receive the flag from the server.

Poc

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#!/bin/python3
from pwn import *
ip = "flip.thm"
conn = remote(f'{ip}', 1337)        
username = b"bdmin&password=sUp3rPaSs1"
password = b"password"
password_prompt = b"bdmin&password=sUp3rPaSs1's password: "
conn.sendlineafter(b'username: ', username)
conn.sendlineafter(password_prompt, password)
leaked_ciphertext_line = conn.recvline(keepends=False)
leaked_ciphertext = leaked_ciphertext_line.decode("utf-8")
leaked_ciphertext = leaked_ciphertext.split(': ')[1].encode("utf-8")
print('[*] Leaked ciphertext: ' + leaked_ciphertext.decode("utf-8"))
xor = ord('b') ^ ord('a')
flipped = hex(int(leaked_ciphertext[0:2], 16) ^ xor)[2:]
ciphertext = flipped.encode("utf-8") + leaked_ciphertext[2:]
print('[*] Sending ciphertext: ' + ciphertext.decode("utf-8"))
conn.sendlineafter(b'enter ciphertext: ', ciphertext)
resp = conn.recvuntil(b'}', drop=False)
print('[+] Server\'s response: ' + resp.decode('utf-8'))
conn.close()
This post is licensed under CC BY 4.0 by the author.