Skip to content

Commit 0f8d4aa

Browse files
committedAug 27, 2017
Participate SCTF 2017 Finals
1 parent 97da167 commit 0f8d4aa

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

75 files changed

+7694
-1
lines changed
 

‎.gitignore

+1-1
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
.ftpconfig
1+
.vscode

‎SCTF/2017 Finals/3-lights/3-lights.py

+136
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,136 @@
1+
import pyqrcode
2+
from random import random
3+
from base64 import b64encode as b64e
4+
from time import sleep
5+
import signal
6+
import sys
7+
8+
from helper import check_apikey, save_success_log, save_fail_log
9+
10+
DEFAULT_LEN = 60
11+
VERSION = 7
12+
TIME_LIMIT = 40
13+
STAGE = 100
14+
TOO_SLOW = '''
15+
_______ _ _____
16+
|__ __| | | _| __ \\
17+
| | ___ ___ ___| | _____ __ (_) |__) |
18+
| |/ _ \\ / _ \\ / __| |/ _ \\ \\ /\\ / / | ___/
19+
| | (_) | (_) | \\__ \\ | (_) \\ V V / _| |
20+
|_|\\___/ \\___/ |___/_|\\___/ \\_/\\_/ (_)_|
21+
'''
22+
23+
INTRO_MSG = '''Welcome to 3-lights-out hell :P
24+
100 stages are here.
25+
Give me data encoded by qrcode.
26+
You can find qrcode when you make board all red.
27+
28+
Good Luck'''
29+
30+
def gen_rand_str(n):
31+
with open('/dev/urandom', 'r') as f:
32+
data = b64e(f.read(n))[:n]
33+
34+
return data
35+
36+
def gen_qrcode(n=DEFAULT_LEN):
37+
data = gen_rand_str(n)
38+
qrdata = pyqrcode.create(data, version=VERSION)
39+
40+
return qrdata.code, data
41+
42+
def gen_click_map():
43+
map, data = gen_qrcode()
44+
45+
for i in xrange(len(map)):
46+
for j in xrange(len(map[0])):
47+
map[i][j] *= 2 if random() > 0.5 else 1
48+
49+
return map, data
50+
51+
class TLight:
52+
def __init__(self, map):
53+
self.table = {0: 'R', 1: 'G', 2: 'B'}
54+
self.map = map
55+
self.h = len(self.map)
56+
self.w = len(self.map[0])
57+
self.board = [[0 for j in xrange(self.w)] for i in xrange(self.h)]
58+
return
59+
60+
def click(self, x, y):
61+
dist = [[-1, 0], [-1, 0],
62+
[0, 1], [0, 1],
63+
[0, 0],
64+
[0, -1], [0, -1],
65+
[1, 0], [1, 0]]
66+
67+
for dx, dy in dist:
68+
if 0 <= dx+x < self.h and 0 <= dy+y < self.w:
69+
self.board[dx+x][dy+y] += 1
70+
self.board[dx+x][dy+y] %= 3
71+
72+
return
73+
74+
def mk_board(self):
75+
for i in xrange(self.h):
76+
for j in xrange(self.w):
77+
if self.map[i][j] == 1:
78+
self.click(i, j)
79+
elif self.map[i][j] == 2:
80+
self.click(i, j)
81+
self.click(i, j)
82+
83+
return
84+
85+
def pprint(self):
86+
for line in self.board:
87+
print ''.join(self.table[i] for i in line)
88+
return
89+
90+
def handler(signum, frame):
91+
print TOO_SLOW
92+
exit(0)
93+
return
94+
95+
def main():
96+
print INTRO_MSG
97+
print
98+
99+
apikey = raw_input('give me your apikey: ')
100+
apikey_res = check_apikey(apikey)
101+
102+
if apikey_res['code'] != 200:
103+
print 'Invalid API key'
104+
return
105+
else:
106+
print 'hi {}'.format(apikey_res['username'])
107+
108+
sleep(3)
109+
110+
username = apikey_res['username']
111+
signal.signal(signal.SIGALRM, handler)
112+
signal.alarm(TIME_LIMIT)
113+
114+
for i in xrange(STAGE):
115+
print 'STAGE ({}/{})'.format(i+i, STAGE)
116+
click_map, answer = gen_click_map()
117+
t = TLight(click_map)
118+
t.mk_board()
119+
120+
t.pprint()
121+
122+
get_answer = raw_input('answer: ')
123+
if answer != get_answer:
124+
print 'try again :P'
125+
save_fail_log(username)
126+
return
127+
128+
print 'yay! Now you will get a flag'
129+
with open('flag', 'r') as f:
130+
print f.read()
131+
save_success_log(username)
132+
133+
return
134+
135+
if __name__ == '__main__':
136+
main()

0 commit comments

Comments
 (0)
Please sign in to comment.