]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
homework: make libcryptsetup dep runtime optional
authorLennart Poettering <lennart@poettering.net>
Mon, 31 May 2021 20:50:44 +0000 (22:50 +0200)
committerLennart Poettering <lennart@poettering.net>
Tue, 1 Jun 2021 11:32:40 +0000 (13:32 +0200)
meson.build
src/home/homework-luks.c
src/home/homework-luks.h
src/home/homework.c
src/shared/cryptsetup-util.c
src/shared/cryptsetup-util.h

index 0ce978f8e529b15c550d3a5524853c3bdd2fb721..65d0a0f6eaaf71e5cc98402716bc898651c483e0 100644 (file)
@@ -2254,7 +2254,6 @@ if conf.get('ENABLE_HOMED') == 1
                 include_directories : includes,
                 link_with : [libshared],
                 dependencies : [threads,
-                                libcryptsetup,
                                 libblkid,
                                 libcrypt,
                                 libopenssl,
index 7a06bb4b8e539f3faa1d69af5d37cf739125eae8..87c999b6e3031541cb35374b2aa43a792e78c719 100644 (file)
@@ -243,7 +243,7 @@ static int luks_try_passwords(
         STRV_FOREACH(pp, passwords) {
                 size_t vks = *volume_key_size;
 
-                r = crypt_volume_key_get(
+                r = sym_crypt_volume_key_get(
                                 cd,
                                 CRYPT_ANY_SLOT,
                                 volume_key,
@@ -276,7 +276,7 @@ static int luks_setup(
                 void **ret_volume_key,
                 size_t *ret_volume_key_size) {
 
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         _cleanup_(erase_and_freep) void *vk = NULL;
         sd_id128_t p;
         size_t vks;
@@ -287,17 +287,17 @@ static int luks_setup(
         assert(dm_name);
         assert(ret);
 
-        r = crypt_init(&cd, node);
+        r = sym_crypt_init(&cd, node);
         if (r < 0)
                 return log_error_errno(r, "Failed to allocate libcryptsetup context: %m");
 
         cryptsetup_enable_logging(cd);
 
-        r = crypt_load(cd, CRYPT_LUKS2, NULL);
+        r = sym_crypt_load(cd, CRYPT_LUKS2, NULL);
         if (r < 0)
                 return log_error_errno(r, "Failed to load LUKS superblock: %m");
 
-        r = crypt_get_volume_key_size(cd);
+        r = sym_crypt_get_volume_key_size(cd);
         if (r <= 0)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Failed to determine LUKS volume key size");
         vks = (size_t) r;
@@ -305,7 +305,7 @@ static int luks_setup(
         if (!sd_id128_is_null(uuid) || ret_found_uuid) {
                 const char *s;
 
-                s = crypt_get_uuid(cd);
+                s = sym_crypt_get_uuid(cd);
                 if (!s)
                         return log_error_errno(SYNTHETIC_ERRNO(EMEDIUMTYPE), "LUKS superblock has no UUID.");
 
@@ -319,10 +319,10 @@ static int luks_setup(
                         return log_error_errno(SYNTHETIC_ERRNO(EMEDIUMTYPE), "LUKS superblock has wrong UUID.");
         }
 
-        if (cipher && !streq_ptr(cipher, crypt_get_cipher(cd)))
+        if (cipher && !streq_ptr(cipher, sym_crypt_get_cipher(cd)))
                 return log_error_errno(SYNTHETIC_ERRNO(EMEDIUMTYPE), "LUKS superblock declares wrong cipher.");
 
-        if (cipher_mode && !streq_ptr(cipher_mode, crypt_get_cipher_mode(cd)))
+        if (cipher_mode && !streq_ptr(cipher_mode, sym_crypt_get_cipher_mode(cd)))
                 return log_error_errno(SYNTHETIC_ERRNO(EMEDIUMTYPE), "LUKS superblock declares wrong cipher mode.");
 
         if (volume_key_size != UINT64_MAX && vks != volume_key_size)
@@ -343,7 +343,7 @@ static int luks_setup(
         if (r < 0)
                 return log_error_errno(r, "Failed to unlocks LUKS superblock: %m");
 
-        r = crypt_activate_by_volume_key(
+        r = sym_crypt_activate_by_volume_key(
                         cd,
                         dm_name,
                         vk, vks,
@@ -374,7 +374,7 @@ static int luks_open(
                 void **ret_volume_key,
                 size_t *ret_volume_key_size) {
 
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         _cleanup_(erase_and_freep) void *vk = NULL;
         sd_id128_t p;
         char **list;
@@ -387,17 +387,17 @@ static int luks_open(
         /* Opens a LUKS device that is already set up. Re-validates the password while doing so (which also
          * provides us with the volume key, which we want). */
 
-        r = crypt_init_by_name(&cd, dm_name);
+        r = sym_crypt_init_by_name(&cd, dm_name);
         if (r < 0)
                 return log_error_errno(r, "Failed to initialize cryptsetup context for %s: %m", dm_name);
 
         cryptsetup_enable_logging(cd);
 
-        r = crypt_load(cd, CRYPT_LUKS2, NULL);
+        r = sym_crypt_load(cd, CRYPT_LUKS2, NULL);
         if (r < 0)
                 return log_error_errno(r, "Failed to load LUKS superblock: %m");
 
-        r = crypt_get_volume_key_size(cd);
+        r = sym_crypt_get_volume_key_size(cd);
         if (r <= 0)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Failed to determine LUKS volume key size");
         vks = (size_t) r;
@@ -405,7 +405,7 @@ static int luks_open(
         if (ret_found_uuid) {
                 const char *s;
 
-                s = crypt_get_uuid(cd);
+                s = sym_crypt_get_uuid(cd);
                 if (!s)
                         return log_error_errno(SYNTHETIC_ERRNO(EMEDIUMTYPE), "LUKS superblock has no UUID.");
 
@@ -433,7 +433,7 @@ static int luks_open(
 
         /* This is needed so that crypt_resize() can operate correctly for pre-existing LUKS devices. We need
          * to tell libcryptsetup the volume key explicitly, so that it is in the kernel keyring. */
-        r = crypt_activate_by_volume_key(cd, NULL, vk, vks, CRYPT_ACTIVATE_KEYRING_KEY);
+        r = sym_crypt_activate_by_volume_key(cd, NULL, vk, vks, CRYPT_ACTIVATE_KEYRING_KEY);
         if (r < 0)
                 return log_error_errno(r, "Failed to upload volume key again: %m");
 
@@ -640,11 +640,11 @@ static int crypt_device_to_evp_cipher(struct crypt_device *cd, const EVP_CIPHER
         /* Let's find the right OpenSSL EVP_CIPHER object that matches the encryption settings of the LUKS
          * device */
 
-        cipher = crypt_get_cipher(cd);
+        cipher = sym_crypt_get_cipher(cd);
         if (!cipher)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Cannot get cipher from LUKS device.");
 
-        cipher_mode = crypt_get_cipher_mode(cd);
+        cipher_mode = sym_crypt_get_cipher_mode(cd);
         if (!cipher_mode)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Cannot get cipher mode from LUKS device.");
 
@@ -652,7 +652,7 @@ static int crypt_device_to_evp_cipher(struct crypt_device *cd, const EVP_CIPHER
         if (e)
                 cipher_mode = strndupa(cipher_mode, e - cipher_mode);
 
-        r = crypt_get_volume_key_size(cd);
+        r = sym_crypt_get_volume_key_size(cd);
         if (r <= 0)
                 return log_error_errno(r < 0 ? r : SYNTHETIC_ERRNO(EINVAL), "Cannot get volume key size from LUKS device.");
 
@@ -703,7 +703,7 @@ static int luks_validate_home_record(
                 unsigned line, column;
                 const EVP_CIPHER *cc;
 
-                state = crypt_token_status(cd, token, &type);
+                state = sym_crypt_token_status(cd, token, &type);
                 if (state == CRYPT_TOKEN_INACTIVE) /* First unconfigured token, give up */
                         break;
                 if (IN_SET(state, CRYPT_TOKEN_INTERNAL, CRYPT_TOKEN_INTERNAL_UNKNOWN, CRYPT_TOKEN_EXTERNAL))
@@ -714,7 +714,7 @@ static int luks_validate_home_record(
                 if (!streq(type, "systemd-homed"))
                         continue;
 
-                r = crypt_token_json_get(cd, token, &text);
+                r = sym_crypt_token_json_get(cd, token, &text);
                 if (r < 0)
                         return log_error_errno(r, "Failed to read LUKS token %i: %m", token);
 
@@ -919,7 +919,7 @@ int home_store_header_identity_luks(
                 crypt_token_info state;
                 const char *type;
 
-                state = crypt_token_status(setup->crypt_device, token, &type);
+                state = sym_crypt_token_status(setup->crypt_device, token, &type);
                 if (state == CRYPT_TOKEN_INACTIVE) /* First unconfigured token, we are done */
                         break;
                 if (IN_SET(state, CRYPT_TOKEN_INTERNAL, CRYPT_TOKEN_INTERNAL_UNKNOWN, CRYPT_TOKEN_EXTERNAL))
@@ -930,7 +930,7 @@ int home_store_header_identity_luks(
                 if (!streq(type, "systemd-homed"))
                         continue;
 
-                r = crypt_token_json_set(setup->crypt_device, token, text);
+                r = sym_crypt_token_json_set(setup->crypt_device, token, text);
                 if (r < 0)
                         return log_error_errno(r, "Failed to set JSON token for slot %i: %m", token);
 
@@ -1048,7 +1048,7 @@ int home_prepare_luks(
         sd_id128_t found_partition_uuid, found_luks_uuid, found_fs_uuid;
         _cleanup_(user_record_unrefp) UserRecord *luks_home = NULL;
         _cleanup_(loop_device_unrefp) LoopDevice *loop = NULL;
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         _cleanup_(erase_and_freep) void *volume_key = NULL;
         _cleanup_close_ int root_fd = -1, image_fd = -1;
         bool dm_activated = false, mounted = false;
@@ -1064,6 +1064,10 @@ int home_prepare_luks(
 
         assert(user_record_storage(h) == USER_LUKS);
 
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
         if (already_activated) {
                 struct loop_info64 info;
                 const char *n;
@@ -1082,7 +1086,7 @@ int home_prepare_luks(
                 if (r < 0)
                         return r;
 
-                n = crypt_get_device_name(cd);
+                n = sym_crypt_get_device_name(cd);
                 if (!n)
                         return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Failed to determine backing device for DM %s.", setup->dm_name);
 
@@ -1265,7 +1269,7 @@ fail:
                 (void) umount_verbose(LOG_ERR, "/run/systemd/user-home-mount", UMOUNT_NOFOLLOW);
 
         if (dm_activated)
-                (void) crypt_deactivate(cd, setup->dm_name);
+                (void) sym_crypt_deactivate_by_name(cd, setup->dm_name, 0);
 
         if (image_fd >= 0 && marked_dirty)
                 (void) run_mark_dirty(image_fd, false);
@@ -1301,6 +1305,10 @@ int home_activate_luks(
         assert(user_record_storage(h) == USER_LUKS);
         assert(ret_home);
 
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
         assert_se(hdo = user_record_home_directory(h));
         hd = strdupa(hdo); /* copy the string out, since it might change later in the home record object */
 
@@ -1358,7 +1366,7 @@ int home_activate_luks(
 
         loop_device_relinquish(setup.loop);
 
-        r = crypt_deactivate_by_name(NULL, setup.dm_name, CRYPT_DEACTIVATE_DEFERRED);
+        r = sym_crypt_deactivate_by_name(NULL, setup.dm_name, CRYPT_DEACTIVATE_DEFERRED);
         if (r < 0)
                 log_warning_errno(r, "Failed to relinquish DM device, ignoring: %m");
 
@@ -1375,7 +1383,7 @@ int home_activate_luks(
 }
 
 int home_deactivate_luks(UserRecord *h) {
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         _cleanup_free_ char *dm_name = NULL, *dm_node = NULL;
         bool we_detached;
         int r;
@@ -1386,11 +1394,15 @@ int home_deactivate_luks(UserRecord *h) {
          * don't bother about the loopback device because unlike the DM device it doesn't have a fixed
          * name. */
 
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
         r = make_dm_names(h->user_name, &dm_name, &dm_node);
         if (r < 0)
                 return r;
 
-        r = crypt_init_by_name(&cd, dm_name);
+        r = sym_crypt_init_by_name(&cd, dm_name);
         if (IN_SET(r, -ENODEV, -EINVAL, -ENOENT)) {
                 log_debug_errno(r, "LUKS device %s has already been detached.", dm_name);
                 we_detached = false;
@@ -1401,7 +1413,7 @@ int home_deactivate_luks(UserRecord *h) {
 
                 cryptsetup_enable_logging(cd);
 
-                r = crypt_deactivate(cd, dm_name);
+                r = sym_crypt_deactivate_by_name(cd, dm_name, 0);
                 if (IN_SET(r, -ENODEV, -EINVAL, -ENOENT)) {
                         log_debug_errno(r, "LUKS device %s is already detached.", dm_node);
                         we_detached = false;
@@ -1477,7 +1489,7 @@ static int luks_format(
                 struct crypt_device **ret) {
 
         _cleanup_(user_record_unrefp) UserRecord *reduced = NULL;
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         _cleanup_(erase_and_freep) void *volume_key = NULL;
         struct crypt_pbkdf_type good_pbkdf, minimal_pbkdf;
         char suuid[ID128_UUID_STRING_MAX], **pp;
@@ -1490,7 +1502,7 @@ static int luks_format(
         assert(hr);
         assert(ret);
 
-        r = crypt_init(&cd, node);
+        r = sym_crypt_init(&cd, node);
         if (r < 0)
                 return log_error_errno(r, "Failed to allocate libcryptsetup context: %m");
 
@@ -1511,7 +1523,7 @@ static int luks_format(
 
 #if HAVE_CRYPT_SET_METADATA_SIZE
         /* Increase the metadata space to 4M, the largest LUKS2 supports */
-        r = crypt_set_metadata_size(cd, 4096U*1024U, 0);
+        r = sym_crypt_set_metadata_size(cd, 4096U*1024U, 0);
         if (r < 0)
                 return log_error_errno(r, "Failed to change LUKS2 metadata size: %m");
 #endif
@@ -1519,7 +1531,7 @@ static int luks_format(
         build_good_pbkdf(&good_pbkdf, hr);
         build_minimal_pbkdf(&minimal_pbkdf, hr);
 
-        r = crypt_format(cd,
+        r = sym_crypt_format(cd,
                          CRYPT_LUKS2,
                          user_record_luks_cipher(hr),
                          user_record_luks_cipher_mode(hr),
@@ -1542,15 +1554,15 @@ static int luks_format(
                 if (strv_contains(cache->pkcs11_passwords, *pp) ||
                     strv_contains(cache->fido2_passwords, *pp)) {
                         log_debug("Using minimal PBKDF for slot %i", slot);
-                        r = crypt_set_pbkdf_type(cd, &minimal_pbkdf);
+                        r = sym_crypt_set_pbkdf_type(cd, &minimal_pbkdf);
                 } else {
                         log_debug("Using good PBKDF for slot %i", slot);
-                        r = crypt_set_pbkdf_type(cd, &good_pbkdf);
+                        r = sym_crypt_set_pbkdf_type(cd, &good_pbkdf);
                 }
                 if (r < 0)
                         return log_error_errno(r, "Failed to tweak PBKDF for slot %i: %m", slot);
 
-                r = crypt_keyslot_add_by_volume_key(
+                r = sym_crypt_keyslot_add_by_volume_key(
                                 cd,
                                 slot,
                                 volume_key,
@@ -1564,7 +1576,7 @@ static int luks_format(
                 slot++;
         }
 
-        r = crypt_activate_by_volume_key(
+        r = sym_crypt_activate_by_volume_key(
                         cd,
                         dm_name,
                         volume_key,
@@ -1583,7 +1595,7 @@ static int luks_format(
         if (r < 0)
                 return r;
 
-        r = crypt_token_json_set(cd, CRYPT_ANY_TOKEN, text);
+        r = sym_crypt_token_json_set(cd, CRYPT_ANY_TOKEN, text);
         if (r < 0)
                 return log_error_errno(r, "Failed to set LUKS JSON token: %m");
 
@@ -1876,7 +1888,7 @@ int home_create_luks(
         _cleanup_(user_record_unrefp) UserRecord *new_home = NULL;
         sd_id128_t partition_uuid, fs_uuid, luks_uuid, disk_uuid;
         _cleanup_(loop_device_unrefp) LoopDevice *loop = NULL;
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         _cleanup_close_ int image_fd = -1, root_fd = -1;
         const char *fstype, *ip;
         struct statfs sfs;
@@ -1886,6 +1898,10 @@ int home_create_luks(
         assert(h->storage < 0 || h->storage == USER_LUKS);
         assert(ret_home);
 
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
         assert_se(ip = user_record_image_path(h));
 
         fstype = user_record_file_system_type(h);
@@ -2152,8 +2168,8 @@ int home_create_luks(
                         partition_uuid,
                         luks_uuid,
                         fs_uuid,
-                        crypt_get_cipher(cd),
-                        crypt_get_cipher_mode(cd),
+                        sym_crypt_get_cipher(cd),
+                        sym_crypt_get_cipher_mode(cd),
                         luks_volume_key_size_convert(cd),
                         fstype,
                         NULL,
@@ -2178,13 +2194,13 @@ int home_create_luks(
 
         mounted = false;
 
-        r = crypt_deactivate(cd, dm_name);
+        r = sym_crypt_deactivate_by_name(cd, dm_name, 0);
         if (r < 0) {
                 log_error_errno(r, "Failed to deactivate LUKS device: %m");
                 goto fail;
         }
 
-        crypt_free(cd);
+        sym_crypt_free(cd);
         cd = NULL;
 
         dm_activated = false;
@@ -2245,7 +2261,7 @@ fail:
                 (void) umount_verbose(LOG_WARNING, "/run/systemd/user-home-mount", UMOUNT_NOFOLLOW);
 
         if (dm_activated)
-                (void) crypt_deactivate(cd, dm_name);
+                (void) sym_crypt_deactivate_by_name(cd, dm_name, 0);
 
         loop = loop_device_unref(loop);
 
@@ -2633,6 +2649,10 @@ int home_resize_luks(
         assert(setup);
         assert(ret_home);
 
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
         assert_se(ipo = user_record_image_path(h));
         ip = strdupa(ipo); /* copy out since original might change later in home record object */
 
@@ -2733,7 +2753,7 @@ int home_resize_luks(
             setup->partition_offset + new_partition_size > new_image_size)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "New partition doesn't fit into backing storage, refusing.");
 
-        crypto_offset = crypt_get_data_offset(setup->crypt_device);
+        crypto_offset = sym_crypt_get_data_offset(setup->crypt_device);
         if (setup->partition_size / 512U <= crypto_offset)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Weird, old crypto payload offset doesn't actually fit in partition size?");
         if (new_partition_size / 512U <= crypto_offset)
@@ -2797,7 +2817,7 @@ int home_resize_luks(
                         log_debug_errno(errno, "BLKRRPART failed on block device, ignoring: %m");
 
                 /* Tell LUKS about the new bigger size too */
-                r = crypt_resize(setup->crypt_device, setup->dm_name, new_fs_size / 512U);
+                r = sym_crypt_resize(setup->crypt_device, setup->dm_name, new_fs_size / 512U);
                 if (r < 0)
                         return log_error_errno(r, "Failed to grow LUKS device: %m");
 
@@ -2838,7 +2858,7 @@ int home_resize_luks(
         if (new_fs_size < old_fs_size) {
 
                 /* Shrink the LUKS device now, matching the new file system size */
-                r = crypt_resize(setup->crypt_device, setup->dm_name, new_fs_size / 512);
+                r = sym_crypt_resize(setup->crypt_device, setup->dm_name, new_fs_size / 512);
                 if (r < 0)
                         return log_error_errno(r, "Failed to shrink LUKS device: %m");
 
@@ -2919,16 +2939,20 @@ int home_passwd_luks(
         assert(user_record_storage(h) == USER_LUKS);
         assert(setup);
 
-        type = crypt_get_type(setup->crypt_device);
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
+        type = sym_crypt_get_type(setup->crypt_device);
         if (!type)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Failed to determine crypto device type.");
 
-        r = crypt_keyslot_max(type);
+        r = sym_crypt_keyslot_max(type);
         if (r <= 0)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Failed to determine number of key slots.");
         max_key_slots = r;
 
-        r = crypt_get_volume_key_size(setup->crypt_device);
+        r = sym_crypt_get_volume_key_size(setup->crypt_device);
         if (r <= 0)
                 return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Failed to determine volume key size.");
         volume_key_size = (size_t) r;
@@ -2954,7 +2978,7 @@ int home_passwd_luks(
         build_minimal_pbkdf(&minimal_pbkdf, h);
 
         for (size_t i = 0; i < max_key_slots; i++) {
-                r = crypt_keyslot_destroy(setup->crypt_device, i);
+                r = sym_crypt_keyslot_destroy(setup->crypt_device, i);
                 if (r < 0 && !IN_SET(r, -ENOENT, -EINVAL)) /* Returns EINVAL or ENOENT if there's no key in this slot already */
                         return log_error_errno(r, "Failed to destroy LUKS password: %m");
 
@@ -2967,15 +2991,15 @@ int home_passwd_luks(
                 if (strv_contains(cache->pkcs11_passwords, effective_passwords[i]) ||
                     strv_contains(cache->fido2_passwords, effective_passwords[i])) {
                         log_debug("Using minimal PBKDF for slot %zu", i);
-                        r = crypt_set_pbkdf_type(setup->crypt_device, &minimal_pbkdf);
+                        r = sym_crypt_set_pbkdf_type(setup->crypt_device, &minimal_pbkdf);
                 } else {
                         log_debug("Using good PBKDF for slot %zu", i);
-                        r = crypt_set_pbkdf_type(setup->crypt_device, &good_pbkdf);
+                        r = sym_crypt_set_pbkdf_type(setup->crypt_device, &good_pbkdf);
                 }
                 if (r < 0)
                         return log_error_errno(r, "Failed to tweak PBKDF for slot %zu: %m", i);
 
-                r = crypt_keyslot_add_by_volume_key(
+                r = sym_crypt_keyslot_add_by_volume_key(
                                 setup->crypt_device,
                                 i,
                                 volume_key,
@@ -2992,7 +3016,7 @@ int home_passwd_luks(
 }
 
 int home_lock_luks(UserRecord *h) {
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         _cleanup_free_ char *dm_name = NULL, *dm_node = NULL;
         _cleanup_close_ int root_fd = -1;
         const char *p;
@@ -3009,7 +3033,11 @@ int home_lock_luks(UserRecord *h) {
         if (r < 0)
                 return r;
 
-        r = crypt_init_by_name(&cd, dm_name);
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
+        r = sym_crypt_init_by_name(&cd, dm_name);
         if (r < 0)
                 return log_error_errno(r, "Failed to initialize cryptsetup context for %s: %m", dm_name);
 
@@ -3025,7 +3053,7 @@ int home_lock_luks(UserRecord *h) {
 
         /* Note that we don't invoke FIFREEZE here, it appears libcryptsetup/device-mapper already does that on its own for us */
 
-        r = crypt_suspend(cd, dm_name);
+        r = sym_crypt_suspend(cd, dm_name);
         if (r < 0)
                 return log_error_errno(r, "Failed to suspend cryptsetup device: %s: %m", dm_node);
 
@@ -3045,7 +3073,7 @@ static int luks_try_resume(
         assert(dm_name);
 
         STRV_FOREACH(pp, password) {
-                r = crypt_resume_by_passphrase(
+                r = sym_crypt_resume_by_passphrase(
                                 cd,
                                 dm_name,
                                 CRYPT_ANY_SLOT,
@@ -3064,7 +3092,7 @@ static int luks_try_resume(
 
 int home_unlock_luks(UserRecord *h, PasswordCache *cache) {
         _cleanup_free_ char *dm_name = NULL, *dm_node = NULL;
-        _cleanup_(crypt_freep) struct crypt_device *cd = NULL;
+        _cleanup_(sym_crypt_freep) struct crypt_device *cd = NULL;
         char **list;
         int r;
 
@@ -3074,7 +3102,11 @@ int home_unlock_luks(UserRecord *h, PasswordCache *cache) {
         if (r < 0)
                 return r;
 
-        r = crypt_init_by_name(&cd, dm_name);
+        r = dlopen_cryptsetup();
+        if (r < 0)
+                return r;
+
+        r = sym_crypt_init_by_name(&cd, dm_name);
         if (r < 0)
                 return log_error_errno(r, "Failed to initialize cryptsetup context for %s: %m", dm_name);
 
index c43bdfcba3f31c039ead6cc385d7eb20f63669a7..8764862bd2cb47821bdb3b07adb166c95874e6aa 100644 (file)
@@ -31,7 +31,7 @@ static inline uint64_t luks_volume_key_size_convert(struct crypt_device *cd) {
 
         /* Convert the "int" to uint64_t, which we usually use for byte sizes stored on disk. */
 
-        k = crypt_get_volume_key_size(cd);
+        k = sym_crypt_get_volume_key_size(cd);
         if (k <= 0)
                 return UINT64_MAX;
 
index ed6fc2c3449f8e0d96f73fe134f0c86f0976e590..cfabf348acdfbe29df22a40ff59082fb90269d83 100644 (file)
@@ -304,7 +304,7 @@ int home_setup_undo(HomeSetup *setup) {
         }
 
         if (setup->undo_dm && setup->crypt_device && setup->dm_name) {
-                q = crypt_deactivate(setup->crypt_device, setup->dm_name);
+                q = sym_crypt_deactivate_by_name(setup->crypt_device, setup->dm_name, 0);
                 if (q < 0)
                         r = q;
         }
@@ -335,8 +335,10 @@ int home_setup_undo(HomeSetup *setup) {
         setup->dm_node = mfree(setup->dm_node);
 
         setup->loop = loop_device_unref(setup->loop);
-        crypt_free(setup->crypt_device);
-        setup->crypt_device = NULL;
+        if (setup->crypt_device) {
+                sym_crypt_free(setup->crypt_device);
+                setup->crypt_device = NULL;
+        }
 
         explicit_bzero_safe(setup->volume_key, setup->volume_key_size);
         setup->volume_key = mfree(setup->volume_key);
@@ -660,8 +662,8 @@ int home_extend_embedded_identity(UserRecord *h, UserRecord *used, HomeSetup *se
                         setup->found_partition_uuid,
                         setup->found_luks_uuid,
                         setup->found_fs_uuid,
-                        setup->crypt_device ? crypt_get_cipher(setup->crypt_device) : NULL,
-                        setup->crypt_device ? crypt_get_cipher_mode(setup->crypt_device) : NULL,
+                        setup->crypt_device ? sym_crypt_get_cipher(setup->crypt_device) : NULL,
+                        setup->crypt_device ? sym_crypt_get_cipher_mode(setup->crypt_device) : NULL,
                         setup->crypt_device ? luks_volume_key_size_convert(setup->crypt_device) : UINT64_MAX,
                         file_system_type_fd(setup->root_fd),
                         user_record_home_directory(used),
index c1ba9f6ab7c92d0e44093fddbdfd3aa2483e4945..ca88f4931f77351fdb31e1f85a55724734c78c79 100644 (file)
@@ -17,23 +17,38 @@ int (*sym_crypt_activate_by_volume_key)(struct crypt_device *cd, const char *nam
 int (*sym_crypt_deactivate_by_name)(struct crypt_device *cd, const char *name, uint32_t flags);
 int (*sym_crypt_format)(struct crypt_device *cd, const char *type, const char *cipher, const char *cipher_mode, const char *uuid, const char *volume_key, size_t volume_key_size, void *params);
 void (*sym_crypt_free)(struct crypt_device *cd);
+const char *(*sym_crypt_get_cipher)(struct crypt_device *cd);
+const char *(*sym_crypt_get_cipher_mode)(struct crypt_device *cd);
+uint64_t (*sym_crypt_get_data_offset)(struct crypt_device *cd);
+const char *(*sym_crypt_get_device_name)(struct crypt_device *cd);
 const char *(*sym_crypt_get_dir)(void);
+const char *(*sym_crypt_get_type)(struct crypt_device *cd);
+const char *(*sym_crypt_get_uuid)(struct crypt_device *cd);
 int (*sym_crypt_get_verity_info)(struct crypt_device *cd, struct crypt_params_verity *vp);
+int (*sym_crypt_get_volume_key_size)(struct crypt_device *cd);
 int (*sym_crypt_init)(struct crypt_device **cd, const char *device);
 int (*sym_crypt_init_by_name)(struct crypt_device **cd, const char *name);
 int (*sym_crypt_keyslot_add_by_volume_key)(struct crypt_device *cd, int keyslot, const char *volume_key, size_t volume_key_size, const char *passphrase, size_t passphrase_size);
+int (*sym_crypt_keyslot_destroy)(struct crypt_device *cd, int keyslot);
+int (*sym_crypt_keyslot_max)(const char *type);
 int (*sym_crypt_load)(struct crypt_device *cd, const char *requested_type, void *params);
 int (*sym_crypt_resize)(struct crypt_device *cd, const char *name, uint64_t new_size);
+int (*sym_crypt_resume_by_passphrase)(struct crypt_device *cd, const char *name, int keyslot, const char *passphrase, size_t passphrase_size);
 int (*sym_crypt_set_data_device)(struct crypt_device *cd, const char *device);
 void (*sym_crypt_set_debug_level)(int level);
 void (*sym_crypt_set_log_callback)(struct crypt_device *cd, void (*log)(int level, const char *msg, void *usrptr), void *usrptr);
-int (*sym_crypt_set_pbkdf_type)(struct crypt_device *cd, const struct crypt_pbkdf_type *pbkdf) = NULL;
-int (*sym_crypt_token_json_get)(struct crypt_device *cd, int token, const char **json) = NULL;
-int (*sym_crypt_token_json_set)(struct crypt_device *cd, int token, const char *json) = NULL;
-int (*sym_crypt_volume_key_get)(struct crypt_device *cd, int keyslot, char *volume_key, size_t *volume_key_size, const char *passphrase, size_t passphrase_size);
+#if HAVE_CRYPT_SET_METADATA_SIZE
+int (*sym_crypt_set_metadata_size)(struct crypt_device *cd, uint64_t metadata_size, uint64_t keyslots_size);
+#endif
+int (*sym_crypt_set_pbkdf_type)(struct crypt_device *cd, const struct crypt_pbkdf_type *pbkdf);
+int (*sym_crypt_suspend)(struct crypt_device *cd, const char *name);
+int (*sym_crypt_token_json_get)(struct crypt_device *cd, int token, const char **json);
+int (*sym_crypt_token_json_set)(struct crypt_device *cd, int token, const char *json);
 #if HAVE_CRYPT_TOKEN_MAX
 int (*sym_crypt_token_max)(const char *type);
 #endif
+crypt_token_info (*sym_crypt_token_status)(struct crypt_device *cd, int token, const char **type);
+int (*sym_crypt_volume_key_get)(struct crypt_device *cd, int keyslot, char *volume_key, size_t *volume_key_size, const char *passphrase, size_t passphrase_size);
 
 int dlopen_cryptsetup(void) {
         _cleanup_(dlclosep) void *dl = NULL;
@@ -58,23 +73,38 @@ int dlopen_cryptsetup(void) {
                         DLSYM_ARG(crypt_deactivate_by_name),
                         DLSYM_ARG(crypt_format),
                         DLSYM_ARG(crypt_free),
+                        DLSYM_ARG(crypt_get_cipher),
+                        DLSYM_ARG(crypt_get_cipher_mode),
+                        DLSYM_ARG(crypt_get_data_offset),
+                        DLSYM_ARG(crypt_get_device_name),
                         DLSYM_ARG(crypt_get_dir),
+                        DLSYM_ARG(crypt_get_type),
+                        DLSYM_ARG(crypt_get_uuid),
                         DLSYM_ARG(crypt_get_verity_info),
+                        DLSYM_ARG(crypt_get_volume_key_size),
                         DLSYM_ARG(crypt_init),
                         DLSYM_ARG(crypt_init_by_name),
                         DLSYM_ARG(crypt_keyslot_add_by_volume_key),
+                        DLSYM_ARG(crypt_keyslot_destroy),
+                        DLSYM_ARG(crypt_keyslot_max),
                         DLSYM_ARG(crypt_load),
                         DLSYM_ARG(crypt_resize),
+                        DLSYM_ARG(crypt_resume_by_passphrase),
                         DLSYM_ARG(crypt_set_data_device),
                         DLSYM_ARG(crypt_set_debug_level),
                         DLSYM_ARG(crypt_set_log_callback),
+#if HAVE_CRYPT_SET_METADATA_SIZE
+                        DLSYM_ARG(crypt_set_metadata_size),
+#endif
                         DLSYM_ARG(crypt_set_pbkdf_type),
+                        DLSYM_ARG(crypt_suspend),
                         DLSYM_ARG(crypt_token_json_get),
                         DLSYM_ARG(crypt_token_json_set),
-                        DLSYM_ARG(crypt_volume_key_get),
 #if HAVE_CRYPT_TOKEN_MAX
                         DLSYM_ARG(crypt_token_max),
 #endif
+                        DLSYM_ARG(crypt_token_status),
+                        DLSYM_ARG(crypt_volume_key_get),
                         NULL);
         if (r < 0)
                 return r;
index 855997f3354c26383fad1b5801b1a813bd52b7ff..1bf9830a7daad2b68e44bcb3ba3e9d46dec5f773 100644 (file)
@@ -23,20 +23,33 @@ extern int (*sym_crypt_activate_by_volume_key)(struct crypt_device *cd, const ch
 extern int (*sym_crypt_deactivate_by_name)(struct crypt_device *cd, const char *name, uint32_t flags);
 extern int (*sym_crypt_format)(struct crypt_device *cd, const char *type, const char *cipher, const char *cipher_mode, const char *uuid, const char *volume_key, size_t volume_key_size, void *params);
 extern void (*sym_crypt_free)(struct crypt_device *cd);
+extern const char *(*sym_crypt_get_cipher)(struct crypt_device *cd);
+extern const char *(*sym_crypt_get_cipher_mode)(struct crypt_device *cd);
+extern uint64_t (*sym_crypt_get_data_offset)(struct crypt_device *cd);
+extern const char *(*sym_crypt_get_device_name)(struct crypt_device *cd);
 extern const char *(*sym_crypt_get_dir)(void);
+extern const char *(*sym_crypt_get_type)(struct crypt_device *cd);
+extern const char *(*sym_crypt_get_uuid)(struct crypt_device *cd);
 extern int (*sym_crypt_get_verity_info)(struct crypt_device *cd, struct crypt_params_verity *vp);
+extern int (*sym_crypt_get_volume_key_size)(struct crypt_device *cd);
 extern int (*sym_crypt_init)(struct crypt_device **cd, const char *device);
 extern int (*sym_crypt_init_by_name)(struct crypt_device **cd, const char *name);
 extern int (*sym_crypt_keyslot_add_by_volume_key)(struct crypt_device *cd, int keyslot, const char *volume_key, size_t volume_key_size, const char *passphrase, size_t passphrase_size);
+extern int (*sym_crypt_keyslot_destroy)(struct crypt_device *cd, int keyslot);
+extern int (*sym_crypt_keyslot_max)(const char *type);
 extern int (*sym_crypt_load)(struct crypt_device *cd, const char *requested_type, void *params);
 extern int (*sym_crypt_resize)(struct crypt_device *cd, const char *name, uint64_t new_size);
+extern int (*sym_crypt_resume_by_passphrase)(struct crypt_device *cd, const char *name, int keyslot, const char *passphrase, size_t passphrase_size);
 extern int (*sym_crypt_set_data_device)(struct crypt_device *cd, const char *device);
 extern void (*sym_crypt_set_debug_level)(int level);
 extern void (*sym_crypt_set_log_callback)(struct crypt_device *cd, void (*log)(int level, const char *msg, void *usrptr), void *usrptr);
+#if HAVE_CRYPT_SET_METADATA_SIZE
+extern int (*sym_crypt_set_metadata_size)(struct crypt_device *cd, uint64_t metadata_size, uint64_t keyslots_size);
+#endif
 extern int (*sym_crypt_set_pbkdf_type)(struct crypt_device *cd, const struct crypt_pbkdf_type *pbkdf);
+extern int (*sym_crypt_suspend)(struct crypt_device *cd, const char *name);
 extern int (*sym_crypt_token_json_get)(struct crypt_device *cd, int token, const char **json);
 extern int (*sym_crypt_token_json_set)(struct crypt_device *cd, int token, const char *json);
-extern int (*sym_crypt_volume_key_get)(struct crypt_device *cd, int keyslot, char *volume_key, size_t *volume_key_size, const char *passphrase, size_t passphrase_size);
 #if HAVE_CRYPT_TOKEN_MAX
 extern int (*sym_crypt_token_max)(const char *type);
 #else
@@ -47,6 +60,8 @@ static inline int sym_crypt_token_max(_unused_ const char *type) {
     return 32;
 }
 #endif
+extern crypt_token_info (*sym_crypt_token_status)(struct crypt_device *cd, int token, const char **type);
+extern int (*sym_crypt_volume_key_get)(struct crypt_device *cd, int keyslot, char *volume_key, size_t *volume_key_size, const char *passphrase, size_t passphrase_size);
 
 int dlopen_cryptsetup(void);