game.zip

题目只给了一个 dis python 的字节码 代码长度不算长 可以通过逆向分析 写出主要逻辑

根据顺序 换了下 dis代码

# Python 2.7
# Embedded file name: game.py

   1       0  LOAD_CONST               249
           3  LOAD_CONST               91
           6  LOAD_CONST               149
           9  LOAD_CONST               113
          12  LOAD_CONST               16
          15  LOAD_CONST               91
          18  LOAD_CONST               53
          21  LOAD_CONST               41
          24  BUILD_LIST_8          8
          27  STORE_NAME            0  'arr0'   arr0 = [249,91,149,113,16,91,53,41]

   2      30  LOAD_CONST               43
          33  LOAD_CONST               1
          36  LOAD_CONST               6
          39  LOAD_CONST               69
          42  LOAD_CONST               20
          45  LOAD_CONST               62
          48  LOAD_CONST               6
          51  LOAD_CONST               44
          54  LOAD_CONST               24
          57  LOAD_CONST               113
          60  LOAD_CONST               6
          63  LOAD_CONST               35
          66  LOAD_CONST               0
          69  LOAD_CONST               3
          72  LOAD_CONST               6
          75  LOAD_CONST               44
          78  LOAD_CONST               20
          81  LOAD_CONST               22
          84  LOAD_CONST               127
          87  LOAD_CONST               60
          90  BUILD_LIST_20        20
          93  STORE_NAME            1  'arr1'  arr1 = [43,1,6,69,20,62,6,44,24,113,6,35,0,3,6,44,20,22,127,60]

   3      96  LOAD_CONST               90
          99  LOAD_CONST               100
         102  LOAD_CONST               87
         105  LOAD_CONST               109
         108  LOAD_CONST               86
         111  LOAD_CONST               108
         114  LOAD_CONST               86
         117  LOAD_CONST               105
         120  LOAD_CONST               90
         123  LOAD_CONST               104
         126  LOAD_CONST               88
         129  LOAD_CONST               102
         132  BUILD_LIST_12        12
         135  STORE_NAME            2  'arr2'

   5     138  LOAD_CODE                <code_object check0>    
         141  MAKE_FUNCTION_0       0  None
         144  STORE_NAME            3  'check0'

# check0 line 5 of game.py

   6       0  LOAD_GLOBAL           0  'all'     
           3  LOAD_GENEXPR             '<code_object <genexpr>>'
           6  MAKE_FUNCTION_0       0  None
           9  LOAD_FAST             0  's'
          12  GET_ITER
          13  CALL_FUNCTION_1       1  None
          16  CALL_FUNCTION_1       1  None
          19  RETURN_VALUE

# <genexpr> line 6 of game.py

   6       0  LOAD_FAST             0  '.0'
           3  FOR_ITER             32  'to 38'
           6  STORE_FAST            1  'x'
           9  LOAD_GLOBAL           0  'ord'
          12  LOAD_FAST             1  'x'
          15  CALL_FUNCTION_1       1  None
          18  LOAD_GLOBAL           1  'range'
          21  LOAD_CONST               32
          24  LOAD_CONST               128
          27  CALL_FUNCTION_2       2  None
          30  COMPARE_OP            6  in
          33  YIELD_VALUE                     判断所有字符在 32 - 128之间
          34  POP_TOP
          35  JUMP_BACK             3  'to 3'
          38  LOAD_CONST               None
          41  RETURN_VALUE

   8     147  LOAD_CODE                <code_object check1>
         150  MAKE_FUNCTION_0       0  None
         153  STORE_NAME            4  'check1'

         # check1 line 8 of game.py
																								check1()
   9       0  LOAD_GLOBAL           0  'len'
           3  LOAD_FAST             0  's'
           6  CALL_FUNCTION_1       1  None
           9  LOAD_CONST               100
          12  COMPARE_OP            0  <
          15  POP_JUMP_IF_FALSE    58  'to 58'if(len(s)<100):
        return False
          18  LOAD_GLOBAL           0  'len'
          21  LOAD_FAST             0  's'
          24  CALL_FUNCTION_1       1  None
          27  LOAD_GLOBAL           0  'len'
          30  LOAD_FAST             0  's'
          33  CALL_FUNCTION_1       1  None
          36  BINARY_MULTIPLY             a = len(s) * len(s)
          37  LOAD_CONST               777
          40  BINARY_MODULO               a = a%777
          41  LOAD_CONST               233
          44  BINARY_XOR                  a = a^233
          45  LOAD_CONST               513
          48  COMPARE_OP            2  ==
        51_0  COME_FROM            15  '15'
          51  POP_JUMP_IF_FALSE    58  'to 58'
                                         if(a == 513):
        return True  # 32
  10      54  LOAD_GLOBAL           1  'True'
          57  RETURN_END_IF
        58_0  COME_FROM            51  '51'

  12      58  LOAD_GLOBAL           2  'False'
          61  RETURN_VALUE
          62  LOAD_CONST               None
          65  RETURN_VALUE

  14     156  LOAD_CODE                <code_object check2>
         159  MAKE_FUNCTION_0       0  None
         162  STORE_NAME            5  'check2'
# check2 line 14 of game.py
																		check2()
  15       0  LOAD_GLOBAL           0  'ord'
           3  LOAD_FAST             0  's'
           6  LOAD_CONST               0
           9  BINARY_SUBSCR             a = ord(s[0])
          10  CALL_FUNCTION_1       1  None
          13  LOAD_CONST               128
          16  BINARY_MULTIPLY
          17  LOAD_GLOBAL           0  'ord'
          20  LOAD_FAST             0  's'
          23  LOAD_CONST               1
          26  BINARY_SUBSCR            a = a*128 + ord(s[1])
          27  CALL_FUNCTION_1       1  None
          30  BINARY_ADD
          31  LOAD_CONST               128
          34  BINARY_MULTIPLY
          35  LOAD_GLOBAL           0  'ord'
          38  LOAD_FAST             0  's'
          41  LOAD_CONST               2
          44  BINARY_SUBSCR             a = a*128 + ord(s[2])
          45  CALL_FUNCTION_1       1  None
          48  BINARY_ADD
          49  LOAD_CONST               128
          52  BINARY_MULTIPLY
          53  LOAD_GLOBAL           0  'ord'
          56  LOAD_FAST             0  's'
          59  LOAD_CONST               3
          62  BINARY_SUBSCR            a = a*128 + ord(s[3])
          63  CALL_FUNCTION_1       1  None
          66  BINARY_ADD
          67  LOAD_CONST               128
          70  BINARY_MULTIPLY
          71  LOAD_GLOBAL           0  'ord'
          74  LOAD_FAST             0  's'
          77  LOAD_CONST               4
          80  BINARY_SUBSCR           a = a*128 + ord(s[4])
          81  CALL_FUNCTION_1       1  None
          84  BINARY_ADD
          85  LOAD_CONST               128
          88  BINARY_MULTIPLY
          89  LOAD_GLOBAL           0  'ord'
          92  LOAD_FAST             0  's'
          95  LOAD_CONST               5
          98  BINARY_SUBSCR          a = a*128 + ord(s[5])
          99  CALL_FUNCTION_1       1  None
         102  BINARY_ADD
         103  LOAD_CONST               3533889469877L
         106  COMPARE_OP            2  ==
         109  POP_JUMP_IF_FALSE   138  'to 138'
         112  LOAD_GLOBAL           0  'ord'
         115  LOAD_FAST             0  's'
         118  LOAD_CONST               -1
         121  BINARY_SUBSCR
         122  CALL_FUNCTION_1       1  None
         125  LOAD_CONST               125
         128  COMPARE_OP            2  ==
       131_0  COME_FROM           109  '109'
         131  POP_JUMP_IF_FALSE   138  'to 138'
                                      if(a == 3533889469877):
        if(ord(s[-1]==125)):
            return True
    return False
  16     134  LOAD_GLOBAL           1  'True'
         137  RETURN_END_IF
       138_0  COME_FROM           131  '131'

  18     138  LOAD_GLOBAL           2  'False'
         141  RETURN_VALUE
         142  LOAD_CONST               None
         145  RETURN_VALUE

  20     165  LOAD_CODE                <code_object check3>
         168  MAKE_FUNCTION_0       0  None
         171  STORE_NAME            6  'check3'

# check3 line 20 of game.py
													check3()
  21       0  LOAD_GLOBAL           0  'map'
           3  LOAD_GLOBAL           1  'ord'
           6  LOAD_FAST             0  's'
           9  CALL_FUNCTION_2       2  None
          12  STORE_FAST            1  'arr'
                                      arr = map(ord,s)
  22      15  LOAD_FAST             1  'arr'
          18  LOAD_CONST               6
          21  LOAD_CONST               30
          24  LOAD_CONST               3
          27  BUILD_SLICE_3         3
          30  BINARY_SUBSCR
          31  STORE_FAST            2  'a'
                                      **a = arr[slice(6,30,3)]**
  23      34  SETUP_LOOP           62  'to 99'
          37  LOAD_GLOBAL           2  'range'
          40  LOAD_GLOBAL           3  'len'
          43  LOAD_FAST             2  'a'
          46  CALL_FUNCTION_1       1  None
          49  CALL_FUNCTION_1       1  None
          52  GET_ITER
          53  FOR_ITER             42  'to 98'
          56  STORE_FAST            3  'i'
                                        **for i in range(len(a)):**
  24      59  LOAD_FAST             2  'a'
          62  LOAD_FAST             3  'i'
          65  BINARY_SUBSCR
          66  LOAD_CONST               17684
          69  BINARY_MULTIPLY
          70  LOAD_CONST               372511
          73  BINARY_ADD
          74  LOAD_CONST               257
          77  BINARY_MODULO
          78  LOAD_GLOBAL           4  'arr0'
          81  LOAD_FAST             3  'i'
          84  BINARY_SUBSCR
          85  COMPARE_OP            3  !=
          88  POP_JUMP_IF_FALSE    53  'to 53'
                                    **if((a[i] * 17684 + 372511)% 257 != arr0[i]):
            return False**
  25      91  LOAD_GLOBAL           5  'False'
          94  RETURN_END_IF
        95_0  COME_FROM            88  '88'
          95  JUMP_BACK            53  'to 53'
          98  POP_BLOCK
        99_0  COME_FROM            34  '34'

  26      99  LOAD_FAST             1  'arr'
         102  LOAD_CONST               -2
         105  LOAD_CONST               33
         108  LOAD_CONST               -1
         111  BUILD_SLICE_3         3
         114  BINARY_SUBSCR
         115  LOAD_CONST               5
         118  BINARY_MULTIPLY
         119  STORE_FAST            4  'b'
                                     **b = arr[slice(-2,33,-1)] * 5**
  27     122  LOAD_GLOBAL           0  'map'
         125  LOAD_LAMBDA              '<code_object <lambda>>'
         128  MAKE_FUNCTION_0       0  None
         131  LOAD_GLOBAL           6  'zip'
         134  LOAD_FAST             4  'b'
         137  LOAD_FAST             1  'arr'
         140  LOAD_CONST               7
         143  LOAD_CONST               27
         146  SLICE+3
         147  CALL_FUNCTION_2       2  None
         150  CALL_FUNCTION_2       2  None
         153  STORE_FAST            5  'c'
                               c = map(lambda x[0]^x[1],zip(b, arr[7:27]))
# <lambda> line 27 of game.py

  27       0  LOAD_FAST             0  'x'
           3  LOAD_CONST               0
           6  BINARY_SUBSCR
           7  LOAD_FAST             0  'x'
          10  LOAD_CONST               1
          13  BINARY_SUBSCR
          14  BINARY_XOR
          15  RETURN_VALUE
                                 lambda x[0]^x[1],zip(b, arr[7:27])
  28     156  LOAD_FAST             5  'c'
         159  LOAD_GLOBAL           7  'arr1'
         162  COMPARE_OP            3  !=
         165  POP_JUMP_IF_FALSE   172  'to 172'
                                  if c != arr1:
        return False
  29     168  LOAD_GLOBAL           5  'False'
         171  RETURN_END_IF
       172_0  COME_FROM           165  '165'

  30     172  LOAD_CONST               0
         175  STORE_FAST            6  'p'
                                   **p = 0**
  31     178  SETUP_LOOP          105  'to 286'
         181  LOAD_GLOBAL           2  'range'
         184  LOAD_CONST               28
         187  LOAD_CONST               34
         190  CALL_FUNCTION_2       2  None
         193  GET_ITER
         194  FOR_ITER             88  'to 285'
         197  STORE_FAST            3  'i'

  32     200  LOAD_FAST             1  'arr'
         203  LOAD_FAST             3  'i'
         206  BINARY_SUBSCR
         207  LOAD_CONST               107
         210  BINARY_ADD
         211  LOAD_CONST               16
         214  BINARY_DIVIDE
         215  LOAD_CONST               77
         218  BINARY_ADD
         219  LOAD_GLOBAL           8  'arr2'
         222  LOAD_FAST             6  'p'
         225  BINARY_SUBSCR
         226  COMPARE_OP            3  !=
         229  POP_JUMP_IF_TRUE    268  'to 268'
         232  LOAD_FAST             1  'arr'
         235  LOAD_FAST             3  'i'
         238  BINARY_SUBSCR
         239  LOAD_CONST               117
         242  BINARY_ADD
         243  LOAD_CONST               16
         246  BINARY_MODULO
         247  LOAD_CONST               99
         250  BINARY_ADD
         251  LOAD_GLOBAL           8  'arr2'
         254  LOAD_FAST             6  'p'
         257  LOAD_CONST               1
         260  BINARY_ADD
         261  BINARY_SUBSCR
         262  COMPARE_OP            3  !=
       265_0  COME_FROM           229  '229'
         265  POP_JUMP_IF_FALSE   272  'to 272'
                                    for i in range(28, 34):
        if ((arr[i] + 107) // 16) + 77 != arr2[p]:
            return False
        if ((arr[i] + 117) % 16) + 99 != arr2[p + 1]:
            return False
        p += 2
  33     268  LOAD_GLOBAL           9  'false'
         271  RETURN_END_IF
       272_0  COME_FROM           265  '265'

  34     272  LOAD_FAST             6  'p'
         275  LOAD_CONST               2
         278  INPLACE_ADD
         279  STORE_FAST            6  'p'
         282  JUMP_BACK           194  'to 194'
         285  POP_BLOCK
       286_0  COME_FROM           178  '178'

  35     286  LOAD_GLOBAL          10  'True'
         289  RETURN_VALUE

  37     174  LOAD_NAME             7  'raw_input'
         177  CALL_FUNCTION_0       0  None
         180  STORE_NAME            8  'flag'           

  38     183  LOAD_NAME             3  'check0'
         186  LOAD_NAME             8  'flag'
         189  CALL_FUNCTION_1       1  None
         192  POP_JUMP_IF_FALSE   239  'to 239'
         195  LOAD_NAME             4  'check1'
         198  LOAD_NAME             8  'flag'
         201  CALL_FUNCTION_1       1  None
         204  POP_JUMP_IF_FALSE   239  'to 239'
         207  LOAD_NAME             5  'check2'
         210  LOAD_NAME             8  'flag'
         213  CALL_FUNCTION_1       1  None
         216  POP_JUMP_IF_FALSE   239  'to 239'
         219  LOAD_NAME             6  'check3'
         222  LOAD_NAME             8  'flag'
         225  CALL_FUNCTION_1       1  None
       228_0  COME_FROM           216  '216'
       228_1  COME_FROM           204  '204'
       228_2  COME_FROM           192  '192'
         228  POP_JUMP_IF_FALSE   239  'to 239'

  39     231  LOAD_CONST               'ok'
         234  PRINT_ITEM
         235  PRINT_NEWLINE_CONT
         236  JUMP_FORWARD          5  'to 244'

  41     239  LOAD_CONST               'no'
         242  PRINT_ITEM
         243  PRINT_NEWLINE_CONT
       244_0  COME_FROM           236  '236'
         244  LOAD_CONST               None
         247  RETURN_VALUE

全部翻译完

# -*- encoding: utf-8 -*-
from __future__ import print_function
'''
@文件        :game.py
@时间        :2020/04/21 09:18:31
@作者        :0xc4m3l
'''

arr0 = [249,91,149,113,16,91,53,41]
arr1 = [43,1,6,69,20,62,6,44,24,113,6,35,0,3,6,44,20,22,127,60]
arr2 = [90,100,87,109,86,108,86,105,90,104,88,102]

flag = raw_input()
def check0(all):
    # 输入在 32 和 128之间
    pass
def check1(s):
    if(len(s)<100):
        return False
    a = len(s) * len(s)
    a = a%777
    a = a^233
    if(a == 513):
        return True  # 32

def check2(s):
    a = ord(s[0])
    a = a*128 + ord(s[1])
    a = a*128 + ord(s[2])
    a = a*128 + ord(s[3])
    a = a*128 + ord(s[4])
    a = a*128 + ord(s[5])
    if(a == 3533889469877):
        if(ord(s[-1]==125)):
            return True
    return False

def check3(s):
    arr = map(ord,s)
    a = arr[slice(6,30,3)]
    for i in range(len(a)):
        if((a[i] * 17684 + 372511)% 257 != arr0[i]):
            return False
    b = arr[slice(-2,33,-1)] * 5
    c = map(lambda x[0]^x[1],zip(b, arr[7:27]))
    if c != arr1:
        return False
    p = 0
    for i in range(28, 34):
        if ((arr[i] + 107) // 16) + 77 != arr2[p]:
            return False
        if ((arr[i] + 117) % 16) + 99 != arr2[p + 1]:
            return False
        p += 2
# for s in range(100):
#     if (s*s)%777^233==513:
#         print(s)
# 得到长度 39

可以用 check1 退出 flag长度为 39

接下来就是对 代码逆向 求解

check2() 6个数的判断 且每个数 都在 32-128之间 用python 爆破太大

所有用 z3 求解

sol = Solver()
x = Int('x')
x1 = Int('x1')
x2 = Int('x2')
x3 = Int('x3')
x4 = Int('x4')
x5 = Int('x5')
a = x
a = a *128 + x1
a = a *128 + x2
a = a *128 + x3
a = a *128 + x4
a = a *128 + x5
sol.add(x>33,x<128)
sol.add(x1>33,x1<128)
sol.add(x2>33,x2<128)
sol.add(x3>33,x3<128)
sol.add(x4>33,x4<128)
sol.add(x5>33,x5<128)
sol.add((((((x*128+x1)*128+x2)*128+x3)*128+x4)*128+x5) == 3533889469877)
if(sol.check()==sat):
    m = sol.model()
    # print(m)   
# [x5 = 53, x = 48, x4 = 123, x1 = 76, x2 = 97, x3 = 103]

得到 flag 前6位 flag{5 最后一个字符位 }

然后对 check3 进行逆向

第一部分

a = flag[slice(6,30,3)]
# print(a)
for i in range(8):
    for x in range(32,128):
        if (x * 17684 + 372511) % 257 == arr0[i]:
            flag[a[i]] = x

第二部分

b = flag[slice(-2,33,-1)] * 5
c = flag[7:27]

# 37, 36, 35, 34
flag[35] = flag[9]^arr1[2]
flag[36] = flag[12]^arr1[5]
flag[37] = flag[15]^arr1[8]
flag[34] = flag[18]^arr1[11]
for i in range(len(arr1)):
    flag[7+i] = arr1[i] ^ flag[37-(i%4)]
print(flag)

第三部分

arr2 = [90,100,87,109,86,108,86,105,90,104,88,102] *2
p = 0
for i in range(28,34):
    for x in range(32,128):
        if((x+107)//16+77)==arr2[p]:
            if(((x+117)%16+99)==arr2[p+1]):
                print(i,x,p)
                p+=2
                flag[i] = x
                break

print(flag)
print("".join(map(chr,flag)))