我认为代码除了混淆之外还被严重混淆,我可以识别出它正在使用DESEDE和CBC和PKCS5Padding这样的算法来加密来自应用的http发布流量。我的问题是,有人知道如何在这里检索密钥吗?
package c.e.a.a.g;
import a.a;
import android.util.Base64;
import java.io.UnsupportedEncodingException;
import java.security.GeneralSecurityException;
import java.security.InvalidKeyException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Random;
import java.util.regex.Pattern;
import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.spec.SecretKeySpec;
public class b {
/* renamed from: a reason: collision with root package name */
private static volatile b f4799a;
/* renamed from: b reason: collision with root package name */
private byte[] f4800b = null;
/* renamed from: c reason: collision with root package name */
private String f4801c;
private b() {
try {
this.f4801c = a.a(new byte[]{97, 110, 100, 95, 50, 51, 116, 107, 108, 35, 95, 97, 105, 116, 33}, new byte[]{75, 24, 109, 27, -24, -51, 22, -58, -44, -74, 21, 91, -88, 48, -52, -63, 69, -67, 71, 17, 116, 77, 70, -94, 41, 121, 20, 120, 8, 121, 33, 77});
} catch (GeneralSecurityException e2) {
e2.printStackTrace();
}
this.f4800b = e(this.f4801c);
}
public static b a() {
if (f4799a == null) {
synchronized (b.class) {
if (f4799a == null) {
f4799a = new b();
}
}
}
return f4799a;
}
private final String c(String str) {
try {
Cipher instance = Cipher.getInstance("DESEDE/ECB/PKCS5Padding");
instance.init(2, new SecretKeySpec(this.f4800b, "DESede"));
return a(instance.doFinal(new a().a(str)));
} catch (Exception e2) {
e2.printStackTrace();
return null;
}
}
private final String d(String str) {
try {
Cipher instance = Cipher.getInstance("DESEDE/ECB/PKCS5Padding");
instance.init(1, new SecretKeySpec(this.f4800b, "DESede"));
try {
return Base64.encodeToString(instance.doFinal(str.getBytes()), 0);
} catch (IllegalBlockSizeException e2) {
e2.printStackTrace();
return "";
} catch (BadPaddingException e3) {
e3.printStackTrace();
return "";
}
} catch (NoSuchAlgorithmException e4) {
e4.printStackTrace();
} catch (NoSuchPaddingException e5) {
e5.printStackTrace();
} catch (InvalidKeyException e6) {
e6.printStackTrace();
}
}
private final byte[] e(String str) {
try {
return MessageDigest.getInstance("MD5").digest(str.getBytes("UTF-8"));
} catch (NoSuchAlgorithmException e2) {
e2.printStackTrace();
return null;
} catch (UnsupportedEncodingException e3) {
e3.printStackTrace();
return null;
}
}
public String b(String str) {
StringBuilder sb = new StringBuilder();
sb.append(str);
sb.append(b());
return d(sb.toString());
}
private String b() {
int nextInt = new Random().nextInt(999999);
StringBuilder sb = new StringBuilder();
sb.append("|");
sb.append(nextInt);
return sb.toString();
}
public String a(String str) {
return c(str).split(Pattern.quote("|"))[0];
}
public b(String str) {
this.f4800b = e(str);
}
private final String a(byte[] bArr) {
StringBuffer stringBuffer = new StringBuffer();
for (byte b2 : bArr) {
stringBuffer.append((char) b2);
}
return stringBuffer.toString();
}
}
此代码生成的加密的HTTP发布请求示例如下:
{"MobileUsersBE":{"AppVersion":"vB0gg8dKw8/ssTAXDUHLDw==\n","DeviceCode":"NUIDvs43seBumI3SU7Q1R/NWzO0ylo08jPjWcGUxZsFCjEu/IEjcEUYM4V6zswVc\n","DeviceType":"android","GCMCellId":"","Password":"P4fM264BxQXhd3RQu5vk8w==\n","UserName":"i2WZyhFJ9CZTx40Th83siw==\n"},"ServiceUsersBE":{"AppVersion":"ZA+PaD1HcAVZ384ENwEWBw==\n","DeviceCode":"NUIDvs43seBumI3SU7Q1R/NWzO0ylo08jPjWcGUxZsFOFoCbYVotoPrT8YV4yEHL\n","DeviceType":"android","Password":"t1h6/ATZ26VA8nS+fcnvkv0wtPbV8onO\n","TransactionCode":"vfTVe1PFdoFSMOdyYSxAI33cLtBw3z3uUrzOGlZJafQYzgg+Te+n/sDv/nyll3T2","UserName":"N67a2TEuY68jsRadkP0JGrh64aKxVin1\n"}}
#1 楼
加密密钥存储在变量f4800b
中。它出现在以下字节数组中。43, 57, 97, -68, -63, -61, -40, 9, 50, 87, -104, 101, 63, 34, -78, 60
使用的密码算法是ECB模式下的Triple-DES。可以通过以下片段对其进行解密。请注意,它需要用于Java的BouncyCastle加密提供程序。
import java.security.*;
import java.util.Base64;
import javax.crypto.Cipher;
import javax.crypto.spec.SecretKeySpec;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
public class Main
{
public static void main(String args[]) throws Exception
{
Security.addProvider(new BouncyCastleProvider());
byte key[] = new byte[] {43, 57, 97, -68, -63, -61, -40, 9, 50, 87, -104, 101, 63, 34, -78, 60};
//Base64 encoded cipher text here
byte ct[] = Base64.getDecoder().decode("i2WZyhFJ9CZTx40Th83siw==");
Cipher instance = Cipher.getInstance("DESEDE/ECB/PKCS5Padding");
instance.init(Cipher.DECRYPT_MODE, new SecretKeySpec(key, "DESede"));
String pt = new String(instance.doFinal(ct));
System.out.println(pt);
}
}
示例输出
使用提供的JSON代码段
{
"MobileUsersBE":{
"AppVersion":"vB0gg8dKw8/ssTAXDUHLDw==\n",
"DeviceCode":"NUIDvs43seBumI3SU7Q1R/NWzO0ylo08jPjWcGUxZsFCjEu/IEjcEUYM4V6zswVc\n",
"DeviceType":"android",
"GCMCellId":"",
"Password":"P4fM264BxQXhd3RQu5vk8w==\n",
"UserName":"i2WZyhFJ9CZTx40Th83siw==\n"
},
"ServiceUsersBE":{
"AppVersion":"ZA+PaD1HcAVZ384ENwEWBw==\n",
"DeviceCode":"NUIDvs43seBumI3SU7Q1R/NWzO0ylo08jPjWcGUxZsFOFoCbYVotoPrT8YV4yEHL\n",
"DeviceType":"android",
"Password":"t1h6/ATZ26VA8nS+fcnvkv0wtPbV8onO\n",
"TransactionCode":"vfTVe1PFdoFSMOdyYSxAI33cLtBw3z3uUrzOGlZJafQYzgg+Te+n/sDv/nyll3T2",
"UserName":"N67a2TEuY68jsRadkP0JGrh64aKxVin1\n"
}
}
下面显示的是密文和解密到的密文。
vB0gg8dKw8/ssTAXDUHLDw==
2.3|138771
NUIDvs43seBumI3SU7Q1R/NWzO0ylo08jPjWcGUxZsFCjEu/IEjcEUYM4V6zswVc
8f850645-36ec-350a-8bb3-09c004daeb14|36159
P4fM264BxQXhd3RQu5vk8w==
test1234|364081
i2WZyhFJ9CZTx40Th83siw==
test|55664
请注意,每个纯文本均在
|
符号后附加一个随机数。这就像盐一样,因此相同的纯文本不会加密为相同的密文。评论
评论不作进一步讨论;此对话已移至聊天。
– 0xC0000022L♦
20-3-22在23:16
评论
与参考。根据您发布的代码,密钥派生为md5(this.f4801c)。您需要找出a.a函数对两个字节数组的作用。你好,兄弟@ 0xec,我已经在这里将a.a的源代码发布在[pastebin.com/L03kwbpj]中,感谢您的帮助,在某些情况下,此方法代码看起来像是在进行解密。看看,感谢您的帮助。