原设计图
Flag格式
NepCTF{%s}
逻辑复原
main
UPX拆壳,main函数逻辑复原得到
- getInput
- checkInputFormat
- debuggerCheck
- 如果存在,则加密一些数据
- cotIsDebuggerPresent++
- checkCRC
- checkBreakPoint1
- checkBreakPoint2
- thread3
- FinalCheck
checkCRC
- CRCcheck
- cotCRCcheck++
- create CRC thread
- function: checkCRC
checkBreakPoint1
- BreakPoint则cotBreakPoint++
- 其它的则不管
checkBreakPoint2
- 检测cotBreakPoint个数,判断是否失败
thread3
- checkCRC
- keyTEA
keyTEA[0] = 0x19 * cotIsDebuggerPresent;
keyTEA[1] = 0x28 * cotBreakPoint1;
keyTEA[2] = 0x37 * cotCRCcheck;
keyTEA[3] = cotIsDebuggerPresent + cotCRCcheck + cotBreakPoint1
- xxTEA加密,分析密钥结构可以知道是keyTEA
- xxTEA可以看加密结构判断,TEA族加密可以通过魔数看出
- cotSame = flag经过xxTEA后得到的字符串中,相邻且相同的字符个数
- BitInvert
- keyAES
keyAES->m128i_i8[0] = 0x19 * cotIsDebuggerPresent;
keyAES->m128i_i8[1] = 5 * cotBreakPoint1 * 8;
keyAES->m128i_i8[2] = 0x37 * cotCRCcheck;
keyAES->m128i_i8[3] = cotSame + cotIsDebuggerPresent + cotBreakPoint1 + cotCRCcheck;
keyAES->m128i_i8[4] = 0x19 * cotIsDebuggerPresent;
keyAES->m128i_i8[5] = 5 * cotBreakPoint1 * 8;
keyAES->m128i_i8[6] = 0x37 * cotCRCcheck;
keyAES->m128i_i8[7] = cotIsDebuggerPresent + cotBreakPoint1 + cotCRCcheck - cotSame;
keyAES->m128i_i8[8] = 70 * cotIsDebuggerPresent;
keyAES->m128i_i8[9] = 85 * cotBreakPoint1;
keyAES->m128i_i8[10] = 100 * cotCRCcheck;
keyAES->m128i_i8[11] = cotSame + cotIsDebuggerPresent + cotBreakPoint1 + cotCRCcheck;
keyAES->m128i_i8[12] = 70 * cotIsDebuggerPresent;
keyAES->m128i_i8[13] = 85 * cotBreakPoint1;
keyAES->m128i_i8[14] = 100 * cotCRCcheck;
keyAES->m128i_i8[15] = cotIsDebuggerPresent + cotBreakPoint1 + cotCRCcheck - cotSame;
- AES
- checkCRC
FinalCheck
- 检查加密后的数据和cmpVal是否相同
- 不同的话触发异常处理,要求输入不需要的password并且不可能正确
WP
只有cotSame是不确定的值,范围是0~47,后面爆破即可
cotXXX全部都是固定的,只有动态调试的时候会因为触发检测而错误,静态分析显然可以得到不同时刻的状态表
int main() {
unsigned char flag[SIZE + 1] = "NepCTF{tEA_with_AES_by_mixing_antiDebug_hahaHah}";
unsigned char comp[SIZE + 1] = { 0 };
data.cot_Anti1 += 1;
data.cot_Anti3 += 1;
data.cot_Anti3 += 1;
unsigned int keyTEA[4];
keyTEA[0] = data.cot_Anti1 * 0x19;
keyTEA[1] = data.cot_Anti2 * 0x28;
keyTEA[2] = data.cot_Anti3 * 0x37;
keyTEA[3] = data.cot_Anti1 + data.cot_Anti2 + data.cot_Anti3;
xxtea_uint_encrypt((unsigned int*)flag, SIZE/4, (unsigned int*)keyTEA);
data.cot_same = 0;
data.cot_Anti2 += 1;
for (int i = 0; i
int main() {
for (int i = 0; i
经测试,仅有cot_same==0时有合法flag
NepCTF{tEA_with_AES_by_mixing_antiDebug_hahaHah}
机房租用,北京机房托管,大带宽租用,IDC机房服务器主机租用托管-价格及服务咨询 www.e1idc.net