ISCC re Badcode

这题学习了好多知识。
首先查壳,无壳。然后扔进IDA按F5。
在这里插入图片描述
这些估计是垃圾代码。

在这里插入图片描述这部分就很有意思了,一开始我也以为是垃圾代码,毕竟对输入的v17根本没影响。
但很明显,B60这个函数是接受两个参数的,IDA只识别出来一个参数。
在这里插入图片描述
那就是IDA识别出了点问题,那怎么办呢?
那就对着上图这一行的libname_4函数右击,点击这个:
在这里插入图片描述
就可以正常显示了:
在这里插入图片描述
这样子的话,可以猜测sub_311B60是string的[ ]。
在这里插入图片描述
然后这里是秘钥和密文。注意,这的密钥是小端序的,也就是说把字节拼起来的时候要注意是小端序顺序。(涉及到数组都可以考虑小端序)
在这里插入图片描述

这里的密文也是小端序,但放进去解密的时候要按照IDA反汇编的顺序放,不然解密会出错,等到最后打印字符的时候再按小端序处理。

解密脚本如下:

#include<iostream>
#include<cstring>
#include<algorithm>
#include<cstdio>
#include<cstdlib>
#include<ctime>
using namespace std;
unsigned int cipher[50]=
{
0x2C796E3E,0x3FD7AA48,0x30D01B1D,0x22873528,0xE61567C6,0x207FA2D5
};
unsigned char flag[50];
unsigned char key2[50]="674094872038771148666737";
//这里的是sub_401620生成的v16,把代码拉下来跑一下就可以得到
//至于为什么v16就是随机数生成的这些数字,只能靠猜猜看尝试下了
unsigned int a3[50]=
{
  0x12345678, 0x9ABCDEF0, 0xFEDCBA98, 0x76543210
};

signed main()
{
	int v8=52/6+6;
	unsigned int v9=0;
	//unsigned int delta=0x4786C861;
	unsigned int delta=0x61C88647;
	v9-=delta*v8;
	unsigned int z;
	unsigned int e;
	unsigned int y=cipher[0];
	for(int round=0;round<v8;round++)
	{
		e=(v9>>2)&3;
		for(int i=6-1;i>=0;i--)
		{
			z=cipher[(i-1+6)%6];
			cipher[i]-=(((z^a3[1*(e^i&3)])+(cipher[(i+1)%6]^v9))^(((16*z)^(cipher[(i+1)%6]>>3))+((4*cipher[(i+1)%6])^(z>>5))));
		}
		v9+=delta;
		for(int i=0;i<6;i++)
		{
			printf("%u ",cipher[i]);
		}
		printf("%u\n",v9);
	}
	int len=0;
	for(int i=0;i<6;i++)
	{
		flag[len++]=(cipher[i]>>(0*8))&0xFF;
		flag[len++]=(cipher[i]>>(1*8))&0xFF;
		flag[len++]=(cipher[i]>>(2*8))&0xFF;
		flag[len++]=(cipher[i]>>(3*8))&0xFF;
	}
	for(int i=0;i<len;i++)
	{
		flag[i]^=(key2[i]-'0');
		if(i%2)
		{	
			flag[i]-=2;
		}
		else
		{
			flag[i]+=3;
		}
	}
	printf("%s",flag);
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值