一个apk的包,用jd打开看原码,它先是行成一个码表用两个序列s和k生成,然后调用libnative_lib.so中的checkflag(s,flag)进行校验
1,每点一次button1会执行一次交换共99999次(所以说屏幕裂开了)
复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17this.btn.setOnClickListener(new OnClickListener() { public void onClick(View v) { MainActivity mainActivity = MainActivity.this; mainActivity.hit_count++; char j = 0; for (char i = 0; i < 256; i = (char) (i + 1)) { j = (char) (((MainActivity.this.s[i] + j) + MainActivity.this.k[i]) % 256); char tmp = MainActivity.this.s[i]; MainActivity.this.s[i] = MainActivity.this.s[j]; MainActivity.this.s[j] = tmp; } MainActivity.this.btn.setText(String.valueOf(MainActivity.this.hit_count)); if (MainActivity.this.hit_count >= 99999) { MainActivity.this.btn2.setEnabled(true); } }
2,在lib.so里由s通过63交换次交换每次的结果与输入flag值异或与check比较
复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33__int64 __fastcall Java_com_zxc_ClickStorm_MainActivity_checkflag(__int64 a1, __int64 a2, __int64 a3, __int64 a4) { int j; // [rsp+10h] [rbp-180h] int i; // [rsp+14h] [rbp-17Ch] __int64 v7; // [rsp+18h] [rbp-178h] const char *v8; // [rsp+20h] [rbp-170h] char v9; // [rsp+2Bh] [rbp-165h] int v10; // [rsp+30h] [rbp-160h] int v11; // [rsp+34h] [rbp-15Ch] char v14[264]; // [rsp+80h] [rbp-110h] unsigned __int64 v15; // [rsp+188h] [rbp-8h] v15 = __readfsqword(0x28u); LOBYTE(v11) = 0; LOBYTE(v10) = 0; v8 = (const char *)_JNIEnv::GetStringUTFChars(a1, a4, 0LL);// 读入的flag if ( strlen(v8) != 63 ) return 0; v7 = _JNIEnv::GetCharArrayElements(a1, a3, 0LL);// 传入的码表 for ( i = 0; i < 256; ++i ) v14[i] = *(_WORD *)(v7 + 2LL * i); // 没用,仅尾1字节有效 for ( j = 0; j < 63; ++j ) { v11 = (unsigned __int8)(v11 + 1); v10 = (unsigned __int8)(v14[v11] + v10); v9 = v14[v11]; v14[v11] = v14[v10]; v14[v10] = v9; if ( ((unsigned __int8)v14[((unsigned __int8)v14[v10] + (unsigned __int8)v14[v11]) % 256] ^ v8[j]) != answer[j] ) return 0; } return 1; }
根据大意写逆向程序
复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24#tab_s s = [i for i in range(256)] k = (b"InfinityLoop"*22) [0:256] for hit_count in range(99999): j = 0 for i in range(256): j = (s[i]+j+k[i])%256 s[i],s[j] = s[j],s[i] answer = [0xA6,0x3D,0x54,0x0B0,0x74,0xCC,0xBD,0x2A,0x4A,0x0DE,0x0BD,0x35,0x0D1,0x1D,0x80,0x32,0x5F,0x64,0x2F,0x0C5,0x0DD,0x11,0x3E,0x95,0x0CC,0x17,0x13,0x0E5,0x5E,0x65,0x0CE,0x42,0x9E,0x47,0x0C8,0x0F3,0x4D,0x8A,0x0A6,0x1F,0x0F0,0x50,0x27,0x0A2,0x28,0x81,0x24,0x0A7,0x0B4,0x90,0x0FC,0x93,0x8A,0x0C1,0x77,0x0D5,0x16,0x1E,0x0FD,0x87,0x0C7,0x0BB,0x0B3,0x0] v10,v11 = 0,0 v14 = s tab = [0]*63 for j in range(63): v11 = v11+1 v10 = (v14[v11] + v10)& 0xff v14[v11],v14[v10] = v14[v10],v14[v11] tab[j] = v14[(v14[v10]+ v14[v11]) %256] flag = [answer[i]^tab[i] for i in range(63)] print(bytes(flag)) #flag{i_hope_you_didnt_click_the_button_99999__justRE_in_Static}
最后
以上就是执着白昼最近收集整理的关于[ctf.show.reverse] 屏幕裂开了的全部内容,更多相关[ctf.show.reverse]内容请搜索靠谱客的其他文章。
本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
发表评论 取消回复