Rating:
The compression shifts and removes some bits. After couple of tests I've discovered that the password length is 6.
First I was thinking about bruteforcing it all, but it can take too much time. So I've decided to create a decompress function and brute force only the unknown bits.
Here is a full python code:
```
import hashlib, sys
def text_from_bits(s):
return ''.join(chr(int(s[i*8:i*8+8],2)) for i in range(len(s)//8))
def drop(b,m):
return(b[:m]+b[(m+1):])
def dedrop(b, m):
return(b[:m]+'2'+b[m:]) # 2 = unknown bit
def shift(b, i):
return(b[i:] + b[:i])
def deshift(b, i):
return shift(b, len(b) - i)
# filled by compress function for 6 chars password
#msaved=[]
msaved = [0, 1, 1, 1, 4, 1, 0, 1, 4, 9, 5, 1, 10, 7, 4, 1, 15, 13, 11, 9, 7, 5, 3, 1]
#def compress(b):
# l = len(b)
# i = 1
# while(i<l):
# m = l%i
# msaved.append(m)
# b = drop(b,m)
# b = shift(b,i)
# l = len(b)
# i+=1
# return b
def decompress(b):
i = len(msaved) - 1
while i >= 0:
m = msaved[i]
b = deshift(b, i+1)
b = dedrop(b, m)
i = i - 1
return b
def hash(flag):
h = hashlib.sha256()
h.update(flag)
return h.hexdigest()
flagHash = 'e67753ef818688790288702b0592a46c390b695a732e1b9fec47a14e2f6f25ae'
def brute(b):
for i in range(len(b)):
if b[i] == '2': # replace unknown bit
brute(b[:i] + '0' + b[(i+1):])
brute(b[:i] + '1' + b[(i+1):])
return
flag = 'evlz{%s}ctf' % text_from_bits(b)
if hash(flag) == flagHash:
print flag
sys.exit(0)
brute(decompress('100001000100110000000100'))
```
The flag:
```
evlz{20o8@d}ctf
```