1、初识 llvm源码编译 及virtualbox和ubuntu环境搭建

2023-12-14 11:01:13

很久没更新了,最近准备研究逆向和加固,于是跟着看雪hanbing老师学习彻底搞懂ollvm,终于把所有流程跑通了,中间遇到了太多的坑,所以必须记录一下,能避免自己和帮助他人最好。

环境搭建太重要了,折腾了好几遍,老师的视频里对初始环境说得太少了,吃了太多这方面的亏,这里我是在windows中添加虚拟机完成的,原以为mac上应该也可以,但后面发现还是很多地方走不通。

系统使用VirtualBox和ubuntu-18.0.4,最新的版本需要编译的时间会很长

virtualbox下载地址:Oracle VM VirtualBox - Downloads | Oracle Technology Network | Oracleicon-default.png?t=N7T8https://www.oracle.com/virtualization/technologies/vm/downloads/virtualbox-downloads.htmlubuntu 下载地址 :?

https://old-releases.ubuntu.com/releases/18.04.4/ubuntu-18.04.3-desktop-amd64.isoicon-default.png?t=N7T8https://old-releases.ubuntu.com/releases/18.04.4/ubuntu-18.04.3-desktop-amd64.iso

先安装虚拟机环境并配好网络,整个下载和安装过程大部分时间就是等

下载好这两个文件后,可以开始安装了

我准备了一个空盘,465G,为了防止llvm编译时内存报错,搞得很大

VirtualBox安装,配置内存24000MB,差不多20G,处理器8,硬盘给到320G,因为llvm编译很容易内存溢出,所以硬件还是要跟上,这里我是吃过亏的。

配置完毕后,等待一段时间的安装,检查Terminal应用是否正常,默认浏览器是否能上网。

terminal无法打开的问题解决:

CTRL + ALT + F3 # 进入命令行模式(需要返回桌面时CTRL + ALT + F1)
cd /etc/default
sudo nano locale
# 把文件中的 “en_US” 改成 “en_US.UTF-8”
#注意是所有的en_US,我这边发现了两处
# 保存退出
sudo locale-gen --purge
reboot # 重启虚拟机

安装git,去官网下载llvm 9.0.1版本源代码,注意是linux的版本,然后上传到一个自己的git仓库,这里上传是为了后面有用,这里很重要,后面要做代码分支切换。

下载地址:https://github.com/llvm/llvm-project/releases/download/llvmorg-9.0.1/llvm-project-9.0.1.tar.xz

git 添加ssh命令

ssh-keygen -t ed25519 -C "your_email@example.com"

安装llvm编译命令,同Android源码编译的命令相同:

sudo apt-get install git-core gnupg flex bison build-essential zip curl zlib1g-dev libc6-dev-i386 libncurses5 lib32ncurses5-dev x11proto-core-dev libx11-dev lib32z1-dev libgl1-mesa-dev libxml2-utils xsltproc unzip fontconfig

?安装完毕后可以编译安卓源码也可以编译llvm。

安装cmake, sudo apt install cmake?

安装ninja , sudo apt-get install ninja-build

两个工具安装完毕后,mkdir build-debug? cd build-debug

cmake -G Ninja -DCMAKE_BUILD_TYPE=Debug -DLLVM_ENABLE_PROJECTS="clang" ../llvm

目录结构如上,命令正常后执行,ninja -j8,然后等待编译完成。3000多个文件,至少半个小时吧。

同样的操作,再编译release目录,先创建build-release文件夹,再执行

cmake -G Ninja -DCMAKE_BUILD_TYPE=Release -DLLVM_ENABLE_PROJECTS="clang" ../llvm

同样执行 ninja -j8。

然后就是在clion中编译llvm了,先去官网下clion并安装,注意下载的是linux的版本,

clion下载地址:

Download CLion: A Smart Cross-Platform IDE for C and C++

打开llvm项目,目录为/home/nowind/llvm/llvm-project-9.0.1/llvm /CMakeLists.txt,然后手动配置CMake参数:

Debug和Release,-G Ninja -DLLVM_ENABLE_PROJECTS="clang",在llvm目录下会自动生成

cmake-build-debug和cmake-build-release目录,再使用命令行进入这两个目录,执行ninja -j8

debug模式在编译llc文件的时候,我等了将近半个小时,也是这里容易将内存给崩了,需要随时查看free -m,查看剩余内存还够不够,不够就添加swap内存。这个文件非常难过,编译完成后直接吞掉了我近100G,编译后debug包的大小有65G

这里我添加了40G的swap内存

sudo swapoff -a

sudo rm /swapfile

sudo dd if=/dev/zero of=/swapfile bs=1M count=40960

sudo chmod 600 /swapfile

sudo mkswap /swapfile

sudo swapon /swapfile

sudo swapon --show

以上是在外层生成的编译文件,但我在后面看老师讲解的时候,并没有用到这个,所以很奇怪,为啥多这一步,如果时间不足可以先往后看,有空再来编译这边的。

终于编译完了。

编译最大的坑:报错ninja: warning: bad deps log signature or version; starting over

ninja 版本不一致,导致日志文件损坏,每次修改代码都会全部重新编译,甚至reload cmake project都会损坏日志,需要将clion中使用的ninja版本改成和本地的一致

???????

编译遇到错误:

llvm-project-9.0.1/llvm/utils/benchmark/src/benchmark_register.h:17:30: error: ‘numeric_limits’ is not a member of ‘std’ 17 | static const T kmax = std::numeric_limits<T>::max();

需要在llvm-project-9.0.1/llvm/utils/benchmark/src/benchmark_register.h中增加

#include <limits>

无论在clion中编译还是使用cmake直接编译,都是后续的第一步,这步遇到问题,一定是要解决的

接下来我们使用编译后的clang和llvm来执行c文件

先配置环境变量:

export PATH=/home/nowind/llvm/llvm-project-9.0.1/llvm/cmake-build-debug/bin:$PATH
clang -emit-llvm -S hello_clang.c -o hello_clang.ll    其中ll文件可以直接修改,改字符串名字和长度
lli hello_clang.ll
llvm-as hello_clang.ll -o hello_clang.bc
llc hello_clang.bc -o hello_clang.s  转化成汇编
clang  hello_clang.s -o hello_clang_s 汇编转可执行文件
llvm-dis hello_clang.bc -o hello_clang_re.ll   同样可以把bc文件转ll文件,和上面使用clang的结果是一样的
opt --print-bb hello_clang.bc 打印内容

熟悉下c文件编译后的几种格式? ? 灵活运用

clion断点调试,

使用clang命令行:

clang?/home/nowind/llvm/pro/pro1/hello_clang.c -o?/home/nowind/llvm/pro/pro1/hello_clang_s

使用clang 断点:clion 切换到Clang Debug模式,配置参数

/home/nowind/llvm/pro/pro1/hello_clang.c -o /home/nowind/llvm/pro/pro1/hello_clang_s

然后断点打在/home/nowind/llvm/llvm-project-9.0.1/clang/tools/driver/driver.cpp的main函数中,这里是clang的入口

使用pass:

bc或者ll文件使用hello pass

opt 命令行运行

opt -load /home/nowind/llvm/llvm-project-9.0.1/llvm/cmake-build-debug/lib/LLVMHello.so -hello /home/nowind/llvm/pro/pro1/hello_clang.ll

clion调试opt? 切换至 opt debug,进行断点 在 llvm/lib/Transform/Hello/hello.cpp

配置参数?

-load /home/nowind/llvm/llvm-project-9.0.1/llvm/cmake-build-debug/lib/LLVMHello.so -hello /home/nowind/llvm/pro/pro1/hello_clang.bc 

以上基本是第一课的所有内容了,并不复杂,但编译时间会比较长,遇到相关问题也可以一起讨论

文章来源:https://blog.csdn.net/ahjxly/article/details/134853031
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。