Normal - ImaginaryCTF
Posted on
Description:
module normal(out, in);
output [255:0] out;
input [255:0] in;
wire [255:0] w1, w2, w3, w4, w5, w6, w7, w8;
wire [255:0] c1, c2;
assign c1 = 256'h44940e8301e14fb33ba0da63cd5d2739ad079d571d9f5b987a1c3db2b60c92a3;
assign c2 = 256'hd208851a855f817d9b3744bd03fdacae61a70c9b953fca57f78e9d2379814c21;
nor n1 [255:0] (w1, in, c1);
nor n2 [255:0] (w2, in, w1);
nor n3 [255:0] (w3, c1, w1);
nor n4 [255:0] (w4, w2, w3);
nor n5 [255:0] (w5, w4, w4);
nor n6 [255:0] (w6, w5, c2);
nor n7 [255:0] (w7, w5, w6);
nor n8 [255:0] (w8, c2, w6);
nor n9 [255:0] (out, w7, w8);
endmodule
module main;
wire [255:0] flag = 256'h696374667b00000000000000000000000000000000000000000000000000007d;
wire [255:0] wrong;
normal flagchecker(wrong, flag);
initial begin
#10;
if (wrong) begin
$display("Incorrect flag...");
$finish;
end
$display("Correct!");
end
endmodule
I have never used verilog before so I had to learn the syntax of verilog.
After going through the syntax of verilog and then analyzing the program it was passing the flag through all the NOR gates. If flagchecker returns 1, flag is correct or else it is incorrect. So I just brute forced the gates with all printable characters.
I should have use boolean algebra or bit hacking to reduce the computation and redundant part of the code. Anyways here is my solution.
import string
def convert(l1):
l2 = []
j = 0
for i in range(2, len(l1)+2, 2):
l2.append(int(l1[j:i], 16))
j = i
return l2
def _not(x):
y = ""
for i in bin(x)[2:].rjust(8, "0"):
if i == '0':
y += '1'
else:
y += '0'
return y
def nor(l1, l2):
l3 = []
for i in zip(l1, l2):
l3.append(int(_not(i[0] | i[1]), 2))
return l3
def process(flag):
c1 = "d208851a855f817d9b3744bd03fdacae61a70c9b953fca57f78e9d2379814c21"
c2 = "44940e8301e14fb33ba0da63cd5d2739ad079d571d9f5b987a1c3db2b60c92a3"
flag = convert(flag)
c1 = convert(c1)
c2 = convert(c2)
w1 = nor(flag, c1)
w2 = nor(flag, w1)
w3 = nor(c1, w1)
w4 = nor(w2, w3)
w5 = nor(w4, w4)
w6 = nor(w5, c2)
w7 = nor(w5, w6)
w8 = nor(c2, w6)
return nor(w7, w8)
def str_to_hex(s):
h = ""
for i in s:
h += hex(ord(i))[2:]
return h
def decode():
#flag = "696374667b00000000000000000000000000000000000000000000000000007d"
flag = "ictf{"
for i in range(5, 32):
print(flag)
for j in string.printable:
c = flag
c += j
if process(str_to_hex(c))[i] == 0:
print(c)
flag += j
break
print(flag)
decode()
Flag:
flag: ictf{A11_ha!1_th3_n3w_n0rm_n0r!}