我可以使用以下命令为自定义基于ARM的板创建基于指定体系结构默认值的Linux内核.config
文件:
ARCH=arm make defconfig KBUILD_DEFCONFIG=var_som_mx6_android_defconfig
我认为这个命令或多或少会将./arch/arm/configs/var_som_mx6_android_defconfig
复制到./.config
。然而,生成的.config
文件并不完全是一个副本:
$ diff --unified arch/arm/configs/var_som_mx6_android_defconfig .config
--- arch/arm/configs/var_som_mx6_android_defconfig 2017-01-20 12:10:51.891515984 -0800
+++ .config 2017-01-26 15:31:29.000000000 -0800
@@ -407,6 +407,7 @@
CONFIG_ARM_ERRATA_751472=y
CONFIG_ARM_ERRATA_794072=y
CONFIG_ARM_ERRATA_761320=y
+CONFIG_ARM_ERRATA_845369=y
# CONFIG_ARM_ERRATA_753970 is not set
CONFIG_ARM_ERRATA_754322=y
# CONFIG_ARM_ERRATA_754327 is not set
@@ -2683,7 +2684,6 @@
CONFIG_AUTOFS4_FS=y
CONFIG_FUSE_FS=y
# CONFIG_CUSE is not set
-CONFIG_AUFS_FS=y
#
# Caches
@@ -2759,6 +2759,21 @@
# CONFIG_PSTORE is not set
# CONFIG_SYSV_FS is not set
# CONFIG_UFS_FS is not set
+CONFIG_AUFS_FS=y
+CONFIG_AUFS_BRANCH_MAX_127=y
+# CONFIG_AUFS_BRANCH_MAX_511 is not set
+# CONFIG_AUFS_BRANCH_MAX_1023 is not set
+# CONFIG_AUFS_BRANCH_MAX_32767 is not set
+CONFIG_AUFS_SBILIST=y
+# CONFIG_AUFS_HNOTIFY is not set
+# CONFIG_AUFS_RDU is not set
+# CONFIG_AUFS_PROC_MAP is not set
+# CONFIG_AUFS_SP_IATTR is not set
+# CONFIG_AUFS_SHWH is not set
+# CONFIG_AUFS_BR_RAMFS is not set
+# CONFIG_AUFS_BR_FUSE is not set
+CONFIG_AUFS_BDEV_LOOP=y
+# CONFIG_AUFS_DEBUG is not set
CONFIG_NETWORK_FILESYSTEMS=y
CONFIG_NFS_FS=y
CONFIG_NFS_V3=y
我不明白额外的行是从哪里来的,我总是发现内核配置、makefile和构建脚本的内部工作很难理解。有人能解释一下.config
中的这些线条可能来自哪里吗?
动机
.config
文件不是简单地从defconfig
文件中复制的。以这种格式存储defconfig
的动机是:在defconfig
中,我们只能指定具有非默认值的选项(即我们为董事会更改的选项)。这样我们就可以保持它的小而清晰。每个新的内核版本都会带来一堆新的选项,这样我们就不需要在每次内核发布时更新defconfig
文件。此外,需要注意的是,内核构建系统在defconfig
文件中保留了非常特定的选项顺序,因此最好避免手动修改。相反,您应该使用make savedefconfig
规则。
简化说明
当生成.config
文件时,内核构建系统会遍历所有Kconfig
文件(来自所有子目录),检查这些Kconfig
文件中的所有选项:
- 如果在
defconfig
中提到选项,则构建系统将该选项放入.config
中,并在defconfig
中选择值 - 如果
defconfig
中没有提到该选项,则构建系统会使用相应的Kconfig
中指定的默认值将该选项放入.config
中
检查脚本/kconfig/Makefile和脚本/kconfig/conf.c文件,看看它是如何实际完成的。
更精确、更详细的解释
从";Kbuild:Linux内核构建系统";哈维尔·马丁内斯:
定义配置符号:
Kconfig
文件配置符号在称为
Kconfig
文件的文件中定义。每个Kconfig
文件可以描述任意数量的符号,并且还可以包括(源)其他Kconfig
文件。构造内核编译选项的配置菜单的编译目标,如make menuconfig
,读取这些文件以构建树状结构。内核中的每个目录都有一个Kconfig
,其中包括其子目录的Kconfig
文件。在内核源代码目录的顶部,有一个Kconfig
文件,它是选项树的根。menuconfig
(scripts/kconfig/mconf
)、gconfig
(scripts/kconfig/gconf
)和其他编译目标调用从该根Kconfig
开始的程序,并递归地读取位于每个子目录中的Kconfig
文件以构建它们的菜单。访问哪个子目录也在每个Kconfig
文件中定义,也取决于用户选择的配置符号值。存储符号值:
.config
文件所有配置符号值都保存在一个名为
.config
的特殊文件中。每次想要更改内核编译配置时,都要执行一个make目标,例如menuconfig
或xconfig
。这些读取Kconfig
文件以创建菜单,并使用.config
文件中定义的值更新配置符号的值。此外,这些工具使用您选择的新选项更新.config
文件,如果以前不存在,也可以生成一个。因为
.config
文件是纯文本的,所以您也可以在不需要任何专用工具的情况下对其进行更改。它也非常方便地保存和恢复以前的内核编译配置。
有用的命令
您可以对make defconfig
使用更简单的语法,如:
$ make ARCH=arm your_board_defconfig
查看可用defconfigs的完整列表:
$ make ARCH=arm help | grep defconfig
如果你需要做反向操作(即从大量的.config
创建一个整洁的小defconfig
),你可以使用savedefconfig
规则:
$ make ARCH=arm savedefconfig
此外,正如0andry所提到的,您可以使用diffconfig
脚本查看从一个.config
到另一个的更改:
$ scripts/diffconfig .config_old .config_new
它还生成include/generated/autoconf.h
。
这个头文件包含在C源文件中。另一方面,.config
用于Makefile系统。
构建系统生成两个文件,并保持它们的一致性。