chkboot icon indicating copy to clipboard operation
chkboot copied to clipboard

"chkboot -u" does not update files, causes false positives

Open d51iq3mzd2pkc opened this issue 10 years ago • 0 comments

After making intended changes to the /boot filesystem, the user is intended to run the command "chkboot -u". However, running this command does effectively nothing. This causes a false positive the next time the system boots.

Proof:

Suppose a user runs "chkboot -u" after making intended changes to the /boot partition.

At the beginning of the script, this causes the $CHANGED variable to be set to "-1":

if [ "$1" = "-u" -o "$1" = "--update" ]; then
        CHANGED="-1"

Afterwards, the script generates the hashes for the filesystem to $DISKHEAD and $BOOTFILES.

The following piece of code is NOT run when running "chkboot -u":

    if [ ! "$CHANGED" = "-1" ]; then
        ( diff $BOOTFILES_LAST $BOOTFILES >> "${CHANGES_ALERT}-now" ) || CHANGED="1"
        ( diff $DISKHEAD_LAST $DISKHEAD >> "${CHANGES_ALERT}-now" ) || CHANGED="1"
    fi

Therefore, the $CHANGED variable remains "-1".

Immediately after, the following piece of code runs:

    if [ ! $CHANGED = "1" ] ; then
        rm -f $DISKHEAD "${CHANGES_ALERT}-now" $BOOTFILES
    else
        [snip]
    fi

Since $CHANGED is not "1" (it is "-1"), this causes the program to remove the generated files (the first branch is chosen), causing a false positive on the next boot, since the last hashes still point to the old files.

Proposed solution

Replace the following lines:

if [ ! -z "$1" ]; then
    if [ "$1" = "-u" -o "$1" = "--update" ]; then
        CHANGED="-1"
    elif [ "$1" = "-h" -o "$1" = "--help" ]; then
        help
        exit 0
    else
        echo -e "Invalid argument: ${1}"
        help
        exit 1
    fi
else
    CHANGED="0"
fi

With:

if [ ! -z "$1" ]; then
    if [ "$1" = "-u" -o "$1" = "--update" ]; then
        UPDATEONLY="1"
    elif [ "$1" = "-h" -o "$1" = "--help" ]; then
        help
        exit 0
    else
        echo -e "Invalid argument: ${1}"
        help
        exit 1
    fi
else
    UPDATEONLY="0"
fi

Rationale: The $CHANGED variable should only be used to specify whether the boot hashes have changed, not the running mode of the program.

Replace the following lines:

    if [ ! "$CHANGED" = "-1" ]; then
        ( diff $BOOTFILES_LAST $BOOTFILES >> "${CHANGES_ALERT}-now" ) || CHANGED="1"
        ( diff $DISKHEAD_LAST $DISKHEAD >> "${CHANGES_ALERT}-now" ) || CHANGED="1"
    fi

With:

    CHANGED="0"
    ( diff $BOOTFILES_LAST $BOOTFILES >> "${CHANGES_ALERT}-now" ) || CHANGED="1"
    ( diff $DISKHEAD_LAST $DISKHEAD >> "${CHANGES_ALERT}-now" ) || CHANGED="1"

Rationale: Independently of the running mode, the $CHANGED variable will be set to "0" if the boot files have changed, and to "1" otherwise.

Replace the following lines:

    if [ ! $CHANGED = "1" ] ; then
        rm -f $DISKHEAD "${CHANGES_ALERT}-now" $BOOTFILES
    else
        # create the changes alert file with a heading and the date and the list of changed files
        echo -e "List of changed files on `date`:\n" > "${CHANGES_ALERT}"
        cat "${CHANGES_ALERT}-now" >> "$CHANGES_ALERT"

        # copy the latest changes file to the end of the log
        cat "$CHANGES_ALERT" >> "$CHANGES_LOG"
        echo >> "$CHANGES_LOG"

        # set the latest hashes to the old ones for next time then exit
        ln -s -f $BOOTFILES $BOOTFILES_LAST
        ln -s -f $DISKHEAD $DISKHEAD_LAST
        exit 1
    fi

With:

    if [ ! $CHANGED = "1" ] ; then
        rm -f $DISKHEAD "${CHANGES_ALERT}-now" $BOOTFILES
    else
        if [ ! $UPDATEONLY = "1" ] ; then
            # create the changes alert file with a heading and the date and the list of changed files
            echo -e "List of changed files on `date`:\n" > "${CHANGES_ALERT}"
            cat "${CHANGES_ALERT}-now" >> "$CHANGES_ALERT"

            # copy the latest changes file to the end of the log
            cat "$CHANGES_ALERT" >> "$CHANGES_LOG"
            echo >> "$CHANGES_LOG"
        else
            # since we're updating, remove the changes log and just leave the check files
            rm -f "${CHANGES_ALERT}-now"
        fi

        # set the latest hashes to the old ones for next time then exit
        ln -s -f $BOOTFILES $BOOTFILES_LAST
        ln -s -f $DISKHEAD $DISKHEAD_LAST
        exit 1
    fi

Rationale: Implement the documented behaviour. If the boot files didn't change, then no changes are made to the filesystem. Otherwise, report changes unless we're in update mode and update the hash files.

DISCLAIMER: The author of this issue does not guarantee, in any way, that the explained changes will result in the solution to the exposed issue and/or will not cause the program to report false positives or false negatives.

d51iq3mzd2pkc avatar Apr 15 '14 19:04 d51iq3mzd2pkc