初识defconfig

什么是defconfig?

  • defconfig是决定什么内容将被编译进内核的关键文件,位于arch/<架构>/configs
  • defconfig将被传入给内核的编译系统,指导编译系统选择性的编译内核代码的东西
  • 编译内核前defconfig将会通过make <config name>的方式传入给内核

defconfig是从哪里来的?

  • 这个问题问的好啊,首先它肯定不是由我们这些kanger默写出来的
  • 高通机型的对应defconfig最终都来源于CAF开源代码中的对应芯片组的defconfig,比如
sdm660-perf_defconfig (sdm660)
msm-perf_defconfig (msm8996)
msmcortex-perf_defconfig (msm8998)
sm8150-perf_defconfig (sm8150)
sdm845_defconfig (sdm845)
  • 厂商/内核开发者会将这些config复制一份,然后在其中增加自己的修改(启用自己专有的驱动之类的)

我怎么知道有哪些条目可以用?

  • defconfig的条目全部定义在内核各个目录的Kconfig文件中,比如
config BOOST_CONTROL
    bool "boost control"
    default y
    help
      A simple driver to control boosts in userspace.

defconfig在编译系统中是如何被使用的?

  • 首先是在Makefile中控制一个代码文件是否被编译,比如
obj-$(CONFIG_BOOST_CONTROL)        += boost_control.o
  • 其次是可以在代码中控制哪些代码要被编译进去,比如
#ifdef CONFIG_DYNAMIC_STUNE_BOOST
int do_stune_boost(char *st_name, int boost);
int reset_stune_boost(char *st_name);
#endif /* CONFIG_DYNAMIC_STUNE_BOOST *

这里有个注意点,那就是Kconfig中的条目是没有CONFIG_的“头部”的

编辑deconfig

这也许是很多人非常迷惑的点,为什么别人的commit都是在config的中间增减修改,他们怎么知道往哪儿放?
接下来让本菜鸡教各位大佬改config
也许很多操作非常不标准,欢迎补充更加“正式”的方法

两种config

  • 目前常见的defconfig保存方式其实有两种,一种是最简config,比如CAF开源代码中的默认config。另一种是在第三方开发中可以见到的完整defconfig,它包含了整个内核树的全部config选项,可以让你一(没)目(有)了(卵)然(用)
  • 两种config本质是一样的,最简defconfig在执行了make <config name>后也会在输出目录生成完整的.config
  • 至于你喜欢怎么保存你的config,这是一个信仰问题,反正我觉得,最简config赛高
  • 还有第三种defconfig,那就是手工修改后生成的垃圾config

接下来教各位大佬如何摆脱垃圾config

重生成defconfig

  • 在这个操作之后,你的垃圾config将会变得整齐如CAF
  • 直接上bash脚本(在内核目录中运行)
#!/bin/bash
export ARCH=arm64
target=<目标config名称(不带路径)>
make ${target}
make savedefconfig
mv defconfig arch/${ARCH}/configs/${target}

是不是很简单鸭

  • 这么干完之后,你的config中多余的条目将会被移除,条目的顺序也会变得和编译系统一致
  • 只要你每改一次config就这么干一次,你就会显得非常NB

menuconfig

  • 这是一个内核自带的非常好玩的调整defconfig的工具
  • 直接上bash脚本
#!/bin/bash
export ARCH=arm64
target=<目标config名称(不带路径)>
make ${target}
make menuconfig
echo "Press any key to save"
read
make savedefconfig
mv defconfig arch/${ARCH}/configs/${target}
  • 运行这个脚本后你将会看到一个非常美的内核config控制台,你可以使用小键盘上下左右进行操作,使用键盘的y,m,n来控制各个模块的编译状态。你甚至可以按/然后进行搜索,搜出结果后在键盘上敲击结果前面的数字,直接前往config条目的位置,是不是吼方便啊?
  • 改完后,通过小键盘左右选择到save,(弹出框中的.config无需修改,脚本会自动处理)点击回车,再选择到exit退出menuconfig即可。此时命令行应该提示Press any key to save,随意敲击一个键(别是ctrl+c),你的新config就保存好了,是不是很好用啊?

生成完整defconfig

  • 太简单了
#!/bin/bash
export ARCH=arm64
target=<目标config名称(不带路径)>
make ${target}
cp .config arch/${ARCH}/configs/${target}
  • 执行后你的defconfig应该就变成完整的了

收尾工作

  • 建议make mrproper一下,因为上述操作使用了内核根目录,可能造成CAF内核编译环境被破坏(其实不用根目录也行,调用make的时候后面再加个O=out即可)