【攻防世界】Reverse—— maze writeup

__int64 __fastcall main(int a1, char **a2, char **a3)
{
  __int64 i; // rbx
  int input_c; // eax
  char v5; // bp
  char v6; // al
  const char *v7; // rdi
  unsigned int v9; // [rsp+0h] [rbp-28h] BYREF
  int v10[9]; // [rsp+4h] [rbp-24h] BYREF

  v10[0] = 0;
  v9 = 0;
  puts("Input flag:");
  scanf("%s", &input);
  if ( strlen(&input) != 24 || strncmp(&input, "nctf{", 5uLL) || *(&byte_6010BF + 24) != 125 )
  {
LABEL_22:
    puts("Wrong flag!");
    exit(-1);
  }
  i = 5LL;
  if ( strlen(&input) - 1 > 5 )
  {
    while ( 1 )
    {
      input_c = *(&input + i);
      v5 = 0;
      if ( input_c > 78 )
      {
        if ( (unsigned __int8)input_c == 79 )
        {
          v6 = sub_400650(v10);                 // v10-- > 0
                                                // 
          goto LABEL_14;
        }
        if ( (unsigned __int8)input_c == 111 )
        {
          v6 = sub_400660(v10);                 // v10++ < 8
          goto LABEL_14;
        }
      }
      else
      {
        if ( (unsigned __int8)input_c == 46 )
        {
          v6 = sub_400670(&v9);                 // v9-- > 0
          goto LABEL_14;
        }
        if ( (unsigned __int8)input_c == 48 )
        {
          v6 = sub_400680((int *)&v9);          // v9++ < 8
LABEL_14:
          v5 = v6;
          goto LABEL_15;
        }
      }
LABEL_15:
      if ( !(unsigned __int8)sub_400690(asc_601060, (unsigned int)v10[0], v9) )// a1[v10[0]+8 * v9] == 32 || ==35
        goto LABEL_22;
      if ( ++i >= strlen(&input) - 1 )
      {
        if ( v5 )
          break;
LABEL_20:
        v7 = "Wrong flag!";
        goto LABEL_21;
      }
    }
  }
  if ( asc_601060[8 * v9 + v10[0]] != 35 )
    goto LABEL_20;
  v7 = "Congratulations!";
LABEL_21:
  puts(v7);
  return 0LL;
}

首先,根据下面的代码可知,flag是以“nctf{"开头,”}“结尾,长度是24,也就是我们要推理的字符串长度为24-5-1=18

if ( strlen(&input) != 24 || strncmp(&input, "nctf{", 5uLL) || *(&byte_6010BF + 24) != 125 )
  {
LABEL_22:
    puts("Wrong flag!");
    exit(-1);
  }

从下面的代码可知:当输入字符input_c=79-》v10--;input_c=111-》v10++,input_c=46-》v9--, input_c=48-》v9++,而且v9,v10的取值范围都是【0,8)

 input_c = *(&input + i);
      v5 = 0;
      if ( input_c > 78 )
      {
        if ( (unsigned __int8)input_c == 79 )
        {
          v6 = sub_400650(v10);                 // v10-- > 0
                                                // 
          goto LABEL_14;
        }
        if ( (unsigned __int8)input_c == 111 )
        {
          v6 = sub_400660(v10);                 // v10++ < 8
          goto LABEL_14;
        }
      }
      else
      {
        if ( (unsigned __int8)input_c == 46 )
        {
          v6 = sub_400670(&v9);                 // v9-- > 0
          goto LABEL_14;
        }
        if ( (unsigned __int8)input_c == 48 )
        {
          v6 = sub_400680((int *)&v9);          // v9++ < 8
LABEL_14:
          v5 = v6;
          goto LABEL_15;
        }

只要用户输入的是【79,111,46,48】,LABEL_15一定会被执行。根据下面的代码:asc_601060[v10+v9*8]==35||32

LABEL_15:
      if ( !(unsigned __int8)sub_400690(asc_601060, (unsigned int)v10[0], v9) )// a1[v10[0]+8 * v9] == 32 || ==35
        goto LABEL_22;
      if ( ++i >= strlen(&input) - 1 )
      {
        if ( v5 )
          break;

#########################
__int64 __fastcall sub_400690(__int64 a1, int a2, int a3)
{
  __int64 result; // rax

  result = *(unsigned __int8 *)(a1 + a2 + 8LL * a3);
  LOBYTE(result) = (_DWORD)result == 32 || (_DWORD)result == 35;
  return result;
}

于是,我们可以找出asc_601060中所有等于32或35的位置:

def find_all_positions(lst, element):
    positions = [i for i, x in enumerate(lst) if x == element]
    return positions

asc_601060 = [ 32,  32,  42,  42,  42,  42,  42,  42,  42,  32, 
   32,  32,  42,  32,  32,  42,  42,  42,  42,  32, 
   42,  32,  42,  42,  42,  42,  32,  32,  42,  32, 
   42,  42,  42,  32,  32,  42,  35,  32,  32,  42, 
   42,  42,  32,  42,  42,  42,  32,  42,  42,  42, 
   32,  32,  32,  32,  32,  42,  42,  42,  42,  42, 
   42,  42,  42,  42]

i_35 = find_all_positions(asc_601060,35)
print(i_35)
i_32 = find_all_positions(asc_601060,32)
print(i_32)

结果:

 if ( asc_601060[8 * v9 + v10[0]] != 35 )
    goto LABEL_20;
  v7 = "Congratulations!";

根据上面的代码我们可以知道:因为35在asc_601060的位置是36,所以我们可以知道循环体结束时候v9和v10的所有可能的取值(0,36),(1,28),(2,20),(3,12),(4,4),事实上仅有可能是(4,4),因为v9,v10的取值范围是【0,8)。而(v9,v10)的初始值是(0,0)

综上,我们可以写个程序获取v9和v10在循环的时候可能的取值:

c_values = [0, 1, 9, 10, 11, 13, 14, 19, 21, 26, 27, 29, 33, 34,36,37, 38, 42, 46, 50, 51, 52, 53, 54]  
results = []  
  
for c in c_values:  
    for b in range(0, 8):  
        a = c - 8*b  
        if a >= 0 and a < 8: # a是非负数  
            results.append((a, b))  
  
print(results)

结果:

[(0, 0), (1, 0), (1, 1), (2, 1), (3, 1), (5, 1), (6, 1), (3, 2), (5, 2), (2, 3), (3, 3), (5, 3), (1, 4), (2, 4), (4, 4), (5, 4), (6, 4), (2, 5), (6, 5), (2, 6), (3, 6), (4, 6), (5, 6), (6, 6)]

用1表示可能,0表示不可能,于是有:

for i in range(8):
    for j in range(8):
        c = '0'
        if (j,i) in results:
            c = '1'
        print(c, end='\t')
    print('\n')

结果:

我们可以找到一条由(0,0)到(4,4)的通路,下面黄色数字组成,刚好是18个。

(v9,v10)的坐标是:

(0,0),(0,1)(1,1),(1,2),(1,3),(2,3),(3,3),(3,2),(4,2),(5,2),(6,2),(6,3),(6,4),(6,5),(6,6),(5,6),(4,6),(4,5),(4,4)

根据之前分析得到的:input_c=79-》v10--;input_c=111-》v10++,input_c=46-》v9--, input_c=48-》v9++。所以输入的字符是:

[111,48,111,111,48,48,79,48,48,48,111,111,111,111,46,46,79,79]

也就是

o0oo00O000oooo..OO

所以flag就是:nctf{o0oo00O000oooo..OO}

  • 8
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
,发送类别,概率,以及物体在相机坐标系下的xyz.zip目标检测(Object Detection)是计算机视觉领域的一个核心问题,其主要任务是找出图像中所有感兴趣的目标(物体),并确定它们的类别和位置。以下是对目标检测的详细阐述: 一、基本概念 目标检测的任务是解决“在哪里?是什么?”的问题,即定位出图像中目标的位置并识别出目标的类别。由于各类物体具有不同的外观、形状和姿态,加上成像时光照、遮挡等因素的干扰,目标检测一直是计算机视觉领域最具挑战性的任务之一。 二、核心问题 目标检测涉及以下几个核心问题: 分类问题:判断图像中的目标属于哪个类别。 定位问题:确定目标在图像中的具体位置。 大小问题:目标可能具有不同的大小。 形状问题:目标可能具有不同的形状。 三、算法分类 基于深度学习的目标检测算法主要分为两大类: Two-stage算法:先进行区域生成(Region Proposal),生成有可能包含待检物体的预选框(Region Proposal),再通过卷积神经网络进行样本分类。常见的Two-stage算法包括R-CNN、Fast R-CNN、Faster R-CNN等。 One-stage算法:不用生成区域提议,直接在网络中提取特征来预测物体分类和位置。常见的One-stage算法包括YOLO系列(YOLOv1、YOLOv2、YOLOv3、YOLOv4、YOLOv5等)、SSD和RetinaNet等。 四、算法原理 以YOLO系列为例,YOLO将目标检测视为回归问题,将输入图像一次性划分为多个区域,直接在输出层预测边界框和类别概率。YOLO采用卷积网络来提取特征,使用全连接层来得到预测值。其网络结构通常包含多个卷积层和全连接层,通过卷积层提取图像特征,通过全连接层输出预测结果。 五、应用领域 目标检测技术已经广泛应用于各个领域,为人们的生活带来了极大的便利。以下是一些主要的应用领域: 安全监控:在商场、银行
目标检测(Object Detection)是计算机视觉领域的一个核心问题,其主要任务是找出图像中所有感兴趣的目标(物体),并确定它们的类别和位置。以下是对目标检测的详细阐述: 一、基本概念 目标检测的任务是解决“在哪里?是什么?”的问题,即定位出图像中目标的位置并识别出目标的类别。由于各类物体具有不同的外观、形状和姿态,加上成像时光照、遮挡等因素的干扰,目标检测一直是计算机视觉领域最具挑战性的任务之一。 二、核心问题 目标检测涉及以下几个核心问题: 分类问题:判断图像中的目标属于哪个类别。 定位问题:确定目标在图像中的具体位置。 大小问题:目标可能具有不同的大小。 形状问题:目标可能具有不同的形状。 三、算法分类 基于深度学习的目标检测算法主要分为两大类: Two-stage算法:先进行区域生成(Region Proposal),生成有可能包含待检物体的预选框(Region Proposal),再通过卷积神经网络进行样本分类。常见的Two-stage算法包括R-CNN、Fast R-CNN、Faster R-CNN等。 One-stage算法:不用生成区域提议,直接在网络中提取特征来预测物体分类和位置。常见的One-stage算法包括YOLO系列(YOLOv1、YOLOv2、YOLOv3、YOLOv4、YOLOv5等)、SSD和RetinaNet等。 四、算法原理 以YOLO系列为例,YOLO将目标检测视为回归问题,将输入图像一次性划分为多个区域,直接在输出层预测边界框和类别概率。YOLO采用卷积网络来提取特征,使用全连接层来得到预测值。其网络结构通常包含多个卷积层和全连接层,通过卷积层提取图像特征,通过全连接层输出预测结果。 五、应用领域 目标检测技术已经广泛应用于各个领域,为人们的生活带来了极大的便利。以下是一些主要的应用领域: 安全监控:在商场、银行
目标检测(Object Detection)是计算机视觉领域的一个核心问题,其主要任务是找出图像中所有感兴趣的目标(物体),并确定它们的类别和位置。以下是对目标检测的详细阐述: 一、基本概念 目标检测的任务是解决“在哪里?是什么?”的问题,即定位出图像中目标的位置并识别出目标的类别。由于各类物体具有不同的外观、形状和姿态,加上成像时光照、遮挡等因素的干扰,目标检测一直是计算机视觉领域最具挑战性的任务之一。 二、核心问题 目标检测涉及以下几个核心问题: 分类问题:判断图像中的目标属于哪个类别。 定位问题:确定目标在图像中的具体位置。 大小问题:目标可能具有不同的大小。 形状问题:目标可能具有不同的形状。 三、算法分类 基于深度学习的目标检测算法主要分为两大类: Two-stage算法:先进行区域生成(Region Proposal),生成有可能包含待检物体的预选框(Region Proposal),再通过卷积神经网络进行样本分类。常见的Two-stage算法包括R-CNN、Fast R-CNN、Faster R-CNN等。 One-stage算法:不用生成区域提议,直接在网络中提取特征来预测物体分类和位置。常见的One-stage算法包括YOLO系列(YOLOv1、YOLOv2、YOLOv3、YOLOv4、YOLOv5等)、SSD和RetinaNet等。 四、算法原理 以YOLO系列为例,YOLO将目标检测视为回归问题,将输入图像一次性划分为多个区域,直接在输出层预测边界框和类别概率。YOLO采用卷积网络来提取特征,使用全连接层来得到预测值。其网络结构通常包含多个卷积层和全连接层,通过卷积层提取图像特征,通过全连接层输出预测结果。 五、应用领域 目标检测技术已经广泛应用于各个领域,为人们的生活带来了极大的便利。以下是一些主要的应用领域: 安全监控:在商场、银行
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值