This puzzle is a puzzling puzzle.
main関数はこんなかんじ
ulong main(int argc,char **argv)
{
long *plVar1;
int *keys;
long in_FS_OFFSET;
int local_24;
long local_20;
local_20 = *(long *)(in_FS_OFFSET + 0x28);
if (argc < 4) {
__printf_chk(1,"Usage: %s [qr] [key] [output]\n",*argv);
}
else {
puts("[+] Loading QR...");
plVar1 = (long *)LoadQr(&local_24,argv[1]); // fun_400980
puts("[+] Done!");
puts("[+] Loading key...");
keys = LoadKey(argv[2]); // fun_400af0
puts("[+] Done!");
puts("[+] Encrypting...");
Encrypt((long)plVar1,keys); // fun_400c35
puts("[+] Done!");
puts("[+] Saving encrypted QR...");
Output(plVar1,local_24,argv[3]); // 400ca0
puts("[+] Done!");
}
if (local_20 == *(long *)(in_FS_OFFSET + 0x28)) {
return (ulong)(argc < 4);
}
/* WARNING: Subroutine does not return */
__stack_chk_fail();
}
LoadQrとLoadKeyはだいたい察しがつくので、Encryptを見る
void Encrypt(long param_1,int *param_2)
{
long *y_o;
long *y_p;
int d;
int y;
long x_o;
int x;
long x_p;
int iVar1;
do {
if (param_2 == (int *)0x0) {
return;
}
d = param_2[2];
x = *param_2;
x_o = (long)x;
y = param_2[1];
iVar1 = y;
if (d == 1) {
x = x + 1;
}
else {
if (d < 2) {
if (d == 0) {
x = x + -1;
}
else {
LAB_00400c70:
iVar1 = y;
}
}
else {
if (d == 2) {
iVar1 = y + -1;
}
else {
iVar1 = y + 1;
if (d != 3) goto LAB_00400c70;
}
}
}
y_o = (long *)(param_1 + (long)y * 8);
x_p = (long)x;
y_p = (long *)(param_1 + (long)iVar1 * 8);
*(char *)(*y_o + x_o) = *(char *)(*y_o + x_o) + *(char *)(*y_p + x_p);
*(char *)(*y_p + x_p) = *(char *)(*y_o + x_o) - *(char *)(*y_p + x_p);
*(char *)(x_o + *y_o) = *(char *)(x_o + *y_o) - *(char *)(*y_p + x_p);
param_2 = *(int **)(param_2 + 4);
} while( true );
}
あとはこの関数の逆の処理を書けばいいだけ
#!/usr/bin/env python3
from PIL import Image
key = []
qr = []
def load():
keysrc = open("./key", 'r')
qrsrc = open("./encrypted.qr", 'r')
l = keysrc.readline()
while l:
try:
d, p = l.split('#')
except:
l = keysrc.readline()
continue
p = eval(p)
d = int(d)
key.append((d, p))
l = keysrc.readline()
buf = []
c = qrsrc.read(1)
while c:
if c == '1':
buf.append(1)
elif c == '0':
buf.append(0)
else:
qr.append(buf)
buf = []
c = qrsrc.read(1)
def decrypt():
for (d, (x, y)) in key:
xo = x
yo = y
if d == 0:
x -= 1
elif d == 1:
x += 1
elif d == 2:
y -= 1
elif d == 3:
y += 1
qr[yo][xo] = qr[yo][xo] + qr[y][x]
qr[y][x] = qr[yo][xo] - qr[y][x]
qr[yo][xo] = qr[yo][xo] - qr[y][x]
def export():
img = Image.new("RGB", (25, 25), (255, 255, 255))
for i in range(25):
for j in range(25):
if qr[i][j] == 1:
img.putpixel((i, j), (0, 0, 0))
elif qr[i][j] == 0:
img.putpixel((i, j), (255, 255, 255))
else:
for i in qr:
print(i)
exit()
img.save("out.png")
if __name__ == "__main__":
load()
decrypt()
export()
出力されたQRコードをデコードするとflag
zer0pts{puzzl3puzzl3}