clion是linux下比较强大的C/C++ IDE,通过扩展也可以支持很多其他语言,例如shell,lua, perl, python,rust。唯一缺点是收费,但是相对它给我带来的便利,这点费用不算什么。我一般用来开发C/C++/项目,它支持3种方式解析工程源码,分别是
- Makefile
- CMake
- 编译数据库
像代码的高亮,跳转,补全,都依赖对源码的解析,其实CMake和Makefile应该是一回事,CMake最终也会生成Makefile。首先通过make分析出工程里面用到哪些源文件,然后通过内置语法分析器解析得到符号表等信息,从而实现高亮,补全等。
当你的工程是针对你开发的PC时,这些都没问题,但是如果是交叉编译时,便会由于无法通过make来获取依赖的源文件,导致接下来的语法分析也无法进行。例如基于openwrt,buildroot开发时,或者编译uboot,kernel。因为这些构建框架都有自己特定的一些环境变量,编译脚本什么的,导致clion这种IDE无法简单的通过指定工具链来执行make,来分析依赖的源文件。于是编译数据库这种方式就派上了用场。cmake可以直接生成编译数据库,通过cmake -DCMAKE_EXPORT_COMPILE_COMMANDS=1
,但是嵌入式开发里面用的一些库,工具可能是基于比较古老的版本,仅支持automake, makefile等。此时需要借助另一个工具bear
,ubuntu20.04上直接apt安装即可,或者源码编译。bear
的用法十分的简单
bear 编译命令
#例如,builrdroot中编译某个软件
bear make xl2tpd-{dirclean,build}
#或者,openwrt中
bear make package/xl2tpd/{clean,prepare,compile}
它的工作原理好像是创建子进程执行编译命令,然后监听工具链的gcc的调用,类似strace分析gcc的调用,知道gcc执行时,参数是怎么样的,open等系统调用又是怎么样的。最终生成编译数据库文件,其实就是个json文件。这个文件里面对每个gcc处理过的文件作了记录,包括3个值:
- gcc的参数
- 源文件名称
- 源文件目录
{
"arguments": [
"/home/a/workspace/exc-m620d/openwrt/staging_dir/toolchain-arm_cortex-a7+neon-vfpv4_gcc-5.4.0_musl-1.1.16_eabi/bin/arm-openwrt-linux-muslgnueabi-gcc",
"-c",
"-Os",
"-pipe",
"-mcpu=cortex-a7",
"-mfpu=neon-vfpv4",
"-fno-caller-saves",
"-fno-plt",
"-fhonour-copts",
"-Wno-error=unused-but-set-variable",
"-Wno-error=unused-result",
"-mfloat-abi=hard",
"-iremap/home/a/workspace/exc-m620d/openwrt/build_dir/target-arm_cortex-a7+neon-vfpv4_musl-1.1.16_eabi/xl2tpd-devel-20151125:xl2tpd-devel-20151125",
"-Wformat",
"-Werror=format-security",
"-fstack-protector",
"-D_FORTIFY_SOURCE=1",
"-I/home/a/workspace/exc-m620d/openwrt/staging_dir/target-arm_cortex-a7+neon-vfpv4_musl-1.1.16_eabi/usr/include",
"-I/home/a/workspace/exc-m620d/openwrt/staging_dir/target-arm_cortex-a7+neon-vfpv4_musl-1.1.16_eabi/include",
"-I/home/a/workspace/exc-m620d/openwrt/staging_dir/toolchain-arm_cortex-a7+neon-vfpv4_gcc-5.4.0_musl-1.1.16_eabi/usr/include",
"-I/home/a/workspace/exc-m620d/openwrt/staging_dir/toolchain-arm_cortex-a7+neon-vfpv4_gcc-5.4.0_musl-1.1.16_eabi/include/fortify",
"-I/home/a/workspace/exc-m620d/openwrt/staging_dir/toolchain-arm_cortex-a7+neon-vfpv4_gcc-5.4.0_musl-1.1.16_eabi/include",
"-DDEBUG_PPPD",
"-DTRUST_PPPD_TO_DIE",
"-fno-builtin",
"-Wall",
"-DSANITY",
"-DLINUX",
"-I./linux/include/",
"-DUSE_KERNEL",
"-DIP_ALLOCATION",
"-o",
"call.o",
"call.c"
],
"directory": "/home/a/workspace/exc-m620d/openwrt/build_dir/target-arm_cortex-a7+neon-vfpv4_musl-1.1.16_eabi/xl2tpd-devel-20151125",
"file": "call.c"
}
然后语法分析器就知道分析谁了。这样就可以愉快的使用clion阅读编辑跑在ARM上的代码了。不过有个地方需要注意,如果你的交叉编译工具链是通过export到环境变量的方式来执行的,那么编译数据库的的arguments的第一项,gcc就不会是一个绝对路径,导致clion解析异常,这时只要全局替换这个编译数据库文件里面的xxx-gcc为绝对路径即可。其实我认为这个应该是bear需要改进的一个地方,bear在填这个工具链的gcc时,通过realpath就知道工具链的绝对路径。
标签:gcc,交叉,neon,编译,vfpv4,clion,arm,openwrt From: https://www.cnblogs.com/thammer/p/17665846.html