Following API calls trigerred LUKS2 metadata reload
from storage in case of failure:
crypt_convert
crypt_keyslot_add_by_key
crypt_keyslot_add_by_keyfile_device_offset
crypt_keyslot_add_by_passphrase
crypt_keyslot_change_by_passphrase
crypt_reencrypt_init_by_keyring
crypt_reencrypt_init_by_passphrase
This patch replaces LUKS2 metadata reload with
backup LUKS2 metadata copy kept in memory that is updated on
each sucessfull metadata write and rolled back to it whenever
needed in any of those calls listed above.
Adds support for LUKS2 decryption of devices with a
header put in the head of data device. During the initialization
header is exported to a file and first data segment
is moved to head of data device in place of original header.
The feature introduces several new resilience modes (combination
of existing modes datashift and "checksum" or "journal").
Where datashift resilience mode is applied for data moved towards
the first segment and first segment is decrypted in-place.
The mode is not backward compatible with prior LUKS2 reencryption
and therefor interrupted operation in progress can not be resumed
using older cryptsetup releases.
Fixes: #669.
Refresh (and therefore suspend hotzone) reencryption dm
segments in-before actual hotzone reencryption takes place.
This commit shortens time window during which hotzone is
suspended. Also it avoids eventual deadlock if reencryption process
triggers page miss during storage wrapper reinitialization and required
data is stored in (previously) suspended hotzone (corner case).
Due to commit 0113ac2d88
we recalculate reencryption digest whenever LUKS2 reencryption
keyslot gets updated. Until now we perform reencryption digest
refresh every time we call LUKS2_keyslot_reencrypt_update even
when no metadata was updated.
This improves on it and should speed up reencryption resume
process.
The LUKS2 reencrypt keyslot update process should
not be performed in crypt_reencrypt_run() loop where
data reencryption takes place.
The proper location is reencryption process initialization
when we validate reencryption metadata and decide if
new user provided resilience metadata are valid.
Prior to commit 0113ac2d88 it did
not matter what resilince metadata we stored during initialization.
So we stored 'none' type unless 'datashift' operation was initialized.
After the commit, it triggered reencryption metadata digest refresh
almost each time (except 'datashift') which was suboptimal.
By storing proper resilience type during reencryption initialization
we will avoid the needless reencryption digest refresh later (after
update optimization).
The structure is supposed to store all data necessary to perform
reencryption crash recovery. The data block size stored
in LUKS2 metadata was missing and stored in reencryption top level handle
instead.