4TRUN
We found this archaic thing in our lab. Could you please investigate its purpose?
Download:
100 Basepoints + 100 Bonuspoints * min(1, 3/21 Solves) = 114 Points
When run, the executable asks for the flag, and checks it:
1
2
3
$ ./4TRUN
Give flag: test
:(
We can open the application in HexRays or Snowman and study the flag checking logic. It consists of the following steps:
- Load the encoded flag data in a 6x6 encoded flag matrix
- Read the flag from the input and store it into a 6x6 flag matrix
- Update the flag matrix by successively adding values in columns
- Fill encoding factor matrix with constant values
0
through35
, and then update them with values from vector[1,3,3,3,3,7]
- Multiply flag matrix and encoding factor matrix
- Compare encoded flag matrix and flag matrix, returning an indicator of whether the flag is valid or not
These steps can be reversed and the flag can be generated from encoded flag matrix and encoding factor matrix. Let’s put the reverse steps into a script:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
import struct, numpy
# extract encoded flag from executable
enc_flag_data = bytearray(open("4TRUN","rb").read())[0x1180:0x1180+0xc0]
factor = [1,3,3,3,3,7]
enc_flag = numpy.tile(0,(6,6))
enc_factors = numpy.tile(0,(6,6))
# fill the flag matrix and the encoding factors
for i in range(6):
for j in range(6):
enc_flag[j,i] = struct.unpack("<I",enc_flag_data[0x20*j + i*4:0x20*j + i*4 + 4])[0]
enc_factors[j,i] = 6 * j + i
enc_factors[i,i] += factor[i]
print "Encoded flag:"
print enc_flag
print "Encoding factors:"
print enc_factors
# solve the matrix
res = numpy.linalg.solve(enc_factors, enc_flag)
print "Solved matrix:"
print res
# decode the resulting matrix by successively subrtacting values in columns
for i in range(6):
for j in range(5,0,-1):
for k in range(j-1,-1,-1):
res[k,i] -= res[j,i]
print "Flag matrix:"
print res
flag = ""
for i in range(6):
for j in range(6):
flag += chr(int(round(res[j,i])))
print "Flag: " + flag
Running the script gets us the flag:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
$ python solve.py
Encoded flag:
[[ 3510 4337 3131 3500 4180 3476]
[16140 18737 13815 15158 17061 14488]
[27510 31814 23403 25718 29043 24670]
[38904 44915 33165 36464 41034 34660]
[50265 58013 42729 47003 52824 44809]
[61890 71592 52558 58126 65153 55548]]
Encoding factors:
[[ 1 1 2 3 4 5]
[ 6 10 8 9 10 11]
[12 13 17 15 16 17]
[18 19 20 24 22 23]
[24 25 26 27 31 29]
[30 31 32 33 34 42]]
Solved matrix:
[[ 606. 648. 467. 549. 550. 493.]
[ 502. 540. 415. 435. 431. 389.]
[ 382. 423. 309. 321. 379. 337.]
[ 270. 314. 261. 269. 330. 221.]
[ 147. 204. 147. 148. 214. 158.]
[ 48. 109. 52. 95. 119. 125.]]
Flag matrix:
[[ 104. 108. 52. 114. 119. 104.]
[ 120. 117. 106. 114. 52. 52.]
[ 112. 109. 48. 52. 49. 116.]
[ 123. 110. 114. 121. 116. 63.]
[ 99. 95. 95. 53. 95. 33.]
[ 48. 109. 52. 95. 119. 125.]]
Flag: hxp{c0lumn_m4j0r_4rr4y5_w41t_wh4t?!}