For this challenge, we’re handed two files: server.py and omglob_what_is_dis_crap.txt. Taking a quick look at server.py, it looks like this is a server running somewhere, accepting connections, checking a regex, and then returning a key if the passed information doesn’t match the regex.

class DoAThing(SocketServer.StreamRequestHandler):
    def handle(self):
        self.request.sendall("Enter your key:\n")
        msg = self.rfile.readline().strip()

        if not r.match(msg):
            self.request.sendall("Correct key. Here's all the passwords: %s\n" % FLAG)
        else:
            self.request.sendall("Failure...\n")

So what’s the regex that it tests against? Well, we see that it reads in the string from omglob_what_is_dis_crap.txt. So lets take a look at that…


From this regex we can see three different types of conditions:

1.  **.*[^0mglo8sc1enC3].*\
    **This condition tells us that the regex will match on any string
    containing characters other than “0mglo8sc1enC3”

2.  **.{,190}|.{192,}\
    **This condition tells us that the regex will match on any string
    that is not 191 characters long, giving us the correct key length.

3.  **.{97}[cgClm]\
    **The rest of the conditions look like this one. Each of them gives
    us a position in the key string, and tells us characters that that
    position will match on. Essentially, each one is telling us what
    characters don’t work at certain positions.

So, we need to create a string that is 191 characters long, and use the
third type of condition to tell what characters each position can be. We
can create a python script that parses the regex and gets out all of the
appropriate conditions, then creates a string for us that won’t match
those conditions. So feast your eyes below on a regex to parse a regex .

```python
import re
 
with open("omglob_what_is_dis_crap.txt", "r") as f:
    r = f.read()
 
stuff = re.findall(r"\.\{(\d+)\}\[(\w+)\]", r)
solution = [list('0mglo8sc1enC3')] * 191
 
for pos, s in stuff:
    solution[int(pos)] = list(set(solution[int(pos)]) - set(list(s)))
print "".join(map(str, [item[0] for item in solution]))

When we run this, we get the following output:

gg0ssgccCn8ggs83sggC01n8lecgs311eocc0m0n3C81gmoC1nm1Cn0Cs1g330sgnc0mCc18l18Cco8em0mC80m88csogceemoClCl00nC3gocn0egconsCcm3Clmeglo1lensgmsgnssslels10sglom31mlleg0le80csmnC033nm8oglgs0cellgmmns

We can now test this regex to see if it works with the server and will give us the key:

Which returns the key to get us to the next level:

PAN{th4t5_4_pr311y_dum8_w4y_10_us3_r3g3x}