提示md5哈希碰撞(并没有用)
照旧ssh ls -al
和上一关差不多,一个可执行文件,一个源码,一个无法读取的flag文件
查看源码
#include <stdio.h>
#include <string.h>
unsigned long hashcode = 0x21DD09EC;
//转换并相加
unsigned long check_password(const char* p){
int* ip = (int*)p;
int i;
int res=;
for(i=; i<; i++){
res += ip[i];
}
return res;
} int main(int argc, char* argv[]){
//至少有一个参数
if(argc<){
printf("usage : %s [passcode]\n", argv[]);
return ;
}
//参数长度必须为20
if(strlen(argv[]) != ){
printf("passcode length should be 20 bytes\n");
return ;
} if(hashcode == check_password( argv[] )){
system("/bin/cat flag");
return ;
}
else
printf("wrong passcode.\n");
return ;
}
分析源码:
将长度为20byte的char型数组转换为int型数组.得到五个整型
(char型为1Byte,int型为4Byte,而且数据是从右向左存储,所以每四个char转换成一个int)
最终要求五个整型数字之和等于0x21DD09EC
解决方法:
理论上有无数种组合,方便起见这里我们设置四组都是相同的’0x02020202’,最后一组算出来是:
>>> hex(0x21dd09ec-0x02020202*4)
'0x19d501e4'
所以反序输入应该为0xe4 0x01 0xd5 0x19
由于有非可见字符串,我们无法手动从终端输入,利用python进行输入:
python -c 'print 4*"\x02\x02\x02\x02"+"\xe4\x01\xd5\x19"' | xargs ./col
操作:
flag: daddy! I just managed to create a hash collision
完毕
附:
char型数组转换为int型数组:
例如我们构造了char型数组abcdefgh,即传入了四个char:0xab、0xcd、0xef、0xgh,转换成int后对应的数值变成0xghefcdab,(小端存储)
然后一共构造了5组这样的0xghefcdab进行求和最后的结果为0x21DD09EC
python -c (command):
Execute the Python code in command. command can be one or more statements separated by newlines, with significant leading whitespace as in normal module code.
If this option is given, the first element of
sys.argv
will be"-c"
and the current directory will be added to the start ofsys.path
(allowing modules in that directory to be imported as top level modules).
xargs命令:
xargs是给命令传递参数的一个过滤器.通常情况下,xargs从管道或者stdin中读取数据.
xargs的默认命令是echo,这意味着数据将会包含换行和空白,不过通过xargs的处理,换行和空白将被空格取代。