re-not_gcc(.bc后缀文件+中间编译+数独)

二木 王者

re-not_gcc

拿到题目我们可以发现是.bc文件

Untitled

经过搜索我们可以知道,bc文件为LLVM IR bitcode文件,所谓LLVM IR bitcode文件,就是代码到可执行文件的中间码。我们可以使用命令将其继续编译下去,生成可执行文件

在linux下,我们使用命令

clang not_gcc.bc -o not_gcc(这里文件需要改名,题目文件有空格,将其改为_)

Untitled

生成可执行文件

我们放入ida中进行分析

Untitled

各种跳转,有点花,不好厘清逻辑

动态调试,厘清一下思路

先判断字符长度,81位

Untitled

判断第一个输入的字符是否为0

Untitled

判断输入,输入字符的都必须满足1~9

Untitled

进入关键逻辑

Untitled

函数内部,分析逻辑可以知道,是生成了9*9的数独盘,以0为标志,作为未填充

Untitled

因此需要我们写脚本将数独解出。

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
def is_valid(board, row, col, num):
if num in board[row * 9: (row + 1) * 9]:
return False
if num in [board[i * 9 + col] for i in range(9)]:
return False
start_row, start_col = 3 * (row // 3), 3 * (col // 3)
for i in range(start_row, start_row + 3):
for j in range(start_col, start_col + 3):
if board[i * 9 + j] == num:
return False
return True
#解数独
def solve_sudoku(board):
for row in range(9):
for col in range(9):
if board[row * 9 + col] == 0:
for num in range(1, 10):
if is_valid(board, row, col, num):
board[row * 9 + col] = num
if solve_sudoku(board):
return True
board[row * 9 + col] = 0
return False
return True

# 示例数独板,0表示需要填充的位置
sudoku_board = [0x00000004, 0x00000000, 0x00000007, 0x00000000, 0x00000000, 0x00000003, 0x00000002, 0x00000000,
0x00000008, 0x00000005, 0x00000000, 0x00000000, 0x00000000, 0x00000002, 0x00000000, 0x00000009,
0x00000000, 0x00000000, 0x00000000, 0x00000001, 0x00000002, 0x00000009, 0x00000008, 0x00000000,
0x00000000, 0x00000000, 0x00000004, 0x00000007, 0x00000000, 0x00000009, 0x00000001, 0x00000000,
0x00000004, 0x00000008, 0x00000000, 0x00000000, 0x00000000, 0x00000006, 0x00000001, 0x00000000,
0x00000000, 0x00000000, 0x00000004, 0x00000007, 0x00000000, 0x00000000, 0x00000000, 0x00000003,
0x00000002, 0x00000007, 0x00000000, 0x00000000, 0x00000000, 0x00000006, 0x00000000, 0x00000008,
0x00000006, 0x00000003, 0x00000000, 0x00000000, 0x00000000, 0x00000004, 0x00000000, 0x00000000,
0x00000002, 0x00000000, 0x00000007, 0x00000004, 0x00000000, 0x00000006, 0x00000003, 0x00000000,
0x00000003, 0x00000000, 0x00000004, 0x00000000, 0x00000000, 0x00000002, 0x00000000, 0x00000000,
0x00000000]
if solve_sudoku(sudoku_board):
for i in range(9):
row = sudoku_board[i * 9:(i + 1) * 9]
print(row)
else:
print("无解")

我们可以解出

497513268538426917612987354759164823261839475843275196986351742125748639374692581

这个就是我们的解出来的数独,但是由于程序有第一位检测,所以我们需要将第一位的4改我0

因此

097513268538426917612987354759164823261839475843275196986351742125748639374692581

检测

Untitled

可以发现解成功了。

交时对数据md5即可

 评论
目录