Skip to content

Commit 89c6fde

Browse files
authored
Add picoctf (#6)
1 parent 3de1a22 commit 89c6fde

File tree

14 files changed

+1019
-0
lines changed

14 files changed

+1019
-0
lines changed
+80
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
# PicoCTF
2+
# https://play.picoctf.org/practice/challenge/121
3+
4+
import hashlib
5+
6+
def check_key(key, username_trial):
7+
global key_full_template_trial
8+
9+
if len(key) != len(key_full_template_trial):
10+
return False
11+
else:
12+
# Check static base key part --v
13+
i = 0
14+
for c in key_part_static1_trial:
15+
if key[i] != c:
16+
return False
17+
i += 1
18+
19+
# TODO : test performance on toolbox container
20+
# Check dynamic part --v
21+
if key[i] != hashlib.sha256(username_trial).hexdigest()[4]:
22+
return False
23+
else:
24+
i += 1
25+
if key[i] != hashlib.sha256(username_trial).hexdigest()[5]:
26+
return False
27+
else:
28+
i += 1
29+
if key[i] != hashlib.sha256(username_trial).hexdigest()[3]:
30+
return False
31+
else:
32+
i += 1
33+
if key[i] != hashlib.sha256(username_trial).hexdigest()[6]:
34+
return False
35+
else:
36+
i += 1
37+
if key[i] != hashlib.sha256(username_trial).hexdigest()[2]:
38+
return False
39+
else:
40+
i += 1
41+
if key[i] != hashlib.sha256(username_trial).hexdigest()[7]:
42+
return False
43+
else:
44+
i += 1
45+
if key[i] != hashlib.sha256(username_trial).hexdigest()[1]:
46+
return False
47+
else:
48+
i += 1
49+
if key[i] != hashlib.sha256(username_trial).hexdigest()[8]:
50+
return False
51+
return True
52+
53+
54+
username_trial = "GOUGH"
55+
bUsername_trial = b"GOUGH"
56+
57+
key_part_static1_trial = "picoCTF{1n_7h3_|<3y_of_"
58+
key_part_dynamic1_trial = "xxxxxxxx"
59+
key_part_static2_trial = "}"
60+
key_full_template_trial = key_part_static1_trial + key_part_dynamic1_trial + key_part_static2_trial
61+
62+
# Template key
63+
# picoCTF{1n_7h3_|<3y_of_xxxxxxxx}
64+
65+
digest = hashlib.sha256(bUsername_trial).hexdigest()
66+
print(f'digest: {digest}')
67+
68+
bytes = [4, 5, 3, 6, 2, 7, 1, 8]
69+
digest_reordered = [digest[i] for i in bytes]
70+
print(f'digest_reordered: {digest_reordered}')
71+
72+
key_part_dynamic1_trial = "".join(digest_reordered)
73+
key_full_template_trial = key_part_static1_trial + key_part_dynamic1_trial + key_part_static2_trial
74+
print(f'key_full_template_trial: {key_full_template_trial}')
75+
check_key_result = check_key(key_full_template_trial, bUsername_trial)
76+
print(f'check_key(key_full_template_trial, bUsername_trial): {check_key_result}')
77+
78+
# picoCTF{1n_7h3_|<3y_of_f911a486}
79+
if check_key_result:
80+
print(f'Key: {key_full_template_trial}')

picoctf/keygenme-py/keygenme-trial.py

+244
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,244 @@
1+
#============================================================================#
2+
#============================ARCANE CALCULATOR===============================#
3+
#============================================================================#
4+
5+
import hashlib
6+
from cryptography.fernet import Fernet
7+
import base64
8+
9+
10+
11+
# GLOBALS --v
12+
arcane_loop_trial = True
13+
jump_into_full = False
14+
full_version_code = ""
15+
16+
username_trial = "GOUGH"
17+
bUsername_trial = b"GOUGH"
18+
19+
key_part_static1_trial = "picoCTF{1n_7h3_|<3y_of_"
20+
key_part_dynamic1_trial = "xxxxxxxx"
21+
key_part_static2_trial = "}"
22+
key_full_template_trial = key_part_static1_trial + key_part_dynamic1_trial + key_part_static2_trial
23+
24+
star_db_trial = {
25+
"Alpha Centauri": 4.38,
26+
"Barnard's Star": 5.95,
27+
"Luhman 16": 6.57,
28+
"WISE 0855-0714": 7.17,
29+
"Wolf 359": 7.78,
30+
"Lalande 21185": 8.29,
31+
"UV Ceti": 8.58,
32+
"Sirius": 8.59,
33+
"Ross 154": 9.69,
34+
"Yin Sector CL-Y d127": 9.86,
35+
"Duamta": 9.88,
36+
"Ross 248": 10.37,
37+
"WISE 1506+7027": 10.52,
38+
"Epsilon Eridani": 10.52,
39+
"Lacaille 9352": 10.69,
40+
"Ross 128": 10.94,
41+
"EZ Aquarii": 11.10,
42+
"61 Cygni": 11.37,
43+
"Procyon": 11.41,
44+
"Struve 2398": 11.64,
45+
"Groombridge 34": 11.73,
46+
"Epsilon Indi": 11.80,
47+
"SPF-LF 1": 11.82,
48+
"Tau Ceti": 11.94,
49+
"YZ Ceti": 12.07,
50+
"WISE 0350-5658": 12.09,
51+
"Luyten's Star": 12.39,
52+
"Teegarden's Star": 12.43,
53+
"Kapteyn's Star": 12.76,
54+
"Talta": 12.83,
55+
"Lacaille 8760": 12.88
56+
}
57+
58+
59+
def intro_trial():
60+
print("\n===============================================\n\
61+
Welcome to the Arcane Calculator, " + username_trial + "!\n")
62+
print("This is the trial version of Arcane Calculator.")
63+
print("The full version may be purchased in person near\n\
64+
the galactic center of the Milky Way galaxy. \n\
65+
Available while supplies last!\n\
66+
=====================================================\n\n")
67+
68+
69+
def menu_trial():
70+
print("___Arcane Calculator___\n\n\
71+
Menu:\n\
72+
(a) Estimate Astral Projection Mana Burn\n\
73+
(b) [LOCKED] Estimate Astral Slingshot Approach Vector\n\
74+
(c) Enter License Key\n\
75+
(d) Exit Arcane Calculator")
76+
77+
choice = input("What would you like to do, "+ username_trial +" (a/b/c/d)? ")
78+
79+
if not validate_choice(choice):
80+
print("\n\nInvalid choice!\n\n")
81+
return
82+
83+
if choice == "a":
84+
estimate_burn()
85+
elif choice == "b":
86+
locked_estimate_vector()
87+
elif choice == "c":
88+
enter_license()
89+
elif choice == "d":
90+
global arcane_loop_trial
91+
arcane_loop_trial = False
92+
print("Bye!")
93+
else:
94+
print("That choice is not valid. Please enter a single, valid \
95+
lowercase letter choice (a/b/c/d).")
96+
97+
98+
def validate_choice(menu_choice):
99+
if menu_choice == "a" or \
100+
menu_choice == "b" or \
101+
menu_choice == "c" or \
102+
menu_choice == "d":
103+
return True
104+
else:
105+
return False
106+
107+
108+
def estimate_burn():
109+
print("\n\nSOL is detected as your nearest star.")
110+
target_system = input("To which system do you want to travel? ")
111+
112+
if target_system in star_db_trial:
113+
ly = star_db_trial[target_system]
114+
mana_cost_low = ly**2
115+
mana_cost_high = ly**3
116+
print("\n"+ target_system +" will cost between "+ str(mana_cost_low) \
117+
+" and "+ str(mana_cost_high) +" stone(s) to project to\n\n")
118+
else:
119+
# TODO : could add option to list known stars
120+
print("\nStar not found.\n\n")
121+
122+
123+
def locked_estimate_vector():
124+
print("\n\nYou must buy the full version of this software to use this \
125+
feature!\n\n")
126+
127+
128+
def enter_license():
129+
user_key = input("\nEnter your license key: ")
130+
user_key = user_key.strip()
131+
132+
global bUsername_trial
133+
134+
if check_key(user_key, bUsername_trial):
135+
decrypt_full_version(user_key)
136+
else:
137+
print("\nKey is NOT VALID. Check your data entry.\n\n")
138+
139+
140+
def check_key(key, username_trial):
141+
return True
142+
143+
global key_full_template_trial
144+
145+
if len(key) != len(key_full_template_trial):
146+
return False
147+
else:
148+
# Check static base key part --v
149+
i = 0
150+
for c in key_part_static1_trial:
151+
if key[i] != c:
152+
return False
153+
154+
i += 1
155+
156+
# TODO : test performance on toolbox container
157+
# Check dynamic part --v
158+
if key[i] != hashlib.sha256(username_trial).hexdigest()[4]:
159+
return False
160+
else:
161+
i += 1
162+
163+
if key[i] != hashlib.sha256(username_trial).hexdigest()[5]:
164+
return False
165+
else:
166+
i += 1
167+
168+
if key[i] != hashlib.sha256(username_trial).hexdigest()[3]:
169+
return False
170+
else:
171+
i += 1
172+
173+
if key[i] != hashlib.sha256(username_trial).hexdigest()[6]:
174+
return False
175+
else:
176+
i += 1
177+
178+
if key[i] != hashlib.sha256(username_trial).hexdigest()[2]:
179+
return False
180+
else:
181+
i += 1
182+
183+
if key[i] != hashlib.sha256(username_trial).hexdigest()[7]:
184+
return False
185+
else:
186+
i += 1
187+
188+
if key[i] != hashlib.sha256(username_trial).hexdigest()[1]:
189+
return False
190+
else:
191+
i += 1
192+
193+
if key[i] != hashlib.sha256(username_trial).hexdigest()[8]:
194+
return False
195+
196+
197+
198+
return True
199+
200+
201+
def decrypt_full_version(key_str):
202+
203+
key_base64 = base64.b64encode(key_str.encode())
204+
f = Fernet(key_base64)
205+
206+
try:
207+
with open("keygenme.py", "w") as fout:
208+
global full_version
209+
global full_version_code
210+
full_version_code = f.decrypt(full_version)
211+
fout.write(full_version_code.decode())
212+
global arcane_loop_trial
213+
arcane_loop_trial = False
214+
global jump_into_full
215+
jump_into_full = True
216+
print("\nFull version written to 'keygenme.py'.\n\n"+ \
217+
"Exiting trial version...")
218+
except FileExistsError:
219+
sys.stderr.write("Full version of keygenme NOT written to disk, "+ \
220+
"ERROR: 'keygenme.py' file already exists.\n\n"+ \
221+
"ADVICE: If this existing file is not valid, "+ \
222+
"you may try deleting it and entering the "+ \
223+
"license key again. Good luck")
224+
225+
def ui_flow():
226+
intro_trial()
227+
while arcane_loop_trial:
228+
menu_trial()
229+
230+
231+
232+
# Encrypted blob of full version
233+
full_version = \
234+
b"""
235+
gAAAAABgT_nv39GmDRYkPhrc2hba8UHCHnSTHqdFxXNdemW0svN2hYYw-6n56ErD3NrQYQlNL0sfdsGTmvWKxh5gVRGeCv5kNq-l6PpL0Fzzjo1x_E2Jjbw_xWKIwbvd7BRXFQZKnhs2ehcSEacqES4gsVMOExHUetxFtmYiHLMB0_kqueeT8zf_vcXAPzbiYA0hvD_QSAXzPiKwM2IsGpGzIS5O4_ODq6-knKszeQFstWKFNH_-jNAylCTWSQpPrWqJxCWhSINPhOZ9-PkBsy8lpqmksa6ZBCMvej4W9YFldupRHNoHUHzt8xScEvcsTzIgNmvzOsCBSf5GJGHbLw4yVjsNWmbKRKiE_6BrRMHZW01hcYbfNa1TdJ1MLUX64e_tpDDjMfKvlXZ1qMx4GDwR2lFza9_fm98zoaV-ccgQ1qiSf3wDU1KuKxd9e9TbUAn2TTJfVH9d6IU8emK3QWcn8XRFcMRzVMvlBuNnCVrZmHCYZUzRmwneo15FS-giH63hPzfvjuRfzwp1sFa3wqo5YTJHWejsU0suORvViiDuIpDozmlXTLKLhKj51NkI6QqqDXhMcWkHwKy9V1LN2Furmz_rPbahbNAxnTAWpjF0VELQAvyNHdVy0yxBIbbOJq1oMvHiDJo2adecADc8hMRb4RZJoLqokXxtKLulywhagQjX9METL9bw1YTP9orWXAMwKhTdDbEUdnHViEq8MHo5DcnVvH0yPlnc9Zn2s3_UOfswnhz5vKm0ZbDc5aX0sFTNiMJVjjCrMhQ6HYp5yf_ybd9Tcx_u6xLtwUZBERZWt931n4hQN8n4C_XmDsMehuoSuFmi2NpAuDhX2rcEQK86Ito0KYp-8n2RmbOjzcjo5V5aqHXujmEfX8GYIUWEUKXVcFouF5rZtxtNz3Wsm_j4tqL4Tom27YE5eK7LQSi5B-AsmSF5JGTam2mWeykOGyE-3pHZmNxxkRfdRjxM0uFV13yjQSLFgNIkZ--8n0uAoTb62c7ZFxoFItMNrWasd5zMvp9Nqq70se2KOUieV6VbPJdSL0Sf1uGDmbRFdMmopDm-AuS-7-MLBGiOPmwXtse_9yXjUggeuo3UU4bxyQxCgwh17Ul1ZgxGeopcU7s7Sjm3rqxwlaJWTPRzeF5AXxtZHgyyZjwQ3EB9xYeoMCFh6gsF06bcwnK1Esgar7IYR3JBUfBH6KnWiTyhx_dLkUdomAPMPY0cRoreYsXmFKkEWhYg-TCdifL0nRT8BTEhVyUwFTvqn4PJknTn8NXelYu8co3n8_PoxsOnTrbdNXBJP9vD8Qp2oMi0ZsyCIeekwuX7MCcK4oFVpLGwOrhJdQhJWVqxQdt0ULS-ROB08eOglsXifnVrDl0hi2B0EYcWxxGs-CzsXJPSBvqKWti9XdU5oIhuUH2d7jnAx0pM9tTKqNiL5sfL2mhakMI8XGcljZw2KI0ldgaOW_UvAgh8N3FgKUR4qh_iJ0raoQaaJJFbFneKRoDNT3QsywP_qj6avStEbMGnhN3iBOoc7S3VrN8853X5fow2yDUJaexAKjpYGphE7K4e1g3fHWYjvgnJ-AoXfqALOwDLzaLRjVHSsgF1TQl39XgiAgEzJL-7w_zBn_Hxl5BfYtqe4vxf4PVMZGvof0jXMpM4W-AQ8IW-41LbNgNbPnRuTLubiJCV7MWYu8J7wO0ADSqgv0aXK60IOl0NphAzflWRvjytyT1CljFa0wcsBZvTyyks_ZOoa2__iAj3VlQjcrQynzrxoT5NASs_k51IYPr913nkfOT29oekedYMcxaHzlICLXmjlVHctJfATgYue7xc1BotMDO0Uj5q-wfcg03dq1cZmJ_qhe3AqWrZt3RraYVcvTT2B9Nu2KHBTyjQvCsQMXyFjlqasFZ4jSuNcqybxS3ocP4z-5oGV43zsVjr6YAZyjQiUoLJN6i6h39G5YfH4SStpbTcj7WXWj9WNqxcrF_swHNeIkOPByEa34TIXyJvEOGefZOw7h-F-hxCGuho7LOwabIopS6IykeSLMw1Ra4COmYN-VamVHVUGo50AVEXcmcnHL9NmXP_812Y_sSFdNPo-jglCzjv3KS5jajY1tReYKC9ehz5phUgReaVkiawSc5Tm5BZ42dfJuYZeTwnknsgTWiyGt3Ov6PddqD_40Ye6oHMLO0VjjT_Ul8GWh8hhmxcWxbN8H6dYwLJD0_-YbXvFpRQSi8IQ7BKjY0ZrZm1_tYO87Gg5YcUJznce53ltjXtGCgNIqywt3FDyJ709hOATCIHWf_u-Jfmc7QcIuSss7Rjh68ZgQoQu0Ybjt0Y5bEGEymuyYbgvdUwW8xTksnpl9Jju4x8hMORUQtkyxD0SBG1j7OEsDCK4axMjWxBj4D0liLOSwUuCWr5COJ0Bf_SlydQmufol1HzVIwxTSUG2m7gXEO6cv6gvBIzK0DdcUMjEzXNnqa8davVM0tFvXfuQcgjz8C7tj4-fu4UvikQyAvO5PdSIhClyl06fAyuUmmJgKvyyuoX3plOaMqq5rJbCzXl8OV1anQzSscXIR2Ur_ePhX5IoZNe2XifzLkgVk-lc-Z0gj5Q4WRuo2IYxOcJG-woHvml0oHDY-hQU-gNflauD38YQcfpwdXV0WgcQseWgKNlXfEuldWVktYXn8JNvqVUTOXrNJBEGB9RDyQqp9IubjhQqOJh31eunKYq6oTx4PgjSii0QOKaLKkonBsYtAbb3cUwSoCvek719cI2tp33XWYq2UqQ8J74PtRNzG061_RR_TxHKyWBll-6ii9dgFPki104UzjFkFXkYPzButkzcvcXIDAWD2RNBK6-bshYKS2xr5XxJXgr3QBTWdjrm-p6EwlbFd4DGDR7ran7b38NRkrFD0ignYiKc68xlAPGg9E084LBVXCVlRas8YvYReJH_sl6ZR7faNme2F-qYFzbcvD3jmp5fX0nzvyJuTGWa51qh7siaVBxHETZ_rzoqTh-tr91b_aHPFdcQMfe1Pd-GBQiy9e5N41GQ4MCpvzs87kV5spprXd_DOKnkjeC5bJDFUoIdMk5r-UO2boRH0tHONCbUOzw7HOgFcJUA13yjtvGGbfPPMHvhFMtMDMRw8gacd-5WHaLeh05yBy4UjT_9flAGAqYMWbvrhkAbwEYPJ0abxp1weANOcYZ-gMHm7kn9kF_eTpzKXxWsViR0AekfepQICVZI1eJzLjV2w6qWq7yDA2ALUxFW10GuEqhP9DI_OVVg6AILHPgokj0pcVA9zUizVTWaGnB1Te8_Zlw5Ik-MwNFPJHYLAug14JI4iYeY0zVsgvkpPJmg_dJD4U7Lr4PBwANvyz5NmGZiITqslCAwUDRMK10u3o2ZmSMn-MuBje_9NRYvh8SRvtbWCB46Yj1YMSJvaqci0MaJK8FdPeDPJ84uSK3eWzq75X96k9nVPnHPnlLkcls3480mlq_81V9MTWlLcvgqhEU4FxE7lGjSF9orw7HCK_9lx2rXwuFAaovFweQw2bu7Nr7pH1X82y0XQCI7aeP687QHdONEoIkWikG5Oub8kEGTBq1D4yeRLocq8dPSoRUAPOb6g-QVAOlu3fiJBGIikubJUWSdQ97pbLgxhnpCrRYS3uFZVo-4f5lnwBNEHrR7DuVc13M-rkUXO-oeqrz6Txmr-xAjYtWrg7IsMr-UPihTJC0Gsmm1FAlXtVOmuKYjwOV7DG4aPzE1MjDAHMWidls3ECcueaLdUV-oY6Hw3WwOK_Nnj10sPmWSFSuMPeOBwPEL2M-1tCkbOvilqccCAelhS87qU_fDUKzD68TV1tJIoXEKW4sdwAVGxguEv1BAm4G7LhrH08McB5n3ja5I_3IqkeYdyHaxAXJ-O2thg==
236+
"""
237+
238+
239+
240+
# Enter main loop
241+
ui_flow()
242+
243+
if jump_into_full:
244+
exec(full_version_code)

0 commit comments

Comments
 (0)