kumquat-buildroot/fs/ext2/genext2fs.sh

122 lines
3.5 KiB
Bash
Raw Normal View History

#!/bin/sh
# genext2fs wrapper calculating needed blocks/inodes values if not specified
set -e
export LC_ALL=C
CALC_BLOCKS=1
CALC_INODES=1
EXT_OPTS=
EXT_OPTS_O=
while getopts x:d:D:b:i:N:m:g:e:zfqUPhVv f
do
case $f in
b) CALC_BLOCKS=0 ;;
N) CALC_INODES=0; INODES=$OPTARG ;;
d) TARGET_DIR=$OPTARG ;;
esac
done
eval IMG="\"\${${OPTIND}}\""
# calculate needed inodes
if [ $CALC_INODES -eq 1 ];
then
INODES=$(find $TARGET_DIR | wc -l)
INODES=$(expr $INODES + 400)
set -- $@ -N $INODES
fi
# calculate needed blocks
if [ $CALC_BLOCKS -eq 1 ];
then
# size ~= superblock, block+inode bitmaps, inodes (8 per block), blocks
# we scale inodes / blocks with 10% to compensate for bitmaps size + slack
BLOCKS=$(du -s -c -k $TARGET_DIR | grep total | sed -e "s/total//")
BLOCKS=$(expr 500 + \( $BLOCKS + $INODES / 8 \) \* 11 / 10)
# we add 1300 blocks (a bit more than 1 MiB, assuming 1KiB blocks) for
# the journal if ext3/4
# Note: I came to 1300 blocks after trial-and-error checks. YMMV.
if [ ${GEN} -ge 3 ]; then
BLOCKS=$(expr 1300 + $BLOCKS )
fi
set -- $@ -b $BLOCKS
fi
e2tunefsck() {
# genext2fs does not generate a UUID, but fsck will whine if one is
# is missing, so we need to add a UUID.
# Of course, this has to happend _before_ we run fsck.
# Also, some ext4 metadata are based on the UUID, so we must
# set it before we can convert the filesystem to ext4.
# Although a random UUID may seem bad for reproducibility, there
# already are so many things that are not reproducible in a
# filesystem: file dates, file ordering, content of the files...
tune2fs -U random "${IMG}"
# Upgrade the filesystem
if [ $# -ne 0 ]; then
tune2fs "$@" "${IMG}"
fi
# After changing filesystem options, running fsck is required
# (see: man tune2fs). Running e2fsck in other cases will ensure
# coherency of the filesystem, although it is not required.
# 'e2fsck -pDf' means:
# - automatically repair
# - optimise and check for duplicate entries
# - force checking
# Sending output to oblivion, as e2fsck can be *very* verbose,
# especially with filesystems generated by genext2fs.
# Exit codes 1 & 2 are OK, it means fs errors were successfully
# corrected, hence our little trick with $ret.
ret=0
e2fsck -pDf "${IMG}" >/dev/null || ret=$?
case ${ret} in
0|1|2) ;;
*) exit ${ret};;
esac
printf "\ne2fsck was successfully run on '%s' (ext%d)\n\n" \
"${IMG##*/}" "${GEN}"
# Remove count- and time-based checks, they are not welcome
# on embedded devices, where they can cause serious boot-time
# issues by tremendously slowing down the boot.
tune2fs -c 0 -i 0 "${IMG}"
}
# Check we know what generation to generate
case "${GEN}:${REV}" in
2:0|2:1|3:1|4:1)
;;
*)
printf "%s: unknown ext generation '%s' and/or revision '%s'\n" \
"${0##*/}" "${GEN}" "${REV}" >&2
exit 1
;;
esac
# Upgrade to rev1 if needed
if [ ${REV} -ge 1 ]; then
EXT_OPTS_O="${EXT_OPTS_O},filetype"
fi
# Add a journal for ext3 and above
if [ ${GEN} -ge 3 ]; then
EXT_OPTS="${EXT_OPTS} -j -J size=1"
fi
# Add ext4 specific features
if [ ${GEN} -ge 4 ]; then
EXT_OPTS_O="${EXT_OPTS_O},extents,uninit_bg,dir_index"
fi
# Add our -O options (there will be at most one leading comma, remove it)
if [ -n "${EXT_OPTS_O}" ]; then
EXT_OPTS="${EXT_OPTS} -O ${EXT_OPTS_O#,}"
fi
# Generate and upgrade the filesystem
genext2fs "$@"
e2tunefsck ${EXT_OPTS}