内核pwn环境

1
2
3
4
5
1. qemu安装与使用
2. busybox文件系统
3. kernel编译
4. 启动kernel
5. kernel调试

qemu的安装和使用

  • 主要需要了解Kernel-mode emulation
  • 还有qemu system

busbox文件系统

  • 当做内核开发和研究的时候,并不需要准备完备的文件系统,那样太复杂也很占存储空间,busybox对于kernel开发和调试来说正好合适

  • 当进行跨平台内核调试时,用完备的ext4系统,运行非常慢,busybox主要是为了嵌入式之类的运算能力弱的设备

  • qemu-system的纯软件模拟非常慢,busybox刚好合适

  • 一般选择:自定义安装busybox(编译安装)

  • 注意:

    • busybox默认是动态编译,但是这里需要的是静态编译,如果动态编译的话会让文件系统变得很大
  • 首先下载依赖工具(编译安装的工具)

1
2
sudo apt update
sudo apt install build-essential libncurses-dev bison flex
  • 然后使用命令去官网上下载busybox
1
wget https://busybox.net/downloads/busybox-1.36.1.tar.bz2
  • 下载之后解压缩文件
1
2
tar xjf busybox-1.36.1.tar.bz2
cd busybox-1.36.1
  • 然后进行编译安装make xxxxxconfig,busybox提供了几种编译配置
    • defconfig(缺省配置)
    • allyesconfig(最大配置)
    • allnoconfig(最小配置)
    • 这里我们一般选择缺省配置
1
make defconfig
  • 然后是make menuconfig,选择静态编译
    • 当你认为上述配置中还有不满意的地方,可以进行微调,加入或去除某些命令。
  • make menuconfig进入后选择安装位置,进入设置

image-20240831125531168

  • 将静态链接选择进去

image-20240831125737790

  • 然后也可以选择这个修改安装目录

image-20240831125828178

  • 选择保存你所选择的配置

image-20240831130532459

  • 最后就是编译安装了
1
2
在x86_64下只要输入该指令即可:make -j4
如果要使用ARM64编译的话需要输入指令make -j4 CROSS_COMPILE=aarch64-linux-gnu-
  • 编译好了之后进行安装
1
make install
  • 安装好后找到你之前配置的安装路径

image-20240831131311999

内核pwn介绍

附件介绍

  • 一般的内核pwn都会存在三个文件
    • boot.sh:启动脚本
    • balmage:内核
    • rootfs.cpio:BusyBox 文件系统的文件,该文件里面就会有相对应的内核
    • babydriver.ko:这时驱动

image-20240831132022935

image-20240831132324373

busybox文件

init文件

  • init文件中可以自行配置出方便我们调试的配置

image-20240831132742272

pack.sh文件

  • 主要做一些前置工作。init,etc之类的我们完全可以自定义,到这里文件系统基本搭建完成

image-20240831132841290

内核pwn本地题目搭建

1
./pack.sh
  • 打包好后所生成的文件系统就在这个里面,取决于你的安装目录,我的应该会在installroot

image-20240831133637690

内核编译

  • 在对内核进行编译的时候需要查看题目的内核脚本

  • 对题目附件bzImage进行如下命令操作

    • 可以看到是4.4.42的内核版本
1
file bzImage

image-20240831133926642

  • 所以这就需要去官网下载4.4.42版本对应的内核文件,下载地址如下

Index of /pub/linux/kernel/v4.x/

  • 然后还要查看使用的gcc版本
    • 可以从图中可以得知gcc版本为5.4.0,这个版本对应的刚好就是Ubuntu16.04的gcc。对应的内核版本最好在对应的gcc上编译,否则会出现某些奇怪的问题
1
string bzImage | grep gcc

image-20240831135414477

  • 接下来就开始编译了
  • 这里先介绍一下几个编译指令。注意:如果是第一次编译内核的话可能会缺少某些依赖,这时候根据报错下载对应的依赖即可。如果缺少什么就到官方网站查找缺少的东西即可https://pachages.ubuntu.com/sv/
1
2
3
4
5
6
7
8
make menuconfig # 需要什么的参数,都在这里配置
make help # 查看可以编译的帮助信息
make -j4 bImage # 仅编译内核

跨平台编译
ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- make config
ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- make help
ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- make -j4 Image
  • 这里一般不要修改make menuconfig,输入make menuconfig然后退出即可

  • 有些内核没有开启debug symbol选项,需要我们自行开启,即下图文件没有带该选项

    • 在编译的时候要带上参数CONFIG_DEBUG_INFO=y

image-20240831140741744

  • 编译时,如果驱动参数不对的花,就make menuconfig调整
  • 直接通过字符串搜索查看参数,不同版本略有差异

image-20240831141034477

内核启动

  • 编写启动脚本,在init文件下编写

image-20240831141230301

  • 然后使用打包命令后再运行启动脚本,即可启动内核

image-20240831141306446

内核exp

  • 在写好exp脚本之后,在pack.sh这个脚本中要进行配置

  • 在编译的时候一般是要静态编译的,一般出题人所出的题目文件系统里面是不包含动态链接库的,所以要选择静态编译

image-20240831143109623
  • 然后再在pack.sh这个脚本中将exp复制到文件系统里面
image-20240831143255230
  • 然后再文件系统里面运行exp,这样就能获得root权限了

image-20240831143345798

内核调试

  • 手动安装符合表:使用gdb调试内核的时候一般是不会正常识别驱动的符号表。
  • 要使用root权限,找到解区表,该表通常会保存在sys文件夹下面,冉家找到这里面的.text,再以root权限读出基地址值。
    • 其他的根据需求读入.bss.data等文件里面的基地址内容

image-20240831143814039

  • 然后配置gdb.sh

image-20240831144014287

  • 下面是一个例子

  • 先获得root权限,然后使用find命令找到符号表

1
find /sys/ | grep babydriver
  • 然后找到相应文件,并读出文件里面的相关基地址

image-20240831144348156

  • 将相关信息配置进入gdb.sh这个脚本文件里面

image-20240831144447502

  • 符号表导入进去后,使用gdb调试时就会出现符号表了

image-20240831144535969