mirror of
https://github.com/torvalds/linux.git
synced 2024-11-22 04:02:20 +00:00
sed-opal: allow using IOC_OPAL_SAVE for locking too
Usually when closing a crypto device (eg: dm-crypt with LUKS) the volume key is not required, as it requires root privileges anyway, and root can deny access to a disk in many ways regardless. Requiring the volume key to lock the device is a peculiarity of the OPAL specification. Given we might already have saved the key if the user requested it via the 'IOC_OPAL_SAVE' ioctl, we can use that key to lock the device if no key was provided here and the locking range matches, and the user sets the appropriate flag with 'IOC_OPAL_SAVE'. This allows integrating OPAL with tools and libraries that are used to the common behaviour and do not ask for the volume key when closing a device. Callers can always pass a non-zero key and it will be used regardless, as before. Suggested-by: Štěpán Horáček <stepan.horacek@gmail.com> Signed-off-by: Luca Boccassi <bluca@debian.org> Reviewed-by: Christoph Hellwig <hch@lst.de> Reviewed-by: Christian Brauner <brauner@kernel.org> Link: https://lore.kernel.org/r/20221206092913.4625-1-luca.boccassi@gmail.com Signed-off-by: Jens Axboe <axboe@kernel.dk>
This commit is contained in:
parent
37754595e9
commit
c1f480b2d0
@ -2437,6 +2437,44 @@ static int __opal_set_mbr_done(struct opal_dev *dev, struct opal_key *key)
|
||||
return execute_steps(dev, mbrdone_step, ARRAY_SIZE(mbrdone_step));
|
||||
}
|
||||
|
||||
static void opal_lock_check_for_saved_key(struct opal_dev *dev,
|
||||
struct opal_lock_unlock *lk_unlk)
|
||||
{
|
||||
struct opal_suspend_data *iter;
|
||||
|
||||
if (lk_unlk->l_state != OPAL_LK ||
|
||||
lk_unlk->session.opal_key.key_len > 0)
|
||||
return;
|
||||
|
||||
/*
|
||||
* Usually when closing a crypto device (eg: dm-crypt with LUKS) the
|
||||
* volume key is not required, as it requires root privileges anyway,
|
||||
* and root can deny access to a disk in many ways regardless.
|
||||
* Requiring the volume key to lock the device is a peculiarity of the
|
||||
* OPAL specification. Given we might already have saved the key if
|
||||
* the user requested it via the 'IOC_OPAL_SAVE' ioctl, we can use
|
||||
* that key to lock the device if no key was provided here, the
|
||||
* locking range matches and the appropriate flag was passed with
|
||||
* 'IOC_OPAL_SAVE'.
|
||||
* This allows integrating OPAL with tools and libraries that are used
|
||||
* to the common behaviour and do not ask for the volume key when
|
||||
* closing a device.
|
||||
*/
|
||||
setup_opal_dev(dev);
|
||||
list_for_each_entry(iter, &dev->unlk_lst, node) {
|
||||
if ((iter->unlk.flags & OPAL_SAVE_FOR_LOCK) &&
|
||||
iter->lr == lk_unlk->session.opal_key.lr &&
|
||||
iter->unlk.session.opal_key.key_len > 0) {
|
||||
lk_unlk->session.opal_key.key_len =
|
||||
iter->unlk.session.opal_key.key_len;
|
||||
memcpy(lk_unlk->session.opal_key.key,
|
||||
iter->unlk.session.opal_key.key,
|
||||
iter->unlk.session.opal_key.key_len);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int opal_lock_unlock(struct opal_dev *dev,
|
||||
struct opal_lock_unlock *lk_unlk)
|
||||
{
|
||||
@ -2446,6 +2484,7 @@ static int opal_lock_unlock(struct opal_dev *dev,
|
||||
return -EINVAL;
|
||||
|
||||
mutex_lock(&dev->dev_lock);
|
||||
opal_lock_check_for_saved_key(dev, lk_unlk);
|
||||
ret = __opal_lock_unlock(dev, lk_unlk);
|
||||
mutex_unlock(&dev->dev_lock);
|
||||
|
||||
|
@ -44,6 +44,11 @@ enum opal_lock_state {
|
||||
OPAL_LK = 0x04, /* 0100 */
|
||||
};
|
||||
|
||||
enum opal_lock_flags {
|
||||
/* IOC_OPAL_SAVE will also store the provided key for locking */
|
||||
OPAL_SAVE_FOR_LOCK = 0x01,
|
||||
};
|
||||
|
||||
struct opal_key {
|
||||
__u8 lr;
|
||||
__u8 key_len;
|
||||
@ -76,7 +81,8 @@ struct opal_user_lr_setup {
|
||||
struct opal_lock_unlock {
|
||||
struct opal_session_info session;
|
||||
__u32 l_state;
|
||||
__u8 __align[4];
|
||||
__u16 flags;
|
||||
__u8 __align[2];
|
||||
};
|
||||
|
||||
struct opal_new_pw {
|
||||
|
Loading…
Reference in New Issue
Block a user