IDA動態除錯解RC4
本篇部落格所有內容,均學習於無名俠大佬在bilibili的影片:https://www.bilibili.com/video/BV1WQ4y1X7TY
LazyIDA熊貓版:https://github.com/P4nda0s/LazyIDA
實驗檔案下載:https://github.com/P4nda0s/SycRevLearn
有一些演算法的加密與解密是相同的演算法過程,例如 RC4、部分簡單的異或演算法等。
測試方法:
1.設定演算法輸入資料A
2.獲取演算法輸出資料B
3.設定演算法輸入資料為B (上一步結果代入)
4.獲取演算法輸出資料 B',對比 B' 與 A 的值,若相等則該演算法加密解密是同一段程式碼。
通俗來講,就是輸入A輸出B,輸入B輸出A。
拿影片中的題目來分析:
sub_85F057(v14);//反除錯
puts("Welcome!! give me your flag:\n");
do
{
v8 = j_j_j___fgetchar();
if ( v8 == 10 )
break;
input[index++] = v8;
}
while ( (int)index < 44 );
if ( index >= 0x200 )
j____report_rangecheckfailure();
input[index] = 0;
len = j__strlen(input);
sub_85CEFB((int)v13, (int)v14, len);
for ( i = 0; i < 256; ++i )
v12[i] = v13[i];
fun1((int)v13, (int)input, len);//加密函式
for ( j = 0; j < 44; ++j )
{
if ( v7[j] == input[j] )
++v10;
}
if ( v10 == 44 )
puts("Yes, u right!\n");
else
puts("no no no\n");
system("pause");
return 0;
}
啥也不要分析,主要看fun1((int)v13, (int)input, len);
input是我們輸入的,這個函式會將我們的input進行加密。
for ( j = 0; j < 44; ++j )
{
if ( v7[j] == input[j] )
++v10;
}
然後在透過這裡進行比較。
根據for語句可以得知,flag的長度可能是44,這裡為什麼說是可能呢,如果是逐位元組加密,就是我們輸入的每一個字元加密後都是一個字元,那麼flag的長度肯定是44,如果我們的輸入,一個字元加密成了兩個字元,那麼我們輸入的flag的長度就是22,因為這裡並不確定,所以只能猜測是44。
程式有反除錯,我嘗試將反除錯給nop掉,但是發現反除錯似乎又與加密程式碼有著一定的關係,我嘗試了,沒能理清楚反除錯和加密程式碼的關係,所以這裡和影片中的一樣,還是帶著反除錯來分析,這裡用IDA附加執行中的程式就行,因為已經執行完反除錯的那句程式碼了。
測試是否加密與解密是相同的演算法
在加密函式處斷下
先輸入:aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
檢視input的值
再F8單步步過,檢視此時加密後的input
用外掛將資料提取出來
[+] Dump 0xCFF1BC - 0xCFF1E8 (44 bytes) :
D62DE6F797244F2EA92DDDA37904C885B9E4E8D90B325F9908C07B804E134AC497DA7562D0AD31C558C3BBF6
可以看到我們輸入的44個a被加密成了上述資料
這次我們將上述資料進行輸入,看執行之後是否可以還原成44個a
上述資料存在不可見字元,不能從命令框裡直接輸入,這裡需要用到Paste Data來改棧上的資料。
這次我們先輸入41個b
透過Paste Data將資料改成D62DE6F797244F2EA92DDDA37904C885B9E4E8D90B325F9908C07B804E134AC497DA7562D0AD31C558C3BBF6
再F8單步步過,檢視此時加密後的input
可以看到資料恢復成了41個a
fun1((int)v13, (int)input, len);//加密函式
for ( j = 0; j < 44; ++j )
{
if ( v7[j] == input[j] )
++v10;
}
if ( v10 == 44 )
puts("Yes, u right!\n");
else
puts("no no no\n");
system("pause");
再回頭看一下程式,程式是將v7和input進行比較,v7其實就是flag加密之後的形式,我們此時只要將v7dump下來,把v7的資料當作input進行傳入,經過加密函式之後就可以得到flag了。
v7:
[+] Dump 0x7DF5F0 - 0x7DF61C (44 bytes) :
E415C4EDA62F5610BB13EBAD7556C7BBBBE9B9CC023A509F369069BE7C4244CAC6D4245CD2B924C11893B3EA
再一次執行程式
將input用Paste Data改成E415C4EDA62F5610BB13EBAD7556C7BBBBE9B9CC023A509F369069BE7C4244CAC6D4245CD2B924C11893B3EA
再F8單步步過,檢視此時加密後的input
可以看到flag已經被還原了,按一下鍵盤上的A鍵就能轉成字串形式方便複製
SYC{Pjx_s_Wom3n_cl0thing_1s_S0oo0o0_cute!1i}
今天就先這樣,等明天我試著做一下其它題目,看是否學到了精髓。
2024年5月2日23點28分