diff --git a/receiver/challenges/Carbeat.py b/receiver/challenges/Carbeat.py new file mode 100644 index 0000000..54023f6 --- /dev/null +++ b/receiver/challenges/Carbeat.py @@ -0,0 +1,157 @@ +from .Challenge import Challenge + +import subprocess +import time +import re +import os + +class Carbeat(Challenge): + flag_location = 'flags/carbeat.txt' + history_location = 'history/carbeat.txt' + + _CONTAINER = "carbeat_container" + _SERVICE_CMD = ["docker", "exec", "-i", _CONTAINER, "/home/ctf/chall/mybini"] + _HEX_RE = re.compile(r'^[0-9a-fA-F]+$') + + def _read_container_flag(self) -> str: + out = subprocess.run(["docker", "exec", self._CONTAINER, "cat", "/flag.txt"], + capture_output=True, text=True) + if out.returncode != 0 or not out.stdout.strip(): + raise FileNotFoundError("Flag not found in container (/flag.txt)") + return out.stdout.strip() + + def _spawn(self): + return subprocess.Popen( + self._SERVICE_CMD, + stdin=subprocess.PIPE, + stdout=subprocess.PIPE, + stderr=subprocess.STDOUT, + text=True, + bufsize=0, + ) + + def _read_until(self, proc, token, timeout=5.0, max_bytes=1_000_000): + start = time.time() + buf = [] + r = proc.stdout.read + while True: + if time.time() - start > timeout: + tail = ''.join(buf)[-500:] + raise TimeoutError(f"Timeout waiting for '{token}'. Got so far:\n{tail}") + ch = r(1) + if ch == "" and proc.poll() is not None: + raise RuntimeError(f"Process ended while waiting for '{token}'. Output:\n{''.join(buf)}") + buf.append(ch) + if len(buf) > max_bytes: + raise RuntimeError("Exceeded max read size") + if token in "".join(buf): + return "".join(buf) + + def _send_line(self, proc, s: str): + proc.stdin.write(s + "\n") + proc.stdin.flush() + + def _expect_hex_field(self, text: str, label: str) -> str: + m = re.search(rf"{re.escape(label)}\s*:\s*([0-9a-fA-F]+)", text) + assert m, f"Missing '{label}' in output. Tail:\n{text[-400:]}" + hx = m.group(1) + assert self._HEX_RE.match(hx), f"{label} is not hex" + return hx + + def distribute(self, flag): + try: + os.makedirs(os.path.dirname(self.flag_location), exist_ok=True) + with open(self.flag_location, 'w') as f: + f.write(flag) + + os.makedirs(os.path.dirname(self.history_location), exist_ok=True) + with open(self.history_location, 'a') as f: + f.write(flag + '\n') + + self.logger.info(f'Flag {flag} written to {self.flag_location}') + return True + except Exception as e: + self.logger.error(f'Could not write flag to {self.flag_location}: {e}') + return False + + + def register(self, proc, name, level, timeout=1.): + self._read_until(proc, "> ", timeout=timeout) + self._send_line(proc, "1") + self._read_until(proc, ": ", timeout=timeout) + self._send_line(proc, name) + self._read_until(proc, ": ", timeout=timeout) + self._send_line(proc, str(level)) + + def login(self, proc, name, timeout=1.): + self._read_until(proc, "> ", timeout=timeout) + self._send_line(proc, "2") + self._read_until(proc, ": ", timeout=timeout) + self._send_line(proc, name) + + def list_user(self, proc, timeout=1.): + self._read_until(proc, "> ", timeout=timeout) + self._send_line(proc, "3") + return self._read_until(proc, "\n1. register") + + def bini(self, proc, id, data, timeout=1.0): + self._read_until(proc, "> ", timeout=timeout) + self._send_line(proc, str(id)) + self._read_until(proc, ": ", timeout=timeout) + self._send_line(proc, data) + + def logout(self, proc, timeout=1.): + self._read_until(proc, "> ", timeout=timeout) + self._send_line(proc, "4") + + def exit(self, proc, timeout=1.): + self._read_until(proc, "> ", timeout=timeout) + self._send_line(proc, "3") + + def check(self): + try: + with open(self.flag_location, 'r') as f: + host_flag = f.read().strip() + container_flag = self._read_container_flag() + assert host_flag == container_flag, 'Flag mismatch between host and container' + self.logger.info('[ok] flag parity (carbeat)') + + proc = self._spawn() + + self.register(proc, "karbit", 1337) + + name = self.list_user(proc) + assert "karbit" in name + + self.login(proc, "karbit") + self.bini(proc, 1, "waguri") + self.bini(proc, 2, "0") + waguri = self._read_until(proc, "0. edit", timeout=1.) + assert "waguri" in waguri + + self.bini(proc, 3, "0") + self.logout(proc) + self.exit(proc) + + try: + proc.wait(timeout=2.0) + except subprocess.TimeoutExpired: + proc.kill() + raise AssertionError("Program did not exit after option 3") + self.logger.info("[ok] service exit on 3") + + proc_alarm = self._spawn() + self._read_until(proc_alarm, "zzz", timeout=190.0) # 180s + slack + try: + proc_alarm.wait(timeout=5.0) + except subprocess.TimeoutExpired: + proc_alarm.kill() + raise AssertionError("Alarm fired but process did not exit") + self.logger.info("[ok] alarm fired ('zzz') and process self-terminated") + + self.logger.info('Check passed for carbeat') + return True + + except Exception as e: + self.logger.error(f'Could not check carbeat: {e}') + return False \ No newline at end of file diff --git a/receiver/challenges/Naraka.py b/receiver/challenges/Naraka.py deleted file mode 100644 index 32ed9b3..0000000 --- a/receiver/challenges/Naraka.py +++ /dev/null @@ -1,99 +0,0 @@ -from .Challenge import Challenge - -import io -import requests -import random -import subprocess -import requests -import re - -class Naraka(Challenge): - flag_location = 'flags/naraka.txt' - history_location = 'history/naraka.txt' - - def distribute(self, flag): - try: - with open(self.flag_location, 'w') as f: - f.write(flag) - - with open(self.history_location, 'a') as f: - f.write(flag + '\n') - - self.logger.info(f'Flag {flag} written to {self.flag_location}') - return True - - except Exception as e: - self.logger.error(f'Could not write flag to {self.flag_location}: {e}') - return False - - def check(self): - random_name = [ - "nael", "mufat", "rayhan", "wicak", "Kingggg", - "osdie", "udin", "memet", "entong", "krabby", - "mew", "charizard", "pidgey", "rattata", "vulpix", - "eevee", "snorlax", "magikarp", "growlithe", "abra" - ] - - math_expression = "+-*" - - python_programs = [ - "a = 10;b = 5;print(a+b)", "a = 'add'; b='string';print(a+b)","x = [1,2,3,4,5,6,7,8];print(max(x))" - ] - - programs_result = ["b'15","b'addstring","b'8"] - try: - # Step 1: Chekc Greetings return name - name = random.choice(random_name) - url = f'http://localhost:{self.port}/render?name={name}' - r = requests.get(url, timeout=5) - assert name in r.text, 'Greetings is not greetings my name :(' - - # Step 2: Check eval calculator using random math expression - math = f'{random.randint(1,100)}{random.choice(math_expression)}{random.randint(1,100)}' - math_result = eval(math) - data = {'chall': '2','input':math} - url = f'http://localhost:{self.port}/chall' - r = requests.post(url, data=data, timeout=5) - assert str(math_result) in r.text, 'Eval calculator is not working :(' - - # Step 3: Check exec that execute python program - ind = random.randint(0,2) - pythononeline = python_programs[ind] - pythonresult = programs_result[ind] - data = {'chall': '1','input':pythononeline} - url = f'http://localhost:{self.port}/chall' - r = requests.post(url, data=data, timeout=5) - assert pythonresult in r.text, 'My code line is not execute :(' - - # Step 4: Check execute FLAG declaration execute - url = f'http://localhost:{self.port}/sourcecode/1' - r = requests.get(url, timeout=5) - flag_assignments = re.findall(r'^\s*FLAG\s*=\s*sys\.argv\[2\]\s*$', r.text, re.MULTILINE) - flag_assignments_num = flag_assignments = re.findall(r'^\s*FLAG\s*=\s*.+$', r.text, re.MULTILINE) - assert flag_assignments != 1 or flag_assignments_num != 1, "execute FLAG declared incorrectly" - - # Step 5: Check evaluate FLAG declaration execute - url = f'http://localhost:{self.port}/sourcecode/1' - r = requests.get(url, timeout=5) - flag_assignments = re.findall(r'^\s*FLAG\s*=\s*sys\.argv\[2\]\s*$', r.text, re.MULTILINE) - flag_assignments_num = flag_assignments = re.findall(r'^\s*FLAG\s*=\s*.+$', r.text, re.MULTILINE) - assert flag_assignments != 1 or flag_assignments_num != 1, "evaluate FLAG declared incorrectly" - - # Step 6: Check flag - with open(self.flag_location, 'r') as f: - host_flag = f.read().strip() - - container_flag = subprocess.run( - ["docker", "exec", "naraka_container", "cat", "/flag.txt"], - capture_output=True, - text=True - ).stdout.strip() - - assert host_flag == container_flag, 'Flag mismatch between host and container' - - self.logger.info('Check passed for naraka') - return True - - except Exception as e: - self.logger.error(f'Could not check naraka: {e}') - return False \ No newline at end of file diff --git a/receiver/flags/carbeat.txt b/receiver/flags/carbeat.txt new file mode 100644 index 0000000..804b091 --- /dev/null +++ b/receiver/flags/carbeat.txt @@ -0,0 +1 @@ +GEMASTIK18{PLACEHOLDER} \ No newline at end of file diff --git a/receiver/flags/phew.txt b/receiver/flags/phew.txt new file mode 100644 index 0000000..804b091 --- /dev/null +++ b/receiver/flags/phew.txt @@ -0,0 +1 @@ +GEMASTIK18{PLACEHOLDER} \ No newline at end of file diff --git a/services/carbeat/Dockerfile b/services/carbeat/Dockerfile index c7e9dfe..26f8e54 100644 --- a/services/carbeat/Dockerfile +++ b/services/carbeat/Dockerfile @@ -4,7 +4,7 @@ FROM ubuntu:24.04 # Build-time args ARG PASSWORD=root ENV DEBIAN_FRONTEND=noninteractive -WORKDIR /home/ctf/chall +WORKDIR /home/ctfuser/chall RUN apt-get update && \ apt-get install -y --no-install-recommends \ @@ -18,15 +18,15 @@ RUN apt-get update && \ vim \ && rm -rf /var/lib/apt/lists/* -RUN useradd -m -d /home/ctf -s /bin/bash ctf && echo "ctf:${PASSWORD}" | chpasswd +RUN useradd -m -d /home/ctfuser -s /bin/bash ctfuser && echo "ctfuser:${PASSWORD}" | chpasswd RUN mkdir -p /var/run/sshd -COPY chall/ /home/ctf/chall +COPY chall/ /home/ctfuser/chall COPY ./entrypoint.sh /entrypoint.sh -RUN chmod +x /entrypoint.sh /home/ctf/chall/run.sh && \ - chown -R root:root /home/ctf/chall && chmod -R 555 /home/ctf/chall +RUN chmod +x /entrypoint.sh /home/ctfuser/chall/run.sh && \ + chown -R root:root /home/ctfuser/chall && chmod -R 555 /home/ctfuser/chall EXPOSE 9000 22 CMD ["/entrypoint.sh"] \ No newline at end of file diff --git a/services/carbeat/entrypoint.sh b/services/carbeat/entrypoint.sh index 1d285ef..f6d4f31 100644 --- a/services/carbeat/entrypoint.sh +++ b/services/carbeat/entrypoint.sh @@ -11,7 +11,7 @@ grep -q "^PasswordAuthentication" /etc/ssh/sshd_config && \ sed -i "s/^PasswordAuthentication.*/PasswordAuthentication yes/" /etc/ssh/sshd_config || \ echo "PasswordAuthentication yes" >> /etc/ssh/sshd_config -echo "AllowUsers ctf" >> /etc/ssh/sshd_config +echo "AllowUsers ctfuser" >> /etc/ssh/sshd_config /usr/sbin/sshd @@ -21,4 +21,4 @@ if [ -n "$FLAG" ]; then chown root:root /flag.txt fi -exec su -c "cd /home/ctf/chall && ./run.sh" -s /bin/bash ctf \ No newline at end of file +exec su -c "cd /home/ctfuser/chall && ./run.sh" -s /bin/bash ctfuser \ No newline at end of file diff --git a/services/phew/Dockerfile b/services/phew/Dockerfile index 0d0920d..d6fd39a 100644 --- a/services/phew/Dockerfile +++ b/services/phew/Dockerfile @@ -2,8 +2,8 @@ FROM python:3.12-slim ARG PASSWORD=root ENV DEBIAN_FRONTEND=noninteractive -ENV HOME=/home/ctf -WORKDIR /home/ctf/chall +ENV HOME=/home/ctfuser +WORKDIR /home/ctfuser/chall RUN apt-get update && apt-get install -y --no-install-recommends \ openssh-server \ @@ -11,22 +11,23 @@ RUN apt-get update && apt-get install -y --no-install-recommends \ libffi-dev \ libssl-dev \ python3-dev \ + socat \ bash \ && rm -rf /var/lib/apt/lists/* -RUN useradd -m -d /home/ctf -s /bin/bash ctf && \ - echo "ctf:${PASSWORD}" | chpasswd +RUN useradd -m -d /home/ctfuser -s /bin/bash ctfuser && \ + echo "ctfuser:${PASSWORD}" | chpasswd RUN mkdir -p /var/run/sshd COPY requirements.txt /tmp/requirements.txt RUN pip install --no-cache-dir -r /tmp/requirements.txt -COPY ./src /home/ctf/chall/src +COPY ./src /home/ctfuser/chall/src COPY ./start.sh /start.sh -RUN chmod +x /start.sh /home/ctf/chall/src/run.sh +RUN chmod +x /start.sh /home/ctfuser/chall/src/run.sh -RUN chown -R root:root /home/ctf/chall && chmod -R 555 /home/ctf/chall +RUN chown -R root:root /home/ctfuser/chall && chmod -R 555 /home/ctfuser/chall EXPOSE 8000 22 CMD ["/start.sh"] diff --git a/services/phew/Pailier.py b/services/phew/src/Pailier.py similarity index 97% rename from services/phew/Pailier.py rename to services/phew/src/Pailier.py index ef7cafc..68d22b1 100644 --- a/services/phew/Pailier.py +++ b/services/phew/src/Pailier.py @@ -1,47 +1,47 @@ -from Crypto.Util.number import * -from math import lcm -import random - -class pailier: - def __init__(self): - self.primes = [getPrime(512) for _ in range(2)] - self.n = 1 - self.phi = 1 - self.mul = 1 - for i in range(2): - self.n *= self.primes[i] - self.phi *= (self.primes[i] - 1) - self.n2 = self.n * self.n - self.g = [pow(random.randrange(1, self.n2), self.primes[i], self.n2) for i in range(2)] - for x in self.g: - self.mul = (self.mul * x) % self.n2 - self.miu = inverse(self.L(pow(self.mul, self.phi, self.n2)), self.n) - self.alpha = [None, None] - for idx in range(2): - while True: - a = random.randrange(2, self.n - 1) - if GCD(a, self.n) == 1: - self.alpha[idx] = a - break - self.beta = [random.randrange(0, self.n), random.randrange(0, self.n)] - - def L(self, val): - return (val - 1) // self.n - - def pubkey(self): - return (self.n, self.g) - - def encrypt(self, msg: int) -> int: - r = random.randrange(0, self.n - 1) - gb = self.g[random.randrange(0, 2)] - gm = pow(gb, msg, self.n2) - rn = pow(r, self.n, self.n2) - return (gm * rn) % self.n2 - - def decrypt(self, ct: int) -> int: - raw = self.L(pow(ct, self.phi, self.n2)) % self.n - raw = (raw * self.miu) % self.n - t = pow(ct % self.n, (self.n - 1) // 2, self.n) if (self.n % 2 == 1) else 0 - idx = 0 if t == 1 else 1 - return (self.alpha[idx] * raw + self.beta[idx]) % self.n - +from Crypto.Util.number import * +from math import lcm +import random + +class pailier: + def __init__(self): + self.primes = [getPrime(512) for _ in range(2)] + self.n = 1 + self.phi = 1 + self.mul = 1 + for i in range(2): + self.n *= self.primes[i] + self.phi *= (self.primes[i] - 1) + self.n2 = self.n * self.n + self.g = [pow(random.randrange(1, self.n2), self.primes[i], self.n2) for i in range(2)] + for x in self.g: + self.mul = (self.mul * x) % self.n2 + self.miu = inverse(self.L(pow(self.mul, self.phi, self.n2)), self.n) + self.alpha = [None, None] + for idx in range(2): + while True: + a = random.randrange(2, self.n - 1) + if GCD(a, self.n) == 1: + self.alpha[idx] = a + break + self.beta = [random.randrange(0, self.n), random.randrange(0, self.n)] + + def L(self, val): + return (val - 1) // self.n + + def pubkey(self): + return (self.n, self.g) + + def encrypt(self, msg: int) -> int: + r = random.randrange(0, self.n - 1) + gb = self.g[random.randrange(0, 2)] + gm = pow(gb, msg, self.n2) + rn = pow(r, self.n, self.n2) + return (gm * rn) % self.n2 + + def decrypt(self, ct: int) -> int: + raw = self.L(pow(ct, self.phi, self.n2)) % self.n + raw = (raw * self.miu) % self.n + t = pow(ct % self.n, (self.n - 1) // 2, self.n) if (self.n % 2 == 1) else 0 + idx = 0 if t == 1 else 1 + return (self.alpha[idx] * raw + self.beta[idx]) % self.n + diff --git a/services/phew/chall.py b/services/phew/src/chall.py similarity index 96% rename from services/phew/chall.py rename to services/phew/src/chall.py index c97146c..e9f22e7 100644 --- a/services/phew/chall.py +++ b/services/phew/src/chall.py @@ -1,29 +1,29 @@ -#!/usr/bin/env python3 - -from Pailier import * -from Crypto.Util.number import * -with open("/flag.txt", "rb") as f: - flag = f.read() -flag = bytes_to_long(flag) -cipher = pailier() -while True: - print("1. encrypt") - print("2. bingo") - print("3. decrypt") - print("4. exit") - inp = int(input("> ")) - if inp==1: - print("pt (hex)") - inp = input("> ") - ct = cipher.encrypt(int(inp,16)) - print('ct : ','{0:x}'.format(ct)) - elif inp==2: - ct = cipher.encrypt(flag) - print('ct : ','{0:x}'.format(ct)) - elif inp==3: - print("ct (hex)") - inp = input("> ") - pt = cipher.decrypt(int(inp,16)) - print('pt : ','{0:x}'.format(pt)) - else: - exit() +#!/usr/bin/env python3 + +from Pailier import * +from Crypto.Util.number import * +with open("/flag.txt", "rb") as f: + flag = f.read() +flag = bytes_to_long(flag) +cipher = pailier() +while True: + print("1. encrypt") + print("2. bingo") + print("3. decrypt") + print("4. exit") + inp = int(input("> ")) + if inp==1: + print("pt (hex)") + inp = input("> ") + ct = cipher.encrypt(int(inp,16)) + print('ct : ','{0:x}'.format(ct)) + elif inp==2: + ct = cipher.encrypt(flag) + print('ct : ','{0:x}'.format(ct)) + elif inp==3: + print("ct (hex)") + inp = input("> ") + pt = cipher.decrypt(int(inp,16)) + print('pt : ','{0:x}'.format(pt)) + else: + exit() diff --git a/services/phew/run.sh b/services/phew/src/run.sh similarity index 100% rename from services/phew/run.sh rename to services/phew/src/run.sh diff --git a/services/phew/start.sh b/services/phew/start.sh index 7b40126..a568495 100644 --- a/services/phew/start.sh +++ b/services/phew/start.sh @@ -12,7 +12,7 @@ grep -q "^PasswordAuthentication" /etc/ssh/sshd_config && \ sed -i "s/^PasswordAuthentication.*/PasswordAuthentication yes/" /etc/ssh/sshd_config || \ echo "PasswordAuthentication yes" >> /etc/ssh/sshd_config -echo "AllowUsers ctf" >> /etc/ssh/sshd_config +echo "AllowUsers ctfuser" >> /etc/ssh/sshd_config /usr/sbin/sshd @@ -22,4 +22,4 @@ if [ -n "$FLAG" ]; then chown root:root /flag.txt fi -exec su -c "cd /home/ctf/chall/src && ./run.sh" -s /bin/bash ctf +exec su -c "cd /home/ctfuser/chall/src && ./run.sh" -s /bin/bash ctfuser diff --git a/services/sheesh/Dockerfile b/services/sheesh/Dockerfile index 073dd6a..04a3a37 100644 --- a/services/sheesh/Dockerfile +++ b/services/sheesh/Dockerfile @@ -11,6 +11,7 @@ RUN apt-get update && apt-get install -y --no-install-recommends \ libffi-dev \ libssl-dev \ python3-dev \ + socat \ bash \ && rm -rf /var/lib/apt/lists/* diff --git a/services/sheesh/chall.py b/services/sheesh/src/chall.py similarity index 95% rename from services/sheesh/chall.py rename to services/sheesh/src/chall.py index a3eca5f..3976d7f 100644 --- a/services/sheesh/chall.py +++ b/services/sheesh/src/chall.py @@ -1,116 +1,116 @@ -#!/usr/bin/env python3 - -import os -import binascii -import hashlib -import threading -import time -import sys -from Crypto.Cipher import AES -from Crypto.Util.Padding import pad, unpad - -seed_bits = 23 -seed_max = 1 << seed_bits -seed_len = (seed_bits + 7) // 8 -key = os.urandom(16) - -def hash_seed(seed_int: int) -> bytes: - sb = seed_int.to_bytes(seed_len, "big") - return hashlib.sha256(sb).digest()[:16] - -seed = int.from_bytes(os.urandom(4), "big") % seed_max -seed2 = int.from_bytes(os.urandom(4), "big") % seed_max -K1 = hash_seed(seed) -K2 = hash_seed(seed2) - -with open("./flag.txt", "rb") as f: - flag = f.read() - -def read_hex(prompt: str): - s = input(prompt).strip() - try: - return binascii.unhexlify(s) - except Exception: - print("hmm") - return None - -def enc_cfb(pt: bytes) -> bytes: - iv = os.urandom(16) - aes = AES.new(key, AES.MODE_CFB, iv=iv, segment_size=128) - ct = aes.encrypt(pt) - return iv + ct - -def enc_cbc(data: bytes, iv1: bytes, iv2: bytes, padd: bool) -> bytes: - x = pad(data, 16) if padd else data - c1 = AES.new(K1, AES.MODE_CBC, iv=iv1).encrypt(x) - c2 = AES.new(K2, AES.MODE_CBC, iv=iv2).encrypt(c1) - return c2 - -def menu(): - print(""" -1. encrypt -2. profit -3. get third -4. exit - """) - -third = 0 -iv11 = None -iv22 = None - -def alarm(): - time.sleep(180) - print("zzz") - sys.exit(0) - -threading.Thread(target=alarm, daemon=True).start() - -while True: - menu() - op = input("> ").strip() - - if op == "1": - data = read_hex("pt: ") - if data is None: - print() - continue - out = enc_cfb(data) - print("ct: ", out.hex()) - print() - - elif op == "2": - if iv11 is not None and iv22 is not None: - iv1, iv2 = iv11, iv22 - iv11 = iv22 = None - else: - iv1 = os.urandom(16) - iv2 = os.urandom(16) - ct = enc_cbc(flag, iv1, iv2, padd=True) - print("iv1: ", iv1.hex()) - print("iv2: ", iv2.hex()) - print("ct: ", ct.hex()) - print() - - elif op == "3": - if third: - print("sheesh") - continue - block = read_hex("pt: ") - if block is None: - print() - continue - if len(block) != 16: - print("hmmm\n") - continue - iv1 = os.urandom(16) - iv2 = os.urandom(16) - ct = enc_cbc(block, iv1, iv2, padd=False) - iv11, iv22 = iv1, iv2 - print("ct: ", ct.hex()) - third = 1 - print() - - elif op == "4": - break - else: - print("mabokkkk?") +#!/usr/bin/env python3 + +import os +import binascii +import hashlib +import threading +import time +import sys +from Crypto.Cipher import AES +from Crypto.Util.Padding import pad, unpad + +seed_bits = 23 +seed_max = 1 << seed_bits +seed_len = (seed_bits + 7) // 8 +key = os.urandom(16) + +def hash_seed(seed_int: int) -> bytes: + sb = seed_int.to_bytes(seed_len, "big") + return hashlib.sha256(sb).digest()[:16] + +seed = int.from_bytes(os.urandom(4), "big") % seed_max +seed2 = int.from_bytes(os.urandom(4), "big") % seed_max +K1 = hash_seed(seed) +K2 = hash_seed(seed2) + +with open("./flag.txt", "rb") as f: + flag = f.read() + +def read_hex(prompt: str): + s = input(prompt).strip() + try: + return binascii.unhexlify(s) + except Exception: + print("hmm") + return None + +def enc_cfb(pt: bytes) -> bytes: + iv = os.urandom(16) + aes = AES.new(key, AES.MODE_CFB, iv=iv, segment_size=128) + ct = aes.encrypt(pt) + return iv + ct + +def enc_cbc(data: bytes, iv1: bytes, iv2: bytes, padd: bool) -> bytes: + x = pad(data, 16) if padd else data + c1 = AES.new(K1, AES.MODE_CBC, iv=iv1).encrypt(x) + c2 = AES.new(K2, AES.MODE_CBC, iv=iv2).encrypt(c1) + return c2 + +def menu(): + print(""" +1. encrypt +2. profit +3. get third +4. exit + """) + +third = 0 +iv11 = None +iv22 = None + +def alarm(): + time.sleep(180) + print("zzz") + sys.exit(0) + +threading.Thread(target=alarm, daemon=True).start() + +while True: + menu() + op = input("> ").strip() + + if op == "1": + data = read_hex("pt: ") + if data is None: + print() + continue + out = enc_cfb(data) + print("ct: ", out.hex()) + print() + + elif op == "2": + if iv11 is not None and iv22 is not None: + iv1, iv2 = iv11, iv22 + iv11 = iv22 = None + else: + iv1 = os.urandom(16) + iv2 = os.urandom(16) + ct = enc_cbc(flag, iv1, iv2, padd=True) + print("iv1: ", iv1.hex()) + print("iv2: ", iv2.hex()) + print("ct: ", ct.hex()) + print() + + elif op == "3": + if third: + print("sheesh") + continue + block = read_hex("pt: ") + if block is None: + print() + continue + if len(block) != 16: + print("hmmm\n") + continue + iv1 = os.urandom(16) + iv2 = os.urandom(16) + ct = enc_cbc(block, iv1, iv2, padd=False) + iv11, iv22 = iv1, iv2 + print("ct: ", ct.hex()) + third = 1 + print() + + elif op == "4": + break + else: + print("mabokkkk?") diff --git a/services/sheesh/run.sh b/services/sheesh/src/run.sh similarity index 100% rename from services/sheesh/run.sh rename to services/sheesh/src/run.sh diff --git a/starter.py b/starter.py index f10d743..bccab3a 100644 --- a/starter.py +++ b/starter.py @@ -35,12 +35,12 @@ def main(): os.chdir(os.path.join(cwd, 'services')) os.system(f'docker compose -f docker-compose.yml up --build -d {args.challenges}') - os.chdir(os.path.join(cwd, 'receiver')) - os.system('apt-get install -y gcc python3-dev libgmp3-dev libssl-dev libffi-dev build-essential python3-venv') - os.system('python3 -m venv .') - os.system('sudo ./bin/activate') - os.system('sudo ./bin/python3 -m pip install -r requirements.txt') - os.system('sudo ./bin/python3 -m uvicorn main:app --reload --host 0.0.0.0 --port 80') + # os.chdir(os.path.join(cwd, 'receiver')) + # os.system('apt-get install -y gcc python3-dev libgmp3-dev libssl-dev libffi-dev build-essential python3-venv') + # os.system('python3 -m venv .') + # os.system('sudo ./bin/activate') + # os.system('sudo ./bin/python3 -m pip install -r requirements.txt') + # os.system('sudo ./bin/python3 -m uvicorn main:app --reload --host 0.0.0.0 --port 80') if __name__ == '__main__': main()