Skip to content

Instantly share code, notes, and snippets.

@gbroiles
Last active June 16, 2020 21:35
Show Gist options
  • Save gbroiles/280942ea27d64f73e71f1902651e9805 to your computer and use it in GitHub Desktop.
Save gbroiles/280942ea27d64f73e71f1902651e9805 to your computer and use it in GitHub Desktop.
CTF_NAHAMCON_Rotten

Written quickly to solve a puzzle in a CTF.

Another competitor came up with a much nicer way to display the output as it was revealed - it wasn't immediately obvious to me how long the flag was going to be, but it looked like it'd be 30-40 characters, so I figured that collecting 200 characters should get me what I needed without grinding on the server unnecessarily. It worked, in a not very elegant sort of way.

Note that I ended up not using the rot() function at all, rot_alpha() ended up doing all of the work. I don't remember why I started going one direction then went the other, it just turned out that way.

In retrospect I'm not sure why I thought it was better to create all 26 possible rot() variations then search them, instead of generating and checking one at a time. Another "it made sense at the time" thing.

import socket
import sys
import time
import re
import pprint
BUFFER = 4096
SLEEP = 0.5
def rot(s, n):
chars = "abcdefghijklmnopqrstuvwxyz"
trans = chars[n:] + chars[:n]
rot_char = lambda c: trans[chars.find(c)] if chars.find(c) > -1 else c
return "".join(rot_char(c) for c in s)
def rot_alpha(n):
from string import ascii_lowercase as lc, ascii_uppercase as uc
lookup = str.maketrans(lc + uc, lc[n:] + lc[:n] + uc[n:] + uc[:n])
return lambda s: s.translate(lookup)
def decoder(text):
ciphertext = text
shift = 0
ciphertext = ciphertext.decode("utf-8")
ciphertext = ciphertext.strip()
decodes = []
for i in range(27):
decodes.append(rot_alpha(i)(ciphertext))
for i in decodes:
if "send back" in i:
# print(i)
return i
print("ROT failed!")
for i in decodes:
print("[{}] {}".format(i, decodes[i]))
sys.exit(0)
key = {}
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server_address = ("jh2i.com", 50034)
print("connecting to {}".format(server_address))
sock.connect(server_address)
sock.settimeout(60)
line = sock.recv(BUFFER)
print("Received first line: {}".format(line))
sock.sendall(line)
print("Sent it back, entering big loop.")
iterations = 0
while True:
line = sock.recv(BUFFER)
# print("Received line: {}".format(line))
solution = decoder(line)
helpful = re.search("character", solution)
if helpful:
iterations += 1
position = solution[helpful.end() : -3]
# print("Position is: {}".format(position))
words = position.split(" ")
# print("Words is: {}".format(words))
finalposition = str(words[1].strip())
# print("Finalposition is: {}".format(finalposition))
key[finalposition] = solution[-2:-1]
# pprint.pprint(key)
if iterations % 10 == 0:
print(iterations)
sock.sendall(solution.encode("utf-8"))
if iterations == 200:
for i in range(len(key)):
print("{}".format(key[str(i)]), end="")
print()
sys.exit(0)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment