Files
fedora-OEMDRV/client_software/0010_kwallet/install.sh
T
Daniel unbrot Pätzold 3429ffa48f kwallet: unmount bind mount cleanly on session logout
Switch kwalletd6-logon from --scope to a transient service with
RemainAfterExit=yes (kwalletd6 forks to background, so the service
must stay active after the main process exits). ExecStop runs
'sudo umount -l' to detach the wallet bind mount before gocryptfs
unmounts ~/data (Before=gocryptfs-home.service ordering).

install.sh adds a per-user sudoers drop-in so the user service
can call umount as root without a password.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-11 11:07:01 +02:00

137 lines
5.2 KiB
Bash
Executable File

#!/usr/bin/env sh
# SPDX-FileCopyrightText: Daniel Pätzold
# SPDX-License-Identifier: AGPL-3.0-or-later
#
# Kwallet Setup to Secure Directory
#
# Kwallet will be used for storing passwords for most KDE- Applications, like for Nextcloud- Client, Talk app and many more.
# Usually Kwallet will set your first logon password for the wallet to have good encryption of your wallet file.
# But when the logon Password changes on the Domain, after new logon you will be asked and you need to know the OLD password
# If the old password was lost. This is a very bad situation, because you cannot recover your passwords.
# Instead we will use Walletfiles without a password, so stored data won't be lost.
# This requires to have them encrypted at a secure place by the domain-encryption that we always use for our Data
#
# Basically, this script checks, if the Walletfile can be used without password and if it is located in the encrypted directory for security.
# Otherwise it will setup a the Walletfile into the encrypted Data-Directory and make it useable.
#
echo "Setup KWallet Password- Service."
#Check for root
if [ "$EUID" -ne 0 ]; then
echo "Error: Script requires root."
exit 1
fi
#Check Token
if [ "${DAVTOKEN_USER}." == "." ]; then
echo "Error: Script cannot be executed standalone and needs a prereserved environment from sync_client_software.sh. Quit."
exit 1
fi
if [[ -z $(wmctrl -m | grep "KWin") ]]; then
# No KDE here - Cinnamon in Test
exit 0
fi
#Local Vars
WALLETNAME="kdewallet"
WALLETFILE="${WALLETNAME}.kwl"
WALLETPATH="${DECRYPTEDDATADIR}/kwallet"
WALLETPATH_CFG="$SUDO_HOME/.local/share/kwalletd"
# Stop the daemon anyway if running
# kwallet and kwalletmanager are optional and only started when an app has been using them already
WALLET_PID=$( pgrep -u $SUDO_USER kwalletd6 )
if [[ ! -z ${WALLET_PID} ]]; then
MANAGER_PID=$( pgrep -u $SUDO_USER kwalletmanager5 )
if [[ ! -z ${MANAGER_PID} ]]; then
echo "Stopping kwalletmanager5 with PID ${MANAGER_PID}"
kill ${MANAGER_PID}
if [[ $? -ne 0 ]]; then
echo "Service could not be stopped, please check why."
exit 1
fi
fi
echo "Stopping kwalletd6 with PID ${WALLET_PID}"
kill ${WALLET_PID} && sleep 0.5
if [[ $? -ne 0 ]]; then
echo "Kwallet Service could not be stopped, please check why."
exit 1
fi
fi
# ksecret is the basic daemon now, it needs to be stopped last
SECTRETS_PID=$( pgrep -u $SUDO_USER ksecretd )
if [[ ! -z ${SECTRETS_PID} ]]; then
echo "Stopping ksecretd with PID ${SECTRETS_PID}"
kill ${SECTRETS_PID} && sleep 0.5
if [[ $? -ne 0 ]]; then
echo "Service could not be stopped, please check why."
exit 1
fi
fi
#Setup encrypted path if not existing already
mkdir -p ${WALLETPATH}
#Check, if wallet ist already setup in encryted dir. If not, copy our empty deafult wallets to it
if [ ! -f "${WALLETPATH}/${WALLETNAME}.kwl" ]; then
echo "Wallet ${WALLETNAME} was not found, setting it up from scratch."
rm -f ${WALLETPATH}/*
cp ${WALLETNAME}.* ${WALLETPATH}
if [[ $? -ne 0 ]]; then
echo "Error: Copy of files for Wallet ${WALLETNAME} failed."
exit 1
fi
else
echo "Will use existing encrypted Wallet in ${WALLETPATH}/${WALLETNAME}.kwl"
fi
chown $SUDO_USER:$SUDO_USER ${WALLETPATH} -R
chmod u=rwX,og-rwx ${WALLETPATH} -R
#Unmount to have free vision to Directory
if grep -q ""${WALLETPATH_CFG}"" "/etc/mtab"; then
echo "Umount of Wallet-Config ${WALLETPATH_CFG}"
umount ${WALLETPATH_CFG}
if [[ $? -ne 0 ]]; then
echo "Error in unmount. Please check."
exit 1
fi
fi
#With every new start of KDE the Files will be recreated in ${WALLETPATH_CFG} containing no passwords but enrcypted with current user password
#We cannot use this wallet, so drop it
rm -f ${WALLETPATH_CFG}/*.*
#Restore initial configuration with defaults and make a backup of the old one
#Only do this once!
if [[ ! -f "$SUDO_HOME/.config/kwalletrc" ]]; then
#New install, never create rc file before -> use predefined
cp -f $(dirname "0")/kwalletrc $SUDO_HOME/.config/
chown $SUDO_USER:$SUDO_USER $SUDO_HOME/.config/kwalletrc
chmod u=rw,og-rwx $SUDO_HOME/.config/kwalletrc
fi
if [[ ! -f "$SUDO_HOME/.config/kwalletrc.bak" ]]; then
# If something else was installed before and no bak is existent, make a bakup and reinstall (could also be the predefined version)
cp $SUDO_HOME/.config/kwalletrc $SUDO_HOME/.config/kwalletrc.bak
cp -f $(dirname "0")/kwalletrc $SUDO_HOME/.config/
chown $SUDO_USER:$SUDO_USER $SUDO_HOME/.config/kwalletrc
chmod u=rw,og-rwx $SUDO_HOME/.config/kwalletrc
fi
#Bind mount secure folder to wallet directory
echo "Mounting secure ${WALLETPATH} to wallet-directory ${WALLETPATH_CFG}"
mount --bind ${WALLETPATH} ${WALLETPATH_CFG}
if [[ $? -ne 0 ]]; then
echo "Error bind mounting secure Files to Wallet. Please check what went wrong."
exit 1
fi
echo "Done setting up kwallet from secure user folder."
# Sudoers rule so kwalletd6-logon.service ExecStop can unmount the bind mount (needs root)
# Filename must not contain '.' or end in '~' or sudo ignores it
_SUDOUSER_SAFE=$(printf '%s' "${SUDO_USER}" | tr -dc 'a-zA-Z0-9_-')
printf '%s ALL=(root) NOPASSWD: /usr/bin/umount -l %s\n' "${SUDO_USER}" "${WALLETPATH_CFG}" \
> "/etc/sudoers.d/kwallet-umount-${_SUDOUSER_SAFE}"
chmod 440 "/etc/sudoers.d/kwallet-umount-${_SUDOUSER_SAFE}"
exit 0