Skip to content

Commit

Permalink
spoof
Browse files Browse the repository at this point in the history
  • Loading branch information
zardus committed Feb 24, 2025
1 parent 0961aad commit 983d458
Show file tree
Hide file tree
Showing 4 changed files with 62 additions and 0 deletions.
2 changes: 2 additions & 0 deletions intercepting-communication/module.yml
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@ challenges:
name: UDP Spoofing 1
- id: udp-spoof-host-2
name: UDP Spoofing 2
- id: udp-spoof-host-3
name: UDP Spoofing 3
- id: level-12
name: ARP
- id: level-13
Expand Down
1 change: 1 addition & 0 deletions intercepting-communication/udp-spoof-host-3/.init
13 changes: 13 additions & 0 deletions intercepting-communication/udp-spoof-host-3/DESCRIPTION.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
Of course, the previous spoofing worked because you know the source port that the client was using, and were thus able to forge the server's response.
This was, in fact, at the core of a [very famous vulnerability](https://citeseerx.ist.psu.edu/document?repid=rep1&type=pdf&doi=0c1e863b6698808b724def8793d7cba023494808) in the [Domain Name System](https://en.wikipedia.org/wiki/Domain_Name_System) that facilitates the translation of host names like `https://pwn.college` to the appropriate IP addresses.
The vulnerability allowed attackers to forge responses from DNS servers and redirect victims to IP addresses of their choice!

The fix for that vulnerability was to randomize the source port that DNS requests go out from.
Likewise, this challenge no longer binds the source port to 31338.
Can you still force the response?

----

**HINT:**
The source port is only set once per socket, whether at bind time or at the first `sendto`.
What do you do when there's a fixed number that you don't know?
46 changes: 46 additions & 0 deletions intercepting-communication/udp-spoof-host-3/run
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
#!/usr/bin/exec-suid --real -- /usr/bin/python -I

import psutil
import socket
import time
import os

from dojjail import Host, Network

flag = open("/flag").read()
parent_process = psutil.Process(os.getppid())

class ServerHost(Host):
def entrypoint(self):
server_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
server_socket.bind(("0.0.0.0", 31337))
while True:
try:
client_message, (client_host, client_port) = server_socket.recvfrom(1024)
if client_message.strip() == b"ACTION?":
server_socket.sendto(b"NONE", (client_host, client_port))
except ConnectionError:
continue

class ClientHost(Host):
def entrypoint(self):
client_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
while True:
try:
client_socket.sendto(b"ACTION?", ("10.0.0.3", 31337))
message, (peer_host, peer_port) = client_socket.recvfrom(1024)
if peer_port == 31337 and message.startswith(b"FLAG"):
_, flag_host, flag_port = message.strip().split(b":")
client_socket.sendto(flag.encode(), (flag_host, int(flag_port)))

time.sleep(1)
except (ConnectionError, ValueError):
continue

user_host = Host("ip-10-0-0-1", privileged_uid=parent_process.uids().effective)
client_host = ClientHost("ip-10-0-0-2")
server_host = ServerHost("ip-10-0-0-3")
network = Network(hosts={user_host: "10.0.0.1", client_host: "10.0.0.2", server_host: "10.0.0.3"}, subnet="10.0.0.0/24")
network.run()

user_host.interactive(environ=parent_process.environ())

0 comments on commit 983d458

Please sign in to comment.