CISCN2021 Reverse--glass

题目下载地址:

https://pan.baidu.com/s/1VqBoQamSxbYXtSeC07wChg 提取码:wbga

拿到题目先用jadx查看主函数.

在这里插入图片描述我们可以发现验证输入的地方主要是在checkFlag的地方。然而在apk的源码中并没有发现相关代码。因此猜测在.so文件中。

在这里插入图片描述
可以看到这里的确加载了一个.so文件。然后我们通过jeb提取出.so文件,拖入ida进行分析。
在这里插入图片描述
在左边的窗口中发现了,验证的函数。直接f5查看伪代码。

在这里插入图片描述
可以看到最后是跟unk_497C进行比较,判断是否正确。但是前面经过了三个函数的处理。点进去分析。
在这里插入图片描述发现了函数中,出现好多次256,猜测是某种加密算法。通过搜索引擎得知。该加密为rc4加密。
在这里插入图片描述
此函数为rc4加密中的初始化。我们跟进下一个函数看一下。
在这里插入图片描述

a2是我们输入的字符串,可以看到这里是将输入的字符进行一个rc4的加密。我们在跟进第三个函数看下。
在这里插入图片描述
这里是将我们输入的值进行rc4加密后,在进行一个异或,最终再跟unk_497C进行比较。那么此时就有了一个解题的思路,因为是逆向分析,所以流程图如下:

在这里插入图片描述
最终代码如下:

#include <iostream>
#include <stdio.h>
#include <cstring>
#include <windows.h>
using namespace std;
unsigned int enc[] = { 0xA3,0x1A ,0xE3 ,0x69 ,0x2F ,0xBB ,0x1A ,0x84 ,0x65 ,0xC2 ,0xAD ,0xAD ,0x9E ,0x96 ,0x05 ,0x02 ,0x1F ,0x8E ,0x36 ,0x4F ,0xE1 ,0xEB
	,0xAF ,0xF0 ,0xEA ,0xC4 ,0xA8 ,0x2D ,0x42 ,0xC7 ,0x6E ,0x3F ,0xB0 ,0xD3 ,0xCC ,0x78 ,0xF9 ,0x98 ,0x3F };
string key = "123456789";
unsigned char S[256];
unsigned char T[256];
void rc4_init()
{
	for (int i = 0; i != 256; i++)
	{
		S[i] = i;
		T[i] = key[i % 8];
	}
	int v9 = 0;
	for (int i = 0; i != 256; i++)
	{
		int middle = S[i];
		v9 = (middle + v9 + T[i]) % 256;
		S[i] = S[v9];
		S[v9] = middle;
	}
}
void rc4_encrpto()
{
	int count = 39;
	int i = 0;
	int v4 = 0;
	int v3 = 0; int v5 = 0;
	int index = 0;
	while (count)
	{
		--count;
		v4 = (v4 + 1) % 256;
		v5 = S[v4];
		v3 = (v3 + S[v4]) % 256;
		S[v4] = S[v3];
		S[v3] = v5;
		enc[index++] ^= S[(v5 + S[v4]) % 256];
	}
}
int main()
{
	int i;
	//a2为flag长度
	int a2 = 39;
	/*
	for ( j = 0; j < a2; j += a4 )
	{
		for ( k = 0; (a4 & ~(a4 >> 31)) != k && j + k < a2; ++k )
		result[k] ^= a3[k];
		result += a4;
	}
	下面的与这个等价
	*/
	for (i = 0; i < a2; i++) {
		enc[i] ^= key[i % 8];

	}
	/*
	for ( i = 0; i < a2; i += 3 )
	{
		v5 = &result[i];
		v6 = result[i + 2];
		v7 = result[i + 1];
		v8 = result[i] ^ v6;
		result[i] = v8;
		v5[2] = v6 ^ v7;
		v5[1] = v7 ^ v8;
	}
	下面的与这个等价
	*/
	for (i = 0; i < a2; i += 3) {
		enc[i + 1] = enc[i + 1] ^ enc[i];
		enc[i + 2] = enc[i + 2] ^ enc[i + 1];
		enc[i] = enc[i + 2] ^ enc[i];
	}
	char v7[256];
	rc4_init();
	rc4_encrpto();
	for (i = 0; i < 39; i++) {
		cout << char(enc[i]);
	}
	cout << endl;
	return 0;

}

结果:
在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 6
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值