char * zuluCryptGetUUIDFromMapper( const char * mapper ) { string_t uuid ; struct crypt_device * cd ; const char * id ; const char * e = " UUID: \t\"Nil\"" ; char * f ; if( crypt_init_by_name( &cd,mapper ) < 0 ){ uuid = String( e ) ; }else{ id = crypt_get_uuid( cd ) ; if( id == NULL ){ /* * Either not a LUKS volume or a LUKS volume but with a detached header. * consult udev to see if it can sort this volume out. */ f = _get_uuid_from_udev( mapper ) ; if( f == NULL ){ uuid = String( e ) ; }else{ uuid = String_1( " UUID: \t\"",f,"\"",NULL ) ; StringFree( f ) ; } }else{ uuid = String_1( " UUID: \t\"",id,"\"",NULL ) ; } crypt_free( cd ) ; } return StringDeleteHandle( &uuid ) ; }
static int backup_luks_headers(struct reenc_ctx *rc) { struct crypt_device *cd = NULL; struct crypt_params_luks1 params = {0}; char cipher [MAX_CIPHER_LEN], cipher_mode[MAX_CIPHER_LEN]; char *old_key = NULL; size_t old_key_size; int r; log_dbg("Creating LUKS header backup for device %s.", rc->device); if ((r = crypt_init(&cd, rc->device)) || (r = crypt_load(cd, CRYPT_LUKS1, NULL))) goto out; crypt_set_confirm_callback(cd, NULL, NULL); if ((r = crypt_header_backup(cd, CRYPT_LUKS1, rc->header_file_org))) goto out; log_verbose(_("LUKS header backup of device %s created.\n"), rc->device); /* For decrypt, new header will be fake one, so we are done here. */ if (rc->reencrypt_mode == DECRYPT) goto out; if ((r = create_empty_header(rc->header_file_new, rc->header_file_org, crypt_get_data_offset(cd)))) goto out; params.hash = opt_hash ?: DEFAULT_LUKS1_HASH; params.data_alignment = crypt_get_data_offset(cd); params.data_alignment += ROUND_SECTOR(opt_reduce_size); params.data_device = rc->device; if (opt_cipher) { r = crypt_parse_name_and_mode(opt_cipher, cipher, NULL, cipher_mode); if (r < 0) { log_err(_("No known cipher specification pattern detected.\n")); goto out; } } if (opt_keep_key) { log_dbg("Keeping key from old header."); old_key_size = crypt_get_volume_key_size(cd); old_key = crypt_safe_alloc(old_key_size); if (!old_key) { r = -ENOMEM; goto out; } r = crypt_volume_key_get(cd, CRYPT_ANY_SLOT, old_key, &old_key_size, rc->p[rc->keyslot].password, rc->p[rc->keyslot].passwordLen); if (r < 0) goto out; } r = create_new_header(rc, opt_cipher ? cipher : crypt_get_cipher(cd), opt_cipher ? cipher_mode : crypt_get_cipher_mode(cd), crypt_get_uuid(cd), old_key, opt_key_size ? opt_key_size / 8 : crypt_get_volume_key_size(cd), ¶ms); out: crypt_free(cd); crypt_safe_free(old_key); if (r) log_err(_("Creation of LUKS backup headers failed.\n")); return r; }
static int activate_and_check_status(const char *path, const char *device_name) { struct crypt_device *cd; struct crypt_active_device cad; int r; /* * LUKS device activation example. * It's sequence of sub-steps: device initialization, LUKS header load * and the device activation itself. */ r = crypt_init(&cd, path); if (r < 0 ) { printf("crypt_init() failed for %s.\n", path); return r; } /* * crypt_load() is used to load the LUKS header from block device * into crypt_device context. */ r = crypt_load(cd, /* crypt context */ CRYPT_LUKS1, /* requested type */ NULL); /* additional parameters (not used) */ if (r < 0) { printf("crypt_load() failed on device %s.\n", crypt_get_device_name(cd)); crypt_free(cd); return r; } /* * Device activation creates device-mapper devie mapping with name device_name. */ r = crypt_activate_by_passphrase(cd, /* crypt context */ device_name, /* device name to activate */ CRYPT_ANY_SLOT,/* which slot use (ANY - try all) */ "foo", 3, /* passphrase */ CRYPT_ACTIVATE_READONLY); /* flags */ if (r < 0) { printf("Device %s activation failed.\n", device_name); crypt_free(cd); return r; } printf("LUKS device %s/%s is active.\n", crypt_get_dir(), device_name); printf("\tcipher used: %s\n", crypt_get_cipher(cd)); printf("\tcipher mode: %s\n", crypt_get_cipher_mode(cd)); printf("\tdevice UUID: %s\n", crypt_get_uuid(cd)); /* * Get info about active device (query DM backend) */ r = crypt_get_active_device(cd, device_name, &cad); if (r < 0) { printf("Get info about active device %s failed.\n", device_name); crypt_deactivate(cd, device_name); crypt_free(cd); return r; } printf("Active device parameters for %s:\n" "\tDevice offset (in sectors): %" PRIu64 "\n" "\tIV offset (in sectors) : %" PRIu64 "\n" "\tdevice size (in sectors) : %" PRIu64 "\n" "\tread-only flag : %s\n", device_name, cad.offset, cad.iv_offset, cad.size, cad.flags & CRYPT_ACTIVATE_READONLY ? "1" : "0"); crypt_free(cd); return 0; }
/* Activate verity device in kernel device-mapper */ int VERITY_activate(struct crypt_device *cd, const char *name, const char *root_hash, size_t root_hash_size, struct crypt_params_verity *verity_hdr, uint32_t activation_flags) { struct crypt_dm_active_device dmd; int r; log_dbg("Trying to activate VERITY device %s using hash %s.", name ?: "[none]", verity_hdr->hash_name); if (verity_hdr->flags & CRYPT_VERITY_CHECK_HASH) { log_dbg("Verification of data in userspace required."); r = VERITY_verify(cd, verity_hdr, root_hash, root_hash_size); if (r < 0) return r; } if (!name) return 0; dmd.target = DM_VERITY; dmd.data_device = crypt_data_device(cd); dmd.u.verity.hash_device = crypt_metadata_device(cd); dmd.u.verity.root_hash = root_hash; dmd.u.verity.root_hash_size = root_hash_size; dmd.u.verity.hash_offset = VERITY_hash_offset_block(verity_hdr), dmd.flags = activation_flags; dmd.size = verity_hdr->data_size * verity_hdr->data_block_size / 512; dmd.uuid = crypt_get_uuid(cd); dmd.u.verity.vp = verity_hdr; r = device_block_adjust(cd, dmd.u.verity.hash_device, DEV_OK, 0, NULL, NULL); if (r) return r; r = device_block_adjust(cd, dmd.data_device, DEV_EXCL, 0, &dmd.size, &dmd.flags); if (r) return r; r = dm_create_device(cd, name, CRYPT_VERITY, &dmd, 0); if (r < 0 && !(dm_flags() & DM_VERITY_SUPPORTED)) { log_err(cd, _("Kernel doesn't support dm-verity mapping.\n")); return -ENOTSUP; } if (r < 0) return r; r = dm_status_verity_ok(cd, name); if (r < 0) return r; if (!r) log_err(cd, _("Verity device detected corruption after activation.\n")); return 0; }