欢迎来到尧图网

客户服务 关于我们

您的位置:首页 > 文旅 > 八卦 > Nssctf.reverse 动态调试

Nssctf.reverse 动态调试

2025/2/25 8:46:57 来源:https://blog.csdn.net/m0_73889365/article/details/145834196  浏览:    关键词:Nssctf.reverse 动态调试

1、[BJDCTF 2020]Easy

考点:keypatch
题解:
方法1:动态调试
(1)分析main函数发现并没啥用;但是发现_ques函数的结果就是flag;于是修改main函数的EIP;让他跳转执行_ques函数;反正main函数也没啥用;首先找到_ques函数地址
在这里插入图片描述

(2)然后在main 函数下个断点;开启调试
在这里插入图片描述
随便修改一个call指令的EIP地址;让去执行_ques函数;修改call _time;右键直接keypatch
在这里插入图片描述
然后f8单步调试;拿到flag结束 flag{HACKIT4FUN}在这里插入图片描述
方法2:静态分析
(1)直接定位_ques函数;然后将代码复制出来运行!

2、[CISCN 2022 东北]easycpp

考点:动态调试 逆向分析
题解:
(1)分析main函数发现对用户输入的内容进行循环异或;然后与v9数组中的内容进行比较;那我们可以调试拿到加密数组的内容;然后逆向还原;先断点调试
在这里插入图片描述
提取bufer2加密数组的内容:首先要输入38长度的内容
在这里插入图片描述
(2)逆向主函数;还原加密数组:main函数非常简单:就是每次选取4的字符;然后第一个与第二个异或;第二个与第三个异或;第三个与第四个异或;那么还原就是从尾部开始逆着异或就行

data=[ 0x0A, 0x0B, 0x7D, 0x2F, 0x7F, 0x67, 0x65, 0x30, 0x63, 0x60,0x37, 0x3F, 0x3C, 0x3F, 0x33, 0x3A, 0x3C, 0x3B, 0x35, 0x3C,0x3E, 0x6C, 0x64, 0x31, 0x64, 0x6C, 0x3B, 0x68, 0x61, 0x62,0x65, 0x36, 0x33, 0x60, 0x62, 0x36, 0x1C, 0x7D]
print(len(data))
for i in range(34, -1, -1):data[i+2] ^= data[i+3]data[i+1] ^= data[i+2]data[i] ^= data[i+1]
for i in range(len(data)):print(chr(data[i]), end="")

3、[HUBUCTF 2022 新生赛]help

考点:动态调试;迷宫
题解:
(1)首先肯定就是动态调试找到迷宫
在这里插入图片描述
(2)然后找到是如何走迷宫的函数:然后使用DFS手搓就行
迷宫解密就是w:向上 s:向下 a:向左 d:向右 迷宫里的0是我们要移动的路线,1是不能走的

import numpy as np
import randomdef generate_maze(rows, cols):maze = np.zeros((rows, cols), dtype=np.int8)stack = []direction = [(-2, 0), (2, 0), (0, -2), (0, 2)]  # 上下左右stack.append((1, 1))while stack:(x, y) = stack[-1]maze[x][y] = 1neighbors = []for (dx, dy) in direction:nx, ny = x + dx, y + dyif 0 < nx < rows-1 and 0 < ny < cols-1:if maze[nx][ny] == 0:maze[nx-dx//2][ny-dy//2] = 1stack.append((nx, ny))else:stack.pop()return mazedef print_maze(maze):for row in maze:print(' '.join('#' if cell == 0 else ' ' for cell in row))print('\n')# 根据提供的迷宫布局生成迷宫
rows, cols = 16, 21
maze_layout = [[1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 1, 1, 0],[1, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1],[0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1],[1, 0, 0, 1, 1, 0, 1, 1, 0, 0, 0, 1, 0, 1, 1, 1],[1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1],[1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 1],[1, 0, 0, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1],[1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1],[1, 0, 0, 0, 1, 1, 1, 1, 1, 0, 1, 1, 0, 1, 0, 1],[0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0],[1, 1, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1],[1, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1],[1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0],[1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1],[1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1]
]
# 生成迷宫
maze = generate_maze(rows, cols)
# 打印迷宫
print_maze(maze)

得到路径:wwdddwwwaaawwwwwwwwwddddssssdddssdsssssssdddwwwwddsssd;最终得到flag
NSSCTF{a8622109e2fb1296e06d5eed6f78f954}

4、[GDOUCTF 2023]Tea

考点:tea
题解:
方法1:静态分析
方法2:动态调试

5、[HNCTF 2022 Week1]CrackMe

考点:动态调试
题解:可以用onlydgb 和xdbg调试;此处使用ida32调试
(1)分析main函数
就是一个简单的验证比较函数;用户输入string1;然后进过处理与string2比较;说明string2就是程序正确的注册码;直接下断点进行调试
在这里插入图片描述
成功得到string2的值
在这里插入图片描述

6、[SWPUCTF 2022 新生赛]贪吃蛇

考点:keypatch
题解:
(1)首先定位核心代码

if (isFlag)
{decode_flag(&t_flag);strcat(s_flag, &t_flag);gameEndmenu(v18, s_flag);
}
else
{gameEndmenu(v18, flag);
}
result = _getch();

分析就是到达指定的分数之后会跳转到 gameEndmenu函数输出flag;我们直接在跳转的下手;不需要满足分数就可以获取FLAG;所以按TAB先看一下汇编代码
在这里插入图片描述
jz指令在这里就是当score满足条件是;输出;但是我们修改为jnz反向跳转就可以不用满足score;keypatch之后直接调试拿到flag
在这里插入图片描述

7、[GDOUCTF 2023]doublegame

考点:patch 迷宫题
题解:The flag is HZCTF{md5(path)+score}
(1)首先看第一个游戏:是贪吃蛇;要求分数大于13371337(现在知道了分数)
在这里插入图片描述
(2)第二个游戏:就是一个迷宫题目(找出路径)

maze = ['0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0',' ', '0', ' ', '0', ' ', '0', ' ', ' ', ' ', ' ', ' ', '0', ' ', ' ', ' ', ' ', ' ', '0', ' ', '0', '0', ' ','0', ' ', '0', ' ', '0', '0', '0', '0', '0', ' ', '0', '0', '0', '0', '0', ' ', '0', ' ', '0', '0', ' ', '0',' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', '0', ' ', '0', '0', ' ', '0', '0','0', ' ', '0', '0', '0', ' ', '0', ' ', '0', '0', '0', ' ', '0', ' ', '0', ' ', '0', '0', ' ', '0', ' ', ' ',' ', ' ', ' ', '0', ' ', '0', ' ', '0', ' ', ' ', ' ', '0', ' ', '0', ' ', '0', '0', ' ', '0', ' ', '0', ' ','0', '0', '0', '0', '0', ' ', '0', '0', '0', ' ', '0', '0', '0', ' ', '0', '0', ' ', '0', ' ', '0', ' ', ' ',' ', ' ', ' ', '0', ' ', ' ', ' ', '0', ' ', '0', ' ', ' ', ' ', ' ', '0', ' ', '0', '0', '0', ' ', '0', ' ','0', ' ', '0', '0', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', '0', ' ', ' ', ' ', ' ', ' ', '0', ' ', '0',' ', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', '0', ' ', '0', '0', '0', '0', '0', ' ', '0', '0','0', ' ', '0', '0', '0', ' ', '0', ' ', '0', ' ', '0', '0', ' ', ' ', ' ', ' ', ' ', '0', ' ', ' ', ' ', ' ',' ', ' ', ' ', '0', ' ', ' ', ' ', '0', ' ', '0', '0', '0', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', '0','0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', ' ', ' ',' ', '0', ' ', '0', ' ', '0', ' ', '0', '0', ' ', '0', '0', '0', '0', '0', '0', '0', ' ', '0', ' ', '0', '0','0', ' ', '0', '0', '0', '0', '0', ' ', ' ', ' ', ' ', '0', ' ', ' ', ' ', '0', ' ', '0', ' ', ' ', ' ', ' ',' ', ' ', ' ', ' ', ' ', '0', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', ' ', '0', '0', '0', '0', '0', '0','0', '0', '0', '0', '0', '0', ' ', '0', ' ', '0', ' ', '0', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',' ', ' ', ' ', '0', '0', '0', '0', ' ', '0', ' ', '0', '0', '0', '0', '0', ' ', '0', ' ', '0', '0', '0', ' ','0', '0', '0', '0', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', '0', ' ', '0', ' ', ' ', ' ', '0', ' ', ' ',' ', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0','0']
maze[21 * 7 + 20] = '2'
# maze[x * 21 + y]
def check_point_valid(map, x, y):if (x >= 0) and (x <= 20) and (y >= 0) and (y <= 20):return (map[x * 21 + y] != '0') and ((map[x * 21 + y] == ' ') or (map[x * 21 + y] == '2'))else:return False
def gen_nex(map, x, y):all_dir = []# if check_point_valid(map, x - 1, y, z):# all_dir.append((x - 1, y, z, 'q'))# if check_point_valid(map, x + 1, y, z):# all_dir.append((x + 1, y, z, 'u'))if check_point_valid(map, x + 1, y):all_dir.append((x + 1, y, 's'))if check_point_valid(map, x - 1, y):all_dir.append((x - 1, y, 'w'))if check_point_valid(map, x, y - 1):all_dir.append((x, y - 1, 'a'))if check_point_valid(map, x, y + 1):all_dir.append((x, y + 1, 'd'))return all_dir
def check_success(map, x, y):if map[x * 21 + y] == '2':return Trueelse:return False
def dfs(mapb, x, y, path):map = mapb.copy()if map[x * 21 + y] != '2':map[x * 21 + y] = '0'if check_success(map, x, y):print(path)return Truenext_point = gen_nex(map, x, y)for n in next_point:pathn = path + n[2]dfs(map, n[0], n[1], pathn)
outpus = ""
dfs(maze, 15, 0, outpus)

最终的结果是dddssssddwwwwddssddwwwwwwddddssaassddddwwwwddwwwwddd
NSSCTF{811173b05afff098b4e0757962127eac13371337}

8、[MoeCTF 2022]fake_key

考点:伪随机数 动态调试
题解:
(1)定位核心代码:加密就是加上随机数;然后与key异或;那么我们首先需要获取key
在这里插入图片描述

ELF文件;需要远程调试(怎么调试就不赘述了!);获取到key
在这里插入图片描述
(2)提取加密数据

unsigned char s2[] =
{23,  32,  18,  30,  31,  92,  23,  51, 102,  55, 56,  50, 115,   9,  69,  68,   4,  94,  47,  12, 116,  67,  35,  51,  39,  31,  19,  19,  30
};

(3)获取随机数:And I use random numbers to rot my input, you can never guess them!;是伪随机数

#include<stdio.h>
#include <stdlib.h>
int main()
{for (int j = 0; j < 29; j++)printf("%d,", rand() % 10);
}
//1,7,4,0,9,4,8,8,2,4,5,5,1,7,1,1,5,2,7,6,1,4,2,3,2,2,1,6,8,

(4)最后一步就是根据加密函数对解密函数进行解密:先减去随机数;然后与key异或即可

# 加密后的数据
enflag = [21, 33, 15, 25, 37, 91, 25, 57, 95, 58,59, 48, 116, 7, 67, 63, 9, 90, 52, 12,116, 63, 30, 45, 39, 33, 18, 22, 31]
# 随机数
randed = [1, 7, 4, 0, 9, 4, 8, 8, 2, 4, 5, 5, 1, 7, 1, 1, 5, 2, 7, 6, 1, 4, 2, 3, 2, 2, 1, 6, 8]
# 密钥
key = [121, 117, 110, 122, 104, 49, 106, 117, 110, 84,67, 76, 44, 116, 114, 97, 99, 107, 89, 89,68, 83]
# 解密
for i in range(29):enflag[i] -= randed[i]  # 逆向加法操作enflag[i] ^= key[i % len(key)]  # 逆向异或操作print(chr(enflag[i]), end='')

9、[HNCTF 2022 WEEK2]Try2Bebug_Plus

题解:动态调试
解法1:典型的tea加密;比较麻烦;需要一步一步解密
解法2:动态调试
(1)定位主函数:

int __cdecl main(int argc, const char **argv, const char **envp)
{int i; // [rsp+Ch] [rbp-4h]for ( i = 0; i <= 11; i += 2 ){argv = (const char **)&k;decrypt((char *)&v + 4 * i, &k);}puts("waiting and i will give you flag!");sleep('\'\x10');function(&v, argv);printf("sorry! something wrong!");printf("please find the flag by Debug!");return 0;
}

很简单的一个调试;首先将slepp函数patch掉;然后调试就行(或者将等待时间修改短一点也可以)
在这里插入图片描述

10、[NSSRound#16 Basic]test your Debugger

考点:反调试
题解:
(1)定位main函数;发现反调试函数;然后nop掉
在这里插入图片描述
发现可以指令;cmp;跟进发现flag
在这里插入图片描述
在这里插入图片描述

持续更新中…

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com

热搜词