C:\Users\13964\Desktop\Misc\bkcrack>bkcrack.exe -C CrackM3.zip -c flag.exe -p mingwen -o 64 bkcrack 1.7.0 - 2024-05-26 [17:16:28] Z reduction using 56 bytes of known plaintext 100.0 % (56 / 56) [17:16:29] Attack on 140645 Z values at index 71 Keys: 60101051 4cba82cb 48eac20c 33.4 % (47010 / 140645) Found a solution. Stopping. You may resume the attack with the option: --continue-attack 47010 [17:16:51] Keys 60101051 4cba82cb 48eac20c
C:\Users\13964\Desktop\Misc\bkcrack>bkcrack.exe -C CrackM3.zip -c flag.exe -k 60101051 4cba82cb 48eac20c -d flag_decrypted.exe bkcrack 1.7.0 - 2024-05-26 [17:18:08] Writing deciphered data flag_decrypted.exe Wrote deciphered data (not compressed).
这个二维码实际上可以直接扫描,直接扫描二维码可能会得到提示信息 There is no password here.,只要换个角度再扫扫,就能得到 ZIP 码 base64_15_n0t_3ncrypt10n 原理是正常的二维码天生设计成360°全方向可扫 但是这幅对二维码做了特殊处理 核心是破坏或利用二维码的方向判定机制
返回: 序号整数(0-14);如果不是SA模式,返回 None """ n = len(matrix) # QR 码矩阵边长(模块数) bits = [] # 收集去掩码后的原始位 coords = [] # 读取坐标列表
# 从右下角开始,沿最右边两列向上收集坐标 # QR 码数据读取是以"两列为一组"的zigzag方式 # 我们简化处理:只读最右边两列,对于SA Header已经足够 r = n - 1 c = n - 1 while len(coords) < 32 and r > 0: coords.extend([(r, c), (r, c - 1)]) r -= 1
# 逐位读取,进行去掩码处理 for r, c in coords[:32]: raw_val = int(matrix[r][c]) # 读取原始矩阵值(已被掩码处理过) m = get_mask_bit(r, c, mask) # 判断该位置掩码是否为1
# 去掩码:如果掩码为1,翻转该位;否则保持不变 bit = (raw_val ^ 1) if m else raw_val bits.append(str(bit))
# ── Step 1:找到网格格子大小 ────────────────────────────────────────── # 寻找能同时整除图片宽和高的所有候选格子尺寸 divs = [d for d in range(40, min(h, w) + 1) if h % d == 0 and w % d == 0] cell_size = 0
for d in divs: # 取左上角第一个格子,加上10像素白边,尝试识别 tile = np.pad(arr[0:d, 0:d], 10, constant_values=255) if zxingcpp.read_barcodes(tile): cell_size = d break
if cell_size == 0: # 找不到网格,当作单个大QR码直接识别 print(" 未找到网格,尝试整图识别...") res = zxingcpp.read_barcodes(arr) return res[0].bytes if res else None
if not res_list: print(f" 格子({r},{c}): 识别失败!") continue
res = res_list[0] # 取第一个识别结果
# ── Step 3:提取 SA 序号 ────────────────────────────────────── seq_idx = -1 try: # 从 extra 字段获取版本和掩码信息 meta = {str(k): v for k, v in res.extra.items()} \ if hasattr(res, 'extra') else {}
version = int(meta.get('Version', 1)) mask = int(meta.get('DataMask', 0))
# 读取 flag.txt 文件 with open('flag.txt', 'r') as f: data = f.read()
# 提取所有 (R,G,B) 元组,注意转义括号 pixels = re.findall(r'\((\d+),(\d+),(\d+)\)', data) if not pixels: print("❌ 未找到任何像素数据!请检查 flag.txt 格式是否为 (R,G,B);...") exit()
pixels = [(int(r), int(g), int(b)) for r, g, b in pixels] total = len(pixels) print(f"✅ 成功加载 {total} 个像素")
# 如果像素数为 0,退出 if total == 0: print("❌ 像素数量为 0,无法生成图像。") exit()
# 尝试找出合适的宽高:优先选择宽 >= 高,且宽高比在 0.5 ~ 2.0 之间(避免太窄或太高) candidates = [] sqrt_n = int(math.isqrt(total)) # 从 sqrt(total) 向下和向上搜索因数 for w in range(sqrt_n, 0, -1): if total % w == 0: h = total // w ratio = w / h if 0.5 <= ratio <= 2.0: # 合理比例 candidates.append((w, h)) if len(candidates) >= 3: break
# 如果没找到合适比例,尝试补白成方形 if not candidates: print("⚠️ 未找到理想比例的尺寸,将使用方形图像(可能补白)") size = math.isqrt(total) if size * size < total: size += 1 new_total = size * size pixels.extend([(255, 255, 255)] * (new_total - total)) width = height = size else: # 选最接近正方形的那个(即 w 和 h 差值最小) best = min(candidates, key=lambda wh: abs(wh[0] - wh[1])) width, height = best print(f"🔍 选择尺寸: {width} x {height} (比例: {width/height:.2f})")
def find_runs(binary_array): runs = [] start = None for i, val in enumerate(binary_array): if val and start is None: start = i elif not val and start is not None: runs.append((start, i - 1)) start = None if start is not None: runs.append((start, len(binary_array) - 1)) return runs
def load_image(): if not IMAGE_FILE.exists(): raise SystemExit(f"❌ 找不到图片: {IMAGE_FILE}\n请确保 'shsolver.jpg' 和脚本在同一目录。") print(f"[+] 加载图像: {IMAGE_FILE}") return Im.open(IMAGE_FILE).convert("L")
if not templates: templates.append(binary_pattern) indices_list.append([(ri, ci)]) continue
distances = [np.count_nonzero(binary_pattern != t) for t in templates] min_dist = min(distances) if min_dist <= CLUSTER_DISTANCE: best_idx = distances.index(min_dist) indices_list[best_idx].append((ri, ci)) else: templates.append(binary_pattern) indices_list.append([(ri, ci)])
return templates, indices_list
def determine_hierarchy(rows_patterns, labels): for perm in it.permutations(labels): rank_map = {icon: rank for rank, icon in enumerate(perm)} valid = True for pattern in rows_patterns: prev_rank = -1 for icon in pattern: curr_rank = rank_map[icon] if prev_rank != -1 and curr_rank < prev_rank: valid = False break prev_rank = curr_rank if not valid: break if valid: return perm return None
# 4. 按频率分配临时标签 A(高频) → D(低频) freq_order = sorted(range(4), key=lambda i: len(coords_list[i]), reverse=True) labels = ["A", "B", "C", "D"] coord_to_label = {} for idx, cid in enumerate(freq_order): for coord in coords_list[cid]: coord_to_label[coord] = labels[idx]
# 5. 构建每行图标序列 row_patterns = [] for ri in range(len(row_ranges)): seq = [coord_to_label[(ri, ci)] for ci in range(len(col_ranges)) if (ri, ci) in coord_to_label] row_patterns.append(seq)
# 6. 确定正确顺序 order = determine_hierarchy(row_patterns, labels) if not order: raise SystemExit("❌ 无法确定图标层级顺序。") print(f"[+] 图标层级(高→低): {order}")
============================================================ ✅ 完整解码文本如下(共 25 行): ============================================================ New York is 3 hours ahead of California, but it does not make California slow. Someone graduated at the age of 22, but waited 5 years before securing a good job! Someone became a CEO at 25, and died at 50. While another became a CEO at 50, and lived to 90 years. Here is your gift (please remove all spaces): fTFhcF 9MdT FQM TNoX0Ff ckV0VVB tT2Nf UlU weV8z S0BNe 0ZUQ0hT Someone is still single, while someone else got married. Obama retires at 55, but Trump starts at 70. Absolutely everyone in this world works based on their Time Zone. People around you might seem to go ahead of you, some might seem to be behind you. But everyone is running their own RACE, in their own TIME. Don't envy them or mock them. They are in their TIME ZONE, and you are in yours! Life is about waiting for the right moment to act. So, RELAX. You're not LATE. You're not EARLY. You are very much ON TIME, and in your TIME ZONE Destiny set up for you. ============================================================