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 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169
| import copy import hashlib
map_table = [[17, 0],[12, 10],[3, 11],[15, 9],[13, 18],[4, 10],[12, 10],[14, 16],[3, 7],[19, 14],[10, 11],[0, 15],[16, 11],[0, 16],[13, 3],[17, 12],[15, 3],[16, 14],[3, 19],[13, 17],[18, 9],[10, 17],[9, 8],[12, 4],[6, 3],[3, 11],[3, 6],[16, 5],[0, 1],[7, 4],[16, 10],[13, 7],[4, 19],[10, 8],[4, 13],[0, 12],[6, 15],[16, 7],[16, 6],[5, 16],[0, 9],[1, 12],[10, 12],[2, 9],[10, 8],[6, 15],[18, 13],[19, 10],[10, 0],[18, 11],[6, 4],[17, 12],[12, 19],[10, 9],[14, 4],[2, 16],[2, 3],[18, 15],[5, 14],[8, 4],[1, 15],[10, 13],[15, 4],[18, 1],[11, 9],[1, 19],[16, 16],[6, 14],[15, 1],[1, 13],[11, 13],[5, 4],[0, 13],[13, 18],[17, 7],[14, 4],[10, 12],[10, 6],[2, 18],[15, 9],[8, 7],[6, 4],[4, 7],[18, 3],[8, 18],[16, 1],[15, 14],[9, 16],[2, 4],[10, 3],[6, 13],[10, 3],[17, 11],[6, 2],[8, 19],[8, 16],[16, 9],[18, 6],[16, 10],[13, 17],[3, 2],[19, 19],[6, 18],[10, 5],[0, 16],[14, 16],[16, 4],[14, 7],[6, 9],[2, 17],[18, 16],[3, 15],[17, 12],[4, 13],[5, 4],[8, 14],[16, 9],[19, 17],[16, 14],[1, 1],[9, 0],[12, 15],[18, 1],[6, 2],[9, 18],[15, 7],[9, 13],[8, 7],[9, 8],[12, 6],[19, 18],[6, 8],[14, 1],[19, 18],[8, 10],[1, 5],[10, 1],[12, 3],[5, 16],[4, 11],[13, 1],[8, 1],[0, 9],[2, 10],[2, 12],[14, 3],[18, 7],[11, 17],[7, 1],[3, 13],[7, 13],[18, 10],[16, 2],[11, 11],[9, 8],[2, 9],[3, 6],[1, 5],[10, 5],[5, 18],[17, 16],[15, 1],[1, 1],[3, 8],[5, 19],[16, 8],[13, 19],[1, 14],[0, 8],[4, 13],[2, 6],[19, 2],[16, 3],[11, 12],[2, 17],[1, 9],[13, 14],[14, 13],[14, 12],[3, 13],[5, 3],[5, 2],[18, 6],[13, 11],[1, 14],[11, 4],[12, 17],[4, 1],[1, 2],[17, 11],[9, 4],[2, 17],[9, 3],[19, 17],[11, 17],[2, 12],[7, 18],[18, 19],[17, 3],[14, 8],[14, 17],[0, 4],[7, 18],[8, 2],[17, 7],[7, 12],[15, 10],[9, 0],[0, 14],[15, 19],[9, 8],[9, 1],[10, 8],[19, 11],[0, 9],[5, 8],[10, 13],[0, 9],[2, 12],[7, 13],[7, 11],[18, 13],[16, 4],[2, 8],[3, 16],[17, 9],[3, 0],[11, 12],[16, 0],[13, 10],[1, 14],[13, 1],[14, 9],[6, 19],[14, 8],[1, 2],[6, 17],[17, 16],[16, 18],[15, 12],[15, 8],[5, 17],[3, 14],[0, 13],[3, 3],[11, 16],[17, 10],[2, 6],[6, 6],[19, 19],[15, 18],[19, 5],[11, 6],[12, 7],[14, 7],[2, 16],[1, 16],[8, 10],[15, 9],[12, 12],[16, 0],[18, 14],[8, 18],[16, 3],[6, 15],[14, 19],[1, 5],[4, 10],[6, 18],[16, 1],[3, 12],[18, 4],[8, 16],[5, 15],[5, 18],[16, 1],[19, 8],[4, 10],[18, 6],[16, 16],[9, 9],[3, 16],[7, 2],[5, 14],[19, 12],[16, 10],[3, 16],[12, 8],[7, 13],[8, 6],[3, 9],[19, 16],[19, 19],[11, 13],[6, 5],[1, 9],[17, 15],[14, 14],[7, 8],[1, 15],[13, 5],[16, 5],[14, 0],[7, 12],[1, 3],[10, 2],[5, 9],[18, 6],[14, 16],[15, 0],[1, 19],[8, 6],[12, 14],[4, 14],[11, 4],[0, 18],[2, 16],[1, 8],[16, 15],[3, 8],[3, 5],[13, 19],[1, 14],[15, 1],[2, 0],[10, 1],[3, 2],[0, 15],[7, 2],[4, 14],[8, 9],[2, 0],[12, 10],[13, 6],[8, 6],[12, 12],[5, 16],[16, 13],[9, 14],[12, 19],[16, 14],[18, 10],[16, 3],[9, 16],[18, 6],[10, 16],[2, 12],[0, 11],[12, 11],[10, 16],[8, 17],[15, 5],[3, 3],[12, 8],[19, 2],[9, 14],[8, 14],[11, 9],[16, 13],[3, 10],[16, 2],[15, 3],[5, 13],[1, 13],[2, 6],[0, 0],[2, 19],[11, 9],[0, 11],[15, 4],[9, 13],[0, 0],[2, 14],[7, 4],[15, 10],[15, 15],[7, 16],[18, 6],[16, 11],[1, 4],[13, 7],[14, 3],[7, 13],[4, 9],[9, 16],[0, 13],[0, 0],[15, 3],[9, 8],[12, 14],[0, 2],[16, 8],[5, 1],[7, 15],[12, 18],[12, 14],[3, 7],[0, 13],[19, 10],[3, 14],[19, 17],[3, 4],[11, 14],[2, 1],[7, 4],[9, 2],[4, 6],[10, 14],[15, 0],[10, 17],[2, 16],[11, 2],[10, 18],[2, 2],[5, 7],[7, 10],[0, 2],[13, 3],[4, 1],[3, 1],[14, 7],[11, 10],[3, 2],[10, 7],[1, 6],[8, 0],[19, 18],[10, 12],[3, 19],[5, 7],[18, 15],[16, 19],[0, 9],[5, 11],[17, 5],[8, 15],[19, 17],[17, 13],[5, 1],[3, 17],[11, 18],[4, 3],[6, 19],[3, 15],[14, 11],[0, 2],[3, 11],[19, 19],[5, 11],[11, 17],[3, 12],[0, 3],[14, 1],[3, 19],[1, 8],[17, 7],[8, 10],[7, 0],[2, 17],[8, 17],[7, 14],[3, 13],[18, 11],[3, 0],[17, 15],[12, 7],[2, 15],[16, 9],[14, 7],[18, 16],[5, 18],[17, 0],[9, 14],[16, 15],[2, 16],[4, 17],[17, 3],[3, 10],[11, 10],[8, 9],[18, 2],[7, 15],[18, 8],[3, 9],[13, 9],[0, 0],[15, 4],[14, 18],[11, 0],[11, 2],[7, 5],[16, 11],[2, 6],[15, 3],[16, 13],[7, 6],[10, 11],[12, 8],[19, 3],[5, 7],[9, 12]] Point_idx = 0 """ & : 0: 左 ( : 1: 右 \ : 2: 上 % : 3: 下 """
class Snake: def __init__(self) -> None: self.x = 0 self.y = 0 self.before_direction = 1 # 前一个按过的方向, 初始时是'(', 也就是1 self.shellcode = b""
def init_shellcode(self): self.shellcode = open( r"./SC", "rb" ).read() assert len(self.shellcode) == 1152
def show(self): print( "x: {}, y: {}, before_direction: {}".format( self.x, self.y, self.before_direction ) )
# next_stat: 可能的下一个snake的状态 def checkValid(next_stat): # 不能超出边界 if next_stat.x < 0 or next_stat.x >= 20 or next_stat.y < 0 or next_stat.y >= 20: # [0, 20) return False return True
def UpdateSC(SC, direction): SC = bytearray(SC) if direction == 0: # 左 return bytes(SC[(n + 6) % 1152] for n in range(1152)) elif direction == 1: # 右 return bytes((byte + 30) & 0xFF for byte in SC) elif direction == 2: # 上 return bytes((byte - 102) & 0xFF for byte in SC) elif direction == 3: # 下 return bytes(((byte << 3) | (byte >> 5)) & 0xFF for byte in SC) else: raise ValueError("Invalid direction")
# 得到该状态的下一个可能状态 import copy
def getNextValidState(data): directions = { 0: [(0, -1, 2), (0, 1, 3)], # 当前向左,只能上下 1: [(0, -1, 2), (0, 1, 3)], # 当前向右,只能上下 2: [(-1, 0, 0), (1, 0, 1)], # 当前向上,只能左右 3: [(-1, 0, 0), (1, 0, 1)] # 当前向下,只能左右 }
if data.before_direction not in directions: raise Exception("before_direction error") next_stat_arr = [] for dx, dy, new_direction in directions[data.before_direction]: new_data = copy.deepcopy(data) new_data.x += dx new_data.y += dy if checkValid(new_data): new_data.before_direction = new_direction new_data.shellcode = UpdateSC(new_data.shellcode, new_direction) next_stat_arr.append(new_data) return next_stat_arr
def check_SC_md5(SC): print("start check md5") md5_hex = "9C06C08F882D7981E91D663364CE5E2E" md5 = hashlib.md5(SC).hexdigest().upper() print(md5) return md5 == md5_hex
def solve(data): global Point_idx # 判断是否已到达目标点 if (data.x, data.y) == map_table[Point_idx]: print(f"Eat Point {data.x} {data.y}") # 检查 shellcode 的 MD5 并写入文件 if check_SC_md5(data.shellcode): with open(r"C:\Users\Tree\Downloads\Compressed\强网杯2024\SC_Real", "wb") as f: f.write(data.shellcode) return True Point_idx += 1 return solve(data)
# 递归处理下一个有效状态 return any(solve(next_stat) for next_stat in getNextValidState(data))
## 0: 向上 1: 向下 2: 向左 3: 向右 # move = [(0,1),(0,-1),(1,0),(-1,0)] """ & : 0: 左 ( : 1: 右 \ : 2: 上 % : 3: 下 """ from collections import deque
# 定义方向向量 move = [(-1, 0), (1, 0), (0, -1), (0, 1)]
def Bfs(start_x, start_y, shellcode, initial_direction): queue = deque([(start_x, start_y, 0, shellcode, initial_direction, 1, "1")]) visit = {(0, start_x, start_y, initial_direction): 0} # 使用字典代替三维数组记录状态 while queue: x, y, idx, current_shellcode, current_direction, count, path = queue.popleft() # 检查是否到达目标点 if (x, y) == tuple(map_table[idx]): idx += 1 print(f"到达目标点 {x}, {y}, idx: {idx}, 操作数: {count}, 方向: {current_direction}, 路径: {path}") if check_SC_md5(current_shellcode): with open(r"C:\Users\Tree\Downloads\Compressed\强网杯2024\SC_Real", "wb") as f: f.write(current_shellcode) print("Success!!!!!!") exit() if idx == len(map_table): return count, path # 尝试直行 new_x, new_y = x + move[current_direction][0], y + move[current_direction][1] if 0 <= new_x < 20 and 0 <= new_y < 20: state = (idx, new_x, new_y, current_direction) if visit.get(state, float('inf')) > count: visit[state] = count queue.append((new_x, new_y, idx, current_shellcode, current_direction, count, path)) # 尝试转向 for new_direction in range(4): if new_direction not in [current_direction, current_direction ^ 1]: new_x, new_y = x + move[new_direction][0], y + move[new_direction][1] if 0 <= new_x < 20 and 0 <= new_y < 20: state = (idx, new_x, new_y, new_direction) new_count = count + 1 if visit.get(state, float('inf')) > new_count: visit[state] = new_count new_shellcode = UpdateSC(current_shellcode, new_direction) new_path = path + chr(new_direction + ord('0')) queue.append((new_x, new_y, idx, new_shellcode, new_direction, new_count, new_path)) return None, None # 没找到路径
if __name__ == "__main__": snake_data = Snake() snake_data.init_shellcode() result = Bfs(10, 10, snake_data.shellcode, 1) if result: min_count, best_path = result print(f"找到最短路径!操作数: {min_count}\n路径: {best_path}") else: print("未找到有效路径")
import sys sys.setrecursionlimit(10000000)
|