BUUCTF [Zer0pts2020]easy strcmp

两个考点:

假的strcmp 实则调用的是其他的函数

用C实现反汇编中的_QWORD等

其实关于第一个考点
表层分析:
image
这个肯定不是flag strcmp也是看似正常的extern strcmp
我们在左边的函数列表中逐一查看
image
只有这个函数有变换的作用
image
深层分析:
在init()函数中
image
可以发现

for ( i = 0LL; i != v4; ++i )
      ((void (__fastcall *)(_QWORD, __int64, __int64))*(&funcs_889 + i))(a1, a2, a3);

这是从&func_889开始调用了一系列函数
找到funcs_889的位置
image
逐一查看 在sub_795中
image
终于看到 strcmp函数的位置被修改为了qword_201090
跟进查看 off_201028
image
正是 strcmp在plt表中的位置 然后被修改为了sub_6EA
所以调用strcmp实际上调用的是sub_6EA



然后可以查看到qword_201060是5个64位16进制数
这里如果用python写的话很容易错也不好写 因为涉及到了字符串转_QWORD后运算
思路就是 最后的qword_201090肯定是比较判断 而我们已知a2 所以将
字符串 "zer0pts{********CENSORED******.}" 8位8位的加回去就可以了

第二个考点 C关于_DWORD这些的处理方法:

#include<bits/stdc++.h>
using namespace std;
int main(){
	char p[] = "zer0pts{********CENSORED********}";
	uint64_t qword_202060[] = {0, 0x410A4335494A0942, 0x0B0EF2F50BE619F0, 0x4F0A3A064A35282B, 0};
	for(int j=0;j<5;j++)
		*(uint64_t *)&(p[8*j]) += qword_202060[j];
	cout<<p;
}

C中 _QWORD等价于 uint64_t (__int64也可以)
这里不直接写 p[8*j]是因为要将字符串转成 __int64
所以这里用指针的形式写
最后得到flagimage

posted @ 2023-09-30 12:43  N0zoM1z0  阅读(268)  评论(0编辑  收藏  举报