static int reencrypt_teardown_ok(struct crypt_device *cd, struct luks2_hdr *hdr, struct luks2_reencrypt *rh)
{
	int i, r;
	uint32_t dmt_flags;
	bool finished = !(rh->device_size > rh->progress);

	if (rh->rp.type == REENC_PROTECTION_NONE &&
	    LUKS2_hdr_write(cd, hdr)) {
		log_err(cd, _("Failed to write LUKS2 metadata."));
		return -EINVAL;
	}

	if (rh->online) {
		r = LUKS2_reload(cd, rh->device_name, rh->vks, rh->device_size, rh->flags);
		if (r)
			log_err(cd, _("Failed to reload device %s."), rh->device_name);
		if (!r) {
			r = dm_resume_device(cd, rh->device_name, DM_SUSPEND_SKIP_LOCKFS | DM_SUSPEND_NOFLUSH);
			if (r)
				log_err(cd, _("Failed to resume device %s."), rh->device_name);
		}
		dm_remove_device(cd, rh->overlay_name, 0);
		dm_remove_device(cd, rh->hotzone_name, 0);

		if (!r && finished && rh->mode == CRYPT_REENCRYPT_DECRYPT &&
		    !dm_flags(cd, DM_LINEAR, &dmt_flags) && (dmt_flags & DM_DEFERRED_SUPPORTED))
		    dm_remove_device(cd, rh->device_name, CRYPT_DEACTIVATE_DEFERRED);
	}

	if (finished) {
		if (reencrypt_wipe_moved_segment(cd, rh))
			log_err(cd, _("Failed to wipe backup segment data."));
		if (reencrypt_get_data_offset_new(hdr) && LUKS2_set_keyslots_size(cd, hdr, reencrypt_get_data_offset_new(hdr)))
			log_dbg(cd, "Failed to set new keyslots area size.");
		if (rh->digest_old >= 0 && rh->digest_new != rh->digest_old)
			for (i = 0; i < LUKS2_KEYSLOTS_MAX; i++)
				if (LUKS2_digest_by_keyslot(hdr, i) == rh->digest_old)
					crypt_keyslot_destroy(cd, i);
		crypt_keyslot_destroy(cd, rh->reenc_keyslot);
		if (reencrypt_erase_backup_segments(cd, hdr))
			log_dbg(cd, "Failed to erase backup segments");

		/* do we need atomic erase? */
		if (reencrypt_update_flag(cd, 0, true))
			log_err(cd, _("Failed to disable reencryption requirement flag."));
	}

	return 0;
}
static int reencrypt_teardown_ok(struct crypt_device *cd, struct luks2_hdr *hdr, struct luks2_reencrypt *rh)
{
	int i, r;
	uint32_t dmt_flags;
	bool finished = !(rh->device_size > rh->progress);

	if (rh->rp.type == REENC_PROTECTION_NONE &&
	    LUKS2_hdr_write(cd, hdr)) {
		log_err(cd, _("Failed to write LUKS2 metadata."));
		return -EINVAL;
	}

	if (rh->online) {
		r = LUKS2_reload(cd, rh->device_name, rh->vks, rh->device_size, rh->flags);
		if (r)
			log_err(cd, _("Failed to reload device %s."), rh->device_name);
		if (!r) {
			r = dm_resume_device(cd, rh->device_name, DM_SUSPEND_SKIP_LOCKFS | DM_SUSPEND_NOFLUSH);
			if (r)
				log_err(cd, _("Failed to resume device %s."), rh->device_name);
		}
		dm_remove_device(cd, rh->overlay_name, 0);
		dm_remove_device(cd, rh->hotzone_name, 0);

		if (!r && finished && rh->mode == CRYPT_REENCRYPT_DECRYPT &&
		    !dm_flags(cd, DM_LINEAR, &dmt_flags) && (dmt_flags & DM_DEFERRED_SUPPORTED))
		    dm_remove_device(cd, rh->device_name, CRYPT_DEACTIVATE_DEFERRED);
	}

	if (finished) {
		if (reencrypt_wipe_moved_segment(cd, rh))
			log_err(cd, _("Failed to wipe backup segment data."));
		if (reencrypt_get_data_offset_new(hdr) && LUKS2_set_keyslots_size(cd, hdr, reencrypt_get_data_offset_new(hdr)))
			log_dbg(cd, "Failed to set new keyslots area size.");
		if (rh->digest_old >= 0 && rh->digest_new != rh->digest_old)
			for (i = 0; i < LUKS2_KEYSLOTS_MAX; i++)
				if (LUKS2_digest_by_keyslot(hdr, i) == rh->digest_old)
					crypt_keyslot_destroy(cd, i);
		crypt_keyslot_destroy(cd, rh->reenc_keyslot);
		if (reencrypt_erase_backup_segments(cd, hdr))
			log_dbg(cd, "Failed to erase backup segments");

		 
		if (reencrypt_update_flag(cd, 0, true))
			log_err(cd, _("Failed to disable reencryption requirement flag."));
	}

	return 0;
}