mountain climbing(bugkuctf逆向)

mountain climbing(bugkuctf逆向)

拿到文件,查看有壳在这里插入图片描述
脱壳后发现还有壳,换个软件试试
在这里插入图片描述在这里插入图片描述
脱壳成功,无法直接运行,拖到od里
在这里插入图片描述
随便输入,得到error
在这里插入图片描述

观察字符串应该是直接输出的error字符串
在这里插入图片描述
在od里跳转发现输出为77points
在这里插入图片描述

观察主函数,输入一个字符串,进行循环判断,其中points是累加的随机生成数,写一个c程序查看

在这里插入图片描述在这里插入图片描述
因为rand为伪随机函数,每次生成随机数相同,那么,我们需要保证输入的字符串经过处理后为L与R可见若为L执行第一个累加,若为R进行第二个累加,两个累加对于对于j处理不同,总体来说为20行每行取一个相加,整体右平移

修改源码得到这个,通过观察并不能得到应该怎么做
在这里插入图片描述
再次对main函数进行观察发现在进行判断前,执行了一个函数,猜测其为对字符串的处理,进入看看
在这里插入图片描述这段代码分析不出什么
在这里插入图片描述
分析很长时间,只得到进行了循环,还有异或操作,无果

放到od里再跑一下,因为主函数里使用的字符串为输入的字符串,地址没有变化,下断点到执行判断条件的时候,查看堆栈里的数据。输入19个L,19个R分别得到如下,那么对字符串的处理是对偶数位的,且将L替换为H,R替换为V再结合之前对汇编的分析,应该是异或的结果。在这里插入图片描述
在这里插入图片描述

验证一下,发现确实,那么输入的东西就明确了,应该是偶数位的L或R应该用H或V替代在这里插入图片描述

尝试一下,确实可行,剩下来需要确定,输入字符串是什么

再次观察代码,从全部可取情况选出最大值并不现实,输入一共十九个字符,决定了第2-20行的累加操作,对于机器来说,因为每次循环只有两个可选值,我们便将这些值大的加起来,附上c语言源码在这里插入图片描述再次观察代码,从全部可取情况选出最大值并不现实,输入一共十九个字符,决定了第2-20行的累加操作,对于机器来说,因为每次循环只有两个可选值,我们便将这些值大的加起来,附上c语言源码

main()
{
char s[20]; 
int a[10000]; 
srand('\f');
for ( int i = 1; i <= 20; ++i )
          {
            for ( int j = 1; j <= i; ++j )a[100*i+j]=rand()%100000;
          }
          for ( int i = 1; i <= 20; ++i )
          {
            for ( int j = 1; j <= i; ++j )cout<<a[100*i+j]<<' ';
            cout<<endl;
          }
          int S=a[101];
          int m=1;
          int n=0;
          for(int i=2;i<=20;i++)
  {
          if(a[100*i+m]>a[100*i+m+1])
          {
                  s[n]='L';
                  S=S+a[100*i+m];
                  
          }
          else
{
s[n] ='R';
m++;
S=S+a[100*i+m+1];
          }
n++; 
}
for(int i=1;i<=17;i+=2)
{
char p=s[i];
s[i]=char((int)p^4);
} 
  cout<<S<<endl<<s; 
}

在这里插入图片描述
最后出现乱码原因不知,但前19位是正确的,这个就是flag

发布了5 篇原创文章 · 获赞 2 · 访问量 145

猜你喜欢

转载自blog.csdn.net/m0_46583304/article/details/105441336