ctf.360.cn第二届,逆向部分writeup——第四题
发表于:2026-11-01 作者:千家信息网编辑
千家信息网最后更新 2026年11月01日,题目:见附件这题开始有些小复杂了。运行程序,可以看见界面如下注意看"隐藏信息完毕!"字符串的位置直接搜索push 40405c,找到代码位置401a48。网上翻找到代码块的入口地址4017a0。很显然
千家信息网最后更新 2026年11月01日ctf.360.cn第二届,逆向部分writeup——第四题
题目:见附件
这题开始有些小复杂了。
运行程序,可以看见界面如下

注意看"隐藏信息完毕!"字符串的位置

直接搜索push 40405c,找到代码位置401a48。
网上翻找到代码块的入口地址4017a0。很显然这是一个非常长的函数,使用IDA进行静态分析。
v2 = CreateFileA(*((LPCSTR *)v1 + 24), 0x80000000u, 1u, 0, 3u, 0x80u, 0); if ( v2 == (HANDLE)-1 ) { result = CWnd::MessageBoxA(v1, &unk_4040D4, 0, 0); } else { v4 = CreateFileA(*((LPCSTR *)v1 + 26), 0x80000000u, 1u, 0, 3u, 0x80u, 0); hObject = v4; if ( v4 == (HANDLE)-1 ) { result = CWnd::MessageBoxA(v1, &unk_4040BC, 0, 0); } else { v33 = CreateFileA(*((LPCSTR *)v1 + 25), 0x40000000u, 1u, 0, 2u, 0x80u, 0); if ( v33 == (HANDLE)-1 ) { result = CWnd::MessageBoxA(v1, &unk_40409C, 0, 0); } else { SetFilePointer(v2, 2, 0, 0); ReadFile(v2, &Buffer, 4u, &NumberOfBytesWritten, 0); SetFilePointer(v2, 4, 0, 1u); ReadFile(v2, &v35, 4u, &NumberOfBytesWritten, 0); SetFilePointer(v2, 0, 0, 0); v5 = operator new(Buffer); lpBuffer = v5; ReadFile(v2, (LPVOID)v5, Buffer, &NumberOfBytesWritten, 0); v6 = (int)((char *)v5 + v35); v7 = GetFileSize(v4, 0); v31 = v7; v28 = operator new(v7); ReadFile(hObject, v28, v7, &NumberOfBytesWritten, 0); v8 = Buffer - v35 - 32; if ( 8 * v7 <= v8 ) { v24 = v7; v9 = 16; do { LOWORD(v8) = *(_BYTE *)v6 & 1; v10 = v24 & 1; v8 ^= v10; if ( (_WORD)v8 ) { v11 = (rand() & 1) == 0; v12 = *(_BYTE *)v6; if ( v11 ) v13 = v12 - 1; else v13 = v12 + 1; *(_BYTE *)v6 = v13; } v24 >>= 1; ++v6; --v9; } while ( v9 ); v14 = 16; v25 = v7 >> 16; do { LOWORD(v10) = *(_BYTE *)v6 & 1; v10 ^= v25 & 1; if ( (_WORD)v10 ) { v11 = (rand() & 1) == 0; v15 = *(_BYTE *)v6; if ( v11 ) v16 = v15 - 1; else v16 = v15 + 1; *(_BYTE *)v6 = v16; } LOWORD(v25) = (unsigned __int16)v25 >> 1; ++v6; --v14; } while ( v14 ); v17 = 0; v26 = 0; if ( v7 ) { do { v18 = 8; v19 = *((_BYTE *)v28 + v17); do { if ( (v19 ^ *(_BYTE *)v6) & 1 ) { v11 = (rand() & 1) == 0; v20 = *(_BYTE *)v6; if ( v11 ) v21 = v20 - 1; else v21 = v20 + 1; *(_BYTE *)v6 = v21; } v19 >>= 1; ++v6; --v18; } while ( v18 ); v17 = v26++ + 1; } while ( v26 < v31 ); } v22 = lpBuffer; v23 = v33; WriteFile(v33, lpBuffer, Buffer, &NumberOfBytesWritten, 0); operator delete((void *)v22); operator delete(v28); CloseHandle(v2); CloseHandle(hObject); CloseHandle(v23); result = CWnd::MessageBoxA(v30, &unk_40405C, 0, 0); } else { result = CWnd::MessageBoxA(v30, &unk_40406C, "Caption", 0); } } } } return result;要理解代码,首先要了解bmp文件的格式,可以参考http://www.cnblogs.com/kingmoon/archive/2011/04/18/2020097.html。
实际上,题目的算法是跳过bmp文件头和最前面的32字节的像素,然后每8个字节编码一个所要加密的明文字节。其中用每一个像素字节的最后一位来表示要加密的明文字节的响应位。
代码中+1、-1实际上就是当像素字节的最后一位与明文字节对应位不一致时,修正到相同。
所以知道了算法就知道如何解密:取出藏有密文的字节的最后一位,拼出相应的明文。
提取源代码就不贴了。
字节
代码
明文
像素
位置
实际
实际上
文件
算法
题目
加密
复杂
相同
一致
中用
信息
入口
函数
地址
字符
数据库的安全要保护哪些东西
数据库安全各自的含义是什么
生产安全数据库录入
数据库的安全性及管理
数据库安全策略包含哪些
海淀数据库安全审计系统
建立农村房屋安全信息数据库
易用的数据库客户端支持安全管理
连接数据库失败ssl安全错误
数据库的锁怎样保障安全
互联网科技
新华互联网科技学校
狮子座互联网科技
贷财互联网科技
奇士达互联网科技
顺玮阁互联网科技
温州喔噻互联网科技有限公司
北京华百购互联网科技有限公司
世界互联网科技公司市值排名
中国航天科技大学国际工业互联网
广州市恰铎互联网科技有限公司
上海京穆互联网科技有限公司
互联网科技年终奖
工业互联网科技成果转化
互联网界的黑科技
北京天晋互联网科技有限公司
互联网的科技体现在哪里
平安好医生打造互联网科技医疗
重庆科技产业互联网有哪些
六子台科技互联网展会
互联网科技开发公司
互联网金融公司科技
互联网科技论文
奇士达互联网科技
互联网科技有限公司 翻译
银川新华互联网科技学校地址
汽车互联网创新科技园
互联网5g黑科技有哪些
科技互联网海报
众联互联网络科技