如何将其他文件编译到Android ROM的根目录中


8

我正在基于Cyanogenmod ROM的内核源代码构建自定义Android内核。我想将文件夹和文件添加到操作系统(/)的根文件夹中。例如,在编译完内核之后,我想创建一个名为toto(absolute path = /toto)的额外文件夹。

我真的不知道必须编辑哪些文件以及如何进行工作。


注意:如果您是Android用户(不是ROM开发人员),想向其中添加文件rootfs,请查看相关的Android.SE问题


3
Android是Linux系统,但是问题是特定于Android,而不是所有Unix。更好的地方在android.stackexchange.com上
nedil 2014年

@enedil通常来说,Android问题在这里是没有意义的,因为从术语的常识上来说,Android不是Linux(它仅使用Linux内核)。但是,相同的问题将适用于其他嵌入式Linux系统,因此我认为在这里还可以。
吉尔斯(Gilles)'所以

@Graeme实际上,根文件系统已编译到每个内核中。通常它是空的,我们将cpio归档文件解压缩到其中-我们的initramfs映像。您可以在编译时将任何内容放入其中。
mikeserv

@enedil在这种情况下,我认为这个问题完全是话题。Android与其他Unix的最大不同之处在于与userspace,其他Linux的in-kernel不同,差别仅在于少数补丁。实际上,Android的普及是内核开发的主要推动力,并且已经持续了几年。查看kernel.org更改日志,并自己决定许多与移动系统(尤其是Android)的相关性。
mikeserv 2014年

Android.SE上的类似问题:如何解压缩和编辑boot.imgROM端口?:那里的答案说明了如何获取和编辑boot.img文件,从而可以永久更改设备的根目录内容。
WhiteWinterWolf's

Answers:


7

与许多基于Linux的系统一样,在Android上,内核首先在上挂载一个initramfs/。initramfs存储在RAM中;它是从CPIO归档文件加载的,该归档文件与内核本身(或在引导加载程序可以找到它的其他位置)存储在一起。

大多数台式机Linux系统都有一个小的initramfs,其中仅包含足够的程序和配置文件来挂载实际的根文件系统,然后将其挂载到该系统上/,以代替initramfs。像某些嵌入式Linux系统一样,Android会永久保留initramfs。Android的initramfs中只包含/initadbd以及一些配置文件。

对于Cyanogenmod,您可以在移植指南中找到构建说明。您想要将更多文件复制到ramdisk(initramfs映像,在Android术语中),因此需要将它们添加到设备PRODUCT_COPY_FILESdevice_*.mkMakefile中的列表中。


实际上,我们的initramfs 映像文件就是包含那些配置文件的文件,initramfs 文件系统被编译到每个内核中。
mikeserv 2014年

1
@mikeserv我邀请您熟悉转喻的概念。技术写作使用它的语言要比普通演讲少,但确实会偶尔使用。
吉尔斯(Gilles)'所以

我会这样做,但首先我必须在字典中对其进行检查...
mikeserv

您的观点很明确,就像我之前说过的,我坚持这一点的唯一原因是,似乎人们对此了解甚少,但它确实非常直截了当,所以我倾向于对此话题不屑一顾-我对此表示歉意。我只是认为,如果上面的细节清楚了,向其他人展示从内核开始设计您自己的系统会多么简单。再次,对不起,吉尔斯,我的意思是没有侮辱。
mikeserv 2014年

@mikeserv谢谢您的建议。我找到了用于复制blobs(blbs.mk)的文件。我仍然不知道必须编辑哪个文件才能在rootfs(/)中添加文件夹文件夹。我可以访问rom的init * .rc文件,但现在无法编辑(例如通过添加mkdir / titi)这些文件将使我能够永久添加文件夹(/ titi)。之后,我将在文件PRODUCT_COPY_FILES + = / titi / myfile:<localpath> / myfiles中添加。有什么线索吗?再次感谢
deadeert 2014年

1

内核文档说明了如何将映像打包到内核本身。从kernel.org

什么是rootfs?

Rootfs是的特殊实例ramfs(或tmpfs如果启用的话),该 实例始终存在于2.6系统中。无法rootfs以无法杀死init进程的相同原因卸载。与其使用特殊的代码来检查和处理一个空列表,不如让内核仅确保某些列表不会为空,它变得更小,更简单。

大多数系统只是挂载另一个文件系统rootfs而忽略它。一个空的ramfs实例占用的空间很小。

如果启用了CONFIG_TMPFSrootfs则默认使用tmpfs代替ramfs。要强制ramfs,请添加"rootfstype=ramfs"到内核​​命令行。

什么是initramfs?

所有2.6 Linux内核都包含gzip压缩"cpio"格式的归档文件,该文件在内核启动时提取到rootfs其中 提取后,内核检查是否rootfs包含文件"init"如果包含则将其作为 PID 1执行 如果找到该文件则该init过程负责使系统其余部分正常运行,包括查找和安装实际的根设备(如果有的话)。 如果在将嵌入式存档解压缩到其中之后rootfs不包含init程序cpio,则内核将陷入较旧的代码中,以查找并挂载根分区,然后执行其中的某种变体/sbin/init

所有这一切都与旧的initrd在以下方面有所不同:

  • 旧的initrd始终是一个单独的文件,而initramfs归档文件已链接到linux内核映像中。 (Linux-* / usr目录专用于在构建过程中生成此归档文件。)

  • 旧的initrd文件是gzip压缩的文件系统映像(采用ext2等某种文件格式,需要内置于内核中的驱动程序),而新的initramfs归档文件是gzip压缩的cpio归档文件(仅比tar更简单,请参见cpio(1))。和文档/early-userspace/buffer-format.txt)。内核的cpio提取代码不仅很小,而且是__init文本和数据,可以在引导过程中将其丢弃。

  • 由旧的initrd(称为/ initrd,而不是/ init)运行的程序进行了一些设置,然后返回内核,而initramfs的init程序预计不会返回内核。(如果/ init需要交出控制权,则可以使用新的根设备来超载/并执行另一个init程序。请参见下面的switch_root实用程序。)

  • 切换另一个根设备时,initrd将使用pivot_root,然后卸载ramdisk。但是initramfs是rootfs:您不能pivot_root rootfs,也不能将其卸载。 而是从rootfs中删除所有内容以释放空间(找到-xdev / -exec rm'{}'';'),用新的根目录(cd / newmount; mount --move ./; chroot。)覆盖rootfs,将stdin / stdout / stderr附加到新的/ dev / console并执行新的init。

由于这是一个非常棘手的过程(需要删除命令才能运行它们),因此klibc软件包引入了一个帮助程序(utils / run_init.c)为您完成所有这些操作。大多数其他软件包(例如busybox)已将此命令命名为“ switch_root”。

填充initramfs:

2.6内核构建过程始终创建gzip cpio格式的initramfs存档,并将其链接到生成的内核二进制文件中。 默认情况下,此存档为空(在x86上消耗134个字节)。

config选项CONFIG_INITRAMFS_SOURCE(位于和位于中的常规设置中)可用于指定存档的源,该源 将自动合并到生成的二进制文件中。 此选项可以指向* 现有 gzip压缩的*归档文件,包含要归档文件的目录文本文件规范,例如以下示例:menuconfig,usr/Kconfiginitramfscpio

 dir /dev 755 0 0
 nod /dev/console 644 0 0 c 5 1
 nod /dev/loop0 644 0 0 b 7 0
 dir /bin 755 1000 1000
 slink /bin/sh busybox 777 0 0
 file /bin/busybox initramfs/busybox 755 0 0
 dir /proc 755 0 0
 dir /sys 755 0 0
 dir /mnt 755 0 0
 file /init initramfs/init.sh 755 0 0

运行usr/gen_init_cpio”(在内核构建之后)以获取使用情况消息,其中记录了上述文件格式。

配置文件的一个优点root是不需要访问权限即可设置权限或在新档案中创建设备节点。

(请注意,这两个示例“文件”条目期望在-2.6。*目录下的名为“ ” 的目录中找到名为“ init.sh”和“ busybox”的文件。有关更多详细信息,请参见Documentation / early-userspace / README。)initramfslinux

内核并不能依赖于外部cpio工具。如果您指定目录而不是配置文件,则内核的构建基础结构会从该目录usr/Makefile称为scripts/gen_initramfs_list.sh创建一个配置文件然后继续使用配置文件将该目录打包(通过将其提供给usr/gen_init_cpio从创建的usr/gen_init_cpio.c)。 内核的构建时cpio创建代码是完全独立的,而内核的引导时提取程序也是(显然)独立的。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.