Tags: misc scripting 

Rating: 5.0

I did some preliminary checks to find that there were only 3 "random values" that are selected. Once you have a sample of the 3, you can XOR them with a known plaintext to get the seeds. Then you can sample the next 3 "random values", XOR them with the seed, then get the 3 candidates for the next letter.

# Code
from pwn import *

octets = [0x77, 0x10, 0x2]

def sample(prefix):
found_octets = set()
while len(found_octets) < 3:
io = remote("challenges.ctfd.io", 30468)
io.sendlineafter("flag]>", prefix)
io.recvuntil('unknown IPv4 address I have...')
sample = io.recvline().strip()
assert b"0x" in sample
found_octets.add(int(sample, 16))

return found_octets

import sys
prefix = sys.argv[1]
o = sample(prefix)
o2 = [hex(_) for _ in o]
print("Octets", o2)
cset = set()
hset = set()
for i in o:
for j in octets:
ij = (i ^ j)


I'm using `pwntools` because it's easy to play with stdin and stdout with it.

The `octets` were discovered beacuse I knew the first several letters would be `flag{`. When I typed in `f`, it would give me one of these 3 outputs: `[0x1b, 0x7c, 0x6e]`.

XOR-ing them with the hex value of `l` gave me the seeds: `[0x77, 0x10, 0x2]`

The `sample()` function will query the server until it can gather 3 unique outputs.

Then it will print out `cset` ("character set") which contains all unique characters.

It's generally up to you to guess which one is next. I didn't automate this part.

# Flag