NSSCTF逆向刷题记录

目录

[WUSTCTF 2020]level3

[SWPUCTF 2022 新生赛]upx

[HNCTF 2022 Week1]你知道什么是Py嘛?

[CISCN 2022 东北]easycpp

 [羊城杯 2020]login

 [GDOUCTF 2023]doublegame

 [GDOUCTF 2023]Tea

 [WUSTCTF 2020]Cr0ssfun

 [HNCTF 2022 Week1]CrackMe

[HDCTF 2023]fake_game 

[MoeCTF 2022]Base

 [watevrCTF 2019]Timeout

[WUSTCTF 2020]level3

base64_encode函数

翻转0-9和10-19位置的值

 base64_table[i]数据

 先翻转表,再base换表

basebiao = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
basebiao = list(basebiao)
for i in range(10):
    v1 = basebiao[i]
    basebiao[i] = basebiao[19-i]
    basebiao[19-i] = v1
basebiao = "".join(basebiao)
print(len(basebiao))
print(basebiao)
import base64
str1 = "d2G0ZjLwHjS7DmOzZAY0X2lzX3CoZV9zdNOydO9vZl9yZXZlcnGlfD=="
#string1 = "TSRQPONMLKJIHGFEDCBAUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
string2 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
print(base64.b64decode(str1.translate(str.maketrans(basebiao,string2))))

[SWPUCTF 2022 新生赛]upx

Upx脱壳

 简单的异或运算

code = "LQQAVDyWRZ]3q]zmpf]uc{]vm]glap{rv]dnce"
code = list(code)
for i in range(len(code)):
    print(chr(ord(code[i])^2),end="")

[HNCTF 2022 Week1]你知道什么是Py嘛?

得到第一位字符"N"以及flag的长度为35

 arr数组的长度只有34,故将i的范围改为34

arr=[29, 0, 16, 23, 18, 61, 43, 41, 13, 28, 88, 94, 49, 110, 66, 44, 43, 28, 91, 108, 61, 7, 22, 7, 43, 51, 44, 46, 9, 18, 20, 6, 2, 24]
s = ['N']
#print(len(arr))
for i in range(34):
    a=ord(s[i])^arr[i]
    s.append(chr(a))
    print(s[i],end="")

[CISCN 2022 东北]easycpp

memcmp() 函数比较 v3v12 指向的内存块前 Size 个字节的内容。将比较结果赋值给 v12=buf2

故我们需要得到buf2加密数据

在if(Size!=38)处下断点,启动动态调试

 打开buf2得到加密数据

逆序解密 

code = [0x0A, 0x0B, 0x7D, 0x2F, 0x7F, 0x67, 0x65, 0x30, 0x63, 0x60,
  0x37, 0x3F, 0x3C, 0x3F, 0x33, 0x3A, 0x3C, 0x3B, 0x35, 0x3C,
  0x3E, 0x6C, 0x64, 0x31, 0x64, 0x6C, 0x3B, 0x68, 0x61, 0x62,
  0x65, 0x36, 0x33, 0x60, 0x62, 0x36, 0x1C, 0x7D]
print(len(code))
for i in range(len(code)-4,-1,-1):
    code[i + 2] = code[i + 2] ^ code[i + 3]
    code[i+1] = code[i+1] ^ code[i + 2]
    code[i]=code[i]^code[i+1]
for i in range(len(code)):
    print(chr(code[i]), end="")

 [羊城杯 2020]login

pyinstxtractor解包

#!/usr/bin/env python
# visit https://tool.lu/pyc/ for more information
# Version: Python 3.6

import sys
input1 = input('input something:')
if len(input1) != 14:
    print('Wrong length!')
    sys.exit()
code = []
for i in range(13):
    code.append(ord(input1[i]) ^ ord(input1[i + 1]))

code.append(ord(input1[13]))
a1 = code[2]
a2 = code[1]
a3 = code[0]
a4 = code[3]
a5 = code[4]
a6 = code[5]
a7 = code[6]
a8 = code[7]
a9 = code[9]
a10 = code[8]
a11 = code[10]
a12 = code[11]
a13 = code[12]
a14 = code[13]
if ((((a1 * 88 + a2 * 67 + a3 * 65 - a4 * 5) + a5 * 43 + a6 * 89 + a7 * 25 + a8 * 13 - a9 * 36) + a10 * 15 + a11 * 11 + a12 * 47 - a13 * 60) + a14 * 29 == 22748) & ((((a1 * 89 + a2 * 7 + a3 * 12 - a4 * 25) + a5 * 41 + a6 * 23 + a7 * 20 - a8 * 66) + a9 * 31 + a10 * 8 + a11 * 2 - a12 * 41 - a13 * 39) + a14 * 17 == 7258) & ((((a1 * 28 + a2 * 35 + a3 * 16 - a4 * 65) + a5 * 53 + a6 * 39 + a7 * 27 + a8 * 15 - a9 * 33) + a10 * 13 + a11 * 101 + a12 * 90 - a13 * 34) + a14 * 23 == 26190) & ((((a1 * 23 + a2 * 34 + a3 * 35 - a4 * 59) + a5 * 49 + a6 * 81 + a7 * 25 + (a8 << 7) - a9 * 32) + a10 * 75 + a11 * 81 + a12 * 47 - a13 * 60) + a14 * 29 == 37136) & (((a1 * 38 + a2 * 97 + a3 * 35 - a4 * 52) + a5 * 42 + a6 * 79 + a7 * 90 + a8 * 23 - a9 * 36) + a10 * 57 + a11 * 81 + a12 * 42 - a13 * 62 - a14 * 11 == 27915) & ((((a1 * 22 + a2 * 27 + a3 * 35 - a4 * 45) + a5 * 47 + a6 * 49 + a7 * 29 + a8 * 18 - a9 * 26) + a10 * 35 + a11 * 41 + a12 * 40 - a13 * 61) + a14 * 28 == 17298) & ((((a1 * 12 + a2 * 45 + a3 * 35 - a4 * 9 - a5 * 42) + a6 * 86 + a7 * 23 + a8 * 85 - a9 * 47) + a10 * 34 + a11 * 76 + a12 * 43 - a13 * 44) + a14 * 65 == 19875) & (((a1 * 79 + a2 * 62 + a3 * 35 - a4 * 85) + a5 * 33 + a6 * 79 + a7 * 86 + a8 * 14 - a9 * 30) + a10 * 25 + a11 * 11 + a12 * 57 - a13 * 50 - a14 * 9 == 22784) & ((((a1 * 8 + a2 * 6 + a3 * 64 - a4 * 85) + a5 * 73 + a6 * 29 + a7 * 2 + a8 * 23 - a9 * 36) + a10 * 5 + a11 * 2 + a12 * 47 - a13 * 64) + a14 * 27 == 9710) & (((((a1 * 67 - a2 * 68) + a3 * 68 - a4 * 51 - a5 * 43) + a6 * 81 + a7 * 22 - a8 * 12 - a9 * 38) + a10 * 75 + a11 * 41 + a12 * 27 - a13 * 52) + a14 * 31 == 13376) & ((((a1 * 85 + a2 * 63 + a3 * 5 - a4 * 51) + a5 * 44 + a6 * 36 + a7 * 28 + a8 * 15 - a9 * 6) + a10 * 45 + a11 * 31 + a12 * 7 - a13 * 67) + a14 * 78 == 24065) & ((((a1 * 47 + a2 * 64 + a3 * 66 - a4 * 5) + a5 * 43 + a6 * 112 + a7 * 25 + a8 * 13 - a9 * 35) + a10 * 95 + a11 * 21 + a12 * 43 - a13 * 61) + a14 * 20 == 27687) & (((a1 * 89 + a2 * 67 + a3 * 85 - a4 * 25) + a5 * 49 + a6 * 89 + a7 * 23 + a8 * 56 - a9 * 92) + a10 * 14 + a11 * 89 + a12 * 47 - a13 * 61 - a14 * 29 == 29250) & (((a1 * 95 + a2 * 34 + a3 * 62 - a4 * 9 - a5 * 43) + a6 * 83 + a7 * 25 + a8 * 12 - a9 * 36) + a10 * 16 + a11 * 51 + a12 * 47 - a13 * 60 - a14 * 24 == 15317):
    print('flag is GWHT{md5(your_input)}')
    print('Congratulations and have fun!')
else:
    print('Sorry,plz try again...')

先z3方程解密,注意a8<<7即code[7]*0x80,或者直接注释掉

from z3 import *
s=Solver()
code=[Int('a1[' + str(i) + ']') for i in range(14)]
for i in range(14):
    s.add((((code[0] * 88 + code[1] * 67 + code[2] * 65 - code[3] * 5) + code[4] * 43 + code[5] * 89 + code[6] * 25 + code[7] * 13 - code[8] * 36) + code[9] * 15 + code[10] * 11 + code[11] * 47 - code[12] * 60) + code[13] * 29 == 22748)
    s.add((((code[0] * 89 + code[1] * 7 + code[2] * 12 - code[3] * 25) + code[4] * 41 + code[5] * 23 + code[6] * 20 - code[7] * 66) + code[8] * 31 + code[9] * 8 + code[10] * 2 - code[11] * 41 - code[12] * 39) + code[13] * 17 == 7258)
    s.add((((code[0] * 28 + code[1] * 35 + code[2] * 16 - code[3] * 65) + code[4] * 53 + code[5] * 39 + code[6] * 27 + code[7] * 15 - code[8] * 33) + code[9] * 13 + code[10] * 101 + code[11] * 90 - code[12] * 34) + code[13] * 23 == 26190)
    s.add((((code[0] * 23 + code[1] * 34 + code[2] * 35 - code[3] * 59) + code[4] * 49 + code[5] * 81 + code[6] * 25 + (code[7] * 0x80) - code[8] * 32) + code[9] * 75 + code[10] * 81 + code[11] * 47 - code[12] * 60) + code[13] * 29 == 37136)
    s.add(((code[0] * 38 + code[1] * 97 + code[2] * 35 - code[3] * 52) + code[4] * 42 + code[5] * 79 + code[6] * 90 + code[7] * 23 - code[8] * 36) + code[9] * 57 + code[10] * 81 + code[11] * 42 - code[12] * 62 - code[13] * 11 == 27915)
    s.add((((code[0] * 22 + code[1] * 27 + code[2] * 35 - code[3] * 45) + code[4] * 47 + code[5] * 49 + code[6] * 29 + code[7] * 18 - code[8] * 26) + code[9] * 35 + code[10] * 41 + code[11] * 40 - code[12] * 61) + code[13] * 28 == 17298)
    s.add((((code[0] * 12 + code[1] * 45 + code[2] * 35 - code[3] * 9 - code[4] * 42) + code[5] * 86 + code[6] * 23 + code[7] * 85 - code[8] * 47) + code[9] * 34 + code[10] * 76 + code[11] * 43 - code[12] * 44) + code[13] * 65 == 19875)
    s.add(((code[0] * 79 + code[1] * 62 + code[2] * 35 - code[3] * 85) + code[4] * 33 + code[5] * 79 + code[6] * 86 + code[7] * 14 - code[8] * 30) + code[9] * 25 + code[10] * 11 + code[11] * 57 - code[12] * 50 - code[13] * 9 == 22784)
    s.add((((code[0] * 8 + code[1] * 6 + code[2] * 64 - code[3] * 85) + code[4] * 73 + code[5] * 29 + code[6] * 2 + code[7] * 23 - code[8] * 36) + code[9] * 5 + code[10] * 2 + code[11] * 47 - code[12] * 64) + code[13] * 27 == 9710)
    s.add(((((code[0] * 67 - code[1] * 68) + code[2] * 68 - code[3] * 51 - code[4] * 43) + code[5] * 81 + code[6] * 22 -code[7] * 12 - code[8] * 38) + code[9] * 75 + code[10] * 41 + code[11] * 27 - code[12] * 52) + code[13] * 31 == 13376)
    s.add((((code[0] * 85 + code[1] * 63 + code[2] * 5 - code[3] * 51) + code[4] * 44 + code[5] * 36 + code[6] * 28 + code[7] * 15 - code[8] * 6) + code[9] * 45 + code[10] * 31 + code[11] * 7 - code[12] * 67) + code[13] * 78 == 24065)
    s.add((((code[0] * 47 + code[1] * 64 + code[2] * 66 - code[3] * 5) + code[4] * 43 + code[5] * 112 + code[6] * 25 + code[7] * 13 - code[8] * 35) + code[9] * 95 + code[10] * 21 + code[11] * 43 - code[12] * 61) + code[13] * 20 == 27687)
    s.add(((code[0] * 89 + code[1] * 67 + code[2] * 85 - code[3] * 25) + code[4] * 49 + code[5] * 89 + code[6] * 23 + code[7] * 56 - code[8] * 92) + code[9] * 14 + code[10] * 89 + code[11] * 47 - code[12] * 61 - code[13] * 29 == 29250)
    s.add(((code[0] * 95 + code[1] * 34 + code[2] * 62 - code[3] * 9 - code[4] * 43) + code[5] * 83 + code[6] * 25 + code[7] * 12 - code[8] * 36) + code[9] * 16 + code[10] * 51 + code[11] * 47 - code[12] * 60 - code[13] * 24 == 15317)
if s.check()==sat:
    print()
print(s.model())

 注意a[i]和code[i]的对应关系

异或运算 

flag = [10, 24, 119, 7, 104, 43, 28, 91, 108, 52, 88, 74, 88, 33]

for i in range(12,-1,-1):
    flag[i] ^= flag[i+1]
for i in flag:
    print(chr(i),end="")

 再md5加密一次,得到flag:https://md5.hwcha.com/

 [GDOUCTF 2023]doublegame

flag为md5加密的路径+得分

得到迷宫 

  

注意从@进入经过*结束,故起点为(0,15)终点(20,7)

maze =[
    [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
    [1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1],
    [1, 0, 1, 0, 1, 0, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 0, 1],
    [1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1],
    [1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1],
    [1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 1],
    [1, 0, 1, 0, 1, 0, 1, 1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1],
    [1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0],
    [1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1],
    [1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1],
    [1, 0, 1, 1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1],
    [1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1],
    [1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1],
    [1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1],
    [1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 1, 1],
    [0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1],
    [1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
    [1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1],
    [1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1],
    [1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1],
    [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]]

usedmap=[[0 for i in range(len(maze))]for i in range(len(maze[0]))]
sti=15
stj=0
edi=7
edj=20
flag=''
def dfs(x,y):
    global flag
    if x==edi and y==edj:
        print(flag)
        return
    if maze[x+1][y]==0 and usedmap[x+1][y]==0:
        usedmap[x][y]=1
        flag+='s'
        dfs(x+1,y)
        flag=flag[:-1]
        usedmap[x][y]=0
    if maze[x-1][y]==0 and usedmap[x-1][y]==0:
        usedmap[x][y]=1
        flag+='w'
        dfs(x-1,y)
        flag=flag[:-1]
        usedmap[x][y]=0
    if maze[x][y+1]==0 and usedmap[x][y+1]==0:
        usedmap[x][y]=1
        flag+='d'
        dfs(x,y+1)
        flag=flag[:-1]
        usedmap[x][y]=0
    if maze[x][y-1]==0 and usedmap[x][y-1]==0:
        usedmap[x][y]=1
        flag+='a'
        dfs(x,y-1)
        flag=flag[:-1]
        usedmap[x][y]=0
dfs(sti,stj)

 还没有结束,还需要找到score

打开sub_140011433(0)函数 

 异或运算

v24= 13376013
result = v24 ^ 0×1DC4
print(result)

 [GDOUCTF 2023]Tea

这两个插件没有检测到tea算法,所以可能是个魔改的

https://blog.csdn.net/abel_big_xu/article/details/115663288

 找key和delta值

 sub_140011339((__int64)v7)函数得到key(2233,4455,6677,8899)

sub_1400112B7((__int64)v8, (__int64)v7函数为tea加密算法,其中a1=加密数据,a2=key,delta=0xF462900(256256256) 

v6 = sub_140011352(v8)得到v8

 用c去写比较简单

#include<stdio.h>
#include<stdint.h>
#define delta 0xF462900
int main()
{
        uint32_t key[4] = { 2233,4455,6677,8899 };
        uint32_t data[10] = { 0x1A800BDA ,0xF7A6219B ,0x491811D8,0xF2013328,0x156C365B, 0x3C6EAAD8,0x84D4BF28,0xF11A7EE7,0x3313B252,0xDD9FE279 };
        unsigned int j;
        int i;
        unsigned int sum;
        for (i = 8; i >= 0; i--)
        {
                j = 33;
                sum = delta * (i + j);
                while (j--)
                {
                        sum -= delta;
                        data[i + 1] -= (sum + key[(sum >> 11) & 3]) ^ ((data[i] + ((data[i] >> 5) ^ (data[i] << 4))));
                        data[i] -= sum ^ (data[i+1] + ((data[i + 1] >> 5) ^ (data[i + 1] << 4))) ^ (sum + key[sum & 3]);

                }
        }
        for (int i = 0; i < 10; i++)
        {
                printf("%x", data[i]);
        }
        return 0;
}

 在线hex解密一下

 [WUSTCTF 2020]Cr0ssfun

直接将check函数中的所有字符拼接一下就好了

a1=33*['']
a1[10] = 112
a1[13] = 64
a1[3] = 102
a1[26] = 114
a1[20] = 101
a1[7] = 48
a1[16] = 95
a1[11] = 112
a1[23] = 101
a1[30] = 117
a1[0] = 119
a1[6] = 50
a1[22] = 115
a1[31] = 110
a1[12] = 95
a1[15] = 100
a1[8] = 123
a1[18] = 51
a1[28] = 95
a1[21] = 114
a1[2] = 116
a1[9] = 99
a1[32] = 125
a1[19] = 118
a1[5] = 48
a1[14] = 110
a1[4] = 50
a1[17] = 114
a1[29] = 102
a1[17] = 114
a1[24] = 95
a1[1] = 99
a1[25] = 64
a1[27] = 101

for i in a1:
     print(chr(i),end='')

 [HNCTF 2022 Week1]CrackMe

ida动态调试

审计代码,找地方下断点

下断点

 

输入规定的Name:CreakMe,注册码随便输 ,点击check

得到CreakMe的注册码

ollydbg调试

在lstrcmpA处下断点,F8步过

输入Name:CreakMe,注册码随便输入

 继续步过,如果出现报错则停止

点击确定,得到注册码

 x32dbg

 下断点,F8步过

得到注册码

[HDCTF 2023]fake_game 

pyinstxtractor解包 

 用uncompyle6反编译

 加密算法

先解xorr数组 

from z3 import *
s=Solver()
xorr=[Int('a1[' + str(i) + ']') for i in range(4)]
for i in range(4):
    s.add(xorr[0] * 256 - xorr[1] / 2 + xorr[2] * 23 + xorr[3] / 2 == 47118166)
    s.add(xorr[0] * 252 - xorr[1] * 366 + xorr[2] * 23 + xorr[3] / 2 - 1987 == 46309775)
    s.add(xorr[0] * 6 - xorr[1] * 88 + xorr[2] / 2 + xorr[3] / 2 - 11444 == 1069997)
    s.add((xorr[0] - 652) * 2 - xorr[1] * 366 + xorr[2] * 233 + xorr[3] / 2 - 13333 == 13509025)
if s.check()==sat:
    print()
print(s.model())

 发现解完的flag有问题,应该为HDCTF,逆向推一下得到a3应为2361(不明白为什么突然从2360变2361)

 所以重新写了个z3解方程组脚本

from z3 import *

xorr = [BitVec('a%d' % i, 64) for i in range(0, 4)]
solver = Solver()

solver.add(xorr[0] * 256 - xorr[1] / 2 + xorr[2] * 23 + xorr[3] / 2 == 47118166)
solver.add(xorr[0] * 252 - xorr[1] * 366 + xorr[2] * 23 + xorr[3] / 2 - 1987 == 46309775)
solver.add(xorr[0] * 6 - xorr[1] * 88 + xorr[2] / 2 + xorr[3] / 2 - 11444 == 1069997)
solver.add((xorr[0] - 652) * 2 - xorr[1] * 366 + xorr[2] * 233 + xorr[3] / 2 - 13333 == 13509025)

solver.check()
result = solver.model()
print(result)

 得到正确的a3

flag = [178868, 188, 56953, 2413, 178874, 131, 56957, 2313, 178867, 156,
         56933, 2377, 178832, 202, 56899, 2314, 178830, 167, 56924,
         2313, 178830, 167, 56938, 2383, 178822, 217, 56859, 2372]

xorr= [178940 , 248 , 56890 , 2361]
for i in range(len(flag)):
    flag[i] = flag[i] ^ xorr[i % 4]
    print(chr(flag[i]),end="")

[MoeCTF 2022]Base

 base64_decode(base64, de64)函数

base表

 在线解密偷懒

 [watevrCTF 2019]Timeout

修改后缀为exe,打开generate函数,得到flag

  • 14
    点赞
  • 29
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值