diff --git a/recipes-bsp/fng-install/common/fnginstall-common.sh b/recipes-bsp/fng-install/common/fnginstall-common.sh index 1a357782caa7e40c3f859507fbc589fa1d6e2c46..f7f07af900e392d4a0e9c6fe4dffab7a1c1d68b2 100644 --- a/recipes-bsp/fng-install/common/fnginstall-common.sh +++ b/recipes-bsp/fng-install/common/fnginstall-common.sh @@ -304,6 +304,12 @@ nop() #======================================== # Called on any ungraceful exit #======================================== +param_error() +{ + error_text "Failed to parse parameter: $*" + exit 1 +} + exit_error() { trap nop EXIT @@ -807,7 +813,7 @@ parse_args() #TODO support old UserPartition parameter --user-partition-size|--user-partition-size=*) parse_args_value PART_USER_SIZE_PARAM "$1" "$2" || shift - is_number "$PART_USER_SIZE_PARAM" || exit_error "User partition size has to be specified as number." + is_number "$PART_USER_SIZE_PARAM" || param_error "User partition size has to be specified as number." ;; --no-AB|--no-AB-partitioning) AB_PARTITIONING_PARAM=false @@ -816,11 +822,11 @@ parse_args() AB_PARTITIONING_PARAM=true ;; --dry) # Dry run, don't actaully write anything - DRYRUN="echo DRYRUN Not executed: " + DRYRUN="error_text DRYRUN Skipping: " ;; --partition-scheme|--partition-scheme=*) # Select the partition scheme for reformating parse_args_value PART_SCHEME_PARAM "$1" "$2" || shift - [ "$PART_SCHEME_PARAM" != "1" ] && [ "$PART_SCHEME_PARAM" != "2" ] && exit_error "Select 1 or 2 for --partition-scheme" + [ "$PART_SCHEME_PARAM" != "1" ] && [ "$PART_SCHEME_PARAM" != "2" ] && param_error "Select 1 or 2 for --partition-scheme" ;; --skip-postinstall) SKIP_POSTINSTALL=true @@ -862,7 +868,7 @@ parse_args() parse_args_value NEWLOGFILE "$1" "$2" || shift touch "$NEWLOGFILE" if [ ! -w "$NEWLOGFILE" ]; then - exit_error "cannot access the given logfile: $NEWLOGFILE" + param_error "cannot access the given logfile: $NEWLOGFILE" fi cat "$LOGFILE" >> "$NEWLOGFILE" LOGFILE="$NEWLOGFILE" @@ -1276,6 +1282,9 @@ analyze_partitions() fi #==================================================== # New and Old Layout + # Loop over all found partitions in "PARTITIONS" and + # sort them by type and sequence to the PART_XX variable + # to use these later #==================================================== p=-1 while true;do @@ -1285,6 +1294,7 @@ analyze_partitions() fi sector_to_MB S "$SI" case $T in + # The type f8 is used for the u-boot partitions f8) if [ -z "$PART_BOOTLOADER" ];then PART="PART_BOOTLOADER" elif [ -z "$PART_BOOTLOADER_EXTRA" ];then @@ -1294,6 +1304,7 @@ analyze_partitions() continue fi ;; + # The type b for fat is used for config, fngsystem and the boot partitions b) if [ -z "$PART_CONFIG" ];then PART="PART_CONFIG" elif [ -z "$PART_FNGSYSTEM" ];then @@ -1309,6 +1320,7 @@ analyze_partitions() continue fi ;; + # The type 83 is used for root and user partitions 83) if [ -z "$PART_A_ROOT" ];then PART="PART_A_ROOT" elif [ -n "$PART_B_BOOT" ] && [ -z "$PART_B_ROOT" ];then # Second linux type partition is Root B is a corresponding boot partition is available @@ -1324,6 +1336,8 @@ analyze_partitions() PART="PART_EXTENDED" continue ;; + # Sometime an empty entry in the partion table is found + # This partition should be overwritten if needed 0) # Empty entry, don't try to keep it dont_keep_partition "$P" continue @@ -1335,11 +1349,17 @@ analyze_partitions() esac # Store the result in the variables + # This uses a little shell magic to set the variables for the + # partition name set in the case above. PART is PART_A_ROOT + # for example, eval "${PART}_SIZE=$S" set PART_A_ROOT_SIZE to $S, + # the size returned from get_partition_data above. eval "${PART}=$DEV$P" eval "${PART}_SIZE=$S" eval "${PART}_TYPE=$T" eval "S_MIN=$"${PART}_SIZE_MIN"" + # Compare with the expected sizes and set a PART_XX_OK variable + # meaning the partition was found and the size in inside the limits if [ -n "$S_MIN" ];then if [ "$S_MIN" -le "$S" ];then eval "${PART}_OK=true" @@ -1348,6 +1368,9 @@ analyze_partitions() fi fi done + # Loop over all partitions again and mark those 'not OK' + # to not keep them, meaning they will be rewritten later. + # The mmc boot partitions are skipped, as their size is fix. for PART in $ALL_PARTITIONS;do # shellcheck disable=2027,2086 eval "P=$"${PART}"" @@ -1406,14 +1429,14 @@ check_partitions_match_spec() if $AB_PARTITIONING; then if ! $PART_B_BOOT_OK || ! $PART_B_ROOT_OK;then - partition_warning "Partitions for secondary OS have not been found, but A-B partition scheme has been selected on the command line." + partition_warning "Partitions for secondary OS have not been found, but A-B partition scheme\n\t has been selected on the command line." # If change from A-only to A-B layout all partitions after # PART_A_BOOT have to be deleted dont_keep_partition "$PART_A_ROOT" fi else if [ -n "$PART_B_ROOT" ] || [ -n "$PART_B_BOOT" ];then - partition_warning "Partitions for secondary OS have been found, but A-only scheme has been selected on the command line." + partition_warning "Partitions for secondary OS have been found, but A-only scheme has been\n\t selected on the command line." # If change from A-B to A-only layout all partitions after # PART_A_BOOT have to be deleted dont_keep_partition "$PART_B_BOOT" @@ -1489,9 +1512,9 @@ PARTITION_NEXT_START_SECTOR=8 append_partition() { start="$1" - if [ -z "$start" ];then - start="$PARTITION_NEXT_START_SECTOR" - fi + #if [ -z "$start" ];then + # start="$PARTITION_NEXT_START_SECTOR" + #fi if [ "$4" = "1" ];then # Bootable flag _B=",*" else @@ -1513,7 +1536,6 @@ append_partition() # #======================================== - create_partitions() { DEV=$1 @@ -1601,14 +1623,16 @@ create_partitions() $FORCE || exit 1 fi - #============================================= + SFDISK_DRY=""; + # -n is sfdisk dry run (--no-act, but the long option is not supported in i + # FNGSystem 15) + [ -n "$DRYRUN" ] && SFDISK_DRY="-n" + + # Compatibility for old sfdisk - #============================================= SFDISK_VERSION="$(sfdisk --version)" SFDISK_VERSION=$(echo "$SFDISK_VERSION" | sed -e 's|[^0-9]*\([0-9]\+\).\([0-9]*\).*|\1\2|') SFDISK_APPEND="" - SFDISK_DRY=""; [ -n "$DRYRUN" ] && SFDISK_DRY="-n" # -n is sfdisk dry run (--no-act, but the long option is not supported in FNGSystem 15) - if [ "$SFDISK_VERSION" -le 225 ]; then SFDISK_APPEND="--force" # Old sfdisk complains about stupid cylinder boundry issues @@ -1703,12 +1727,16 @@ create_partitions() if [ "$SFDISK_VERSION" -gt 225 ];then # The old sfdisk does not support --delete if [ -n "$DELETE_PARTS" ];then milestone "Deleting partitions '$DELETE_PARTS' from $DEV" + [ -z "$DRYRUN" ] || $DRYRUN sfdisk $SFDISK_DRY $FORCE_SFDISK -uS "$DEV" --delete "$DELETE_PARTS" sfdisk $SFDISK_DRY $FORCE_SFDISK -uS "$DEV" --delete "$DELETE_PARTS" sleep 1 # 0.X is not supported by FNGSystem 15, was 0.2 fi fi #=============================================================== milestone "Writing new partitions to $DEV" + if [ -n "$DRYRUN" ];then + $DRYRUN sfdisk $SFDISK_DRY $FORCE_SFDISK $SFDISK_APPEND -uS "$DEV < $(cat "$TMPDIR/partitiontable")" + fi sfdisk $SFDISK_DRY $FORCE_SFDISK $SFDISK_APPEND -uS "$DEV" < "$TMPDIR/partitiontable" sleep 2 diff --git a/recipes-bsp/fng-install/fng-install/fng-install.sh b/recipes-bsp/fng-install/fng-install/fng-install.sh index f736c43d42222279aa03e2ffddddbcd085d0b295..9ba8eb0cc0462c13c02e8dbdaa0c6ac495a4dc87 100644 --- a/recipes-bsp/fng-install/fng-install/fng-install.sh +++ b/recipes-bsp/fng-install/fng-install/fng-install.sh @@ -19,10 +19,10 @@ HELP=" # can access your server (try with 'ping', configure Ethernet if necessary). # Then run the following command (replace the IP # address by your server's IP address, and append required arguments): -# export URL=http://192.168.1.100; curl \$URL/fngsystem-self-update.sh | sh -s -- <args> +# export URL=http://192.168.1.100; curl \$URL/fng-install.sh | sh -s -- <args> # # Installation from local media is possible with: -# unset URL;./fngsystem-self-update.sh <args> +# unset URL;./fng-install.sh <args> # # Options: # -b|--BS Boot script @@ -89,7 +89,7 @@ ABSTARGETTMP="${TARGETROOT}${TARGETTMP}" # allows to create an additional partition # during installation # TODO implement again -# +# # USERFS_START=$(( ROOTFS_START + ROOTFS_SIZE )) # if [ -n "${USERFS_SFDISK}" ];then # USERFS_SFDISK="${USERFS_START},${USERFS_SIZE_S},${USERFS_PTYPE}" @@ -271,7 +271,7 @@ mounttarget() mount -o bind /tmp $TARGETROOT/var/tmp mkdir -p $TARGETROOT/var/tmp - + mkdir -p $TARGETROOT/etc/shared mount -t proc proc ${TARGETROOT}/proc/ @@ -455,7 +455,7 @@ run_install_scripts() sync milestone "Installing $f ..." do_load "$f" - + chmod +x "${TMP}/${f##*/}" # Run the script "${TMP}/${f##*/}" @@ -466,7 +466,7 @@ run_install_scripts() } #========================================= -# Executes 'postinstall' script if it exists +# Executes 'postinstall' script if it exists # in the rootfs #========================================= target_os_postinstall() @@ -530,7 +530,7 @@ user_install() for f in $USER_SCRIPT; do sync do_load "$f" - + chmod a+x "$ABSTARGETTMP/${f##*/}" chroot "${TARGETROOT}" "${TARGETTMP}/${f##*/}" milestone "Installing $f finished." @@ -556,7 +556,7 @@ posttest_check_partition() mount -t "$fstype" "$p" "${TMP_MOUNT_POINT}" || exit_error "Mounting $p failed" - mount | grep "${TMP_MOUNT_POINT}" | grep -q "type $fstype" || + mount | grep "${TMP_MOUNT_POINT}" | grep -q "type $fstype" || exit_error "Wrong fstype seen, expected $fstype, mount returned: $(mount | grep "${TMP_MOUNT_POINT}" )" umount "$p" || exit_error "Unmounting $p failed." @@ -598,13 +598,13 @@ verify_file_access() { # TODO this may also be a common function # Test if the download works, attempt to load the beginning of the rootfs file - while true; + while true; do ROOTFS_TMP=$(mktemp) || exit_error "Failed to create temp file" OLDIFS=$IFS;IFS='|' # shellcheck disable=2086 - curl ${CURL_ARGS#|} --max-filesize 128000 --max-time 5 "${CURL_PREFIX}/${ROOTFS}" > "$ROOTFS_TMP" & + curl ${CURL_ARGS#|} --max-filesize 128000 --max-time 5 "${CURL_PREFIX}/${ROOTFS}" > "$ROOTFS_TMP" & PID=$! IFS=$OLDIFS @@ -613,7 +613,7 @@ verify_file_access() # we still need the loop to kill the download cnt=0 # stop when curl stopped anyway or after 5 seconds - while kill -0 $PID && [ $cnt -lt 50 ]; + while kill -0 $PID && [ $cnt -lt 50 ]; do usleep 100000 cnt=$(( cnt + 1 )) @@ -634,7 +634,7 @@ verify_file_access() rm "$ROOTFS_TMP" # Successful return values - # 28 is the return code for --max-time timeout, which means that the download started but was not finished + # 28 is the return code for --max-time timeout, which means that the download started but was not finished # (the --max-filessize option does not always work, see manpage, and is ignored if not, so we need to have another way out). # 63 is the return code for max filesize exceeded, which means what a big file was found which is enough # 143 is the return code when the process was killed during a running download, which is good @@ -719,10 +719,16 @@ prepare_partitions() #=========================================================== DEV="/dev/$TARGETDEVICE" - # Analyze partitions always, so the PART_XX variables are set + # Analyze partitions always, so the PART_XX variables all are set if ! analyze_partitions "$DEV";then + # If the analyze of the current parition situation fails + # repatitioning is needed REPARTITION_NEEDED=true fi + + # If FORCE_REPARTITION is set, we mark all 'yocto' partitions + # not to be keeped. They are recreated during parition generation + # later in this case if $FORCE_REPARTITION;then REPARTITION_NEEDED=true dont_keep_partition "$PART_A_BOOT" @@ -790,8 +796,13 @@ prepare_partitions() if ! $REPARTITION_NEEDED;then # Analyze partitions already does basic partition checks # here we check the needs for the yocto installation + # if REPARTITION_NEEDED is set, this can be skipped, + # as partitions will be recreated the way yocto needs + # them anyway - # Does the layout match the command line settings + # Basically this checks if the layout matches the command + # line settings. If not the functions bails out with a + # warning and some hints. check_partitions_match_spec if ! "$TARGET_PARTITIONS_OK";then @@ -803,27 +814,38 @@ prepare_partitions() #============================================ # Partitioning #============================================ + # The partitioning is completly skipped if the + # current partition table is in a working state + # matching the specs if $REPARTITION_NEEDED;then if $FORCE_REPARTITION;then + # Recreate all partitions create_partitions "$DEV" else + # Recreate only needed partitions, the second parameter + # holds the number of partitions to keep/not to change. + # Only partitions at the beginning of the disk are + # keeped to allow resizing + # TODO if we are in yocto, the complete partitioning + # should be disabled. create_partitions "$DEV" "$KEEP_PARTITIONS_CNT" fi fi #=========================================== # Store target partitions + # Set the target partitions for the installation, + # depending on the A/B setting + # This is done after create_partitions, as it rereads + # the partition table again #=========================================== - if [ "$AB_PARTITIONING_TARGET" = "A" ];then - TARGET_PARTITION_BOOT="$PART_A_BOOT" - TARGET_PARTITION_ROOT="$PART_A_ROOT" - elif [ "$AB_PARTITIONING_TARGET" = "B" ];then + if [ "$AB_PARTITIONING_TARGET" = "B" ];then TARGET_PARTITION_BOOT="$PART_B_BOOT" TARGET_PARTITION_ROOT="$PART_B_ROOT" else - exit_error "Something went wrong" + TARGET_PARTITION_BOOT="$PART_A_BOOT" + TARGET_PARTITION_ROOT="$PART_A_ROOT" fi - } #=========================================== @@ -906,7 +928,7 @@ load_and_untar() if [ -z "$DRYRUN" ];then curl ${CURL_ARGS#|} "${CURL_PREFIX}/${FILE}" 2>&5 | tar -C "${TARGET}" -x"$COMPRESSION" else - echo "DRYRUN: Skip: curl ${CURL_ARGS#|} ${CURL_PREFIX}/${FILE} \| tar -C ${TARGET} -x$COMPRESSION" + error_text DRYRUN: Skip: curl ${CURL_ARGS#|} ${CURL_PREFIX}/${FILE} \| tar -C ${TARGET} -x$COMPRESSION fi ret=$? IFS=$OLDIFS @@ -963,12 +985,12 @@ load_and_write_files() load_file "${KERNEL}" "${TMPBOOT}/${KERNELFILE}" cd "${TMPBOOT}" tar xzf "${KERNELFILE}" - rm "${KERNELFILE}" + rm "${KERNELFILE}" for i in *;do tailname="IMX6${i#*IMX6}" # Replace the files in /boot rm -fv "${TMP_MOUNT_POINT}/"*"${tailname}" - if string_ends_with "${i}" boot.cfg + if string_ends_with "${i}" boot.cfg then cp -v "$i" "${TMP_MOUNT_POINT}/boot.cfg" else @@ -1047,10 +1069,10 @@ load_and_write_files() do if string_contains "$i" "md5sums" then - grep "[[:space:]*]$( basename "$i" )" "$MD5FILETMP" >> "$MD5FILE" || info_msg "WARNING: no md5sum found for $i" + grep "[[:space:]*]$( basename "$i" )" "$MD5FILETMP" >> "$MD5FILE" || info_msg "WARNING: no md5sum found for $i" fi done - + chmod a-w "$MD5FILE" rm "$MD5FILETMP" fi @@ -1161,7 +1183,12 @@ do_installation() # Setup cleanup function to be called on exit (overwrites the error) trap cleanup EXIT - milestone "Update successful" + + if [ -n "$DRYRUN" ];then + milestone "No errors during dry run. Nothing updated." + else + milestone "Update successful" + fi } #==============================================================