It's not the kernel that's generating the initramfs, it's cpio. So what you're really looking for is a way to build a cpio archive that contains devices, symbolic links, etc.
Your method 2 uses usr/gen_init_cpio
in the kernel source tree to build the cpio archive during the kernel build. That's indeed a good way of building a cpio archive without having to populate the local filesystem first (which would require being root to create all the devices, or using fakeroot or a FUSE filesystem which I'm not sure has been written already).
All you're missing is generating the input file to gen_init_cpio
as a build step. E.g. in shell:
INITRAMFS_SOURCE_DIR=/home/brandon/rascal-initramfs
exec >initramfs_source.txt
echo "dir /bin 755 0 0"
echo "file /bin/busybox $INITRAMFS_SOURCE_DIR/bin/busybox 755 0 0"
for x in sh ls cp …; do echo "slink /bin/$x busybox 777 0 0" done
# etc …
If you want to reflect the symbolic links to busybox that are present in your build tree, here's a way (I assume you're building on Linux):
( cd "$INITRAMFS_SOURCE_DIR/bin" &&
for x in *; do
if [ "$(readlink "$x")" = busybox ]; then
echo "slink /bin/$x busybox 777 0 0"
fi
done )
Here's a way to copy all your symbolic links:
find "$INITRAMFS_SOURCE_DIR" -type l -printf 'slink %p %l 777 0 0\n'
For busybox, maybe your build tree doesn't have the symlinks, and instead you want to create one for every utility that you've compiled in. The simplest way I can think of is to look through your busybox build tree for .*.o.cmd
files: there's one per generated command.
find /path/to/busybox/build/tree -name '.*.cmd' -exec sh -c '
for x; do
x=${x##*/.}
echo "slink /bin/${x%%.*} busybox 777 0 0"
done
' _ {} +
The options that the BusyBox
commands have depends a lot on the options that BusyBox
is compiled with. BusyBox
aims to be highly configurable so that very small cut down versions can be compiled for systems where resources are very limited. Larger, more full featured versions can be built where this isn't an issue.
In your case cpio
needs the -p
or --pass-through
(long form) option enabled. Normally cpio
behaves more like an archive utility like tar
, however it also has an extra function which allows it to copy files. To enable this in BusyBox
, it needs to be built with FEATURE_CPIO_P
defined (also LONG_OPTS
for long form options to be enabled for any program).
From your last question, I strongly recommend that you use rsync
for what you are doing. You are probably better off asking another question detailing exactly what you are doing with rsync
and why it doesn't do what you expect. rsync
is an extremely versatile tool and can no doubt be configured to do what you want.
That said, you could try the following with cpio
, this will create an archive and then extract it again (somewhat less efficient, but still the same result):
find . -mtime -2 | cpio -o | { cd /media/USB_FLASH_2 && cpio -imd; }
Unfortunately the -o
option can also be disabled in BusyBox
(FEATURE_CPIO_O
build option), so this may not work either.
Update
Based on this line of output, you need to add an extra option when creating an archive:
-o Create (requires -H newc)
This changes the command to:
find . -mtime -2 | cpio -oH newc | { cd /media/USB_FLASH_2 && cpio -imd; }
This time I have tested with the cpio
in the BusyBox
for my own system and it works for me, however in some cases the mtimes for directories won't be preserved. rsync
should be the best way to do this.
Best Answer
Use pax and its
-s
option to rename files as they are added to the archive. Pax is POSIX's replacement for the traditional utilitiestar
andcpio
; some Linux distributions don't install it by default but it should always be available as a package.