虚拟机获取

在其官网存在虚拟机版本供其下载,这里我下载的是ova虚拟机镜像。

Pasted_image_20240913164546.png

打开虚拟机镜像

直接使用7z工具进行打开,可以看到本质是zip压缩包文件,内为vmdk格式镜像

Pasted_image_20240913164857.png

继续打开vmdk文件,发现为两个img镜像组成。
Pasted_image_20240913165803.png

0.img

0.img文件为系统启动镜像,负责系统启动初期的运行和解密分区等流程。

Pasted_image_20240913170343.png

GRUB中配置了密码,防止直接修改GRUB参数绕过。虽然可以直接删除密码绕过。。。
Pasted_image_20240913170818.png

使用hexdump查看文件,发现以下文件是加密的,而不是直接的img文件:
initramfs-0-rescue-795882a352b9438790405ff6361875b5.img
initramfs-4.19.181.img
Pasted_image_20240913203627.png

Pasted_image_20240913203837.png

initramfs-4.19.181kdump.img作为kdump使用并未加密。

1.img

root和app分区为LUKS加密,其余分区为xfs分区。

解密initramfs

分析不了一点vmlinuz引导,直接简单点,使用虚拟机运行,引导至系统启动后进行暂停虚拟机拍摄快照。

Snipaste_2024-09-14_10-13-59.png

找到虚拟机文件,找到快照文件*.vmem
Snipaste_2024-09-14_10-14-21.png

使用010edit打开该文件,并搜索关键词。如:initramfs
可以看到搜索到了shell解密initramfs.img命令
openssl rc4 -K a5a7391025cd4052b3fd170e3c749163 -nosalt -e -nopad -in "$outfile" -out /boot/initramfs.img
Snipaste_2024-09-14_10-28-04.png

使用rc4密钥可以成功解密该img文件。
如果出现
40A712850E7F0000:error:0308010C:digital envelope routines:inner_evp_generic_fetch:unsupported:../crypto/evp/evp_fetch.c:349:Global default library context, Algorithm (RC4 : 37), Properties ()

则说明openssl版本较高,使用低版本即可解决。或者使用工具解密https://tomeko.net/bin/RC4/FileEncryptDecrypt.zip By https://tomeko.net/online_tools/rc4.php?lang=en

Pasted_image_20240914221346.png

解密后文件可以使用7z工具打开。
Pasted_image_20240914221606.png

/etc/crypttab文件中存在解密方法root /dev/disk/by-uuid/84b916e1-2242-409d-b2ba-ebf149be7a9a /etc/.appconf/.ramfs
Pasted_image_20240914222309.png

发现相关目录下存在两个文件,一个4k大小的乱码文件,一个headerless的LUKS加密分区文件。
Pasted_image_20240914222405.png

通过搜索内存中cryptsetup命令,发现一处解密的方法。
Snipaste_2024-09-14_10-44-42.png

继续搜索发现.ramfs文件为使用GPG加密的密文,其内容为LUKS加密分区的密码。
Snipaste_2024-09-14_11-26-13.png

搜索不到相关的GPG解密key信息,只好作罢。

解密LUKS加密分区

再次回到快照文件,这次直接使用工具搜索AES的key。
这里使用aeskeyfind ,可以搜索到一些KEY信息。(这里没保存截图)因为LUKS分区默认的master-key是32位的byte,所以排除非16位的byte(显示的hex是字符串类型,所以实际上是32/2大小)。剩下的结果使用python进行排列组合。

strings = [
    "96448b38426076d0332f917d3b28741f4f02d41e32928056b3bb1649526ce8c2",
    "e537e35b305f61e3a674c9d0e1344af261c7e1047a1f363bbb0997f84e460ddc",
    "22d7beb261f134f98e4806504eccd8293c4b5703828d4ac32a510519a43ff836",
    "6b044f66ebbd881dc5954bc69958319a857e9993fd33b17f8f30de266fd32ae9",
    "f2d2ae5c0c849f554da11aed169de5b6f76d1a7258be41b8e399862ac82b1040",
    "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f",
    "db27271c5486bd6820f4603eeb4b6457d3c11f6f1f3e79b9f05ebc83d22581f6",
    "0414dee9cab868f11977ab9552f3b48b632039848143fa8c3dc7d3dd71c86208",
    "29fd7e7664257fd4de1c8be84530d5d360330aa54c2ffabc934f1925eaaf394e",
    "509fa5d0157b2fcca0ce7c3d4c31e6a5d442aae9c9119ea9e660db984a8fe106",
    "78d094ecbe61fd098905748ff4a015d45cb0802ea48ea07f0b9d93e03613da36",
    "f918c5501338737c1e41d243c3edcccb35e1f1129894744aeb58e02096f44281",
    "90152e70bfe5fe834e941abd2778f5371a311753e14cada68cb5c3d1ee089f43",
    "36ea213eed82e4cc00be713b6d1f25a5b784a9a0c6c579f968523f725f09bec4",
    "caee146e5c6e6d8745b63575df55ff92e7290a816a538f76685f86e9fcfd01a1",
    "3266b9a1fda52877c9f2d1f44c9e071290d055ff017a244011a71a4075958091"
        ]

import itertools

for idx, (a, b) in enumerate(itertools.permutations(strings, 2)):
    combined_hex = a + b
    combined_bytes = bytes.fromhex(combined_hex)
    print(f"{idx+1}")
    with open(f"{idx+1}.txt", "wb") as f:
        f.write(combined_bytes)

这里共生成了240中组合。再次使用shell脚本去暴力枚举出正确的key。

#!/bin/bash

start=1
end=240

for ((i=$start; i<=$end; i++))
do
	key_file="1.txt"
	if [ $i -gt 1 ]; then
		key_file="${i}.txt"
	fi

	output=$(cryptsetup luksOpen /tmp/root.img rootenc --master-key-file="$key_file" 2>&1)
	if [[ "$output" != *"Volume key does not match the volume."* ]]
	then
		echo "Found matching key in file: $key_file"
		echo "$output"
	fi
done

经过计算,发现48.txt的master-key可以进行解密。

6b 04 4f 66 eb bd 88 1d c5 95 4b c6 99 58 31 9a  
85 7e 99 93 fd 33 b1 7f 8f 30 de 26 6f d3 2a e9  
22 d7 be b2 61 f1 34 f9 8e 48 06 50 4e cc d8 29  
3c 4b 57 03 82 8d 4a c3 2a 51 05 19 a4 3f f8 36

同样方法,另一个加密分区的master-key也破解出来了16.txt

e5 37 e3 5b 30 5f 61 e3 a6 74 c9 d0 e1 34 4a f2 
61 c7 e1 04 7a 1f 36 3b bb 09 97 f8 4e 46 0d dc 
96 44 8b 38 42 60 76 d0 33 2f 91 7d 3b 28 74 1f 
4f 02 d4 1e 32 92 80 56 b3 bb 16 49 52 6c e8 c2

master-key与key-file

cryptsetup中,存在key-file和–master-file的参数项,他们之间的关系为:
因为分区加密很耗时间,为了节省资源,加密逻辑如下:

  1. 用户密码key使用算法加密master-key并保存加密后的master-key信息。
  2. master-key进行分区加密。

所以,如果用户更改了key-file,只需要计算出加密后的master-key更新即可。大大缩减了资源消耗。
这里很明显,即使用户更改了密码,但是master-key是不会更改的(每改密码一次都要全加密分区重新计算读写不现实)。我们只需要知道master-key的信息照样可以在不知道密码的情况下解密LUKS加密分区。

挂载lvm文件为分区

使用下面命令进行挂载

# 挂载lvm文件为回环设备并显示分配的设备名
sudo losetup -f --show xxx.lvm
# 列出/dev/loop0设备上物理卷信息
sudo pvs /dev/loop0
# 激活卷组cl(上一步命令中获取) 中的所有物理卷
sudo vgchange -ay cl
# 扫描系统中已识别到的lvm分区的信息
sudo vgscan 
# 获取设备块信息
lsblk

经过上面的命令,可以成功挂载lvm文件为分区。

挂载xfs分区

使用命令进行挂载

sudo mount -t xfs /dev/mapper/分区名 <挂载点>