Abstract:
Recently, a commercial security tool named Burpsuite was cracked. A malicious software named BurpLoader appeared on the Internet, which damaged the authentication process of Burpsuite, this poses a serious threat to world peace. This series of articles analyzes the cracking principles of Burpsuite through reverse analysis of several versions of BurpLoader and analyzes the security vulnerabilities in the Burpsuite authentication system.
Use and defects of JD-GUI:
JD-GUI is a free tool to restore JAVA source code from JAVA bytecode, usually use this tool to do JAVA reverse is enough, however, because the principle is to restore the corresponding JAVA source code from the JAVA bytecode according to the specific structure, once the bytecode structure is disrupted (for example, the obfuscator is used ), then the JD-GUI will lose its role, as shown in the figure when opening the Burpsuite with a JD-GUI:
Apparently, the JD-GUI failed to restore the JAVA source code, because Burpsuite uses a obfuscator to disrupt the bytecode structure, so the JD-GUI applies to 'Java bytecode without obfuscat, the defect is that once the bytecode structure is disrupted, it cannot play its role.
Bytecode analysis:
Java bytecode is not directly executed on computers like normal binary code. It runs on different platforms and computers through the JVM engine.
JVM is a stack-based virtual computer that uses the JVM operation code (and its mnemonic), which is very similar to the process of normal binary disassembly. It is actually very easy to decompile Java bytecode. JDK's built-in Javap tool can complete this task.
Example: decompile Javar. class
Note that the-c parameter of javap displays detailed code; otherwise, only method is displayed. Javar does not need to be suffixed according to the old java rules. You can also decompile Bytecode using the eclipse plug-in Bytecode Visualizer.
Pay attention to the flowchart on the right. You have painted it in the course of introducing program design. Now you can see its purpose. It can be seen at a glance that it is an if-else structure, the first two sentences define the I variable, and then take the I = 2 pressure stack constant 1, after comparing I and 1 are all java. lang. system. out. One output is wooyun and the other output is lxj616.
Analysis of old versions of BurpLoader:
As the Burpsuite is updated, the BurpLoader is also updated. Let's start with the old version of BurpLoader and briefly analyze the cracking principles of the old version of burpsuite. This section selects the version 1.5.01 BurpLoader for analysis first try to load the BurpLoader with JD-GUI:
The source code of the BurpLoader is restored successfully. Unfortunately, because of the patch of the burpsuite, the obfuscation of the burpsuite is still very readable in the burploader. However, it can be inferred that the burploader itself does not use the obfuscation tool.
<Span class = "keyword" style = "font-weight: bold;"> public </span> <span class = "keyword" style = "font-weight: bold; "> static </span> <span class =" keyword "style =" font-weight: bold; "> void </span> main (String [] args)
{
<Span class = "keyword" style = "font-weight: bold;"> try </span>
{
<Span class = "keyword" style = "font-weight: bold;"> int </span> ret = JOptionPane. showOptionDialog (<span class = "keyword" style = "font-weight: bold;"> null </span>, <span class = "string" style = "color: # dd1144; ">" This program can not be used for each cial purposes! "</Span>, <span class =" string "style =" color: # dd1144; ">" BurpLoader by larry_lau@163.com "</span>, <span class = "number" style = "color: #009999;"> 0 </span>, <span class = "number" style = "color: #009999; "> 2 </span>, <span class =" keyword "style =" font-weight: bold; "> null </span>, <span class = "keyword" style = "font-weight: bold;"> new </span> String [] {<span class = "string" style = "color: # dd1144; ">" I Accept "</span>, <span class =" string "style =" color: # dd1144; ">" I Decline "</span >}, <span class =" keyword "style =" font-weight: bold; "> null </span> );
<Span class = "comment" style = "font-style: italic; color: #999988;"> // Display selection dialog box: This program is written for learning purpose, author's email: larry_lau (at) 163.com </span>
<Span class = "keyword" style = "font-weight: bold;"> if </span> (ret = <span class = "number" style = "color: #009999; "> 0 </span>) <span class =" comment "style =" font-style: italic; color: #999988; "> // select I agree </span>
{
<Span class = "comment" style = "font-style: italic; color: #999988;"> // The following uses the java reflection mechanism, do not understand reflection, Please Baidu </span>
<Span class = "keyword" style = "font-weight: bold;"> for </span> (<span class = "keyword" style = "font-weight: bold; "> int </span> I = <span class =" number "style =" color: #009999; "> 0 </span>; I <clzzData. length; I ++)
{
Class clzz = Class. forName (clzzData [I]);
<Span class = "comment" style = "font-style: italic; color: #999988;"> // It is a static class of burpsuite (the name has been confused, no need to list them.) </span>
Field field = clzz. getDeclaredField (fieldData [I]);
<Span class = "comment" style = "font-style: italic; color: #999988;"> // The variables in the static class are also confused, you do not need to list them. </span>
Field. setAccessible (<span class = "keyword" style = "font-weight: bold;"> true </span> );
<Span class = "comment" style = "font-style: italic; color: #999988;"> // you must set this parameter before accessing private. Otherwise, an error is returned. </span>
Field. <span class = "keyword" style = "font-weight: bold;"> set </span> (<span class = "keyword" style = "font-weight: bold; "> null </span>, strData [I]);
<Span class = "comment" style = "font-style: italic; color: #999988;"> // Set the variable to strData (what is a long string for the moment) </span>
}
Preferences prefs = Preferences. userNodeForPackage (StartBurp. <span class = "keyword" style = "font-weight: bold;"> class </span> );
<Span class = "comment" style = "font-style: italic; color: #999988;"> // Obviously preferences are used to store the setting information </span>
<Span class = "keyword" style = "font-weight: bold;"> for </span> (<span class = "keyword" style = "font-weight: bold; "> int </span> I = <span class =" number "style =" color: #009999; "> 0 </span>; I <keys. length; I ++)
{
<Span class = "comment" style = "font-style: italic; color: #999988;"> // you can guess what the key and val are. </span>
String v = prefs. <span class = "keyword" style = "font-weight: bold;"> get </span> (keys [I], <span class = "keyword" style = "font-weight: bold;"> null </span> );
<Span class = "keyword" style = "font-weight: bold;"> if </span> (! Vals [I]. equals (v ))
{
Prefs. put (keys [I], vals [I]);
}
}
StartBurp. main (args );
}
}
<Span class = "keyword" style = "font-weight: bold;"> catch </span> (Exception e)
{
JOptionPane. showMessageDialog (<span class = "keyword" style = "font-weight: bold;"> null </span>, <span class = "string" style = "color: # dd1144; ">" This program can only run with burpsuite_pro_v1.5.01.jar "</span>, <span class =" string "style =" color: # dd1144; ">" BurpLoader by larry_lau@163.com "</span>,
<Span class = "number" style = "color: #009999;"> 0 </span> );
}
}
}
Therefore, the principle of BurpLoader is to forge valid keys for detection. Key input is injected through preference, and I guess it is a fixed Key calculation method, some environment variables are fixed as constants through reflection.
Analysis of the new version of BurpLoader:
The following is an analysis using the BurpLoader version 1.6beta: first try opening the BurpLoader with a JD-GUI:
It seems that this version of BurpLoader uses obfuscation for bytecode. This path cannot be used, so you can directly read the bytecode!
We can see that the strings here are all obfuscated, and every one is decrypted from jsr to 151.
This decryption code has obvious features. A switch uses five paths and transmits different decryption keys to 221. Isn't this the Zelix KlassMaster algorithm? It's just a simple difference, and it's easy to write the decryption machine:
<Span class = "keyword" style = "font-weight: bold;"> public </span> <span class = "class" style = "font-weight: bold; color: #445588; "> <span class =" keyword "> class </span> <span class =" title "> Verify </span >{</span>
<Span class = "keyword" style = "font-weight: bold;"> private </span> <span class = "keyword" style = "font-weight: bold; "> static </span> String decrypt (String str ){
<Span class = "keyword" style = "font-weight: bold; "> char </span> key [] = <span class =" keyword "style =" font-weight: bold; "> new </span> <span class =" keyword "style =" font-weight: bold; "> char </span> [] {<span class =" number "style =" color: #009999; "> 73 </span>, <span class = "number" style = "color: #009999;"> 25 </span>, <span class = "number" style = "color: #009999; "> 85 </span>, <span class =" number "style =" color: #009999; "> 1 </span>, <span class = "number" style = "color: #009999;"> 29 </span> };
<Span class = "keyword" style = "font-weight: bold;"> char </span> arr [] = str. toCharArray ();
<Span class = "keyword" style = "font-weight: bold;"> for </span> (<span class = "keyword" style = "font-weight: bold; "> int </span> I = <span class =" number "style =" color: #009999; "> 0 </span>; I <arr. length; I ++ ){
Arr [I] ^ = key [I % <span class = "number" style = "color: #009999;"> 5 </span>];
}
<Span class = "keyword" style = "font-weight: bold;"> return </span> <span class = "keyword" style = "font-weight: bold; "> new </span> String (arr );
}
<Span class = "keyword" style = "font-weight: bold;"> public </span> <span class = "keyword" style = "font-weight: bold; "> static </span> <span class =" keyword "style =" font-weight: bold; "> void </span> main (String args []) {
System. out. println (decrypt (<span class = "string" style = "color: # dd1144;"> "% x 'sdgu4t3 # x # 'egj" hs.7 % m |/7; hp + l &/S t7tn5v: j'} _ dx % "</span> ));
}
}
The Five Keys are the parameters passed by bipush in the preceding figure. Do not forget that the 1 in iconst_1 is decrypted as follows: larry. lau. javax. swing. plaf. nimbus. NimbusLook: 4
In fact, it is useless to decrypt the string here, because we have obtained the source code of the old version, but it may be very useful in reverse analysis of other software.
Summary & POC
Here is the modified BurpLoader. I have removed the malicious code and output the original value before the modification. You can compile and run this code after adding the burpsuite jar package.
<Span class = "keyword" style = "font-weight: bold;"> package </span> stratburp;
<Span class = "keyword" style = "font-weight: bold;"> import </span> burp. StartBurp;
<Span class = "keyword" style = "font-weight: bold;"> import </span> java. lang. reflect. Field;
<Span class = "keyword" style = "font-weight: bold;"> import </span> java. util. prefs. Preferences;
<Span class = "keyword" style = "font-weight: bold;"> import </span> javax. swing. JOptionPane;
<Span class = "keyword" style = "font-weight: bold;"> public </span> <span class = "class" style = "font-weight: bold; color: #445588; "> <span class =" keyword "> class </span> <span class =" title "> startburp </span>
{</Span>
<Span class = "keyword" style = "font-weight: bold;"> private </span> <span class = "keyword" style = "font-weight: bold; "> static </span> <span class =" keyword "style =" font-weight: bold; "> final </span> String [] clzzData = {<span class =" string "style =" color: # dd1144; ">" burp. ecc "</span>, <span class =" string "style =" color: # dd1144; ">" burp. voc "</span>, <span class =" string "style =" color: # dd1144; ">" burp. jfc "</span>,
<Span class = "string" style = "color: # dd1144;"> "burp. gtc "</span>, <span class =" string "style =" color: # dd1144; ">" burp. zi "</span>, <span class =" string "style =" color: # dd1144; ">" burp. q4c "</span>, <span class =" string "style =" color: # dd1144; ">" burp. pid "</span>, <span class =" string "style =" color: # dd1144; ">" burp. y0b "</span> };
<Span class = "keyword" style = "font-weight: bold;"> private </span> <span class = "keyword" style = "font-weight: bold; "> static </span> <span class =" keyword "style =" font-weight: bold; "> final </span> String [] fieldData = {<span class =" string "style =" color: # dd1144; ">" B "</span>, <span class = "string" style = "color: # dd1144;"> "B" </span>, <span class = "string" style = "color: # dd1144; ">" c "</span>, <span class =" string "style =" color: # dd1144; ">" c "</span>, <span class = "string" style = "color: # dd1144;"> "c" </span>, <span class = "string" style = "color: # dd1144; ">" B "</span>, <span class =" string "style =" color: # dd1144; ">" c "</span>, <span class = "string" style = "color: # dd1144;"> "c" </span> };
<Span class = "keyword" style = "font-weight: bold;"> private </span> <span class = "keyword" style = "font-weight: bold; "> static </span> <span class =" keyword "style =" font-weight: bold; "> final </span> String errortip = <span class =" string "style =" color: # dd1144; ">" This program can only run with burpsuite_pro_v1.5.01.jar "</span>;
<Span class = "keyword" style = "font-weight: bold;"> private </span> <span class = "keyword" style = "font-weight: bold; "> static </span> <span class =" keyword "style =" font-weight: bold; "> final </span> String [] keys = {<span class =" string "style =" color: # dd1144; ">" license1 "</span>, <span class = "string" style = "color: # dd1144;"> "uG4NTkffOhFN/on7RT1nbw =" </span> };
<Span class = "keyword" style = "font-weight: bold;"> public </span> <span class = "keyword" style = "font-weight: bold; "> static </span> <span class =" keyword "style =" font-weight: bold; "> void </span> main (String [] args)
{
<Span class = "keyword" style = "font-weight: bold;"> try </span>
{
<Span class = "keyword" style = "font-weight: bold;"> for </span> (<span class = "keyword" style = "font-weight: bold; "> int </span> I = <span class =" number "style =" color: #009999; "> 0 </span>; I <clzzData. length; I ++)
{
Class clzz = Class. forName (clzzData [I]);
Field field = clzz. getDeclaredField (fieldData [I]);
Field. setAccessible (<span class = "keyword" style = "font-weight: bold;"> true </span> );
<Span class = "comment" style = "font-style: italic; color: #999988;"> // field. set (null, strData [I]); </span>
System. out. println (field. get (<span class = "keyword" style = "font-weight: bold;"> null </span> ));
}
Preferences prefs = Preferences. userNodeForPackage (StartBurp. class );
<Span class = "keyword" style = "font-weight: bold;"> for </span> (<span class = "keyword" style = "font-weight: bold; "> int </span> I = <span class =" number "style =" color: #009999; "> 0 </span>; I <keys. length; I ++)
{
String v = prefs. get (keys [I], <span class = "keyword" style = "font-weight: bold;"> null </span> );
System. out. println (prefs. get (keys [I], <span class = "keyword" style = "font-weight: bold;"> null </span> ));
}
StartBurp. main (args );
}
<Span class = "keyword" style = "font-weight: bold;"> catch </span> (Exception e)
{
JOptionPane. showMessageDialog (<span class = "keyword" style = "font-weight: bold;"> null </span>, <span class = "string" style = "color: # dd1144; ">" This program can only run with burpsuite_pro_v1.5.01.jar "</span>, <span class =" string "style =" color: # dd1144; ">" Notice "</span>, <span class =" number "style =" color: #009999; "> 0 </span> );
}
}
}
The effect is shown in the screenshot.
The first eight lines of output are the original values of the target maliciously modified by the former BurpLoader (for my computer). The number of times the same device runs remains unchanged, the following key is a maliciously modified value because I have run the BurpLoader before (but cannot be verified by the Burpsuite because the first eight rows are not modified ), it can be seen that the BurpLoader actually uses the same key to register all the different computers, but it only modifies and fixes some environmental variables involved in key computing. This is probably the main idea of cracking the Burpsuite, how can we calculate the license that can be used at first?