Compare commits

...

196 Commits

Author SHA1 Message Date
Milan Broz
b08212ea45 Version 2.6.0. 2022-11-28 12:27:33 +01:00
Milan Broz
5a976ad1d9 Do not log score from pwquality.
This information is really not needed in debug log.
2022-11-28 10:37:58 +01:00
Yuri Kozlov
0e4182874b po: update ru.po (from translationproject.org) 2022-11-27 23:20:25 +01:00
Milan Broz
487e85fdec Wipe buffers to be sure padding is always empty.
Detected by valgrind as writing unitialized data.
2022-11-27 23:18:36 +01:00
Milan Broz
32344d5a84 tests: fix reencryption-mangle test valgrind log name.
Use the same logic as in compat-test (just the line
number is the last one for cryptsetup_raw).
2022-11-27 21:02:49 +01:00
Milan Broz
ebb16a511c tests: fix list of valgrind tests
FVAULT2 test was missing; systemd test does not support valgrid yet.
2022-11-27 19:48:57 +01:00
Milan Broz
51200eb6da tests: do not require build tools for localtest in systemd plugin test
Fo localtest we use installed binaries, only checkprograms need to be build.
2022-11-24 16:37:38 +01:00
Milan Broz
119c57e00e tests: remove stray backslash in grep expression 2022-11-24 15:01:47 +01:00
Milan Broz
700b0f6e36 tests: do not run systemd plugin test without fake tpm path
We want to avoid touching real TPM during test.
2022-11-24 15:00:19 +01:00
Milan Broz
8fff498062 tests: compile fake_tpm_path util also for localtest
Otherwise TPM_PATH will not be used.
2022-11-24 14:54:18 +01:00
Milan Broz
2ef2f6017d Update release notes. 2022-11-24 13:49:27 +01:00
Ondrej Kozina
cdfa213ad0 Allocate internal buffer in LUKS2 keyring token with crypt_safe_alloc.
With changes in db65a5ceac and subsequent
drop of library memlock_all we should lock keyring key material buffer
in memory system memory as well.
2022-11-24 09:03:29 +00:00
Milan Broz
dab00bfd4f CI: use libsepol-dev for Debian based distros.
Seems libselpol1-dev is disappearing.
2022-11-23 11:57:59 +00:00
Ondrej Kozina
c018558f2d Remove unused define CRYPT_KC_TYPE_UNDEFINED.
The defined was not yet released in stable version.
2022-11-23 11:08:55 +01:00
Milan Broz
3633b81909 CI: fix GutHub action install script 2022-11-22 16:38:10 +01:00
Yuri Chornoivan
b23a02b05c po: update uk.po (from translationproject.org) 2022-11-22 16:17:48 +01:00
Jakub Bogusz
347c39ca97 po: update pl.po (from translationproject.org) 2022-11-22 16:17:48 +01:00
Hiroshi Takekawa
2d1f1833e8 po: update ja.po (from translationproject.org) 2022-11-22 16:17:48 +01:00
Frédéric Marchal
7f09ab67e2 po: update fr.po (from translationproject.org) 2022-11-22 16:17:48 +01:00
Roland Illig
f5fb1f1b94 po: update de.po (from translationproject.org) 2022-11-22 16:17:48 +01:00
Petr Pisar
005141554f po: update cs.po (from translationproject.org) 2022-11-22 16:17:48 +01:00
Ondrej Kozina
cd8f80b7ee Clarify type requirements in crypt_volume_key_get_by_keyslot_context. 2022-11-21 15:56:14 +01:00
Milan Broz
c7bbae01a6 Fix some strings for translations.
No need to translate debug strings.
Fix spaces in key slot queries.
2022-11-20 12:36:26 +01:00
Milan Broz
257bc80ae9 Version 2.6.0-rc0. 2022-11-18 22:32:47 +01:00
Milan Broz
6c2e64bf75 fvault2: fix typo 2022-11-18 22:25:31 +01:00
Milan Broz
942cea1803 Update pot file. 2022-11-18 22:22:06 +01:00
Milan Broz
e7eab5fec2 Prepare version 2.6.0-rc0. 2022-11-18 22:02:44 +01:00
Ondrej Kozina
b0779c6529 Fix --disable-luks2-reencryption configuration option. 2022-11-18 16:40:48 +01:00
Milan Broz
37d045df00 fvault2: add basic info to cryptsetup man page 2022-11-18 15:27:00 +01:00
Milan Broz
4b95f36804 Fix possible undefined use od preprocessor.
Mixing preprocessor #if and code is undefined behavior in general,
rewrite tools_package_version to not use it.
2022-11-18 14:50:34 +01:00
Milan Broz
faf3b27f51 fvault2: reduce debug log, do not print ignored metadata blocks 2022-11-18 14:31:25 +01:00
Josef Andersson
c85d1351ea po: update sv.po (from translationproject.org) 2022-11-18 14:25:40 +01:00
Мирослав Николић
3b18fe2b23 po: update sr.po (from translationproject.org) 2022-11-18 14:25:40 +01:00
Milan Broz
e96588b8b5 Check and allocate header early so wipe fails only for IO errors.
The device_check is done in header write functions,
but these are not recached in normal format path as wipe call
is called earlier.

Call the device check also from wipe function to get better error
description.

This situation happens for example when a block device is too small
(regular file can be enlarged by falloc(); block device cannot).
2022-11-18 13:03:52 +00:00
Milan Broz
c31494abc6 Print warning early if LUKS container is too small for activation.
Activation with header only fails too late (in device-mapper
call) while it is clear from the beginning that it cannot succeed.

Just add an early and better worded error.

Ignore this situation for block device (we have to call ioctl to get size).
The most common case is a file container here anyway.

For block devices it fails during activation later.
2022-11-18 13:03:52 +00:00
Milan Broz
819902a33a Add a better warning if luksFormat ends with image without any space for data.
Header write can call falloc() to increase image size, so we should
check data offset after header is written.

Also change wording to be less cryptic and describe what is the real problem.

Note that the code can be used this way to crate detached header (without
space for data), so it is not an error.
2022-11-18 13:03:52 +00:00
Daniel Zatovic
395beb635c Speed up tests using faster hash and PBKDF options.
Use faster SHA1 instead of SHA256 in reencryption test and pass fast
PBKDF options in mode-test.
2022-11-18 11:08:31 +00:00
Ondrej Kozina
81c56a8395 Move assert include in internal header files. 2022-11-16 16:54:33 +01:00
Milan Broz
3333f3e9bb Fix some warning detected by Coverity.
The FVAULT2 block is always 8192 bytes (for CRC), but used
struct is smaller. Let's not confuse struct size with whole block.
2022-11-15 10:47:22 +01:00
Milan Broz
b086430877 fvault2: Move messages to debug level and add more debug log. 2022-11-14 21:50:18 +01:00
Milan Broz
01f3f3e66c fvault2: volume size can be unsigned 64bit 2022-11-14 21:50:18 +01:00
Milan Broz
e37d8bdf91 fvault2: harden device offset check
Check if value overflows and do not allow reading
metadata block exceeding fixed offset.
2022-11-14 21:50:18 +01:00
Milan Broz
8b4a5e5931 fvault2: some more code cleanup. 2022-11-14 21:50:18 +01:00
Milan Broz
33d8d19408 fvault2: passphr -> passphrase 2022-11-14 21:50:18 +01:00
Milan Broz
9bb98d49c0 fvault2: some minor code reformatting changes. 2022-11-14 21:50:18 +01:00
Pavel Tobias
1c5fd5ae10 Fvault2: add basic error logs 2022-11-14 21:50:18 +01:00
Milan Broz
3d1b965c46 fvault2: fix --test-passphrase option 2022-11-14 21:50:18 +01:00
Milan Broz
2770273582 fvault2: test volume key dump 2022-11-14 21:50:18 +01:00
Milan Broz
f6b6e41951 fvault2: Add a basic man page. 2022-11-14 21:50:18 +01:00
Milan Broz
03059fae75 tests: add valgrind support to fvault2 test. 2022-11-14 21:50:18 +01:00
Pavel Tobias
ba9757b14b Fvault2: add basic test 2022-11-14 21:50:18 +01:00
Pavel Tobias
cd5bd1c773 Fvault2: store UUIDs in text format 2022-11-14 21:50:18 +01:00
Vojtech Trefny
a5c7bba6ee Add missing support for fvault2 commands 2022-11-14 21:50:18 +01:00
Vojtech Trefny
4bce6d5962 Show error when trying to run fvault2Dump on a non-fvault device 2022-11-14 21:50:18 +01:00
Pavel Tobias
cb9deaf354 Fvault2: implement open 2022-11-14 21:50:18 +01:00
Pavel Tobias
0ce5de9c1c Fvault2: implement dump 2022-11-14 21:50:18 +01:00
Pavel Tobias
35071c6d50 Fvault2: derive volume key 2022-11-14 21:50:18 +01:00
Pavel Tobias
af6ea01997 Fvault2: read all relevant metadata from device 2022-11-14 21:50:18 +01:00
Pavel Tobias
1d5d6d73a5 Add support for CRC-32C (Castagnoli polynomial) to lib/crypto_backend 2022-11-14 21:50:18 +01:00
Pavel Tobias
1ffc9d967c Fvault2: prepare module in libcryptsetup 2022-11-14 21:50:18 +01:00
Milan Broz
1f4c7a83f9 Annotate some functions to prevent Coverity tainted input error.
These errors are really annoying, just silence them.
2022-11-14 13:05:04 +00:00
Milan Broz
f312ba6256 Fix json_object_copy return value check.
Reported by Coverity scan.
2022-11-14 13:05:04 +00:00
Milan Broz
5186f49613 tests: fix compilation warnings with C18
Fix the function prototype and define GNU source definition to get strdup().
2022-11-13 19:40:50 +01:00
Milan Broz
616d3cd493 tests: do not require whirlpool hash for LUKS1 test
Just remove unsupported images before test and continue.
2022-11-13 19:40:48 +01:00
Milan Broz
cd2e22cb87 tests: rename systemd plugin test
So the logic works the same as ssh-test-plugin.
2022-11-13 19:40:45 +01:00
Milan Broz
54073ef65f tests: do not run api tests twice in valgrind run.
These are run already just few lines above :)
2022-11-13 19:40:31 +01:00
Milan Broz
3e7c1e46fd tests: add source file dependence for fake tokens 2022-11-08 14:19:19 +01:00
Milan Broz
ea05e4307e tests: check that *.so token helpers are compiled. 2022-11-08 14:19:15 +01:00
Milan Broz
f35b9cc99b tests: do not use global CFLAGS for fake token helper.
Dynamic librarties cannot be linked with sanitizers this way,
just ignore CFLAGS here.
2022-11-08 14:19:11 +01:00
Milan Broz
d4888fba86 tests: compile fake_systemd_tpm_path.so through Makefile
Also fix Makefile to include source in make dist.

Note: we must not use CFLAGS there because possible sanitizers
use will make the loaded library unusable in LD_PRELOAD.
2022-11-08 14:19:04 +01:00
Milan Broz
f9e778a2cd luks2: fix warning undefined shift
Explicitly set uint32_t for shift, found by clang undefined
sanitizer.
Undefine shift cannot happen in reality, though.
2022-11-07 17:30:14 +00:00
Milan Broz
69025faa24 tests: Remove stray \" in grep expression. 2022-11-07 17:30:14 +00:00
Milan Broz
871000fa05 Fix a memory leak in crypt_keyslot_add_by_key.
Found by clang address sanitizer.

Also rename the variable - i's no longer a bare pointer,
the vk also owns the memory [okozina].
2022-11-07 17:30:14 +00:00
Milan Broz
cb53c643c2 CI: fix Debian build as pkfconf and pkg-config cannot co-exit.
Install pkgconf that is more recent and provides pkg-config too.
2022-11-04 20:28:08 +01:00
daniel.zatovic
f771f9a694 CI: install dependencies when running systemd test
Also update Debian to version 11.
2022-11-04 11:00:31 +01:00
daniel.zatovic
9009a2de26 CI: disable systemd tests on unsupported distributions 2022-11-04 11:00:31 +01:00
daniel.zatovic
6a279e21c9 Link compiled systemd to local libcryptsetup. 2022-11-04 11:00:31 +01:00
Christoph Anton Mitterer
124367f365 Add howto for converting printed to raw volume key
Signed-off-by: Christoph Anton Mitterer <mail@christoph.anton.mitterer.name>
2022-11-03 18:40:20 +00:00
Ondrej Kozina
55c39d7d16 Port crypt_volume_key_get internals to keyslot context variant. 2022-11-03 15:56:37 +01:00
Ondrej Kozina
f7e2ed956b Add crypt_volume_key_get_by_keyslot_context.
Extends avaiable methods for retrieving device volume key.
The volume key now may be extracted using passphrase, keyfile
(passphrase in a file) or token (LUKS2 only).

For LUKS devices, it returns generated volume key after
sucessfull crypt_format where new volume key got generated.

Fixes: #777.
2022-11-03 15:56:37 +01:00
Ondrej Kozina
0e6264c53c Do not cache volume key in keyslot context.
First, there was a bug where passphrase based
keyslot contextets did not cache volume keys
properly and caused leaks.

Second, it causes problems when keyslot context
is used twice with different keyslot id, e.g.:
CRYPT_ANY_SLOT vs specific id, unbound key vs
volume key, etc.
2022-11-02 12:22:25 +01:00
Ondrej Kozina
01c16111d7 Fix copy/paste mistakes in API docs. 2022-11-02 09:49:49 +01:00
daniel.zatovic
49ab658c9c CI: build and run fuzzers only conditionally 2022-10-31 20:47:23 +00:00
Milan Broz
888c6321df Do not compile systemd if running as systemd test as non-root. 2022-10-27 14:47:30 +02:00
Milan Broz
20f8c09195 Fix make dist to include systemd plugin test. 2022-10-27 14:38:23 +02:00
daniel.zatovic
57d4c677bd CI: add systemd-tpm2 token integration test. 2022-10-26 15:19:25 +02:00
Milan Broz
cde7b90735 fuzzing: Build OpenSSL with no-shared options
The -static option always disables threads, we want to use no-shared
build option instead.
2022-10-22 10:10:34 +00:00
Ondrej Kozina
3e4c69a017 Fix internal crypt segment compare routine.
The function is supposed to check if manipulated
active dm-crypt device matches the on-disk metadata.
Unfortunately it did not take into account differences
between normal cipher specification (aes-xts-plain64)
and capi format specification (capi:xts(aes)-plain64).
The internal query function always converted capi format
in normal format and therefor failed if capi format was
used in metadata.

Fixes: #759.
2022-10-20 14:24:11 +02:00
Ondrej Kozina
19c15a652f Copy also integrity string in legacy mode.
So that it handles integrity string same as it does
with cipher string.
2022-10-20 14:24:11 +02:00
Ondrej Kozina
2390395150 Code cleanup.
Type cast is not needed here.
2022-10-20 14:24:11 +02:00
Ondrej Kozina
9a9ddc7d22 Move cipher_dm2c to crypto utilities.
(Gets renamed to crypt_capi_to_cipher)
2022-10-20 14:24:02 +02:00
Ondrej Kozina
3616da631f Fix cipher convert routines naming confusion.
The function names were in fact swaped.
2022-10-20 14:23:48 +02:00
daniel.zatovic
b380fa7494 CI: Add fuzzer jobs. 2022-10-19 10:07:03 +02:00
Milan Broz
23f49eca43 Silent new keyslot option warning in tests.
After we introduced --new-key-slot option, just use it and
avoid CLI warning.
2022-10-18 15:51:11 +02:00
Milan Broz
00baa92756 fuzzing: Yet another dependency fix.
Previous fix breaks make dist. Let's set dependency
on object file explicitly.
2022-10-14 15:02:03 +02:00
daniel.zatovic
8bbb018a01 CI: Add Ubuntu 18.04 32bit job. 2022-10-14 09:27:27 +00:00
Milan Broz
c464d61995 fuzzing: Fix dependence issue
This patch avoids a race when running parallel jobs.
2022-10-14 06:48:32 +00:00
Milan Broz
d260ca6680 Fix api-test with older kernel. 2022-10-13 16:08:08 +02:00
Milan Broz
d05a2a6c99 fuzzing: Force dependence for generated header. 2022-10-10 12:32:10 +02:00
Milan Broz
758a2974f5 fuzzing: Clean up includes. 2022-10-09 12:59:57 +02:00
Milan Broz
4b5e814094 fuzzing: Remove unused code.
Also use C comments style in C-only file.
2022-10-09 12:36:52 +02:00
Milan Broz
98f5e0538a fuzzing: use ftruncate() instead of seeking to end of the file 2022-10-09 12:36:24 +02:00
Milan Broz
f03180d06a fuzzing: Simplify converters and used common defines for exit code. 2022-10-09 12:36:09 +02:00
Milan Broz
39b94ae530 fuzzing: Simplify plain JSON fuzzer. 2022-10-09 12:35:58 +02:00
Milan Broz
3690d5f532 fuzzing: Simplify proto fuzzer. 2022-10-09 12:35:20 +02:00
Milan Broz
e595940637 fuzzing: LLVMFuzzerTestOneInput must always return 0.
Also simplify the fuzzer function.
2022-10-09 12:34:26 +02:00
Milan Broz
dab939c3c9 fuzzing: Fix possible overflow in crypt2_load_fuzz.
Fixes OSS-Fuzz 52201.
2022-10-08 20:13:24 +02:00
daniel.zatovic
cc276527c7 fuzzing: Disable assembly in openssl build
Sanitizers can not instrument openssl's assembly and wrongly report
buffers from openssl as uninitialized.
2022-10-06 23:23:06 +02:00
Milan Broz
27429daf5d Fix typo. 2022-10-05 09:49:55 +02:00
Milan Broz
b20821a520 Fuzzing: disable po4a in static library dependence build as it seems to freeze. 2022-10-04 23:42:07 +02:00
Milan Broz
46b465ff2e Use upstream git for protobuf-mutator as required patches are merged now. 2022-10-04 13:10:36 +02:00
Milan Broz
d8fd9caa6a Add missing files to Makefile.am (and reformat lists). 2022-10-04 13:00:38 +02:00
daniel.zatovic
dad11f97ce Copy only selected fuzzers to out directory. 2022-10-04 13:00:33 +02:00
daniel.zatovic
c06e853938 Fix missing prototypes by adding a header file. 2022-10-04 13:00:29 +02:00
daniel.zatovic
c35e4479d5 Update fuzzing README 2022-10-04 13:00:25 +02:00
daniel.zatovic
8585fb29eb Add dictionary for the plain JSON fuzzer. 2022-10-04 13:00:21 +02:00
daniel.zatovic
97b3926655 Fix potential integer underflow. 2022-10-04 13:00:18 +02:00
Milan Broz
a3f248df9b Fix some clang++ warnings. 2022-10-04 13:00:15 +02:00
Milan Broz
e1a84607cc Rework build of fuzzers.
- Do not require any libraries installed, download everything
from upstream git, statically compile (use include, libs and pkg-config
from local directory under tests/fuzz).
Script should work both from OSS-Fuzz and locally.

- Do not require local protobuf (only staticallly compiled, see above).

- Add README.md (TBD, still not finished).

- Fix make dist and distcheck.

- Remove common.[ch] as we can use internal function.
  This makes fuzzers also C++ only (remove CFLAGS from Makefile).
2022-10-04 13:00:10 +02:00
daniel.zatovic
2f4267ba81 Add plain JSON metadata fuzzing 2022-10-04 12:59:07 +02:00
daniel.zatovic
99e8ee6b7e Add checks for compiler when building fuzz targets. 2022-10-04 12:59:04 +02:00
daniel.zatovic
f58aff21a9 Add fuzz targets, custom mutator and fuzzing dictionary 2022-10-04 12:58:59 +02:00
Milan Broz
de8a27ae02 Print a visible error in LUKS2 if AF hash is not available.
In LUKS1 there is only one hash algorithm specification,
it cannot happen, that AF hash algorithm is not
available, as it is used immediately before in PBKDF2.

In LUKS2 this can be completely different algorithm, so
it make sense to print a visible warning for user.

For example, Whirlpool and RIPEMD160 is now in OpenSSL legacy
provider which can be unavailable, see #773.)

This patch adds a message only, the code already fails with -EINVAL.
2022-10-03 10:33:32 +02:00
Milan Broz
b9b08eba7c Fix function prototype (and build for 32bit system). 2022-10-03 09:57:40 +02:00
Milan Broz
82b56300cd Wrap some very long lines. 2022-10-01 22:35:57 +02:00
Milan Broz
9f8fe3da16 Fix some typos. 2022-10-01 22:35:52 +02:00
Ondrej Kozina
50803ebacb Switch existing keslot adding API to new extension. 2022-09-29 17:31:29 +02:00
Ondrej Kozina
5fce0c2ad1 Extend luksAddKey action options via crypt_keyslot_add_by_keyslot_context API.
In practice luksAddKey action does two operations. It unlocks existing
device volume key and stores unlocked volume key in a new keyslot.
Previously the options were limited to key files and passphrases.
With this patch user may combine freely following options:

To unlock keyslot with volume key user may:
- provide existing passphrase via interactive prompt (default method)
- use --key-file option to provide file with a valid passphrase to existing keyslot
- provide volume key directly via --volume-key-file
- unlock keyslot via all available LUKS2 tokens by --token-only
- unlock keyslot via specific token with --token-id
- unlock keyslot via specific token type by --token-type

To provide the passphrase for a new keyslot user may:
- provide existing passphrase via interactive prompt (default method)
- use --new-keyfile parameter or positional parameter to read the
  passphrase from file.
- use --new-token-id to select specific LUKS2 token to get passphrase
  for new keyslot. New keyslot is assigned to selected token id if
  operation is succesfull.

Fixes: #725.
2022-09-29 17:31:29 +02:00
Ondrej Kozina
2e29eb7906 cryptsetup-luksAddKey man page cleanup. 2022-09-22 17:45:20 +02:00
Ondrej Kozina
b867f0b578 Add new API for adding new LUKS keyslots.
The crypt_keyslot_add_by_keyslot_context & associated
helper functions allow more options when adding new
keyslot. For example there was no simple way of
adding new LUKS2 keyslot when the only active keyslot
could be unlocked by passphrase (KEK) provided by LUKS2 token
(plugin). Now all available options for unlocking keyslots
may also be used when creating new keyslot and it combine
as called needs.

The available methods (keyslot contexts) are:
passphrase, keyfile, key (binary representation) and LUSK2 token.
2022-09-21 17:36:28 +02:00
Milan Broz
1745fd5aea Fix missing va_end macro in test error path. 2022-09-19 12:46:42 +00:00
Ondrej Kozina
90ad841a45 Add cryptsetup token unassign action.
Allows removing token binding on specific keyslot.
2022-09-16 14:34:28 +02:00
Ondrej Kozina
0397cac878 Abort assigning tokens with invalid parameters earlier. 2022-09-16 13:30:39 +02:00
Ondrej Kozina
033ff34109 Enable adding unassigned luks2-keyring token in cryptsetup.
There was no easy way to add unassigned luks2-keyring token.
Reuse --unbound parameter for it.
2022-09-16 12:34:32 +02:00
Ondrej Kozina
0d61e4c20f Clarify --unbound usage in man pages. 2022-09-16 12:32:24 +02:00
Milan Broz
b4863897fe Fix verity-compat-test if running with different locale. 2022-09-06 21:55:37 +02:00
Ondrej Kozina
eac02f5605 Fix NULL key_description bug in luks2-keyring token.
json-c parser transforms NULL pointer into special '(null)' string.
While being technically correct it hides the fact user passed NULL
pointer in crypt_token_params_luks2_keyring structure. This bug
could be trigerred by calling crypt_token_luks2_keyring_set().
2022-09-01 15:38:49 +02:00
daniel.zatovic
94e8a7ca96 Fix valgrind in SSH token test. 2022-08-25 08:02:37 +00:00
Milan Broz
b183bb25e2 Add support for dm-verity try_verify_in_tasklet option.
Available since kernel 6.0.
2022-08-25 08:01:07 +00:00
Ondrej Kozina
09ac5321f4 Fix memory leak in ssh token example. 2022-08-23 15:53:25 +02:00
Milan Broz
c1302555b7 Provide pkgconfig Require.private.
While we do not completely provides static build on udev
systems, having theses modules in pkgconfig can be useful otherwise.
2022-08-23 12:06:07 +00:00
Ondrej Kozina
01c032df04 Do not reload LUKS2 metadata when not necessary.
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.
2022-08-19 14:46:42 +02:00
Milan Broz
88d9524e6c Mark crypt_memory_lock() API call deprecated.
And remove its implementation.
2022-08-16 19:56:32 +02:00
Milan Broz
4b47091b85 Remove call to explicit memlockall from cryptsetup.
Memory with keys is now locked per range.
2022-08-16 19:56:28 +02:00
Milan Broz
b9bf657449 Set process priority only for PBKDF benchmark.
Do not increase priority for the whole run, only
increase it when we calculate PBKDF paramaters.
2022-08-16 19:56:24 +02:00
Milan Broz
21d87a246e Do not use safe_malloc for LUKS header backup.
The content of LUKS header is not a key material, no need
to lock memory for possibly big header and big memory area locks.

Just ensure we wipe buffer before release of memory.
2022-08-16 19:56:20 +02:00
Milan Broz
db65a5ceac Lock memory in crypt_safe alloc functions.
This patch locks all memory ranges in safe allocations.

While crypto backend can have some secure memory calls,
it is usually limited by intitial config.

For our use is enough to keep keys in memory and prevent
swapping it out.

If the lock fails (because of limits) we quietly
stay with plain malloc.
2022-08-16 19:56:00 +02:00
daniel.zatovic
132027bafa Force probe in tests instead of lsblk which can use udev cache. 2022-08-11 21:26:03 +02:00
daniel.zatovic
f6fd73aea5 Add FIPS checks before running tests in FIPS mode. 2022-08-10 11:37:25 +00:00
Ondrej Kozina
5b001b7962 Delegate FIPS mode detection to configured crypto backend.
System FIPS mode check is no longer dependent on /etc/system-fips
file. The change should be compatible with older distributions since
we now depend on crypto backend internal routine.

This commit affects only FIPS enabled systems (with FIPS enabled
builds). In case this causes any regression in current distributions
feel free to drop the patch.

For reference see https://bugzilla.redhat.com/show_bug.cgi?id=2080516
2022-08-10 10:53:39 +02:00
daniel.zatovic
429afe8fc3 Add valgrind support to more tests. 2022-08-10 07:45:13 +00:00
Milan Broz
abfb5e374f Remove leftover debug option in test. 2022-08-09 22:54:43 +02:00
daniel.zatovic
f8c79f9a95 Fix valgrind summary leak detection.
Currently, only 1-9 leaks are detected. More than 10 leaks are evaluated
as no leak.
2022-08-05 16:38:38 +02:00
Milan Broz
190e4fc033 Always update automake library files if autogen.sh is run.
Fixes: #761
2022-08-01 08:47:34 +00:00
Ondrej Kozina
093adfc5f9 Fix user defined moved segment size in LUKS2 decryption.
--hotzone-size argument was ignored in cases where actual data size
was less than original LUKS2 data offset.
2022-08-01 07:05:06 +00:00
Milan Broz
a009614191 Set devel version. 2022-07-30 09:29:00 +02:00
Milan Broz
75111d382b Version 2.5.0. 2022-07-28 17:32:33 +02:00
Yuri Kozlov
1cc6c82f21 po: update ru.po (from translationproject.org) 2022-07-28 17:32:04 +02:00
Frédéric Marchal
2c555bd4a0 po: update fr.po (from translationproject.org) 2022-07-28 17:32:04 +02:00
Roland Illig
3f3f5a6aab po: update de.po (from translationproject.org) 2022-07-28 17:32:04 +02:00
Ondrej Kozina
c6ed1becd7 Fix bogus conditions in tests.
Do not test for dm-crypt versions not supported
by upstream kernels.
2022-07-28 17:18:57 +02:00
Milan Broz
766ac108ec Fix option descriptions and lists mentioned in man pages. 2022-07-28 10:51:22 +00:00
Milan Broz
94e5d227ce Fix warning messages if some kernel option is not supported.
Thus was broken by commit
  "Check if DM create device failed in an early phase."
  10b1d6493e

Also we should set EINVAL if we detect unsuported option.
2022-07-28 10:50:55 +00:00
Ondrej Kozina
f96e19147c Add prompt for LUKS2 decryption with header export. 2022-07-28 12:50:13 +02:00
Ondrej Kozina
05dbf04d82 Add early warning for reencryption of image files. 2022-07-28 12:47:10 +02:00
Ondrej Kozina
b9b7c3a9bd Add detached header warning in reencrypt man page. 2022-07-28 10:41:20 +00:00
Ondrej Kozina
17e6d2053a Add mangle tests for LUKS2 decryption with datashift. 2022-07-28 07:57:36 +00:00
Ondrej Kozina
912109ae66 Improve reencryption parameters verification in cli.
Try to catch as many invalid parameters as possible
before entering library call.
2022-07-28 07:57:36 +00:00
Ondrej Kozina
25b877a403 Fix bug in reencryption parameters verification. 2022-07-28 07:57:36 +00:00
Milan Broz
8270b72bfc Use bool instead od int in LUKS1 reencryption context. 2022-07-27 12:01:11 +02:00
Milan Broz
9c0cdcc2f9 Do not use huge LUKS1 reencryption context on heap.
This will reduce cryptsetup tool size (~20kB at least).
2022-07-27 11:57:05 +02:00
Milan Broz
1e2cb2d419 Avoid using huge dummy context in LUKS1 reencryption check.
This struct is not needed at all, just use NULL.
2022-07-27 11:47:06 +02:00
Guilhem Moulin
3e178caeaf Document more supported options in cryptsetup-luksResume(8).
`cryptsetup luksResume --disable-external-tokens --keyfile-offset 123`
does work but these options weren't documented.
2022-07-21 02:29:05 +02:00
Guilhem Moulin
803957cd3e Add support for --key-slot in luksResume action. 2022-07-20 20:00:09 +02:00
Milan Broz
bf4bfeac8a Rename some tests to simplify localtest parsing. 2022-07-18 15:09:28 +02:00
Milan Broz
090dca635a Add ssh-test-plugin to localtest if RUN_SSH_PLUGIN_TEST is set. 2022-07-18 11:16:23 +02:00
Milan Broz
0369ffdcc1 Rename ssh plugin test to ssh-test-plugin.
So we can filter it out in local tests
(*-test means generic tests, *-test-plugin specific plugin tests).
2022-07-18 09:11:23 +02:00
Milan Broz
648a85ed3a Unify use of tabulators in tests. 2022-07-16 19:14:31 +00:00
Milan Broz
8f3884e0d7 Change default target for Makefile.localtest. 2022-07-16 19:14:31 +00:00
Guilhem Moulin
289d5e5891 Add unit-utils-crypt-test to Makefile.localtest's list of tests.
This requires (re-)building the executable with -DNO_CRYPTSETUP_PATH.
Only in that case do we allow the test to run under non-empty
$CRYPTSETUP_PATH.
2022-07-16 19:14:31 +00:00
Guilhem Moulin
b37d04975d Add compat-test-args to Makefile.localtest's list of tests. 2022-07-16 19:14:31 +00:00
Guilhem Moulin
6578dac2f9 Add blockwise-compat to Makefile.localtest's list of tests.
This requires (re-)building `unit-utils-io` with -DNO_CRYPTSETUP_PATH.
Only in that case do we allow the test to run under non-empty
$CRYPTSETUP_PATH.
2022-07-16 19:14:31 +00:00
Guilhem Moulin
dc5f284e42 blockwise-compat: Wait a bit so scsi_debug has a chance to fully initialize.
Similar to a76c96d361.  See also !386.
2022-07-16 19:14:31 +00:00
Guilhem Moulin
32149e4ee7 blockwise-compat: Make skip() exit with status 77.
This is mostly useful under TESTSUITE_NOSKIP=y.
2022-07-16 19:14:31 +00:00
Guilhem Moulin
0e4857ee81 unit-wipe-test: Make skip() exit with status 77.
This is mostly useful under TESTSUITE_NOSKIP=y.
2022-07-16 19:14:31 +00:00
Milan Broz
06dd06ea27 tests: allow unit-wipe-test to run with local tests. 2022-07-16 19:14:31 +00:00
Milan Broz
03eb8f860a tests: check for differ existence in compat-test. 2022-07-16 19:14:31 +00:00
Guilhem Moulin
fbcef71c41 Pass $(LDFLAGS) when building fake_token_path.so.
The Debian tooling sets ‘LDFLAGS = -Wl,-z,relro -Wl,-z,now’ and
complains when anything is built without hardened compiler/linker flags.

Granted this is a non-issue here since fake_token_path.so isn't included
in any binary package, but muting the false positive is arguably no
better fix than honoring $(LDFLAGS) during the build.
2022-07-16 13:51:11 +02:00
Milan Broz
8315ada3b0 Fix wipe unit test if direct-io not available.
If test is run in tmpfs, direct-io is not supported.

Thanks Guilhem Moulin for reporting the issue.
2022-07-15 21:50:21 +02:00
Yuri Chornoivan
782dae9292 po: update uk.po (from translationproject.org) 2022-07-15 20:15:48 +02:00
Jakub Bogusz
96c0544527 po: update pl.po (from translationproject.org) 2022-07-15 20:15:48 +02:00
Hiroshi Takekawa
cb7e2c6433 po: update ja.po (from translationproject.org) 2022-07-15 20:15:48 +02:00
Petr Pisar
f0da65cc63 po: update cs.po (from translationproject.org) 2022-07-15 20:15:48 +02:00
Guilhem Moulin
a76c96d361 unit-wipe-test: Wait a bit so scsi_debug has a chance to fully initialize.
On my test system `tests/unit-wipe-test` fails (as root) due to a race
condition in add_device():

	root@host:~# ./unit-wipe-test
	[1] Wipe full file [0/DIO][0][1048576/DIO][1048576][4194304/DIO][4194304][OK]
	[2] Wipe blocks in file [0/DIO][0][1048576/DIO][1048576][4194304/DIO][4194304][OK]
	[  105.828258] scsi_debug:sdebug_driver_probe: scsi_debug: trim poll_queues to 0. poll_q/nr_hw = (0/1)
	[  105.830450] scsi host2: scsi_debug: version 0191 [20210520]
	[  105.830450]   dev_size_mb=8, opts=0x0, submit_queues=1, statistics=0
	[  105.832924] scsi 2:0:0:0: Direct-Access     Linux    scsi_debug       0191 PQ: 0 ANSI: 7
	[  105.835417] scsi 2:0:0:0: Attached scsi generic sg1 type 0
	FAIL Cannot find /dev/.
	FAILED backtrace:
	48 ./unit-wipe-test
	144 main ./unit-wipe-test
	[  105.875131] sd 2:0:0:0: Power-on or device reset occurred
	[  105.876069] sd 2:0:0:0: [sda] 16384 512-byte logical blocks: (8.39 MB/8.00 MiB)
	[  105.877190] sd 2:0:0:0: [sda] Write Protect is off
	[  105.878002] sd 2:0:0:0: [sda] Write cache: enabled, read cache: enabled, supports DPO and FUA
	[  105.879619] sd 2:0:0:0: [sda] Optimal transfer size 524288 bytes
	[  105.914222] sd 2:0:0:0: [sda] Attached SCSI disk
	[  106.866296] sd 2:0:0:0: [sda] Synchronizing SCSI cache

Observe how the “Power-on or device reset occurred” event occurs only
after add_device() has returned.  Interestingly, for subsequent runs the
delay appears to be much shorter and doesn't trigger the race condition:

	root@host:~# ./unit-wipe-test
	[1] Wipe full file [0/DIO][0][1048576/DIO][1048576][4194304/DIO][4194304][OK]
	[2] Wipe blocks in file [0/DIO][0][1048576/DIO][1048576][4194304/DIO][4194304][OK]
	[  130.639855] scsi_debug:sdebug_driver_probe: scsi_debug: trim poll_queues to 0. poll_q/nr_hw = (0/1)
	[  130.641463] scsi host2: scsi_debug: version 0191 [20210520]
	[  130.641463]   dev_size_mb=8, opts=0x0, submit_queues=1, statistics=0
	[  130.643809] scsi 2:0:0:0: Direct-Access     Linux    scsi_debug       0191 PQ: 0 ANSI: 7
	[  130.645342] sd 2:0:0:0: Power-on or device reset occurred
	[  130.646364] sd 2:0:0:0: [sda] 16384 512-byte logical blocks: (8.39 MB/8.00 MiB)
	[  130.647585] sd 2:0:0:0: [sda] Write Protect is off
	[  130.648428] sd 2:0:0:0: Attached scsi generic sg1 type 0
	[  130.649339] sd 2:0:0:0: [sda] Write cache: enabled, read cache: enabled, supports DPO and FUA
	[  130.650763] sd 2:0:0:0: [sda] Optimal transfer size 524288 bytes
	[  130.682223] sd 2:0:0:0: [sda] Attached SCSI disk
	[3] Wipe full block device [0/DIO][0][1048576/DIO][1048576][4194304/DIO][4194304][OK]
	[4] Wipe blocks in block device [0/DIO][0][1048576/DIO][1048576][4194304/DIO][4194304][OK]
	[  137.858283] sd 2:0:0:0: [sda] Synchronizing SCSI cache

This commit adds an optional 2s delay if scsi_debug hasn't shown up in
sysfs after the modprobe call.
2022-07-15 18:13:37 +00:00
Guilhem Moulin
3106b4e2c1 More typo and spelling fixes.
Reported by `git ls-tree -rz --name-only | grep -Evz -e '\.(pdf|xz)$' -e
^po/ | xargs -r0 spellintian --`.  All changes are
documentation-related (comments, manuals, etc.) except for s/fial/fail/
in tests/unit-wipe-test.

The remaining entry are AFAICT all false positives, mostly annotations
such as `@param name name of xyz` or `struct foo foo`:

	$ git ls-tree -rz HEAD --name-only | grep -Evz -e '\.(pdf|xz)$' -e ^po/ | xargs -r0 spellintian --
	COPYING.LGPL: "GNU Library Public License" -> "GNU Library General Public License"
	autogen.sh: echo echo (duplicate word) -> echo
	configure.ac: fi fi (duplicate word) -> fi
	docs/v1.7.2-ReleaseNotes: option option (duplicate word) -> option
	lib/crypto_backend/cipher_check.c: block block (duplicate word) -> block
	lib/libcryptsetup.h: name name (duplicate word) -> name
	lib/libcryptsetup.h: type type (duplicate word) -> type
	lib/libcryptsetup.h: passphrase passphrase (duplicate word) -> passphrase
	lib/libcryptsetup.h: flags flags (duplicate word) -> flags
	lib/libcryptsetup.h: password password (duplicate word) -> password
	lib/libcryptsetup.h: salt salt (duplicate word) -> salt
	lib/libcryptsetup.h: keyslot keyslot (duplicate word) -> keyslot
	lib/libcryptsetup.h: priority priority (duplicate word) -> priority
	lib/libcryptsetup.h: offset offset (duplicate word) -> offset
	lib/libcryptsetup.h: length length (duplicate word) -> length
	lib/libcryptsetup.h: keyfile keyfile (duplicate word) -> keyfile
	lib/libcryptsetup.h: token token (duplicate word) -> token
	lib/libcryptsetup.h: cipher cipher (duplicate word) -> cipher
	lib/libcryptsetup.h: size size (duplicate word) -> size
	lib/luks2/luks2_json_metadata.c: long long (duplicate word) -> long
	lib/luks2/luks2_keyslot_luks2.c: AFEKSize AFEKSize (duplicate word) -> AFEKSize
	lib/luks2/luks2_reencrypt.c: alignment alignment (duplicate word) -> alignment
	lib/luks2/luks2_reencrypt_digest.c: ptr ptr (duplicate word) -> ptr
	lib/luks2/luks2_reencrypt_digest.c: buffer buffer (duplicate word) -> buffer
	lib/luks2/luks2_segment.c: min min (duplicate word) -> min
	lib/verity/verity_fec.c: blocks blocks (duplicate word) -> blocks
	man/cryptsetup.8.adoc: LUKS LUKS (duplicate word) -> LUKS
	scripts/cryptsetup.conf.in: root root (duplicate word) -> root
	src/Makemodule.am: endif endif (duplicate word) -> endif
	src/cryptsetup.c: long long (duplicate word) -> long
	src/utils_args.c: long long (duplicate word) -> long
	tests/compat-test2: fi fi (duplicate word) -> fi
	tests/device-test: echo echo (duplicate word) -> echo
	tests/differ.c: long long (duplicate word) -> long
	tests/loopaes-test: done done (duplicate word) -> done
	tests/luks2-integrity-test: aead aead (duplicate word) -> aead
	tests/luks2-reencryption-test: fi fi (duplicate word) -> fi
	tests/mode-test: done done (duplicate word) -> done
	tests/password-hash-test: cat cat (duplicate word) -> cat
	tests/password-hash-test: fi fi (duplicate word) -> fi
	tests/unit-wipe.c: long long (duplicate word) -> long
	tests/verity-compat-test: done done (duplicate word) -> done
	tests/verity-compat-test: fi fi (duplicate word) -> fi
	tokens/ssh/cryptsetup-ssh.c: argp argp (duplicate word) -> argp
	tokens/ssh/cryptsetup-ssh.c: arguments arguments (duplicate word) -> arguments

(Treated COPYING.LGPL as a false positive too since it's the exact text
from https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html .)
2022-07-15 16:35:02 +02:00
Guilhem Moulin
5d711c000f Fix minor spelling errors.
(Found by Lintian.)
2022-07-15 12:16:39 +02:00
193 changed files with 18408 additions and 9258 deletions

View File

@@ -4,7 +4,7 @@ set -ex
PACKAGES=(
git make autoconf automake autopoint pkg-config libtool libtool-bin
gettext libssl-dev libdevmapper-dev libpopt-dev uuid-dev libsepol1-dev
gettext libssl-dev libdevmapper-dev libpopt-dev uuid-dev libsepol-dev
libjson-c-dev libssh-dev libblkid-dev tar libargon2-0-dev libpwquality-dev
sharutils dmsetup jq xxd expect keyutils netcat passwd openssh-client sshpass
asciidoctor

1
.gitignore vendored
View File

@@ -58,3 +58,4 @@ tests/unit-utils-io
tests/vectors-test
tests/test-symbols-list.h
tests/all-symbols-test
tests/fuzz/LUKS2.pb*

View File

@@ -18,3 +18,5 @@ include:
- local: .gitlab/ci/compilation-gcc.gitlab-ci.yml
- local: .gitlab/ci/compilation-clang.gitlab-ci.yml
- local: .gitlab/ci/alpinelinux.yml
- local: .gitlab/ci/ubuntu-32bit.yml
- local: .gitlab/ci/cifuzz.yml

View File

@@ -23,11 +23,11 @@ test-main-commit-job-alpinelinux:
variables:
RUN_SSH_PLUGIN_TEST: "0"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
rules:
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
script:
- make -j
- make -j -C tests check-programs
@@ -44,6 +44,8 @@ test-mergerq-job-alpinelinux:
variables:
RUN_SSH_PLUGIN_TEST: "0"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_PIPELINE_SOURCE == "merge_request_event"

View File

@@ -27,6 +27,8 @@ test-main-commit-centos-stream9:
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
@@ -46,6 +48,8 @@ test-mergerq-centos-stream9:
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_PIPELINE_SOURCE == "merge_request_event"

View File

@@ -4,7 +4,7 @@ set -ex
PACKAGES=(
git make autoconf automake autopoint pkg-config libtool libtool-bin
gettext libssl-dev libdevmapper-dev libpopt-dev uuid-dev libsepol1-dev
gettext libssl-dev libdevmapper-dev libpopt-dev uuid-dev libsepol-dev
libjson-c-dev libssh-dev libblkid-dev tar libargon2-0-dev libpwquality-dev
sharutils dmsetup jq xxd expect keyutils netcat passwd openssh-client sshpass
asciidoctor

46
.gitlab/ci/cifuzz.yml Normal file
View File

@@ -0,0 +1,46 @@
cifuzz:
variables:
OSS_FUZZ_PROJECT_NAME: cryptsetup
CFL_PLATFORM: gitlab
CIFUZZ_DEBUG: "True"
FUZZ_SECONDS: 300 # 5 minutes per fuzzer
ARCHITECTURE: "x86_64"
DRY_RUN: "False"
LOW_DISK_SPACE: "True"
BAD_BUILD_CHECK: "True"
LANGUAGE: "c"
DOCKER_HOST: "tcp://docker:2375"
DOCKER_IN_DOCKER: "true"
DOCKER_DRIVER: overlay2
DOCKER_TLS_CERTDIR: ""
image:
name: gcr.io/oss-fuzz-base/cifuzz-base
entrypoint: [""]
services:
- docker:dind
stage: test
parallel:
matrix:
- SANITIZER: [address, undefined, memory]
rules:
# Default code change.
# - if: $CI_PIPELINE_SOURCE == "merge_request_event"
# variables:
# MODE: "code-change"
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $BUILD_AND_RUN_FUZZERS != null
before_script:
# Get gitlab's container id.
- export CFL_CONTAINER_ID=`cut -c9- < /proc/1/cpuset`
script:
# Will build and run the fuzzers.
# We use a hack to override CI_JOB_ID, because otherwise a bad path is used
# in GitLab CI environment
- CI_JOB_ID="$CI_PROJECT_NAMESPACE/$CI_PROJECT_TITLE" python3 "/opt/oss-fuzz/infra/cifuzz/cifuzz_combined_entrypoint.py"
artifacts:
# Upload artifacts when a crash makes the job fail.
when: always
paths:
- artifacts/

View File

@@ -3,12 +3,15 @@
- .dump_kernel_log
before_script:
- >
sudo apt-get -y install -y -qq git gcc make
autoconf automake autopoint pkg-config libtool libtool-bin gettext
libssl-dev libdevmapper-dev libpopt-dev uuid-dev libsepol1-dev
libjson-c-dev libssh-dev libblkid-dev tar libargon2-0-dev
libpwquality-dev sharutils dmsetup jq xxd expect keyutils
netcat passwd openssh-client sshpass asciidoctor
[ -z "$RUN_SYSTEMD_PLUGIN_TEST" ] ||
sudo apt-get -y install -y -qq swtpm meson ninja-build python3-jinja2
gperf libcap-dev tpm2-tss-engine-dev libmount-dev swtpm-tools
- >
sudo apt-get -y install -y -qq git gcc make autoconf automake autopoint
pkgconf libtool libtool-bin gettext libssl-dev libdevmapper-dev
libpopt-dev uuid-dev libsepol-dev libjson-c-dev libssh-dev libblkid-dev
tar libargon2-0-dev libpwquality-dev sharutils dmsetup jq xxd expect
keyutils netcat passwd openssh-client sshpass asciidoctor
- sudo apt-get -y build-dep cryptsetup
- sudo -E git clean -xdf
- ./autogen.sh
@@ -19,7 +22,7 @@ test-mergerq-job-debian:
- .debian-prep
tags:
- libvirt
- debian10
- debian11
stage: test
interruptible: true
variables:
@@ -38,7 +41,7 @@ test-main-commit-job-debian:
- .debian-prep
tags:
- libvirt
- debian10
- debian11
stage: test
interruptible: true
variables:

View File

@@ -3,7 +3,12 @@
- .dump_kernel_log
before_script:
- >
sudo dnf -y -q install
[ -z "$RUN_SYSTEMD_PLUGIN_TEST" ] ||
sudo dnf -y -q install
swtpm meson ninja-build python3-jinja2 gperf libcap-devel tpm2-tss-devel
libmount-devel swtpm-tools
- >
sudo dnf -y -q install
autoconf automake device-mapper-devel gcc gettext-devel json-c-devel
libargon2-devel libblkid-devel libpwquality-devel libselinux-devel
libssh-devel libtool libuuid-devel make popt-devel

View File

@@ -27,6 +27,8 @@ test-main-commit-rhel8:
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
@@ -46,6 +48,8 @@ test-main-commit-rhel9:
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
@@ -67,10 +71,13 @@ test-main-commit-rhel8-fips:
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
script:
- fips-mode-setup --check || exit 1
- make -j
- make -j -C tests check-programs
- sudo -E make check
@@ -87,10 +94,13 @@ test-main-commit-rhel9-fips:
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
script:
- fips-mode-setup --check || exit 1
- make -j
- make -j -C tests check-programs
- sudo -E make check

View File

@@ -0,0 +1,41 @@
test-mergerq-job-ubuntu-32bit:
extends:
- .debian-prep
tags:
- libvirt
- ubuntu-bionic-32bit
stage: test
interruptible: true
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_PIPELINE_SOURCE == "merge_request_event"
script:
- make -j
- make -j -C tests check-programs
- sudo -E make check
test-main-commit-job-ubuntu-32bit:
extends:
- .debian-prep
tags:
- libvirt
- ubuntu-bionic-32bit
stage: test
interruptible: true
variables:
RUN_SSH_PLUGIN_TEST: "1"
rules:
- if: $RUN_SYSTEMD_PLUGIN_TEST != null
when: never
- if: $CI_PROJECT_PATH != "cryptsetup/cryptsetup"
when: never
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH || $CI_COMMIT_BRANCH =~ /v2\..\.x$/
script:
- make -j
- make -j -C tests check-programs
- sudo -E make check

43
FAQ.md
View File

@@ -1192,7 +1192,7 @@
More references can be found at the end of this document. Note that
these are estimates from the defender side, so assuming something is
easier than it actually is is fine. An attacker may still have
easier than it actually is fine. An attacker may still have
significantly higher cost than estimated here.
LUKS1 used SHA1 (since version 1.7.0 it uses SHA256) for hashing per
@@ -1864,11 +1864,11 @@
This basically means that if you already have a slot-key, and you have
set the PBKDF2 iteration count to 1 (it is > 10'000 normally), you could
(maybe) derive a different passphrase that gives you the the same
slot-key. But if you have the slot-key, you can already unlock the
key-slot and get the volume key, breaking everything. So basically,
this SHA-1 vulnerability allows you to open a LUKS1 container with high
effort when you already have it open.
(maybe) derive a different passphrase that gives you the same slot-key.
But if you have the slot-key, you can already unlock the key-slot and
get the volume key, breaking everything. So basically, this SHA-1
vulnerability allows you to open a LUKS1 container with high effort when
you already have it open.
The real problem here is people that do not understand crypto and claim
things are broken just because some mechanism is used that has been
@@ -2506,6 +2506,31 @@ offset length name data type description
individually created (and hence has its own volume key). In this case,
changing the default passphrase will make it secure again.
* **6.16 How to convert the printed volume key to a raw one?**
A volume key printed via something like:
```
cryptsetup --dump-volume-key luksDump /dev/<device> >volume-key
```
(i.e. without using `--volume-key-file`), which gives something like:
```
LUKS header information for /dev/<device>
Cipher name: aes
Cipher mode: xts-plain64
Payload offset: 32768
UUID: 6e914442-e8b5-4eb5-98c4-5bf0cf17ecad
MK bits: 512
MK dump: e0 3f 15 c2 0f e5 80 ab 35 b4 10 03 ae 30 b9 5d
4c 0d 28 9e 1b 0f e3 b0 50 57 ef d4 4d 53 a0 12
b7 4e 43 a1 20 7e c5 02 1f f1 f5 08 04 3c f5 20
a6 0b 23 f6 7b 53 55 aa 22 d8 aa 02 e0 2f d5 04
```
can be converted to the raw volume key for example via:
```
sed -E -n '/^MK dump:\t/,/^[^\t]/{0,/^MK dump:\t/s/^MK dump://; /^([^\t].*)?$/q; s/\t+//p;};' volume-key | xxd -r -p
```
# 7. Interoperability with other Disk Encryption Tools
@@ -3014,9 +3039,9 @@ offset length name data type description
currently associated with any data/crypt segment (encrypted area) in the
LUKS2 'Segments' section (displayed by luksDump).
This is a bit of a more general idea. It basically allows to use a keyslot
as a container for a key to be used in other things than decrypting a
data segment.
This is a bit of a more general idea. It basically allows one to use a
keyslot as a container for a key to be used in other things than decrypting
a data segment.
As of April 2020, the following uses are defined:

View File

@@ -1,5 +1,5 @@
EXTRA_DIST = README.md COPYING.LGPL FAQ.md docs misc autogen.sh
SUBDIRS = po tests
SUBDIRS = po tests tests/fuzz
CLEANFILES =
DISTCLEAN_TARGETS =
@@ -14,8 +14,14 @@ AM_CPPFLAGS = \
-DVERSION=\""$(VERSION)"\" \
-DEXTERNAL_LUKS2_TOKENS_PATH=\"${EXTERNAL_LUKS2_TOKENS_PATH}\"
AM_CFLAGS = -Wall
AM_CXXFLAGS = -Wall
AM_LDFLAGS =
if ENABLE_FUZZ_TARGETS
AM_CFLAGS += -fsanitize=fuzzer-no-link
AM_CXXFLAGS += -fsanitize=fuzzer-no-link
endif
LDADD = $(LTLIBINTL)
tmpfilesddir = @DEFAULT_TMPFILESDIR@
@@ -64,3 +70,8 @@ uninstall-local:
check-programs: libcryptsetup.la
$(MAKE) -C tests $@
if ENABLE_FUZZ_TARGETS
fuzz-targets: libcryptsetup.la libcrypto_backend.la
$(MAKE) -C tests/fuzz $@
endif

View File

@@ -6,7 +6,7 @@ What the ...?
on the [DMCrypt](https://gitlab.com/cryptsetup/cryptsetup/wikis/DMCrypt) kernel module.
These include **plain** **dm-crypt** volumes, **LUKS** volumes, **loop-AES**,
**TrueCrypt** (including **VeraCrypt** extension) and **BitLocker** formats.
**TrueCrypt** (including **VeraCrypt** extension), **BitLocker** and **FileVault2** formats.
The project also includes a **veritysetup** utility used to conveniently setup
[DMVerity](https://gitlab.com/cryptsetup/cryptsetup/wikis/DMVerity) block integrity checking kernel module
@@ -45,22 +45,16 @@ Download
--------
All release tarballs and release notes are hosted on [kernel.org](https://www.kernel.org/pub/linux/utils/cryptsetup/).
**The latest stable release candidate cryptsetup version is 2.5.0-rc1**
* [cryptsetup-2.5.0-rc1.tar.xz](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.5/cryptsetup-2.5.0-rc1.tar.xz)
* Signature [cryptsetup-2.5.0-rc1.tar.sign](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.5/cryptsetup-2.5.0-rc1.tar.sign)
**The latest stable cryptsetup release version is 2.6.0**
* [cryptsetup-2.6.0.tar.xz](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.6/cryptsetup-2.6.0.tar.xz)
* Signature [cryptsetup-2.6.0.tar.sign](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.6/cryptsetup-2.6.0.tar.sign)
_(You need to decompress file first to check signature.)_
* [Cryptsetup 2.5.0-rc1 Release Notes](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.5/v2.5.0-rc1-ReleaseNotes).
**The latest stable cryptsetup version is 2.4.3**
* [cryptsetup-2.4.3.tar.xz](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.4/cryptsetup-2.4.3.tar.xz)
* Signature [cryptsetup-2.4.3.tar.sign](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.4/cryptsetup-2.4.3.tar.sign)
_(You need to decompress file first to check signature.)_
* [Cryptsetup 2.4.3 Release Notes](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.4/v2.4.3-ReleaseNotes).
* [Cryptsetup 2.6.0 Release Notes](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.6/v2.6.0-ReleaseNotes).
Previous versions
* [Version 2.3.7](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.3/cryptsetup-2.3.7.tar.xz) -
[Signature](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.3/cryptsetup-2.3.7.tar.sign) -
[Release Notes](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.3/v2.3.7-ReleaseNotes).
* [Version 2.5.0](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.5/cryptsetup-2.5.0.tar.xz) -
[Signature](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.5/cryptsetup-2.5.0.tar.sign) -
[Release Notes](https://www.kernel.org/pub/linux/utils/cryptsetup/v2.5/v2.5.0-ReleaseNotes).
* [Version 1.7.5](https://www.kernel.org/pub/linux/utils/cryptsetup/v1.7/cryptsetup-1.7.5.tar.xz) -
[Signature](https://www.kernel.org/pub/linux/utils/cryptsetup/v1.7/cryptsetup-1.7.5.tar.sign) -
[Release Notes](https://www.kernel.org/pub/linux/utils/cryptsetup/v1.7/v1.7.5-ReleaseNotes).

View File

@@ -74,7 +74,7 @@ autopoint --force $AP_OPTS
libtoolize --force --copy
aclocal -I m4 $AL_OPTS
autoheader $AH_OPTS
automake --add-missing --copy --gnu $AM_OPTS
automake --force-missing --add-missing --copy --gnu $AM_OPTS
autoconf $AC_OPTS
echo

View File

@@ -1,9 +1,9 @@
AC_PREREQ([2.67])
AC_INIT([cryptsetup],[2.5.0-rc1])
AC_INIT([cryptsetup],[2.6.0])
dnl library version from <major>.<minor>.<release>[-<suffix>]
LIBCRYPTSETUP_VERSION=$(echo $PACKAGE_VERSION | cut -f1 -d-)
LIBCRYPTSETUP_VERSION_INFO=20:0:8
LIBCRYPTSETUP_VERSION_INFO=21:0:9
AM_SILENT_RULES([yes])
AC_CONFIG_SRCDIR(src/cryptsetup.c)
@@ -28,6 +28,7 @@ AC_USE_SYSTEM_EXTENSIONS
AC_PROG_CC
AM_PROG_CC_C_O
AC_PROG_CPP
AC_PROG_CXX
AC_PROG_INSTALL
AC_PROG_MAKE_SET
AC_PROG_MKDIR_P
@@ -150,6 +151,7 @@ if test "x$enable_external_tokens" = "xyes"; then
AC_SUBST(DL_LIBS, $LIBS)
LIBS=$saved_LIBS
fi
AM_CONDITIONAL(EXTERNAL_TOKENS, test "x$enable_external_tokens" = "xyes")
AC_ARG_ENABLE([ssh-token],
AS_HELP_STRING([--disable-ssh-token], [disable LUKS2 ssh-token]),
@@ -213,6 +215,17 @@ if test "x$enable_pwquality" = "xyes"; then
PWQUALITY_STATIC_LIBS="$PWQUALITY_LIBS -lcrack -lz"
fi
dnl ==========================================================================
dnl fuzzers, it requires own static library compilation later
AC_ARG_ENABLE([fuzz-targets],
AS_HELP_STRING([--enable-fuzz-targets], [enable building fuzz targets]))
AM_CONDITIONAL(ENABLE_FUZZ_TARGETS, test "x$enable_fuzz_targets" = "xyes")
if test "x$enable_fuzz_targets" = "xyes"; then
AX_CHECK_COMPILE_FLAG([-fsanitize=fuzzer-no-link],,
AC_MSG_ERROR([Required compiler options not supported; use clang.]), [-Werror])
fi
dnl ==========================================================================
dnl passwdqc library (cryptsetup CLI only)
AC_ARG_ENABLE([passwdqc],
@@ -617,6 +630,22 @@ AC_SUBST([LIBSSH_LIBS])
AC_SUBST([LIBCRYPTSETUP_VERSION])
AC_SUBST([LIBCRYPTSETUP_VERSION_INFO])
dnl Set Requires.private for libcryptsetup.pc
dnl pwquality is used only by tools
PKGMODULES="uuid devmapper json-c"
case $with_crypto_backend in
gcrypt) PKGMODULES+=" libgcrypt" ;;
openssl) PKGMODULES+=" openssl" ;;
nss) PKGMODULES+=" nss" ;;
nettle) PKGMODULES+=" nettle" ;;
esac
if test "x$enable_libargon2" = "xyes"; then
PKGMODULES+=" libargon2"
fi
if test "x$enable_blkid" = "xyes"; then
PKGMODULES+=" blkid"
fi
AC_SUBST([PKGMODULES])
dnl ==========================================================================
AC_ARG_ENABLE([dev-random],
AS_HELP_STRING([--enable-dev-random], [use /dev/random by default for key generation (otherwise use /dev/urandom)]))
@@ -739,5 +768,6 @@ lib/libcryptsetup.pc
po/Makefile.in
scripts/cryptsetup.conf
tests/Makefile
tests/fuzz/Makefile
])
AC_OUTPUT

View File

@@ -74,7 +74,7 @@
2012-03-16 Milan Broz <gmazyland@gmail.com>
* Add --keyfile-offset and --new-keyfile-offset parameters to API and CLI.
* Add repair command and crypt_repair() for known LUKS metadata problems repair.
* Allow to specify --align-payload only for luksFormat.
* Allow one to specify --align-payload only for luksFormat.
2012-03-16 Milan Broz <mbroz@redhat.com>
* Unify password verification option.
@@ -228,7 +228,7 @@
* Fix password callback call.
* Fix default plain password entry from terminal in activate_by_passphrase.
* Add --dump-master-key option for luksDump to allow volume key dump.
* Allow to activate by internally cached volume key
* Allow one to activate by internally cached volume key
(format/activate without keyslots active - used for temporary devices).
* Initialize volume key from active device in crypt_init_by_name()
* Fix cryptsetup binary exitcodes.

View File

@@ -85,7 +85,7 @@ Libcryptsetup API additions:
* Fix optional password callback handling.
* Allow to activate by internally cached volume key immediately after
* Allow one to activate by internally cached volume key immediately after
crypt_format() without active slot (for temporary devices with
on-disk metadata)

View File

@@ -24,7 +24,7 @@ Changes since version 1.4.1
* Fix header check to support old (cryptsetup 1.0.0) header alignment.
(Regression in 1.4.0)
* Allow to specify --align-payload only for luksFormat.
* Allow one to specify --align-payload only for luksFormat.
* Add --master-key-file option to luksOpen (open using volume key).

View File

@@ -32,7 +32,7 @@ Changes since version 1.4.2
Device-mapper now retry removal if device is busy.
* Allow "private" activation (skip some udev global rules) flag.
Cryptsetup library API now allows to specify CRYPT_ACTIVATE_PRIVATE,
Cryptsetup library API now allows one to specify CRYPT_ACTIVATE_PRIVATE,
which means that some udev rules are not processed.
(Used for temporary devices, like internal keyslot mappings where
it is not desirable to run any device scans.)

View File

@@ -4,7 +4,7 @@ Cryptsetup 1.6.0 Release Notes
Changes since version 1.6.0-rc1
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
* Change LUKS default cipher to to use XTS encryption mode,
* Change LUKS default cipher to use XTS encryption mode,
aes-xts-plain64 (i.e. using AES128-XTS).
XTS mode becomes standard in hard disk encryption.
@@ -209,7 +209,7 @@ Important changes
WARNING: these tests do not use dmcrypt, only crypto API.
You have to benchmark the whole device stack and you can get completely
different results. But is is usable for basic comparison.
different results. But it is usable for basic comparison.
(Note for example AES-NI decryption optimization effect in example above.)
Features

View File

@@ -8,7 +8,7 @@ Changes since version 1.6.1
* Fix cipher specification string parsing (found by gcc -fsanitize=address option).
* Try to map TCRYPT system encryption through partition
(allows to activate mapping when other partition on the same device is mounted).
(allows one to activate mapping when other partition on the same device is mounted).
* Print a warning if system encryption is used and device is a partition.
(TCRYPT system encryption uses whole device argument.)

View File

@@ -25,7 +25,7 @@ Changes since version 1.6.3
Please refer to cryptsetup FAQ for detail how to fix this situation.
* Allow to use --disable-gcrypt-pbkdf2 during configuration
* Allow one to use --disable-gcrypt-pbkdf2 during configuration
to force use internal PBKDF2 code.
* Require gcrypt 1.6.1 for imported implementation of PBKDF2

View File

@@ -38,7 +38,7 @@ Changes since version 1.6.4
The command "cryptsetup status" will print basic info, even if you
do not provide detached header argument.
* Allow to specify ECB mode in cryptsetup benchmark.
* Allow one to specify ECB mode in cryptsetup benchmark.
* Add some LUKS images for regression testing.
Note that if image with Whirlpool fails, the most probable cause is that

View File

@@ -35,14 +35,14 @@ Changes since version 1.6.6
* Support permanent device decryption for cryptsetup-reencrypt.
To remove LUKS encryption from a device, you can now use --decrypt option.
* Allow to use --header option in all LUKS commands.
* Allow one to use --header option in all LUKS commands.
The --header always takes precedence over positional device argument.
* Allow luksSuspend without need to specify a detached header.
* Detect if O_DIRECT is usable on a device allocation.
There are some strange storage stack configurations which wrongly allows
to open devices with direct-io but fails on all IO operations later.
one to open devices with direct-io but fails on all IO operations later.
Cryptsetup now tries to read the device first sector to ensure it can use
direct-io.

View File

@@ -30,7 +30,7 @@ Changes since version 1.6.7
cryptsetup resize will try to resize underlying loop device as well.
(It can be used to grow up file-backed device in one step.)
* Cryptsetup now allows to use empty password through stdin pipe.
* Cryptsetup now allows one to use empty password through stdin pipe.
(Intended only for testing in scripts.)
Cryptsetup API NOTE:

View File

@@ -3,7 +3,7 @@ Cryptsetup 1.7.4 Release Notes
Changes since version 1.7.3
* Allow to specify LUKS1 hash algorithm in Python luksFormat wrapper.
* Allow one to specify LUKS1 hash algorithm in Python luksFormat wrapper.
* Use LUKS1 compiled-in defaults also in Python wrapper.

View File

@@ -30,7 +30,7 @@ Changes since version 2.0.1
* Add LUKS2 specific options for cryptsetup-reencrypt.
Tokens and persistent flags are now transferred during reencryption;
change of PBKDF keyslot parameters is now supported and allows
change of PBKDF keyslot parameters is now supported and allows one
to set precalculated values (no benchmarks).
* Do not allow LUKS2 --persistent and --test-passphrase cryptsetup flags

View File

@@ -28,7 +28,7 @@ Changes since version 2.0.2
* New API extensions for unbound keyslots (LUKS2 only)
crypt_keyslot_get_key_size() and crypt_volume_key_get()
These functions allow to get key and key size for unbound keyslots.
These functions allow one to get key and key size for unbound keyslots.
* New enum value CRYPT_SLOT_UNBOUND for keyslot status (LUKS2 only).

View File

@@ -170,21 +170,21 @@ These new calls are now exported, for details see libcryptsetup.h:
* crypt_get_metadata_size
* crypt_set_metadata_size
allows to set/get area sizes in LUKS header
allows one to set/get area sizes in LUKS header
(according to specification).
* crypt_get_default_type
get default compiled-in LUKS type (version).
* crypt_get_pbkdf_type_params
allows to get compiled-in PBKDF parameters.
allows one to get compiled-in PBKDF parameters.
* crypt_keyslot_set_encryption
* crypt_keyslot_get_encryption
allows to set/get per-keyslot encryption algorithm for LUKS2.
allows one to set/get per-keyslot encryption algorithm for LUKS2.
* crypt_keyslot_get_pbkdf
allows to get PBKDF parameters per-keyslot.
allows one to get PBKDF parameters per-keyslot.
and these new defines:
* CRYPT_LOG_DEBUG_JSON (message type for JSON debug)

View File

@@ -9,7 +9,7 @@ native read-write access to BitLocker Full Disk Encryption devices.
The BITLK implementation is based on publicly available information
and it is an independent and opensource implementation that allows
to access this proprietary disk encryption.
one to access this proprietary disk encryption.
Changes since version 2.2.2
~~~~~~~~~~~~~~~~~~~~~~~~~~~

View File

@@ -18,7 +18,7 @@ Changes since version 2.3.1
The slot number --key-slot (-S) option is mandatory here.
An unbound keyslot store a key is that is not assigned to data
area on disk (LUKS2 allows to store arbitrary keys).
area on disk (LUKS2 allows one to store arbitrary keys).
* Rephrase some error messages and remove redundant end-of-lines.

View File

@@ -1,6 +1,6 @@
Cryptsetup 2.5.0-rc1 Release Notes
==================================
Stable release candidate with new features and bug fixes.
Cryptsetup 2.5.0 Release Notes
==============================
Stable release with new features and bug fixes.
Changes since version 2.4.3
~~~~~~~~~~~~~~~~~~~~~~~~~~~
@@ -125,6 +125,11 @@ LUKS volume reencryption changes
* Support all options allowed with luksFormat with encrypt action.
* Add prompt if LUKS2 decryption is run with a detached header.
* Add warning for reencryption of file image and mention
the possible use of --force-offline-reencrypt option.
Other changes
~~~~~~~~~~~~~
@@ -258,6 +263,11 @@ Other changes
* Reimplement BASE64 with simplified code instead of coreutils version.
* Fix regression when warning messages were not displayed
if some kernel feature is not supported (2.4.2).
* Add support for --key-slot option in luksResume action.
Libcryptsetup API extensions and changes
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

236
docs/v2.6.0-ReleaseNotes Normal file
View File

@@ -0,0 +1,236 @@
Cryptsetup 2.6.0 Release Notes
==============================
Stable release with new features and bug fixes.
Changes since version 2.5.0
~~~~~~~~~~~~~~~~~~~~~~~~~~~
* Introduce support for handling macOS FileVault2 devices (FVAULT2).
Cryptsetup now supports the mapping of FileVault2 full-disk encryption
by Apple for the macOS operating system using a native Linux kernel.
You can open an existing USB FileVault portable device and (with
the hfsplus filesystem driver) access the native data read/write.
Cryptsetup supports only (legacy) FileVault2 based on Core Storage
and HFS+ filesystem (introduced in MacOS X 10.7 Lion).
It does NOT support the new version of FileVault based on the APFS
filesystem used in recent macOS versions.
Header formatting and changes are not supported; cryptsetup never
changes the metadata on the device.
FVAULT2 extension requires kernel userspace crypto API and kernel
driver for HFS+ (hfsplus) filesystem (available on most systems today).
Example of using FileVault2 formatted USB device:
A typical encrypted device contains three partitions; the FileVault
encrypted partition is here sda2:
$ lsblk -o NAME,FSTYPE,LABEL /dev/sda
NAME FSTYPE LABEL
sda
|-sda1 vfat EFI
|-sda2
`-sda3 hfsplus Boot OS X
Note: blkid does not recognize FileVault2 format yet.
To dump metadata information about the device, you can use
the fvault2Dump command:
$ cryptsetup fvault2Dump /dev/sda2
Header information for FVAULT2 device /dev/sda2.
Physical volume UUID: 6f353c05-daae-4e76-a0ee-6a9569a22d81
Family UUID: f82cceb0-a788-4815-945a-53d57fcd55a8
Logical volume offset: 67108864 [bytes]
Logical volume size: 3288334336 [bytes]
Cipher: aes
Cipher mode: xts-plain64
PBKDF2 iterations: 97962
PBKDF2 salt: 173a4ec7447662ec79ca7a47df6c2a01
To activate the device, use open --type fvault2 option:
$ cryptsetup open --type fvault2 /dev/sda2 test
Enter passphrase for /dev/sda2: ...
And check the status of the active device:
$ cryptsetup status test
/dev/mapper/test is active.
type: FVAULT2
cipher: aes-xts-plain64
keysize: 256 bits
key location: dm-crypt
device: /dev/sda2
sector size: 512
offset: 131072 sectors
size: 6422528 sectors
mode: read/write
Now, if the kernel contains hfsplus filesystem driver, you can mount
decrypted content:
$ mount /dev/mapper/test /mnt/test
For more info about implementation, please refer to the master thesis
by Pavel Tobias, which was the source for this extension.
https://is.muni.cz/th/p0aok/?lang=en
* libcryptsetup: no longer use global memory locking through mlockall()
For many years, libcryptsetup locked all memory (including dependent
library address space) to prevent swapping sensitive content outside
of RAM.
This strategy no longer works as the locking of basic libraries exceeds
the memory locking limit if running as a non-root user.
Libcryptsetup now locks only memory ranges containing sensitive
material (keys) through crypt_safe_alloc() calls.
This change solves many reported mysterious problems of unexpected
failures. If the initial lock was still under the limit and succeeded,
some following memory allocation could fail later as it exceeded
the locking limit. If the initial locking fails, memory locking
was quietly ignored completely.
The whole crypt_memory_lock() API call is deprecated; it no longer
calls memlockall().
* libcryptsetup: process priority is increased only for key derivation
(PBKDF) calls.
Increasing priority was tight to memory locking and works only if
running under superuser.
Only PBKDF calls and benchmarking now increase the process priority.
* Add new LUKS keyslot context handling functions and API.
In practice, the luksAddKey action does two operations.
It unlocks the existing device volume key and stores the unlocked
volume key in a new keyslot.
Previously the options were limited to key files and passphrases.
Newly available methods (keyslot contexts) are passphrase, keyfile,
key (binary representation), and LUKS2 token.
To unlock a keyslot user may:
- provide existing passphrase via interactive prompt (default method)
- use --key-file option to provide a file with a valid passphrase
- provide volume key directly via --volume-key-file
- unlock keyslot via all available LUKS2 tokens by --token-only
- unlock keyslot via specific token with --token-id
- unlock keyslot via specific token type by --token-type
To provide the passphrase for a new keyslot, a user may:
- provide existing passphrase via interactive prompt (default method)
- use --new-keyfile to read the passphrase from the file
- use --new-token-id to select LUKS2 token to get passphrase
for new keyslot. The new keyslot is assigned to the selected token
id if the operation is successful.
* The volume key may now be extracted using a passphrase, keyfile, or
token. For LUKS devices, it also returns the volume key after
a successful crypt_format call.
* Fix --disable-luks2-reencryption configuration option.
* cryptsetup: Print a better error message and warning if the format
produces an image without space available for data.
Activation now fails early with a more descriptive message.
* Print error if anti-forensic LUKS2 hash setting is not available.
If the specified hash was not available, activation quietly failed.
* Fix internal crypt segment compare routine if the user
specified cipher in kernel format (capi: prefix).
* cryptsetup: Add token unassign action.
This action allows removing token binding on specific keyslot.
* veritysetup: add support for --use-tasklets option.
This option sets try_verify_in_tasklet kernel dm-verity option
(available since Linux kernel 6.0) to allow some performance
improvement on specific systems.
* Provide pkgconfig Require.private settings.
While we do not completely provide static build on udev systems,
it helps produce statically linked binaries in certain situations.
* Always update automake library files if autogen.sh is run.
For several releases, we distributed older automake scripts by mistake.
* reencryption: Fix user defined moved segment size in LUKS2 decryption.
The --hotzone-size argument was ignored in cases where the actual data
size was less than the original LUKS2 data offset.
* Delegate FIPS mode detection to configured crypto backend.
System FIPS mode check no longer depends on /etc/system-fips file.
* tests: externally provided systemd plugin is now optionally compiled
from systemd git and tested with cryptsetup
* tests: initial integration to OSS-fuzz project with basic crypt_load()
test for LUKS2 and JSON mutated fuzzing.
For more info, see README in tests/fuzz directory.
* Update documentation, including FAQ and man pages.
Libcryptsetup API extensions
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The libcryptsetup API is backward compatible with existing symbols.
New symbols:
crypt_keyslot_context_init_by_passphrase
crypt_keyslot_context_init_by_keyfile
crypt_keyslot_context_init_by_token
crypt_keyslot_context_init_by_volume_key
crypt_keyslot_context_get_error
crypt_keyslot_context_set_pin
crypt_keyslot_context_get_type
crypt_keyslot_context_free
crypt_keyslot_add_by_keyslot_context
crypt_volume_key_get_by_keyslot_context
New defines:
CRYPT_FVAULT2 "FVAULT2" (FileVault2 compatible mode)
Keyslot context types:
CRYPT_KC_TYPE_PASSPHRASE
CRYPT_KC_TYPE_KEYFILE
CRYPT_KC_TYPE_TOKEN
CRYPT_KC_TYPE_KEY
CRYPT_ACTIVATE_TASKLETS (dm-verity: use tasklets activation flag)
WARNING!
~~~~~~~~
The next version of cryptsetup will change the encryption mode and key
derivation option for the PLAIN format.
This change will cause backward incompatibility.
For this reason, the user will have to specify the exact parameters
for cipher, key size, and key derivation parameters for plain format.
The default encryption mode will be AES-XTS with 512bit key (AES-256).
The CBC mode is no longer considered the best default, as it allows easy
bit-flipped ciphertext modification attacks and performance problems.
For the passphrase hashing in plain mode, the encryption key is directly
derived through iterative hashing from a user-provided passphrase
(except a keyfile that is not hashed).
The default hash is RIPEMD160, which is no longer the best default
option. The exact change will be yet discussed but should include
the possibility of using a password-based key derivation function
instead of iterative hashing.

View File

@@ -53,8 +53,6 @@ libcryptsetup_la_SOURCES = \
lib/utils_loop.h \
lib/utils_devpath.c \
lib/utils_wipe.c \
lib/utils_fips.c \
lib/utils_fips.h \
lib/utils_device.c \
lib/utils_keyring.c \
lib/utils_keyring.h \
@@ -75,6 +73,8 @@ libcryptsetup_la_SOURCES = \
lib/loopaes/loopaes.c \
lib/tcrypt/tcrypt.h \
lib/tcrypt/tcrypt.c \
lib/keyslot_context.h \
lib/keyslot_context.c \
lib/luks1/af.h \
lib/luks1/af.c \
lib/luks1/keyencryption.c \
@@ -106,4 +106,6 @@ libcryptsetup_la_SOURCES = \
lib/utils_blkid.c \
lib/utils_blkid.h \
lib/bitlk/bitlk.h \
lib/bitlk/bitlk.c
lib/bitlk/bitlk.c \
lib/fvault2/fvault2.h \
lib/fvault2/fvault2.c

View File

@@ -24,7 +24,6 @@
#include <errno.h>
#include <stdlib.h>
#include <limits.h>
#include <assert.h>
#include "crypto_backend.h"

View File

@@ -97,12 +97,71 @@ static const uint32_t crc32_tab[] = {
0x2d02ef8dL
};
static const uint32_t crc32c_tab[] = {
0x00000000L, 0xF26B8303L, 0xE13B70F7L, 0x1350F3F4L, 0xC79A971FL,
0x35F1141CL, 0x26A1E7E8L, 0xD4CA64EBL, 0x8AD958CFL, 0x78B2DBCCL,
0x6BE22838L, 0x9989AB3BL, 0x4D43CFD0L, 0xBF284CD3L, 0xAC78BF27L,
0x5E133C24L, 0x105EC76FL, 0xE235446CL, 0xF165B798L, 0x030E349BL,
0xD7C45070L, 0x25AFD373L, 0x36FF2087L, 0xC494A384L, 0x9A879FA0L,
0x68EC1CA3L, 0x7BBCEF57L, 0x89D76C54L, 0x5D1D08BFL, 0xAF768BBCL,
0xBC267848L, 0x4E4DFB4BL, 0x20BD8EDEL, 0xD2D60DDDL, 0xC186FE29L,
0x33ED7D2AL, 0xE72719C1L, 0x154C9AC2L, 0x061C6936L, 0xF477EA35L,
0xAA64D611L, 0x580F5512L, 0x4B5FA6E6L, 0xB93425E5L, 0x6DFE410EL,
0x9F95C20DL, 0x8CC531F9L, 0x7EAEB2FAL, 0x30E349B1L, 0xC288CAB2L,
0xD1D83946L, 0x23B3BA45L, 0xF779DEAEL, 0x05125DADL, 0x1642AE59L,
0xE4292D5AL, 0xBA3A117EL, 0x4851927DL, 0x5B016189L, 0xA96AE28AL,
0x7DA08661L, 0x8FCB0562L, 0x9C9BF696L, 0x6EF07595L, 0x417B1DBCL,
0xB3109EBFL, 0xA0406D4BL, 0x522BEE48L, 0x86E18AA3L, 0x748A09A0L,
0x67DAFA54L, 0x95B17957L, 0xCBA24573L, 0x39C9C670L, 0x2A993584L,
0xD8F2B687L, 0x0C38D26CL, 0xFE53516FL, 0xED03A29BL, 0x1F682198L,
0x5125DAD3L, 0xA34E59D0L, 0xB01EAA24L, 0x42752927L, 0x96BF4DCCL,
0x64D4CECFL, 0x77843D3BL, 0x85EFBE38L, 0xDBFC821CL, 0x2997011FL,
0x3AC7F2EBL, 0xC8AC71E8L, 0x1C661503L, 0xEE0D9600L, 0xFD5D65F4L,
0x0F36E6F7L, 0x61C69362L, 0x93AD1061L, 0x80FDE395L, 0x72966096L,
0xA65C047DL, 0x5437877EL, 0x4767748AL, 0xB50CF789L, 0xEB1FCBADL,
0x197448AEL, 0x0A24BB5AL, 0xF84F3859L, 0x2C855CB2L, 0xDEEEDFB1L,
0xCDBE2C45L, 0x3FD5AF46L, 0x7198540DL, 0x83F3D70EL, 0x90A324FAL,
0x62C8A7F9L, 0xB602C312L, 0x44694011L, 0x5739B3E5L, 0xA55230E6L,
0xFB410CC2L, 0x092A8FC1L, 0x1A7A7C35L, 0xE811FF36L, 0x3CDB9BDDL,
0xCEB018DEL, 0xDDE0EB2AL, 0x2F8B6829L, 0x82F63B78L, 0x709DB87BL,
0x63CD4B8FL, 0x91A6C88CL, 0x456CAC67L, 0xB7072F64L, 0xA457DC90L,
0x563C5F93L, 0x082F63B7L, 0xFA44E0B4L, 0xE9141340L, 0x1B7F9043L,
0xCFB5F4A8L, 0x3DDE77ABL, 0x2E8E845FL, 0xDCE5075CL, 0x92A8FC17L,
0x60C37F14L, 0x73938CE0L, 0x81F80FE3L, 0x55326B08L, 0xA759E80BL,
0xB4091BFFL, 0x466298FCL, 0x1871A4D8L, 0xEA1A27DBL, 0xF94AD42FL,
0x0B21572CL, 0xDFEB33C7L, 0x2D80B0C4L, 0x3ED04330L, 0xCCBBC033L,
0xA24BB5A6L, 0x502036A5L, 0x4370C551L, 0xB11B4652L, 0x65D122B9L,
0x97BAA1BAL, 0x84EA524EL, 0x7681D14DL, 0x2892ED69L, 0xDAF96E6AL,
0xC9A99D9EL, 0x3BC21E9DL, 0xEF087A76L, 0x1D63F975L, 0x0E330A81L,
0xFC588982L, 0xB21572C9L, 0x407EF1CAL, 0x532E023EL, 0xA145813DL,
0x758FE5D6L, 0x87E466D5L, 0x94B49521L, 0x66DF1622L, 0x38CC2A06L,
0xCAA7A905L, 0xD9F75AF1L, 0x2B9CD9F2L, 0xFF56BD19L, 0x0D3D3E1AL,
0x1E6DCDEEL, 0xEC064EEDL, 0xC38D26C4L, 0x31E6A5C7L, 0x22B65633L,
0xD0DDD530L, 0x0417B1DBL, 0xF67C32D8L, 0xE52CC12CL, 0x1747422FL,
0x49547E0BL, 0xBB3FFD08L, 0xA86F0EFCL, 0x5A048DFFL, 0x8ECEE914L,
0x7CA56A17L, 0x6FF599E3L, 0x9D9E1AE0L, 0xD3D3E1ABL, 0x21B862A8L,
0x32E8915CL, 0xC083125FL, 0x144976B4L, 0xE622F5B7L, 0xF5720643L,
0x07198540L, 0x590AB964L, 0xAB613A67L, 0xB831C993L, 0x4A5A4A90L,
0x9E902E7BL, 0x6CFBAD78L, 0x7FAB5E8CL, 0x8DC0DD8FL, 0xE330A81AL,
0x115B2B19L, 0x020BD8EDL, 0xF0605BEEL, 0x24AA3F05L, 0xD6C1BC06L,
0xC5914FF2L, 0x37FACCF1L, 0x69E9F0D5L, 0x9B8273D6L, 0x88D28022L,
0x7AB90321L, 0xAE7367CAL, 0x5C18E4C9L, 0x4F48173DL, 0xBD23943EL,
0xF36E6F75L, 0x0105EC76L, 0x12551F82L, 0xE03E9C81L, 0x34F4F86AL,
0xC69F7B69L, 0xD5CF889DL, 0x27A40B9EL, 0x79B737BAL, 0x8BDCB4B9L,
0x988C474DL, 0x6AE7C44EL, 0xBE2DA0A5L, 0x4C4623A6L, 0x5F16D052L,
0xAD7D5351L
};
/*
* This a generic crc32() function, it takes seed as an argument,
* and does __not__ xor at the end. Then individual users can do
* whatever they need.
*/
uint32_t crypt_crc32(uint32_t seed, const unsigned char *buf, size_t len)
static uint32_t compute_crc32(
const uint32_t *crc32_tab,
uint32_t seed,
const unsigned char *buf,
size_t len)
{
uint32_t crc = seed;
const unsigned char *p = buf;
@@ -112,3 +171,13 @@ uint32_t crypt_crc32(uint32_t seed, const unsigned char *buf, size_t len)
return crc;
}
uint32_t crypt_crc32(uint32_t seed, const unsigned char *buf, size_t len)
{
return compute_crc32(crc32_tab, seed, buf, len);
}
uint32_t crypt_crc32c(uint32_t seed, const unsigned char *buf, size_t len)
{
return compute_crc32(crc32c_tab, seed, buf, len);
}

View File

@@ -21,6 +21,7 @@
#ifndef _CRYPTO_BACKEND_H
#define _CRYPTO_BACKEND_H
#include <assert.h>
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
@@ -88,6 +89,7 @@ int crypt_pbkdf_perf(const char *kdf, const char *hash,
/* CRC32 */
uint32_t crypt_crc32(uint32_t seed, const unsigned char *buf, size_t len);
uint32_t crypt_crc32c(uint32_t seed, const unsigned char *buf, size_t len);
/* Base64 */
int crypt_base64_encode(char **out, size_t *out_length, const char *in, size_t in_length);
@@ -152,4 +154,7 @@ static inline void crypt_backend_memzero(void *s, size_t n)
/* Memcmp helper (memcmp in constant time) */
int crypt_backend_memeq(const void *m1, const void *m2, size_t n);
/* crypto backend running in FIPS mode */
bool crypt_fips_mode(void);
#endif /* _CRYPTO_BACKEND_H */

View File

@@ -22,7 +22,6 @@
#include <string.h>
#include <stdio.h>
#include <errno.h>
#include <assert.h>
#include <gcrypt.h>
#include "crypto_backend_internal.h"
@@ -555,3 +554,20 @@ int crypt_backend_memeq(const void *m1, const void *m2, size_t n)
{
return crypt_internal_memeq(m1, m2, n);
}
#if !ENABLE_FIPS
bool crypt_fips_mode(void) { return false; }
#else
bool crypt_fips_mode(void)
{
static bool fips_mode = false, fips_checked = false;
if (fips_checked)
return fips_mode;
fips_mode = gcry_fips_mode_active();
fips_checked = true;
return fips_mode;
}
#endif /* ENABLE FIPS */

View File

@@ -421,3 +421,8 @@ int crypt_backend_memeq(const void *m1, const void *m2, size_t n)
{
return crypt_internal_memeq(m1, m2, n);
}
bool crypt_fips_mode(void)
{
return false;
}

View File

@@ -453,3 +453,8 @@ int crypt_backend_memeq(const void *m1, const void *m2, size_t n)
/* The logic is inverse to memcmp... */
return !memeql_sec(m1, m2, n);
}
bool crypt_fips_mode(void)
{
return false;
}

View File

@@ -400,3 +400,8 @@ int crypt_backend_memeq(const void *m1, const void *m2, size_t n)
{
return NSS_SecureMemcmp(m1, m2, n);
}
bool crypt_fips_mode(void)
{
return false;
}

View File

@@ -812,3 +812,29 @@ int crypt_backend_memeq(const void *m1, const void *m2, size_t n)
{
return CRYPTO_memcmp(m1, m2, n);
}
#if !ENABLE_FIPS
bool crypt_fips_mode(void) { return false; }
#else
static bool openssl_fips_mode(void)
{
#if OPENSSL_VERSION_MAJOR >= 3
return EVP_default_properties_is_fips_enabled(NULL);
#else
return FIPS_mode();
#endif
}
bool crypt_fips_mode(void)
{
static bool fips_mode = false, fips_checked = false;
if (fips_checked)
return fips_mode;
fips_mode = openssl_fips_mode();
fips_checked = true;
return fips_mode;
}
#endif /* ENABLE FIPS */

View File

@@ -28,7 +28,6 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include <assert.h>
#include <errno.h>
#include <endian.h>

1057
lib/fvault2/fvault2.c Normal file

File diff suppressed because it is too large Load Diff

80
lib/fvault2/fvault2.h Normal file
View File

@@ -0,0 +1,80 @@
/*
* FVAULT2 (FileVault2-compatible) volume handling
*
* Copyright (C) 2021-2022 Pavel Tobias
*
* This file is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This file is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this file; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#ifndef _CRYPTSETUP_FVAULT2_H
#define _CRYPTSETUP_FVAULT2_H
#include <stddef.h>
#include <stdint.h>
#define FVAULT2_WRAPPED_KEY_SIZE 24
#define FVAULT2_PBKDF2_SALT_SIZE 16
#define FVAULT2_UUID_LEN 37
struct crypt_device;
struct volume_key;
struct fvault2_params {
const char *cipher;
const char *cipher_mode;
uint16_t key_size;
uint32_t pbkdf2_iters;
char pbkdf2_salt[FVAULT2_PBKDF2_SALT_SIZE];
char wrapped_kek[FVAULT2_WRAPPED_KEY_SIZE];
char wrapped_vk[FVAULT2_WRAPPED_KEY_SIZE];
char family_uuid[FVAULT2_UUID_LEN];
char ph_vol_uuid[FVAULT2_UUID_LEN];
uint64_t log_vol_off;
uint64_t log_vol_size;
};
int FVAULT2_read_metadata(
struct crypt_device *cd,
struct fvault2_params *params);
int FVAULT2_get_volume_key(
struct crypt_device *cd,
const char *passphrase,
size_t passphrase_len,
const struct fvault2_params *params,
struct volume_key **vol_key);
int FVAULT2_dump(
struct crypt_device *cd,
struct device *device,
const struct fvault2_params *params);
int FVAULT2_activate_by_passphrase(
struct crypt_device *cd,
const char *name,
const char *passphrase,
size_t passphrase_len,
const struct fvault2_params *params,
uint32_t flags);
int FVAULT2_activate_by_volume_key(
struct crypt_device *cd,
const char *name,
const char *key,
size_t key_size,
const struct fvault2_params *params,
uint32_t flags);
#endif

View File

@@ -31,6 +31,7 @@
#include <unistd.h>
#include <inttypes.h>
#include <fcntl.h>
#include <assert.h>
#include "nls.h"
#include "bitops.h"
@@ -38,7 +39,6 @@
#include "utils_crypt.h"
#include "utils_loop.h"
#include "utils_dm.h"
#include "utils_fips.h"
#include "utils_keyring.h"
#include "utils_io.h"
#include "crypto_backend/crypto_backend.h"
@@ -178,8 +178,7 @@ int init_crypto(struct crypt_device *ctx);
int crypt_get_debug_level(void);
int crypt_memlock_inc(struct crypt_device *ctx);
int crypt_memlock_dec(struct crypt_device *ctx);
void crypt_process_priority(struct crypt_device *cd, int *priority, bool raise);
int crypt_metadata_locking_enabled(void);

488
lib/keyslot_context.c Normal file
View File

@@ -0,0 +1,488 @@
/*
* LUKS - Linux Unified Key Setup, keyslot unlock helpers
*
* Copyright (C) 2022 Red Hat, Inc. All rights reserved.
* Copyright (C) 2022 Ondrej Kozina
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <errno.h>
#include "luks1/luks.h"
#include "luks2/luks2.h"
#include "keyslot_context.h"
static int get_luks2_key_by_passphrase(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
int segment,
struct volume_key **r_vk)
{
int r;
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_PASSPHRASE);
assert(r_vk);
r = LUKS2_keyslot_open(cd, keyslot, segment, kc->u.p.passphrase, kc->u.p.passphrase_size, r_vk);
if (r < 0)
kc->error = r;
return r;
}
static int get_luks1_volume_key_by_passphrase(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
struct volume_key **r_vk)
{
int r;
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_PASSPHRASE);
assert(r_vk);
r = LUKS_open_key_with_hdr(keyslot, kc->u.p.passphrase, kc->u.p.passphrase_size,
crypt_get_hdr(cd, CRYPT_LUKS1), r_vk, cd);
if (r < 0)
kc->error = r;
return r;
}
static int get_luks2_volume_key_by_passphrase(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
struct volume_key **r_vk)
{
return get_luks2_key_by_passphrase(cd, kc, keyslot, CRYPT_DEFAULT_SEGMENT, r_vk);
}
static int get_passphrase_by_passphrase(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
const char **r_passphrase,
size_t *r_passphrase_size)
{
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_PASSPHRASE);
assert(r_passphrase);
assert(r_passphrase_size);
*r_passphrase = kc->u.p.passphrase;
*r_passphrase_size = kc->u.p.passphrase_size;
return 0;
}
static int get_passphrase_by_keyfile(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
const char **r_passphrase,
size_t *r_passphrase_size)
{
int r;
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_KEYFILE);
assert(r_passphrase);
assert(r_passphrase_size);
if (!kc->i_passphrase) {
r = crypt_keyfile_device_read(cd, kc->u.kf.keyfile,
&kc->i_passphrase, &kc->i_passphrase_size,
kc->u.kf.keyfile_offset, kc->u.kf.keyfile_size, 0);
if (r < 0) {
kc->error = r;
return r;
}
}
*r_passphrase = kc->i_passphrase;
*r_passphrase_size = kc->i_passphrase_size;
return 0;
}
static int get_luks2_key_by_keyfile(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
int segment,
struct volume_key **r_vk)
{
int r;
const char *passphrase;
size_t passphrase_size;
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_KEYFILE);
assert(r_vk);
r = get_passphrase_by_keyfile(cd, kc, &passphrase, &passphrase_size);
if (r)
return r;
r = LUKS2_keyslot_open(cd, keyslot, segment, passphrase, passphrase_size, r_vk);
if (r < 0)
kc->error = r;
return r;
}
static int get_luks2_volume_key_by_keyfile(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
struct volume_key **r_vk)
{
return get_luks2_key_by_keyfile(cd, kc, keyslot, CRYPT_DEFAULT_SEGMENT, r_vk);
}
static int get_luks1_volume_key_by_keyfile(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
struct volume_key **r_vk)
{
int r;
const char *passphrase;
size_t passphrase_size;
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_KEYFILE);
assert(r_vk);
r = get_passphrase_by_keyfile(cd, kc, &passphrase, &passphrase_size);
if (r)
return r;
r = LUKS_open_key_with_hdr(keyslot, passphrase, passphrase_size,
crypt_get_hdr(cd, CRYPT_LUKS1), r_vk, cd);
if (r < 0)
kc->error = r;
return r;
}
static int get_key_by_key(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot __attribute__((unused)),
int segment __attribute__((unused)),
struct volume_key **r_vk)
{
assert(kc && kc->type == CRYPT_KC_TYPE_KEY);
assert(r_vk);
if (!kc->u.k.volume_key) {
kc->error = -ENOENT;
return kc->error;
}
*r_vk = crypt_alloc_volume_key(kc->u.k.volume_key_size, kc->u.k.volume_key);
if (!*r_vk) {
kc->error = -ENOMEM;
return kc->error;
}
return 0;
}
static int get_volume_key_by_key(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot __attribute__((unused)),
struct volume_key **r_vk)
{
return get_key_by_key(cd, kc, -2 /* unused */, -2 /* unused */, r_vk);
}
static int get_luks2_key_by_token(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot __attribute__((unused)),
int segment,
struct volume_key **r_vk)
{
int r;
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_TOKEN);
assert(r_vk);
r = LUKS2_token_unlock_key(cd, crypt_get_hdr(cd, CRYPT_LUKS2), kc->u.t.id, kc->u.t.type,
kc->u.t.pin, kc->u.t.pin_size, segment, kc->u.t.usrptr, r_vk);
if (r < 0)
kc->error = r;
return r;
}
static int get_luks2_volume_key_by_token(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot __attribute__((unused)),
struct volume_key **r_vk)
{
return get_luks2_key_by_token(cd, kc, -2 /* unused */, CRYPT_DEFAULT_SEGMENT, r_vk);
}
static int get_passphrase_by_token(struct crypt_device *cd,
struct crypt_keyslot_context *kc,
const char **r_passphrase,
size_t *r_passphrase_size)
{
int r;
assert(cd);
assert(kc && kc->type == CRYPT_KC_TYPE_TOKEN);
assert(r_passphrase);
assert(r_passphrase_size);
if (!kc->i_passphrase) {
r = LUKS2_token_unlock_passphrase(cd, crypt_get_hdr(cd, CRYPT_LUKS2), kc->u.t.id,
kc->u.t.type, kc->u.t.pin, kc->u.t.pin_size,
kc->u.t.usrptr, &kc->i_passphrase, &kc->i_passphrase_size);
if (r < 0) {
kc->error = r;
return r;
}
kc->u.t.id = r;
}
*r_passphrase = kc->i_passphrase;
*r_passphrase_size = kc->i_passphrase_size;
return kc->u.t.id;
}
static void unlock_method_init_internal(struct crypt_keyslot_context *kc)
{
assert(kc);
kc->error = 0;
kc->i_passphrase = NULL;
kc->i_passphrase_size = 0;
}
void crypt_keyslot_unlock_by_key_init_internal(struct crypt_keyslot_context *kc,
const char *volume_key,
size_t volume_key_size)
{
assert(kc);
kc->type = CRYPT_KC_TYPE_KEY;
kc->u.k.volume_key = volume_key;
kc->u.k.volume_key_size = volume_key_size;
kc->get_luks2_key = get_key_by_key;
kc->get_luks2_volume_key = get_volume_key_by_key;
kc->get_luks1_volume_key = get_volume_key_by_key;
kc->get_passphrase = NULL; /* keyslot key context does not provide passphrase */
unlock_method_init_internal(kc);
}
void crypt_keyslot_unlock_by_passphrase_init_internal(struct crypt_keyslot_context *kc,
const char *passphrase,
size_t passphrase_size)
{
assert(kc);
kc->type = CRYPT_KC_TYPE_PASSPHRASE;
kc->u.p.passphrase = passphrase;
kc->u.p.passphrase_size = passphrase_size;
kc->get_luks2_key = get_luks2_key_by_passphrase;
kc->get_luks2_volume_key = get_luks2_volume_key_by_passphrase;
kc->get_luks1_volume_key = get_luks1_volume_key_by_passphrase;
kc->get_passphrase = get_passphrase_by_passphrase;
unlock_method_init_internal(kc);
}
void crypt_keyslot_unlock_by_keyfile_init_internal(struct crypt_keyslot_context *kc,
const char *keyfile,
size_t keyfile_size,
uint64_t keyfile_offset)
{
assert(kc);
kc->type = CRYPT_KC_TYPE_KEYFILE;
kc->u.kf.keyfile = keyfile;
kc->u.kf.keyfile_size = keyfile_size;
kc->u.kf.keyfile_offset = keyfile_offset;
kc->get_luks2_key = get_luks2_key_by_keyfile;
kc->get_luks2_volume_key = get_luks2_volume_key_by_keyfile;
kc->get_luks1_volume_key = get_luks1_volume_key_by_keyfile;
kc->get_passphrase = get_passphrase_by_keyfile;
unlock_method_init_internal(kc);
}
void crypt_keyslot_unlock_by_token_init_internal(struct crypt_keyslot_context *kc,
int token,
const char *type,
const char *pin,
size_t pin_size,
void *usrptr)
{
assert(kc);
kc->type = CRYPT_KC_TYPE_TOKEN;
kc->u.t.id = token;
kc->u.t.type = type;
kc->u.t.pin = pin;
kc->u.t.pin_size = pin_size;
kc->u.t.usrptr = usrptr;
kc->get_luks2_key = get_luks2_key_by_token;
kc->get_luks2_volume_key = get_luks2_volume_key_by_token;
kc->get_luks1_volume_key = NULL; /* LUKS1 is not supported */
kc->get_passphrase = get_passphrase_by_token;
unlock_method_init_internal(kc);
}
void crypt_keyslot_context_destroy_internal(struct crypt_keyslot_context *kc)
{
if (!kc)
return;
crypt_safe_free(kc->i_passphrase);
kc->i_passphrase = NULL;
kc->i_passphrase_size = 0;
}
void crypt_keyslot_context_free(struct crypt_keyslot_context *kc)
{
crypt_keyslot_context_destroy_internal(kc);
free(kc);
}
int crypt_keyslot_context_init_by_passphrase(struct crypt_device *cd,
const char *passphrase,
size_t passphrase_size,
struct crypt_keyslot_context **kc)
{
struct crypt_keyslot_context *tmp;
if (!kc || !passphrase)
return -EINVAL;
tmp = malloc(sizeof(*tmp));
if (!tmp)
return -ENOMEM;
crypt_keyslot_unlock_by_passphrase_init_internal(tmp, passphrase, passphrase_size);
*kc = tmp;
return 0;
}
int crypt_keyslot_context_init_by_keyfile(struct crypt_device *cd,
const char *keyfile,
size_t keyfile_size,
uint64_t keyfile_offset,
struct crypt_keyslot_context **kc)
{
struct crypt_keyslot_context *tmp;
if (!kc || !keyfile)
return -EINVAL;
tmp = malloc(sizeof(*tmp));
if (!tmp)
return -ENOMEM;
crypt_keyslot_unlock_by_keyfile_init_internal(tmp, keyfile, keyfile_size, keyfile_offset);
*kc = tmp;
return 0;
}
int crypt_keyslot_context_init_by_token(struct crypt_device *cd,
int token,
const char *type,
const char *pin, size_t pin_size,
void *usrptr,
struct crypt_keyslot_context **kc)
{
struct crypt_keyslot_context *tmp;
if (!kc || (token < 0 && token != CRYPT_ANY_TOKEN))
return -EINVAL;
tmp = malloc(sizeof(*tmp));
if (!tmp)
return -ENOMEM;
crypt_keyslot_unlock_by_token_init_internal(tmp, token, type, pin, pin_size, usrptr);
*kc = tmp;
return 0;
}
int crypt_keyslot_context_init_by_volume_key(struct crypt_device *cd,
const char *volume_key,
size_t volume_key_size,
struct crypt_keyslot_context **kc)
{
struct crypt_keyslot_context *tmp;
if (!kc)
return -EINVAL;
tmp = malloc(sizeof(*tmp));
if (!tmp)
return -ENOMEM;
crypt_keyslot_unlock_by_key_init_internal(tmp, volume_key, volume_key_size);
*kc = tmp;
return 0;
}
int crypt_keyslot_context_get_error(struct crypt_keyslot_context *kc)
{
return kc ? kc->error : -EINVAL;
}
int crypt_keyslot_context_set_pin(struct crypt_device *cd,
const char *pin, size_t pin_size,
struct crypt_keyslot_context *kc)
{
if (!kc || kc->type != CRYPT_KC_TYPE_TOKEN)
return -EINVAL;
kc->u.t.pin = pin;
kc->u.t.pin_size = pin_size;
kc->error = 0;
return 0;
}
int crypt_keyslot_context_get_type(const struct crypt_keyslot_context *kc)
{
return kc ? kc->type : -EINVAL;
}
const char *keyslot_context_type_string(const struct crypt_keyslot_context *kc)
{
assert(kc);
switch (kc->type) {
case CRYPT_KC_TYPE_PASSPHRASE:
return "passphrase";
case CRYPT_KC_TYPE_KEYFILE:
return "keyfile";
case CRYPT_KC_TYPE_TOKEN:
return "token";
case CRYPT_KC_TYPE_KEY:
return "key";
default:
return "<unknown>";
}
}

111
lib/keyslot_context.h Normal file
View File

@@ -0,0 +1,111 @@
/*
* LUKS - Linux Unified Key Setup, keyslot unlock helpers
*
* Copyright (C) 2022 Red Hat, Inc. All rights reserved.
* Copyright (C) 2022 Ondrej Kozina
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#ifndef KEYSLOT_CONTEXT_H
#define KEYSLOT_CONTEXT_H
#include <stdbool.h>
#include <stdint.h>
#include "internal.h"
typedef int (*keyslot_context_get_key) (
struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
int segment,
struct volume_key **r_vk);
typedef int (*keyslot_context_get_volume_key) (
struct crypt_device *cd,
struct crypt_keyslot_context *kc,
int keyslot,
struct volume_key **r_vk);
typedef int (*keyslot_context_get_passphrase) (
struct crypt_device *cd,
struct crypt_keyslot_context *kc,
const char **r_passphrase,
size_t *r_passphrase_size);
/* crypt_keyslot_context */
struct crypt_keyslot_context {
int type;
union {
struct {
const char *passphrase;
size_t passphrase_size;
} p;
struct {
const char *keyfile;
uint64_t keyfile_offset;
size_t keyfile_size;
} kf;
struct {
int id;
const char *type;
const char *pin;
size_t pin_size;
void *usrptr;
} t;
struct {
const char *volume_key;
size_t volume_key_size;
} k;
} u;
int error;
char *i_passphrase;
size_t i_passphrase_size;
keyslot_context_get_key get_luks2_key;
keyslot_context_get_volume_key get_luks1_volume_key;
keyslot_context_get_volume_key get_luks2_volume_key;
keyslot_context_get_passphrase get_passphrase;
};
void crypt_keyslot_context_destroy_internal(struct crypt_keyslot_context *method);
void crypt_keyslot_unlock_by_key_init_internal(struct crypt_keyslot_context *kc,
const char *volume_key,
size_t volume_key_size);
void crypt_keyslot_unlock_by_passphrase_init_internal(struct crypt_keyslot_context *kc,
const char *passphrase,
size_t passphrase_size);
void crypt_keyslot_unlock_by_keyfile_init_internal(struct crypt_keyslot_context *kc,
const char *keyfile,
size_t keyfile_size,
uint64_t keyfile_offset);
void crypt_keyslot_unlock_by_token_init_internal(struct crypt_keyslot_context *kc,
int token,
const char *type,
const char *pin,
size_t pin_size,
void *usrptr);
const char *keyslot_context_type_string(const struct crypt_keyslot_context *kc);
#endif /* KEYSLOT_CONTEXT_H */

View File

@@ -46,6 +46,7 @@ extern "C" {
*/
struct crypt_device; /* crypt device handle */
struct crypt_keyslot_context;
/**
* Initialize crypt device handle and check if the provided device exists.
@@ -344,6 +345,7 @@ void crypt_set_iteration_time(struct crypt_device *cd, uint64_t iteration_time_m
/**
* Helper to lock/unlock memory to avoid swap sensitive data to disk.
* \b Deprecated, only for backward compatibility. Memory with keys are locked automatically.
*
* @param cd crypt device handle, can be @e NULL
* @param lock 0 to unlock otherwise lock memory
@@ -353,7 +355,7 @@ void crypt_set_iteration_time(struct crypt_device *cd, uint64_t iteration_time_m
* @note Only root can do this.
* @note It locks/unlocks all process memory, not only crypt context.
*/
int crypt_memory_lock(struct crypt_device *cd, int lock);
int crypt_memory_lock(struct crypt_device *cd, int lock) __attribute__((deprecated));
/**
* Set global lock protection for on-disk metadata (file-based locking).
@@ -427,6 +429,8 @@ int crypt_get_metadata_size(struct crypt_device *cd,
#define CRYPT_INTEGRITY "INTEGRITY"
/** BITLK (BitLocker-compatible mode) */
#define CRYPT_BITLK "BITLK"
/** FVAULT2 (FileVault2-compatible mode) */
#define CRYPT_FVAULT2 "FVAULT2"
/** LUKS any version */
#define CRYPT_LUKS NULL
@@ -1106,6 +1110,187 @@ int crypt_keyslot_add_by_key(struct crypt_device *cd,
size_t passphrase_size,
uint32_t flags);
/**
* @defgroup crypt-keyslot-context Crypt keyslot context
* @addtogroup crypt-keyslot-context
* @{
*/
/**
* Release crypt keyslot context and used memory.
*
* @param kc crypt keyslot context
*/
void crypt_keyslot_context_free(struct crypt_keyslot_context *kc);
/**
* Initialize keyslot context via passphrase.
*
* @param cd crypt device handle initialized to LUKS device context
* @param passphrase passphrase for a keyslot
* @param passphrase_size size of passphrase
* @param kc returns crypt keyslot context handle type CRYPT_KC_TYPE_PASSPHRASE
*
* @return zero on success or negative errno otherwise.
*/
int crypt_keyslot_context_init_by_passphrase(struct crypt_device *cd,
const char *passphrase,
size_t passphrase_size,
struct crypt_keyslot_context **kc);
/**
* Initialize keyslot context via key file path.
*
* @param cd crypt device handle initialized to LUKS device context
*
* @param keyfile key file with passphrase for a keyslot
* @param keyfile_size number of bytes to read from keyfile, @e 0 is unlimited
* @param keyfile_offset number of bytes to skip at start of keyfile
* @param kc returns crypt keyslot context handle type CRYPT_KC_TYPE_KEYFILE
*
* @return zero on success or negative errno otherwise.
*/
int crypt_keyslot_context_init_by_keyfile(struct crypt_device *cd,
const char *keyfile,
size_t keyfile_size,
uint64_t keyfile_offset,
struct crypt_keyslot_context **kc);
/**
* Initialize keyslot context via LUKS2 token.
*
* @param cd crypt device handle initialized to LUKS2 device context
*
* @param token token providing passphrase for a keyslot or CRYPT_ANY_TOKEN
* @param type restrict type of token, if @e NULL all types are allowed
* @param pin passphrase (or PIN) to unlock token (may be binary data)
* @param pin_size size of @e pin
* @param usrptr provided identification in callback
* @param kc returns crypt keyslot context handle type CRYPT_KC_TYPE_TOKEN
*
* @return zero on success or negative errno otherwise.
*/
int crypt_keyslot_context_init_by_token(struct crypt_device *cd,
int token,
const char *type,
const char *pin, size_t pin_size,
void *usrptr,
struct crypt_keyslot_context **kc);
/**
* Initialize keyslot context via key.
*
* @param cd crypt device handle initialized to LUKS device context
*
* @param volume_key provided volume key or @e NULL if used after crypt_format
* or with CRYPT_VOLUME_KEY_NO_SEGMENT flag
* @param volume_key_size size of volume_key
* @param kc returns crypt keyslot context handle type CRYPT_KC_TYPE_KEY
*
* @return zero on success or negative errno otherwise.
*/
int crypt_keyslot_context_init_by_volume_key(struct crypt_device *cd,
const char *volume_key,
size_t volume_key_size,
struct crypt_keyslot_context **kc);
/**
* Get error code per keyslot context from last failed call.
*
* @note If @link crypt_keyslot_add_by_keyslot_context @endlink passed with
* no negative return code. The return value of this function is undefined.
*
* @param kc keyslot context involved in failed @link crypt_keyslot_add_by_keyslot_context @endlink
*
* @return Negative errno if keyslot context caused a failure, zero otherwise.
*/
int crypt_keyslot_context_get_error(struct crypt_keyslot_context *kc);
/**
* Set new pin to token based keyslot context.
*
* @note Use when @link crypt_keyslot_add_by_keyslot_context @endlink failed
* and token keyslot context returned -ENOANO error code via
* @link crypt_keyslot_context_get_error @endlink.
*
* @param cd crypt device handle initialized to LUKS2 device context
* @param pin passphrase (or PIN) to unlock token (may be binary data)
* @param pin_size size of @e pin
* @param kc LUKS2 keyslot context (only @link CRYPT_KC_TYPE_TOKEN @endlink is allowed)
*
* @return zero on success or negative errno otherwise
*/
int crypt_keyslot_context_set_pin(struct crypt_device *cd,
const char *pin, size_t pin_size,
struct crypt_keyslot_context *kc);
/**
* @defgroup crypt-keyslot-context-types Crypt keyslot context
* @addtogroup crypt-keyslot-context-types
* @{
*/
/** keyslot context initialized by passphrase (@link crypt_keyslot_context_init_by_passphrase @endlink) */
#define CRYPT_KC_TYPE_PASSPHRASE INT16_C(1)
/** keyslot context initialized by keyfile (@link crypt_keyslot_context_init_by_keyfile @endlink) */
#define CRYPT_KC_TYPE_KEYFILE INT16_C(2)
/** keyslot context initialized by token (@link crypt_keyslot_context_init_by_token @endlink) */
#define CRYPT_KC_TYPE_TOKEN INT16_C(3)
/** keyslot context initialized by volume key or unbound key (@link crypt_keyslot_context_init_by_volume_key @endlink) */
#define CRYPT_KC_TYPE_KEY INT16_C(4)
/** @} */
/**
* Get type identifier for crypt keyslot context.
*
* @param kc keyslot context
*
* @return crypt keyslot context type id (see @link crypt-keyslot-context-types @endlink) or negative errno otherwise.
*/
int crypt_keyslot_context_get_type(const struct crypt_keyslot_context *kc);
/** @} */
/**
* Add key slot by volume key provided by keyslot context (kc). New
* keyslot will be protected by passphrase provided by new keyslot context (new_kc).
* See @link crypt-keyslot-context @endlink for context initialization routines.
*
* @pre @e cd contains initialized and formatted LUKS device context.
*
* @param cd crypt device handle
* @param keyslot_existing existing keyslot or CRYPT_ANY_SLOT to get volume key from.
* @param kc keyslot context providing volume key.
* @param keyslot_new new keyslot or CRYPT_ANY_SLOT (first free number is used).
* @param new_kc keyslot context providing passphrase for new keyslot.
* @param flags key flags to set
*
* @return allocated key slot number or negative errno otherwise.
*
* @note new_kc can not be @e CRYPT_KC_TYPE_KEY type keyslot context.
*
* @note For kc parameter with type @e CRYPT_KC_TYPE_KEY the keyslot_existing
* parameter is ignored.
*
* @note in case there is no active LUKS keyslot to get existing volume key from, one of following must apply:
* @li @e cd must be device handle used in crypt_format() by current process (it holds reference to generated volume key)
* @li kc must be of @e CRYPT_KC_TYPE_KEY type with valid volume key.
*
* @note With CRYPT_VOLUME_KEY_NO_SEGMENT flag raised and kc of type @e CRYPT_KC_TYPE_KEY with @e volume_key set to @e NULL
* the new volume_key will be generated and stored in new keyslot. The keyslot will become unbound (unusable to
* dm-crypt device activation).
*
* @warning CRYPT_VOLUME_KEY_SET flag force updates volume key. It is @b not @b reencryption!
* By doing so you will most probably destroy your ciphertext data device. It's supposed
* to be used only in wrapped keys scheme for key refresh process where real (inner) volume
* key stays untouched. It may be involed on active @e keyslot which makes the (previously
* unbound) keyslot new regular keyslot.
*/
int crypt_keyslot_add_by_keyslot_context(struct crypt_device *cd,
int keyslot_existing,
struct crypt_keyslot_context *kc,
int keyslot_new,
struct crypt_keyslot_context *new_kc,
uint32_t flags);
/**
* Destroy (and disable) key slot.
*
@@ -1182,6 +1367,8 @@ int crypt_keyslot_destroy(struct crypt_device *cd, int keyslot);
#define CRYPT_ACTIVATE_NO_WRITE_WORKQUEUE (UINT32_C(1) << 25)
/** dm-integrity: reset automatic recalculation */
#define CRYPT_ACTIVATE_RECALCULATE_RESET (UINT32_C(1) << 26)
/** dm-verity: try to use tasklets */
#define CRYPT_ACTIVATE_TASKLETS (UINT32_C(1) << 27)
/**
* Active device runtime attributes
@@ -1471,6 +1658,9 @@ int crypt_deactivate(struct crypt_device *cd, const char *name);
* @note For TCRYPT cipher chain is the volume key concatenated
* for all ciphers in chain.
* @note For VERITY the volume key means root hash used for activation.
* @note For LUKS devices, if passphrase is @e NULL and volume key is cached in
* device context it returns the volume key generated in preceding
* @link crypt_format @endlink call.
*/
int crypt_volume_key_get(struct crypt_device *cd,
int keyslot,
@@ -1479,6 +1669,41 @@ int crypt_volume_key_get(struct crypt_device *cd,
const char *passphrase,
size_t passphrase_size);
/**
* Get volume key from crypt device by keyslot context.
*
* @param cd crypt device handle
* @param keyslot use this keyslot or @e CRYPT_ANY_SLOT
* @param volume_key buffer for volume key
* @param volume_key_size on input, size of buffer @e volume_key,
* on output size of @e volume_key
* @param kc keyslot context used to unlock volume key
*
* @return unlocked key slot number or negative errno otherwise.
*
* @note See @link crypt-keyslot-context-types @endlink for info on keyslot
* context initialization.
* @note For TCRYPT cipher chain is the volume key concatenated
* for all ciphers in chain (kc may be NULL).
* @note For VERITY the volume key means root hash used for activation
* (kc may be NULL).
* @note For LUKS devices, if kc is @e NULL and volume key is cached in
* device context it returns the volume key generated in preceding
* @link crypt_format @endlink call.
* @note @link CRYPT_KC_TYPE_TOKEN @endlink keyslot context is usable only with LUKS2 devices.
* @note @link CRYPT_KC_TYPE_KEY @endlink keyslot context can not be used.
* @note To get LUKS2 unbound key, keyslot parameter must not be @e CRYPT_ANY_SLOT.
* @note EPERM errno means provided keyslot context could not unlock any (or selected)
* keyslot.
* @note ENOENT errno means no LUKS keyslot is available to retrieve volume key from
* and there's no cached volume key in device handle.
*/
int crypt_volume_key_get_by_keyslot_context(struct crypt_device *cd,
int keyslot,
char *volume_key,
size_t *volume_key_size,
struct crypt_keyslot_context *kc);
/**
* Verify that provided volume key is valid for crypt device.
*

View File

@@ -8,3 +8,4 @@ Description: cryptsetup library
Version: @LIBCRYPTSETUP_VERSION@
Cflags: -I${includedir}
Libs: -L${libdir} -lcryptsetup
Requires.private: @PKGMODULES@

View File

@@ -151,3 +151,17 @@ CRYPTSETUP_2.5 {
crypt_get_subsystem;
crypt_resume_by_token_pin;
} CRYPTSETUP_2.4;
CRYPTSETUP_2.6 {
global:
crypt_keyslot_context_free;
crypt_keyslot_context_init_by_passphrase;
crypt_keyslot_context_init_by_keyfile;
crypt_keyslot_context_init_by_token;
crypt_keyslot_context_init_by_volume_key;
crypt_keyslot_context_get_error;
crypt_keyslot_context_set_pin;
crypt_keyslot_context_get_type;
crypt_keyslot_add_by_keyslot_context;
crypt_volume_key_get_by_keyslot_context;
} CRYPTSETUP_2.5;

View File

@@ -31,7 +31,6 @@
#ifdef HAVE_SYS_SYSMACROS_H
# include <sys/sysmacros.h> /* for major, minor */
#endif
#include <assert.h>
#include "internal.h"
#define DM_CRYPT_TARGET "crypt"
@@ -205,6 +204,9 @@ static void _dm_set_verity_compat(struct crypt_device *cd,
if (_dm_satisfies_version(1, 7, 0, verity_maj, verity_min, verity_patch))
_dm_flags |= DM_VERITY_PANIC_CORRUPTION_SUPPORTED;
if (_dm_satisfies_version(1, 9, 0, verity_maj, verity_min, verity_patch))
_dm_flags |= DM_VERITY_TASKLETS_SUPPORTED;
_dm_verity_checked = true;
}
@@ -473,27 +475,22 @@ static size_t int_log10(uint64_t x)
return r;
}
#define CLEN 64 /* 2*MAX_CIPHER_LEN */
#define CLENS "63" /* for sscanf length + '\0' */
#define CAPIL 144 /* should be enough to fit whole capi string */
#define CAPIS "143" /* for sscanf of crypto API string + 16 + \0 */
static int cipher_c2dm(const char *org_c, const char *org_i, unsigned tag_size,
static int cipher_dm2c(const char *org_c, const char *org_i, unsigned tag_size,
char *c_dm, int c_dm_size,
char *i_dm, int i_dm_size)
{
int c_size = 0, i_size = 0, i;
char cipher[CLEN], mode[CLEN], iv[CLEN+1], tmp[CLEN];
char capi[CAPIL];
char cipher[MAX_CAPI_ONE_LEN], mode[MAX_CAPI_ONE_LEN], iv[MAX_CAPI_ONE_LEN+1],
tmp[MAX_CAPI_ONE_LEN], capi[MAX_CAPI_LEN];
if (!c_dm || !c_dm_size || !i_dm || !i_dm_size)
return -EINVAL;
i = sscanf(org_c, "%" CLENS "[^-]-%" CLENS "s", cipher, tmp);
i = sscanf(org_c, "%" MAX_CAPI_ONE_LEN_STR "[^-]-%" MAX_CAPI_ONE_LEN_STR "s", cipher, tmp);
if (i != 2)
return -EINVAL;
i = sscanf(tmp, "%" CLENS "[^-]-%" CLENS "s", mode, iv);
i = sscanf(tmp, "%" MAX_CAPI_ONE_LEN_STR "[^-]-%" MAX_CAPI_ONE_LEN_STR "s", mode, iv);
if (i == 1) {
memset(iv, 0, sizeof(iv));
strncpy(iv, mode, sizeof(iv)-1);
@@ -540,75 +537,6 @@ static int cipher_c2dm(const char *org_c, const char *org_i, unsigned tag_size,
return 0;
}
static int cipher_dm2c(char **org_c, char **org_i, const char *c_dm, const char *i_dm)
{
char cipher[CLEN], mode[CLEN], iv[CLEN], auth[CLEN];
char tmp[CAPIL], dmcrypt_tmp[CAPIL*2], capi[CAPIL+1];
size_t len;
int i;
if (!c_dm)
return -EINVAL;
/* legacy mode */
if (strncmp(c_dm, "capi:", 4)) {
if (!(*org_c = strdup(c_dm)))
return -ENOMEM;
*org_i = NULL;
return 0;
}
/* modes with capi: prefix */
i = sscanf(c_dm, "capi:%" CAPIS "[^-]-%" CLENS "s", tmp, iv);
if (i != 2)
return -EINVAL;
len = strlen(tmp);
if (len < 2)
return -EINVAL;
if (tmp[len-1] == ')')
tmp[len-1] = '\0';
if (sscanf(tmp, "rfc4309(%" CAPIS "s", capi) == 1) {
if (!(*org_i = strdup("aead")))
return -ENOMEM;
} else if (sscanf(tmp, "rfc7539(%" CAPIS "[^,],%" CLENS "s", capi, auth) == 2) {
if (!(*org_i = strdup(auth)))
return -ENOMEM;
} else if (sscanf(tmp, "authenc(%" CLENS "[^,],%" CAPIS "s", auth, capi) == 2) {
if (!(*org_i = strdup(auth)))
return -ENOMEM;
} else {
if (i_dm) {
if (!(*org_i = strdup(i_dm)))
return -ENOMEM;
} else
*org_i = NULL;
memset(capi, 0, sizeof(capi));
strncpy(capi, tmp, sizeof(capi)-1);
}
i = sscanf(capi, "%" CLENS "[^(](%" CLENS "[^)])", mode, cipher);
if (i == 2)
i = snprintf(dmcrypt_tmp, sizeof(dmcrypt_tmp), "%s-%s-%s", cipher, mode, iv);
else
i = snprintf(dmcrypt_tmp, sizeof(dmcrypt_tmp), "%s-%s", capi, iv);
if (i < 0 || (size_t)i >= sizeof(dmcrypt_tmp)) {
free(*org_i);
*org_i = NULL;
return -EINVAL;
}
if (!(*org_c = strdup(dmcrypt_tmp))) {
free(*org_i);
*org_i = NULL;
return -ENOMEM;
}
return 0;
}
static char *_uf(char *buf, size_t buf_size, const char *s, unsigned u)
{
size_t r = snprintf(buf, buf_size, " %s:%u", s, u);
@@ -626,7 +554,7 @@ static char *get_dm_crypt_params(const struct dm_target *tgt, uint32_t flags)
if (!tgt)
return NULL;
r = cipher_c2dm(tgt->u.crypt.cipher, tgt->u.crypt.integrity, tgt->u.crypt.tag_size,
r = cipher_dm2c(tgt->u.crypt.cipher, tgt->u.crypt.integrity, tgt->u.crypt.tag_size,
cipher_dm, sizeof(cipher_dm), integrity_dm, sizeof(integrity_dm));
if (r < 0)
return NULL;
@@ -734,6 +662,8 @@ static char *get_dm_verity_params(const struct dm_target *tgt, uint32_t flags)
num_options++;
if (flags & CRYPT_ACTIVATE_CHECK_AT_MOST_ONCE)
num_options++;
if (flags & CRYPT_ACTIVATE_TASKLETS)
num_options++;
max_fec_size = (tgt->u.verity.fec_device ? strlen(device_block_path(tgt->u.verity.fec_device)) : 0) + 256;
fec_features = crypt_safe_alloc(max_fec_size);
@@ -764,13 +694,14 @@ static char *get_dm_verity_params(const struct dm_target *tgt, uint32_t flags)
} else
*verity_verify_args = '\0';
if (num_options) { /* MAX length int32 + 18 + 22 + 20 + 19 + 19 */
r = snprintf(features, sizeof(features), " %d%s%s%s%s%s", num_options,
if (num_options) { /* MAX length int32 + 18 + 22 + 20 + 19 + 19 + 22 */
r = snprintf(features, sizeof(features), " %d%s%s%s%s%s%s", num_options,
(flags & CRYPT_ACTIVATE_IGNORE_CORRUPTION) ? " ignore_corruption" : "",
(flags & CRYPT_ACTIVATE_RESTART_ON_CORRUPTION) ? " restart_on_corruption" : "",
(flags & CRYPT_ACTIVATE_PANIC_ON_CORRUPTION) ? " panic_on_corruption" : "",
(flags & CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS) ? " ignore_zero_blocks" : "",
(flags & CRYPT_ACTIVATE_CHECK_AT_MOST_ONCE) ? " check_at_most_once" : "");
(flags & CRYPT_ACTIVATE_CHECK_AT_MOST_ONCE) ? " check_at_most_once" : "",
(flags & CRYPT_ACTIVATE_TASKLETS) ? " try_verify_in_tasklet" : "");
if (r < 0 || (size_t)r >= sizeof(features))
goto out;
} else
@@ -1670,16 +1601,94 @@ int dm_create_device(struct crypt_device *cd, const char *name,
return -ENOTSUP;
r = _dm_create_device(cd, name, type, dmd);
if (r < 0 && dm_flags(cd, dmd->segment.type, &dmt_flags))
if (!r || r == -EEXIST)
goto out;
if (r && (dmd->segment.type == DM_CRYPT || dmd->segment.type == DM_LINEAR || dmd->segment.type == DM_ZERO) &&
if (dm_flags(cd, dmd->segment.type, &dmt_flags))
goto out;
if ((dmd->segment.type == DM_CRYPT || dmd->segment.type == DM_LINEAR || dmd->segment.type == DM_ZERO) &&
check_retry(cd, &dmd->flags, dmt_flags)) {
log_dbg(cd, "Retrying open without incompatible options.");
r = _dm_create_device(cd, name, type, dmd);
if (!r || r == -EEXIST)
goto out;
}
if (dmd->flags & (CRYPT_ACTIVATE_SAME_CPU_CRYPT|CRYPT_ACTIVATE_SUBMIT_FROM_CRYPT_CPUS) &&
!(dmt_flags & (DM_SAME_CPU_CRYPT_SUPPORTED|DM_SUBMIT_FROM_CRYPT_CPUS_SUPPORTED))) {
log_err(cd, _("Requested dm-crypt performance options are not supported."));
r = -EINVAL;
}
if (dmd->flags & (CRYPT_ACTIVATE_NO_READ_WORKQUEUE | CRYPT_ACTIVATE_NO_WRITE_WORKQUEUE) &&
!(dmt_flags & DM_CRYPT_NO_WORKQUEUE_SUPPORTED)) {
log_err(cd, _("Requested dm-crypt performance options are not supported."));
r = -EINVAL;
}
if (dmd->flags & (CRYPT_ACTIVATE_IGNORE_CORRUPTION|
CRYPT_ACTIVATE_RESTART_ON_CORRUPTION|
CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS|
CRYPT_ACTIVATE_CHECK_AT_MOST_ONCE) &&
!(dmt_flags & DM_VERITY_ON_CORRUPTION_SUPPORTED)) {
log_err(cd, _("Requested dm-verity data corruption handling options are not supported."));
r = -EINVAL;
}
if (dmd->flags & CRYPT_ACTIVATE_TASKLETS &&
!(dmt_flags & DM_VERITY_TASKLETS_SUPPORTED)) {
log_err(cd, _("Requested dm-verity tasklets option is not supported."));
r = -EINVAL;
}
if (dmd->flags & CRYPT_ACTIVATE_PANIC_ON_CORRUPTION &&
!(dmt_flags & DM_VERITY_PANIC_CORRUPTION_SUPPORTED)) {
log_err(cd, _("Requested dm-verity data corruption handling options are not supported."));
r = -EINVAL;
}
if (dmd->segment.type == DM_VERITY &&
dmd->segment.u.verity.fec_device && !(dmt_flags & DM_VERITY_FEC_SUPPORTED)) {
log_err(cd, _("Requested dm-verity FEC options are not supported."));
r = -EINVAL;
}
if (dmd->segment.type == DM_CRYPT) {
if (dmd->segment.u.crypt.integrity && !(dmt_flags & DM_INTEGRITY_SUPPORTED)) {
log_err(cd, _("Requested data integrity options are not supported."));
r = -EINVAL;
}
if (dmd->segment.u.crypt.sector_size != SECTOR_SIZE && !(dmt_flags & DM_SECTOR_SIZE_SUPPORTED)) {
log_err(cd, _("Requested sector_size option is not supported."));
r = -EINVAL;
}
}
if (dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_RECALCULATE) &&
!(dmt_flags & DM_INTEGRITY_RECALC_SUPPORTED)) {
log_err(cd, _("Requested automatic recalculation of integrity tags is not supported."));
r = -EINVAL;
}
if (dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_RECALCULATE_RESET) &&
!(dmt_flags & DM_INTEGRITY_RESET_RECALC_SUPPORTED)) {
log_err(cd, _("Requested automatic recalculation of integrity tags is not supported."));
r = -EINVAL;
}
if (dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_ALLOW_DISCARDS) &&
!(dmt_flags & DM_INTEGRITY_DISCARDS_SUPPORTED)) {
log_err(cd, _("Discard/TRIM is not supported."));
r = -EINVAL;
}
if (dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_NO_JOURNAL_BITMAP) &&
!(dmt_flags & DM_INTEGRITY_BITMAP_SUPPORTED)) {
log_err(cd, _("Requested dm-integrity bitmap mode is not supported."));
r = -EINVAL;
}
out:
/*
* Print warning if activating dm-crypt cipher_null device unless it's reencryption helper or
* keyslot encryption helper device (LUKS1 cipher_null devices).
@@ -1688,54 +1697,6 @@ int dm_create_device(struct crypt_device *cd, const char *name,
crypt_is_cipher_null(dmd->segment.u.crypt.cipher))
log_dbg(cd, "Activated dm-crypt device with cipher_null. Device is not encrypted.");
if (r == -EINVAL &&
dmd->flags & (CRYPT_ACTIVATE_SAME_CPU_CRYPT|CRYPT_ACTIVATE_SUBMIT_FROM_CRYPT_CPUS) &&
!(dmt_flags & (DM_SAME_CPU_CRYPT_SUPPORTED|DM_SUBMIT_FROM_CRYPT_CPUS_SUPPORTED)))
log_err(cd, _("Requested dm-crypt performance options are not supported."));
if (r == -EINVAL &&
dmd->flags & (CRYPT_ACTIVATE_NO_READ_WORKQUEUE | CRYPT_ACTIVATE_NO_WRITE_WORKQUEUE) &&
!(dmt_flags & DM_CRYPT_NO_WORKQUEUE_SUPPORTED))
log_err(cd, _("Requested dm-crypt performance options are not supported."));
if (r == -EINVAL && dmd->flags & (CRYPT_ACTIVATE_IGNORE_CORRUPTION|
CRYPT_ACTIVATE_RESTART_ON_CORRUPTION|
CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS|
CRYPT_ACTIVATE_CHECK_AT_MOST_ONCE) &&
!(dmt_flags & DM_VERITY_ON_CORRUPTION_SUPPORTED))
log_err(cd, _("Requested dm-verity data corruption handling options are not supported."));
if (r == -EINVAL && dmd->flags & CRYPT_ACTIVATE_PANIC_ON_CORRUPTION &&
!(dmt_flags & DM_VERITY_PANIC_CORRUPTION_SUPPORTED))
log_err(cd, _("Requested dm-verity data corruption handling options are not supported."));
if (r == -EINVAL && dmd->segment.type == DM_VERITY &&
dmd->segment.u.verity.fec_device && !(dmt_flags & DM_VERITY_FEC_SUPPORTED))
log_err(cd, _("Requested dm-verity FEC options are not supported."));
if (r == -EINVAL && dmd->segment.type == DM_CRYPT) {
if (dmd->segment.u.crypt.integrity && !(dmt_flags & DM_INTEGRITY_SUPPORTED))
log_err(cd, _("Requested data integrity options are not supported."));
if (dmd->segment.u.crypt.sector_size != SECTOR_SIZE && !(dmt_flags & DM_SECTOR_SIZE_SUPPORTED))
log_err(cd, _("Requested sector_size option is not supported."));
}
if (r == -EINVAL && dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_RECALCULATE) &&
!(dmt_flags & DM_INTEGRITY_RECALC_SUPPORTED))
log_err(cd, _("Requested automatic recalculation of integrity tags is not supported."));
if (r == -EINVAL && dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_RECALCULATE_RESET) &&
!(dmt_flags & DM_INTEGRITY_RESET_RECALC_SUPPORTED))
log_err(cd, _("Requested automatic recalculation of integrity tags is not supported."));
if (r == -EINVAL && dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_ALLOW_DISCARDS) &&
!(dmt_flags & DM_INTEGRITY_DISCARDS_SUPPORTED))
log_err(cd, _("Discard/TRIM is not supported."));
if (r == -EINVAL && dmd->segment.type == DM_INTEGRITY && (dmd->flags & CRYPT_ACTIVATE_NO_JOURNAL_BITMAP) &&
!(dmt_flags & DM_INTEGRITY_BITMAP_SUPPORTED))
log_err(cd, _("Requested dm-integrity bitmap mode is not supported."));
out:
dm_exit_context();
return r;
}
@@ -2030,9 +1991,7 @@ static int _dm_target_query_crypt(struct crypt_device *cd, uint32_t get_flags,
/* cipher */
if (get_flags & DM_ACTIVE_CRYPT_CIPHER) {
r = cipher_dm2c(CONST_CAST(char**)&cipher,
CONST_CAST(char**)&integrity,
rcipher, rintegrity);
r = crypt_capi_to_cipher(&cipher, &integrity, rcipher, rintegrity);
if (r < 0)
goto err;
}
@@ -2265,6 +2224,8 @@ static int _dm_target_query_verity(struct crypt_device *cd,
*act_flags |= CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS;
else if (!strcasecmp(arg, "check_at_most_once"))
*act_flags |= CRYPT_ACTIVATE_CHECK_AT_MOST_ONCE;
else if (!strcasecmp(arg, "try_verify_in_tasklet"))
*act_flags |= CRYPT_ACTIVATE_TASKLETS;
else if (!strcasecmp(arg, "use_fec_from_device")) {
str = strsep(&params, " ");
str2 = crypt_lookup_dev(str);
@@ -2736,7 +2697,7 @@ static int _dm_query_device(struct crypt_device *cd, const char *name,
goto out;
}
/* Never allow to return empty key */
/* Never allow one to return empty key */
if ((get_flags & DM_ACTIVE_CRYPT_KEY) && dmi.suspended) {
log_dbg(cd, "Cannot read volume key while suspended.");
r = -EINVAL;
@@ -2818,7 +2779,8 @@ int dm_query_device(struct crypt_device *cd, const char *name,
return r;
}
static int _process_deps(struct crypt_device *cd, const char *prefix, struct dm_deps *deps, char **names, size_t names_offset, size_t names_length)
static int _process_deps(struct crypt_device *cd, const char *prefix, struct dm_deps *deps,
char **names, size_t names_offset, size_t names_length)
{
#if HAVE_DECL_DM_DEVICE_GET_NAME
struct crypt_dm_active_device dmd;
@@ -2864,7 +2826,8 @@ static int _process_deps(struct crypt_device *cd, const char *prefix, struct dm_
#endif
}
int dm_device_deps(struct crypt_device *cd, const char *name, const char *prefix, char **names, size_t names_length)
int dm_device_deps(struct crypt_device *cd, const char *name, const char *prefix,
char **names, size_t names_length)
{
struct dm_task *dmt;
struct dm_info dmi;

View File

@@ -28,7 +28,6 @@
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <assert.h>
#include <uuid/uuid.h>
#include "luks.h"
@@ -232,11 +231,12 @@ int LUKS_hdr_backup(const char *backup_file, struct crypt_device *ctx)
hdr_size = LUKS_device_sectors(&hdr) << SECTOR_SHIFT;
buffer_size = size_round_up(hdr_size, crypt_getpagesize());
buffer = crypt_safe_alloc(buffer_size);
buffer = malloc(buffer_size);
if (!buffer || hdr_size < LUKS_ALIGN_KEYSLOTS || hdr_size > buffer_size) {
r = -ENOMEM;
goto out;
}
memset(buffer, 0, buffer_size);
log_dbg(ctx, "Storing backup of header (%zu bytes) and keyslot area (%zu bytes).",
sizeof(hdr), hdr_size - LUKS_ALIGN_KEYSLOTS);
@@ -280,7 +280,8 @@ int LUKS_hdr_backup(const char *backup_file, struct crypt_device *ctx)
r = 0;
out:
crypt_safe_memzero(&hdr, sizeof(hdr));
crypt_safe_free(buffer);
crypt_safe_memzero(buffer, buffer_size);
free(buffer);
return r;
}
@@ -308,7 +309,7 @@ int LUKS_hdr_restore(
goto out;
}
buffer = crypt_safe_alloc(buffer_size);
buffer = malloc(buffer_size);
if (!buffer) {
r = -ENOMEM;
goto out;
@@ -379,7 +380,8 @@ int LUKS_hdr_restore(
r = LUKS_read_phdr(hdr, 1, 0, ctx);
out:
device_sync(ctx, device);
crypt_safe_free(buffer);
crypt_safe_memzero(buffer, buffer_size);
free(buffer);
return r;
}
@@ -1227,6 +1229,10 @@ int LUKS_wipe_header_areas(struct luks_phdr *hdr,
uint64_t offset, length;
size_t wipe_block;
r = LUKS_check_device_size(ctx, hdr, 1);
if (r)
return r;
/* Wipe complete header, keyslots and padding areas with zeroes. */
offset = 0;
length = (uint64_t)hdr->payloadOffset * SECTOR_SIZE;

View File

@@ -121,6 +121,7 @@ struct luks2_hdr {
uint8_t salt2[LUKS2_SALT_L];
char uuid[LUKS2_UUID_L];
void *jobj;
void *jobj_rollback;
};
struct luks2_keyslot_params {
@@ -167,6 +168,7 @@ int LUKS2_hdr_version_unlocked(struct crypt_device *cd,
int LUKS2_hdr_read(struct crypt_device *cd, struct luks2_hdr *hdr, int repair);
int LUKS2_hdr_write(struct crypt_device *cd, struct luks2_hdr *hdr);
int LUKS2_hdr_write_force(struct crypt_device *cd, struct luks2_hdr *hdr);
int LUKS2_hdr_rollback(struct crypt_device *cd, struct luks2_hdr *hdr);
int LUKS2_hdr_dump(struct crypt_device *cd, struct luks2_hdr *hdr);
int LUKS2_hdr_dump_json(struct crypt_device *cd, struct luks2_hdr *hdr, const char **json);
@@ -283,13 +285,13 @@ int LUKS2_token_open_and_activate(struct crypt_device *cd,
uint32_t flags,
void *usrptr);
int LUKS2_token_unlock_volume_key(struct crypt_device *cd,
int LUKS2_token_unlock_key(struct crypt_device *cd,
struct luks2_hdr *hdr,
int token,
const char *type,
const char *pin,
size_t pin_size,
uint32_t flags,
int segment,
void *usrptr,
struct volume_key **vk);
@@ -300,6 +302,16 @@ int LUKS2_token_keyring_get(struct luks2_hdr *hdr,
int LUKS2_token_keyring_json(char *buffer, size_t buffer_size,
const struct crypt_token_params_luks2_keyring *keyring_params);
int LUKS2_token_unlock_passphrase(struct crypt_device *cd,
struct luks2_hdr *hdr,
int token,
const char *type,
const char *pin,
size_t pin_size,
void *usrptr,
char **passphrase,
size_t *passphrase_size);
void crypt_token_unload_external_all(struct crypt_device *cd);
/*

View File

@@ -19,8 +19,6 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <assert.h>
#include "luks2_internal.h"
/*

View File

@@ -189,6 +189,8 @@ void keyring_dump(struct crypt_device *cd, const char *json);
int keyring_validate(struct crypt_device *cd, const char *json);
void keyring_buffer_free(void *buffer, size_t buffer_size);
struct crypt_token_handler_v2 {
const char *name;
crypt_token_open_func open;

View File

@@ -21,7 +21,6 @@
#include "luks2_internal.h"
#include <uuid/uuid.h>
#include <assert.h>
struct area {
uint64_t offset;
@@ -363,6 +362,10 @@ int LUKS2_wipe_header_areas(struct crypt_device *cd,
wipe_block = 4096;
}
r = device_check_size(cd, crypt_metadata_device(cd), length, 1);
if (r)
return r;
log_dbg(cd, "Wiping LUKS areas (0x%06" PRIx64 " - 0x%06" PRIx64") with zeroes.",
offset, length + offset);

View File

@@ -22,7 +22,6 @@
#include "luks2_internal.h"
#include "../integrity/integrity.h"
#include <assert.h>
#include <ctype.h>
#include <uuid/uuid.h>
@@ -1110,6 +1109,33 @@ int LUKS2_hdr_validate(struct crypt_device *cd, json_object *hdr_jobj, uint64_t
return 0;
}
static bool hdr_json_free(json_object **jobj)
{
assert(jobj);
if (json_object_put(*jobj))
*jobj = NULL;
return (*jobj == NULL);
}
static int hdr_update_copy_for_rollback(struct crypt_device *cd, struct luks2_hdr *hdr)
{
json_object **jobj_copy;
assert(hdr);
assert(hdr->jobj);
jobj_copy = (json_object **)&hdr->jobj_rollback;
if (!hdr_json_free(jobj_copy)) {
log_dbg(cd, "LUKS2 rollback metadata copy still in use");
return -EINVAL;
}
return json_object_copy(hdr->jobj, jobj_copy) ? -ENOMEM : 0;
}
/* FIXME: should we expose do_recovery parameter explicitly? */
int LUKS2_hdr_read(struct crypt_device *cd, struct luks2_hdr *hdr, int repair)
{
@@ -1141,6 +1167,9 @@ int LUKS2_hdr_read(struct crypt_device *cd, struct luks2_hdr *hdr, int repair)
} else
device_read_unlock(cd, crypt_metadata_device(cd));
if (!r && (r = hdr_update_copy_for_rollback(cd, hdr)))
log_dbg(cd, "Failed to update rollback LUKS2 metadata.");
return r;
}
@@ -1153,18 +1182,50 @@ static int hdr_cleanup_and_validate(struct crypt_device *cd, struct luks2_hdr *h
int LUKS2_hdr_write_force(struct crypt_device *cd, struct luks2_hdr *hdr)
{
int r;
if (hdr_cleanup_and_validate(cd, hdr))
return -EINVAL;
return LUKS2_disk_hdr_write(cd, hdr, crypt_metadata_device(cd), false);
r = LUKS2_disk_hdr_write(cd, hdr, crypt_metadata_device(cd), false);
if (!r && (r = hdr_update_copy_for_rollback(cd, hdr)))
log_dbg(cd, "Failed to update rollback LUKS2 metadata.");
return r;
}
int LUKS2_hdr_write(struct crypt_device *cd, struct luks2_hdr *hdr)
{
int r;
if (hdr_cleanup_and_validate(cd, hdr))
return -EINVAL;
return LUKS2_disk_hdr_write(cd, hdr, crypt_metadata_device(cd), true);
r = LUKS2_disk_hdr_write(cd, hdr, crypt_metadata_device(cd), true);
if (!r && (r = hdr_update_copy_for_rollback(cd, hdr)))
log_dbg(cd, "Failed to update rollback LUKS2 metadata.");
return r;
}
int LUKS2_hdr_rollback(struct crypt_device *cd, struct luks2_hdr *hdr)
{
json_object **jobj_copy;
assert(hdr->jobj_rollback);
log_dbg(cd, "Rolling back in-memory LUKS2 json metadata.");
jobj_copy = (json_object **)&hdr->jobj;
if (!hdr_json_free(jobj_copy)) {
log_dbg(cd, "LUKS2 header still in use");
return -EINVAL;
}
return json_object_copy(hdr->jobj_rollback, jobj_copy) ? -ENOMEM : 0;
}
int LUKS2_hdr_uuid(struct crypt_device *cd, struct luks2_hdr *hdr, const char *uuid)
@@ -1201,10 +1262,19 @@ int LUKS2_hdr_labels(struct crypt_device *cd, struct luks2_hdr *hdr,
void LUKS2_hdr_free(struct crypt_device *cd, struct luks2_hdr *hdr)
{
if (json_object_put(hdr->jobj))
hdr->jobj = NULL;
else if (hdr->jobj)
json_object **jobj;
assert(hdr);
jobj = (json_object **)&hdr->jobj;
if (!hdr_json_free(jobj))
log_dbg(cd, "LUKS2 header still in use");
jobj = (json_object **)&hdr->jobj_rollback;
if (!hdr_json_free(jobj))
log_dbg(cd, "LUKS2 rollback metadata copy still in use");
}
static uint64_t LUKS2_keyslots_size_jobj(json_object *jobj)
@@ -1246,7 +1316,7 @@ int LUKS2_hdr_backup(struct crypt_device *cd, struct luks2_hdr *hdr,
hdr_size = LUKS2_hdr_and_areas_size(hdr);
buffer_size = size_round_up(hdr_size, crypt_getpagesize());
buffer = crypt_safe_alloc(buffer_size);
buffer = malloc(buffer_size);
if (!buffer)
return -ENOMEM;
@@ -1257,23 +1327,22 @@ int LUKS2_hdr_backup(struct crypt_device *cd, struct luks2_hdr *hdr,
if (r) {
log_err(cd, _("Failed to acquire read lock on device %s."),
device_path(crypt_metadata_device(cd)));
crypt_safe_free(buffer);
return r;
goto out;
}
devfd = device_open_locked(cd, device, O_RDONLY);
if (devfd < 0) {
device_read_unlock(cd, device);
log_err(cd, _("Device %s is not a valid LUKS device."), device_path(device));
crypt_safe_free(buffer);
return devfd == -1 ? -EINVAL : devfd;
r = (devfd == -1) ? -EINVAL : devfd;
goto out;
}
if (read_lseek_blockwise(devfd, device_block_size(cd, device),
device_alignment(device), buffer, hdr_size, 0) < hdr_size) {
device_read_unlock(cd, device);
crypt_safe_free(buffer);
return -EIO;
r = -EIO;
goto out;
}
device_read_unlock(cd, device);
@@ -1284,8 +1353,8 @@ int LUKS2_hdr_backup(struct crypt_device *cd, struct luks2_hdr *hdr,
log_err(cd, _("Requested header backup file %s already exists."), backup_file);
else
log_err(cd, _("Cannot create header backup file %s."), backup_file);
crypt_safe_free(buffer);
return -EINVAL;
r = -EINVAL;
goto out;
}
ret = write_buffer(fd, buffer, buffer_size);
close(fd);
@@ -1294,8 +1363,9 @@ int LUKS2_hdr_backup(struct crypt_device *cd, struct luks2_hdr *hdr,
r = -EIO;
} else
r = 0;
crypt_safe_free(buffer);
out:
crypt_safe_memzero(buffer, buffer_size);
free(buffer);
return r;
}
@@ -1306,8 +1376,7 @@ int LUKS2_hdr_restore(struct crypt_device *cd, struct luks2_hdr *hdr,
int r, fd, devfd = -1, diff_uuid = 0;
ssize_t ret, buffer_size = 0;
char *buffer = NULL, msg[1024];
struct luks2_hdr hdr_file;
struct luks2_hdr tmp_hdr = {};
struct luks2_hdr hdr_file = {}, tmp_hdr = {};
uint32_t reqs = 0;
r = device_alloc(cd, &backup_device, backup_file);
@@ -1340,7 +1409,7 @@ int LUKS2_hdr_restore(struct crypt_device *cd, struct luks2_hdr *hdr,
}
buffer_size = LUKS2_hdr_and_areas_size(&hdr_file);
buffer = crypt_safe_alloc(buffer_size);
buffer = malloc(buffer_size);
if (!buffer) {
r = -ENOMEM;
goto out;
@@ -1440,10 +1509,9 @@ out:
LUKS2_hdr_free(cd, &tmp_hdr);
crypt_safe_memzero(&hdr_file, sizeof(hdr_file));
crypt_safe_memzero(&tmp_hdr, sizeof(tmp_hdr));
crypt_safe_free(buffer);
crypt_safe_memzero(buffer, buffer_size);
free(buffer);
device_sync(cd, device);
return r;
}

View File

@@ -31,6 +31,7 @@
/* Serialize memory-hard keyslot access: optional workaround for parallel processing */
#define MIN_MEMORY_FOR_SERIALIZE_LOCK_KB 32*1024 /* 32MB */
/* coverity[ -taint_source : arg-0 ] */
static int luks2_encrypt_to_storage(char *src, size_t srcLength,
const char *cipher, const char *cipher_mode,
struct volume_key *vk, unsigned int sector,
@@ -275,7 +276,11 @@ static int luks2_keyslot_set_key(struct crypt_device *cd,
return -ENOMEM;
}
r = AF_split(cd, volume_key, AfKey, volume_key_len, LUKS_STRIPES, af_hash);
r = crypt_hash_size(af_hash);
if (r < 0)
log_err(cd, _("Hash algorithm %s is not available."), af_hash);
else
r = AF_split(cd, volume_key, AfKey, volume_key_len, LUKS_STRIPES, af_hash);
if (r == 0) {
log_dbg(cd, "Updating keyslot area [0x%04" PRIx64 "].", area_offset);
@@ -379,8 +384,13 @@ static int luks2_keyslot_get_key(struct crypt_device *cd,
derived_key, (unsigned)(area_offset / SECTOR_SIZE), cd);
}
if (r == 0)
r = AF_merge(AfKey, volume_key, volume_key_len, LUKS_STRIPES, af_hash);
if (r == 0) {
r = crypt_hash_size(af_hash);
if (r < 0)
log_err(cd, _("Hash algorithm %s is not available."), af_hash);
else
r = AF_merge(AfKey, volume_key, volume_key_len, LUKS_STRIPES, af_hash);
}
out:
free(salt);
crypt_free_volume_key(derived_key);

View File

@@ -19,8 +19,6 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <assert.h>
#include "luks2_internal.h"
#include "utils_device_locking.h"
@@ -513,7 +511,8 @@ static json_object *reencrypt_make_hot_segments_forward(struct crypt_device *cd,
if (tmp < device_size) {
fixed_length = device_size - tmp;
jobj_old_seg = reencrypt_make_segment_old(cd, hdr, rh, data_offset + data_shift_value(&rh->rp), rh->offset + rh->length, rh->fixed_length ? &fixed_length : NULL);
jobj_old_seg = reencrypt_make_segment_old(cd, hdr, rh, data_offset + data_shift_value(&rh->rp),
rh->offset + rh->length, rh->fixed_length ? &fixed_length : NULL);
if (!jobj_old_seg)
goto err;
json_object_object_add_by_uint(jobj_segs_hot, sg, jobj_old_seg);
@@ -668,7 +667,8 @@ static json_object *reencrypt_make_hot_segments_backward(struct crypt_device *cd
if (tmp < device_size) {
fixed_length = device_size - tmp;
jobj_new_seg = reencrypt_make_segment_new(cd, hdr, rh, data_offset, rh->offset + rh->length, rh->offset + rh->length, rh->fixed_length ? &fixed_length : NULL);
jobj_new_seg = reencrypt_make_segment_new(cd, hdr, rh, data_offset, rh->offset + rh->length,
rh->offset + rh->length, rh->fixed_length ? &fixed_length : NULL);
if (!jobj_new_seg)
goto err;
json_object_object_add_by_uint(jobj_segs_hot, sg, jobj_new_seg);
@@ -846,6 +846,50 @@ void LUKS2_reencrypt_free(struct crypt_device *cd, struct luks2_reencrypt *rh)
crypt_unlock_internal(cd, rh->reenc_lock);
free(rh);
}
int LUKS2_reencrypt_max_hotzone_size(struct crypt_device *cd,
struct luks2_hdr *hdr,
const struct reenc_protection *rp,
int reencrypt_keyslot,
uint64_t *r_length)
{
#if USE_LUKS2_REENCRYPTION
int r;
uint64_t dummy, area_length;
assert(hdr);
assert(rp);
assert(r_length);
if (rp->type <= REENC_PROTECTION_NONE) {
*r_length = LUKS2_REENCRYPT_MAX_HOTZONE_LENGTH;
return 0;
}
if (rp->type == REENC_PROTECTION_DATASHIFT) {
*r_length = rp->p.ds.data_shift;
return 0;
}
r = LUKS2_keyslot_area(hdr, reencrypt_keyslot, &dummy, &area_length);
if (r < 0)
return -EINVAL;
if (rp->type == REENC_PROTECTION_JOURNAL) {
*r_length = area_length;
return 0;
}
if (rp->type == REENC_PROTECTION_CHECKSUM) {
*r_length = (area_length / rp->p.csum.hash_size) * rp->p.csum.block_size;
return 0;
}
return -EINVAL;
#else
return -ENOTSUP;
#endif
}
#if USE_LUKS2_REENCRYPTION
static size_t reencrypt_get_alignment(struct crypt_device *cd,
struct luks2_hdr *hdr)
@@ -892,7 +936,8 @@ static void _load_backup_segments(struct luks2_hdr *hdr,
rh->jobj_segment_moved = NULL;
}
static int reencrypt_offset_backward_moved(struct luks2_hdr *hdr, json_object *jobj_segments, uint64_t *reencrypt_length, uint64_t data_shift, uint64_t *offset)
static int reencrypt_offset_backward_moved(struct luks2_hdr *hdr, json_object *jobj_segments,
uint64_t *reencrypt_length, uint64_t data_shift, uint64_t *offset)
{
uint64_t tmp, linear_length = 0;
int sg, segs = json_segments_count(jobj_segments);
@@ -1474,7 +1519,8 @@ static int reencrypt_recover_segment(struct crypt_device *cd,
else
crash_iv_offset = json_segment_get_iv_offset(json_segments_get_segment(rh->jobj_segs_hot, rseg));
log_dbg(cd, "crash_offset: %" PRIu64 ", crash_length: %" PRIu64 ", crash_iv_offset: %" PRIu64, data_offset + rh->offset, rh->length, crash_iv_offset);
log_dbg(cd, "crash_offset: %" PRIu64 ", crash_length: %" PRIu64 ", crash_iv_offset: %" PRIu64,
data_offset + rh->offset, rh->length, crash_iv_offset);
r = crypt_storage_wrapper_init(cd, &cw2, crypt_data_device(cd),
data_offset + rh->offset, crash_iv_offset, new_sector_size,
@@ -1842,7 +1888,9 @@ static int reencrypt_assign_segments(struct crypt_device *cd,
return commit ? LUKS2_hdr_write(cd, hdr) : 0;
}
static int reencrypt_set_encrypt_segments(struct crypt_device *cd, struct luks2_hdr *hdr, uint64_t dev_size, uint64_t data_shift, bool move_first_segment, crypt_reencrypt_direction_info di)
static int reencrypt_set_encrypt_segments(struct crypt_device *cd, struct luks2_hdr *hdr,
uint64_t dev_size, uint64_t data_shift, bool move_first_segment,
crypt_reencrypt_direction_info di)
{
int r;
uint64_t first_segment_offset, first_segment_length,
@@ -1912,7 +1960,6 @@ static int reencrypt_set_encrypt_segments(struct crypt_device *cd, struct luks2_
static int reencrypt_set_decrypt_shift_segments(struct crypt_device *cd,
struct luks2_hdr *hdr,
uint64_t dev_size,
uint64_t data_shift,
uint64_t moved_segment_length,
crypt_reencrypt_direction_info di)
{
@@ -1922,7 +1969,7 @@ static int reencrypt_set_decrypt_shift_segments(struct crypt_device *cd,
data_offset = LUKS2_get_data_offset(hdr) << SECTOR_SHIFT;
json_object *jobj_segment_first = NULL, *jobj_segment_second = NULL, *jobj_segments;
if (!data_shift || di == CRYPT_REENCRYPT_BACKWARD)
if (di == CRYPT_REENCRYPT_BACKWARD)
return -ENOTSUP;
/*
@@ -1930,12 +1977,11 @@ static int reencrypt_set_decrypt_shift_segments(struct crypt_device *cd,
* [encrypted first segment (max data shift size)][gap (data shift size)][second encrypted data segment]
*/
first_segment_offset = 0;
if (dev_size > data_shift) {
first_segment_length = moved_segment_length;
first_segment_length = moved_segment_length;
if (dev_size > moved_segment_length) {
second_segment_offset = data_offset + first_segment_length;
second_segment_length = 0;
} else
first_segment_length = dev_size;
}
jobj_segments = json_object_new_object();
if (!jobj_segments)
@@ -1951,7 +1997,7 @@ static int reencrypt_set_decrypt_shift_segments(struct crypt_device *cd,
return r;
}
if (dev_size > data_shift) {
if (dev_size > moved_segment_length) {
jobj_segment_second = json_segment_create_crypt(second_segment_offset,
crypt_get_iv_offset(cd) + (first_segment_length >> SECTOR_SHIFT),
second_segment_length ? &second_segment_length : NULL,
@@ -2406,7 +2452,10 @@ static int reencrypt_make_backup_segments(struct crypt_device *cd,
return -EINVAL;
if (params->flags & CRYPT_REENCRYPT_MOVE_FIRST_SEGMENT) {
json_object_copy(LUKS2_get_segment_jobj(hdr, 0), &jobj_segment_bcp);
if (json_object_copy(LUKS2_get_segment_jobj(hdr, 0), &jobj_segment_bcp)) {
r = -EINVAL;
goto err;
}
r = LUKS2_segment_set_flag(jobj_segment_bcp, "backup-moved-segment");
if (r)
goto err;
@@ -2431,8 +2480,12 @@ static int reencrypt_make_backup_segments(struct crypt_device *cd,
json_segment_get_cipher(jobj_tmp),
json_segment_get_sector_size(jobj_tmp),
0);
} else
json_object_copy(LUKS2_get_segment_jobj(hdr, CRYPT_DEFAULT_SEGMENT), &jobj_segment_old);
} else {
if (json_object_copy(LUKS2_get_segment_jobj(hdr, CRYPT_DEFAULT_SEGMENT), &jobj_segment_old)) {
r = -EINVAL;
goto err;
}
}
} else if (params->mode == CRYPT_REENCRYPT_ENCRYPT) {
r = LUKS2_get_data_size(hdr, &tmp, NULL);
if (r)
@@ -2640,71 +2693,37 @@ static int reencrypt_verify_datashift_params(struct crypt_device *cd,
static int reencrypt_verify_resilience_params(struct crypt_device *cd,
const struct crypt_params_reencrypt *params,
uint32_t sector_size)
uint32_t sector_size, bool move_first_segment)
{
int r;
/* no change requested */
if (!params || !params->resilience)
return 0;
if (!strcmp(params->resilience, "journal"))
return 0;
return (params->data_shift || move_first_segment) ? -EINVAL : 0;
else if (!strcmp(params->resilience, "none"))
return 0;
return (params->data_shift || move_first_segment) ? -EINVAL : 0;
else if (!strcmp(params->resilience, "datashift"))
return reencrypt_verify_datashift_params(cd, params, sector_size);
else if (!strcmp(params->resilience, "checksum"))
else if (!strcmp(params->resilience, "checksum")) {
if (params->data_shift || move_first_segment)
return -EINVAL;
return reencrypt_verify_checksum_params(cd, params);
else if (!strcmp(params->resilience, "datashift-checksum")) {
r = reencrypt_verify_datashift_params(cd, params, sector_size);
return r ?: reencrypt_verify_checksum_params(cd, params);
} else if (!strcmp(params->resilience, "datashift-journal"))
} else if (!strcmp(params->resilience, "datashift-checksum")) {
if (!move_first_segment ||
reencrypt_verify_datashift_params(cd, params, sector_size))
return -EINVAL;
return reencrypt_verify_checksum_params(cd, params);
} else if (!strcmp(params->resilience, "datashift-journal")) {
if (!move_first_segment)
return -EINVAL;
return reencrypt_verify_datashift_params(cd, params, sector_size);
}
log_err(cd, _("Unsupported resilience mode %s"), params->resilience);
return -EINVAL;
}
int LUKS2_reencrypt_max_hotzone_size(struct crypt_device *cd,
struct luks2_hdr *hdr,
const struct reenc_protection *rp,
int reencrypt_keyslot,
uint64_t *r_length)
{
int r;
uint64_t dummy, area_length;
assert(hdr);
assert(rp);
assert(r_length);
if (rp->type <= REENC_PROTECTION_NONE) {
*r_length = LUKS2_REENCRYPT_MAX_HOTZONE_LENGTH;
return 0;
}
if (rp->type == REENC_PROTECTION_DATASHIFT) {
*r_length = rp->p.ds.data_shift;
return 0;
}
r = LUKS2_keyslot_area(hdr, reencrypt_keyslot, &dummy, &area_length);
if (r < 0)
return -EINVAL;
if (rp->type == REENC_PROTECTION_JOURNAL) {
*r_length = area_length;
return 0;
}
if (rp->type == REENC_PROTECTION_CHECKSUM) {
*r_length = (area_length / rp->p.csum.hash_size) * rp->p.csum.block_size;
return 0;
}
return -EINVAL;
}
static int reencrypt_decrypt_with_datashift_init(struct crypt_device *cd,
const char *name,
struct luks2_hdr *hdr,
@@ -2742,6 +2761,8 @@ static int reencrypt_decrypt_with_datashift_init(struct crypt_device *cd,
return -EINVAL;
}
log_dbg(cd, "Initializing decryption with datashift.");
data_shift = params->data_shift << SECTOR_SHIFT;
/*
@@ -2761,10 +2782,12 @@ static int reencrypt_decrypt_with_datashift_init(struct crypt_device *cd,
moved_segment_length = data_shift < LUKS2_DEFAULT_NONE_REENCRYPTION_LENGTH ?
data_shift : LUKS2_DEFAULT_NONE_REENCRYPTION_LENGTH;
r = reencrypt_set_decrypt_shift_segments(cd, hdr,
data_size, data_shift,
moved_segment_length,
params->direction);
if (moved_segment_length > data_size)
moved_segment_length = data_size;
r = reencrypt_set_decrypt_shift_segments(cd, hdr, data_size,
moved_segment_length,
params->direction);
if (r)
goto out;
@@ -2774,9 +2797,11 @@ static int reencrypt_decrypt_with_datashift_init(struct crypt_device *cd,
goto out;
}
r = reencrypt_verify_resilience_params(cd, params, sector_size);
if (r < 0)
r = reencrypt_verify_resilience_params(cd, params, sector_size, true);
if (r < 0) {
log_err(cd, _("Invalid reencryption resilience parameters."));
goto out;
}
r = LUKS2_keyslot_reencrypt_allocate(cd, hdr, reencrypt_keyslot,
params, reencrypt_get_alignment(cd, hdr));
@@ -2888,8 +2913,8 @@ out:
log_err(cd, _("Failed to resume device %s."), name);
device_release_excl(cd, crypt_data_device(cd));
if (r < 0 && crypt_load(cd, CRYPT_LUKS2, NULL) < 0)
log_dbg(cd, "Cannot reload context after failure.");
if (r < 0 && LUKS2_hdr_rollback(cd, hdr) < 0)
log_dbg(cd, "Failed to rollback LUKS2 metadata after failure.");
return r;
}
@@ -3039,7 +3064,7 @@ static int reencrypt_init(struct crypt_device *cd,
goto out;
}
r = reencrypt_verify_resilience_params(cd, params, check_sector_size);
r = reencrypt_verify_resilience_params(cd, params, check_sector_size, move_first_segment);
if (r < 0)
goto out;
@@ -3096,8 +3121,8 @@ static int reencrypt_init(struct crypt_device *cd,
r = reencrypt_keyslot;
out:
device_release_excl(cd, crypt_data_device(cd));
if (r < 0 && crypt_load(cd, CRYPT_LUKS2, NULL) < 0)
log_dbg(cd, "Cannot reload context after failure.");
if (r < 0 && LUKS2_hdr_rollback(cd, hdr) < 0)
log_dbg(cd, "Failed to rollback LUKS2 metadata after failure.");
return r;
}
@@ -3371,12 +3396,12 @@ static int reencrypt_load_by_passphrase(struct crypt_device *cd,
log_dbg(cd, "Loading LUKS2 reencryption context.");
old_sector_size = reencrypt_get_sector_size_old(hdr);
new_sector_size = reencrypt_get_sector_size_new(hdr);
sector_size = new_sector_size > old_sector_size ? new_sector_size : old_sector_size;
r = reencrypt_verify_resilience_params(cd, params, sector_size);
r = reencrypt_verify_resilience_params(cd, params, sector_size,
LUKS2_get_segment_id_by_flag(hdr, "backup-moved-segment") >= 0);
if (r < 0)
return r;

View File

@@ -21,7 +21,6 @@
*/
#include "luks2_internal.h"
#include <assert.h>
#define MAX_STR 64

View File

@@ -21,7 +21,6 @@
#include <ctype.h>
#include <dlfcn.h>
#include <assert.h>
#include "luks2_internal.h"
@@ -38,6 +37,7 @@ static struct crypt_token_handler_internal token_handlers[LUKS2_TOKENS_MAX] = {
.u = {
.v1 = { .name = LUKS2_TOKEN_KEYRING,
.open = keyring_open,
.buffer_free = keyring_buffer_free,
.validate = keyring_validate,
.dump = keyring_dump }
}
@@ -423,7 +423,8 @@ static const char *token_json_to_string(json_object *jobj_token)
JSON_C_TO_STRING_PLAIN | JSON_C_TO_STRING_NOSLASHESCAPE);
}
static int token_is_usable(struct luks2_hdr *hdr, json_object *jobj_token, int segment, crypt_keyslot_priority minimal_priority)
static int token_is_usable(struct luks2_hdr *hdr, json_object *jobj_token, int segment,
crypt_keyslot_priority minimal_priority, bool requires_keyslot)
{
crypt_keyslot_priority keyslot_priority;
json_object *jobj_array;
@@ -440,7 +441,13 @@ static int token_is_usable(struct luks2_hdr *hdr, json_object *jobj_token, int s
/* no assigned keyslot returns -ENOENT even for CRYPT_ANY_SEGMENT */
len = json_object_array_length(jobj_array);
if (len <= 0)
if (len < 0)
return -ENOENT;
if (!requires_keyslot)
return 0;
if (!len)
return -ENOENT;
for (i = 0; i < len; i++) {
@@ -471,7 +478,7 @@ static int translate_errno(struct crypt_device *cd, int ret_val, const char *typ
return ret_val;
}
static int LUKS2_token_open(struct crypt_device *cd,
static int token_open(struct crypt_device *cd,
struct luks2_hdr *hdr,
int token,
json_object *jobj_token,
@@ -482,7 +489,8 @@ static int LUKS2_token_open(struct crypt_device *cd,
size_t pin_size,
char **buffer,
size_t *buffer_len,
void *usrptr)
void *usrptr,
bool requires_keyslot)
{
const struct crypt_token_handler_v2 *h;
json_object *jobj_type;
@@ -499,10 +507,11 @@ static int LUKS2_token_open(struct crypt_device *cd,
return -ENOENT;
}
r = token_is_usable(hdr, jobj_token, segment, priority);
r = token_is_usable(hdr, jobj_token, segment, priority, requires_keyslot);
if (r < 0) {
if (r == -ENOENT)
log_dbg(cd, "Token %d unusable for segment %d with desired keyslot priority %d.", token, segment, priority);
log_dbg(cd, "Token %d unusable for segment %d with desired keyslot priority %d.",
token, segment, priority);
return r;
}
@@ -594,7 +603,8 @@ static int LUKS2_keyslot_open_by_token(struct crypt_device *cd,
return -EINVAL;
if (keyslot_priority < priority)
continue;
log_dbg(cd, "Trying to open keyslot %u with token %d (type %s).", num, token, json_object_get_string(jobj_type));
log_dbg(cd, "Trying to open keyslot %u with token %d (type %s).",
num, token, json_object_get_string(jobj_type));
r = LUKS2_keyslot_open(cd, num, segment, buffer, buffer_len, vk);
/* short circuit on fatal error */
if (r < 0 && r != -EPERM && r != -ENOENT)
@@ -615,7 +625,7 @@ static bool token_is_blocked(int token, uint32_t *block_list)
/* it is safe now, but have assert in case LUKS2_TOKENS_MAX grows */
assert(token >= 0 && (size_t)token < BITFIELD_SIZE(block_list));
return (*block_list & (1 << token));
return (*block_list & (UINT32_C(1) << token));
}
static void token_block(int token, uint32_t *block_list)
@@ -623,7 +633,7 @@ static void token_block(int token, uint32_t *block_list)
/* it is safe now, but have assert in case LUKS2_TOKENS_MAX grows */
assert(token >= 0 && (size_t)token < BITFIELD_SIZE(block_list));
*block_list |= (1 << token);
*block_list |= (UINT32_C(1) << token);
}
static int token_open_priority(struct crypt_device *cd,
@@ -650,7 +660,7 @@ static int token_open_priority(struct crypt_device *cd,
token = atoi(slot);
if (token_is_blocked(token, block_list))
continue;
r = LUKS2_token_open(cd, hdr, token, val, type, segment, priority, pin, pin_size, &buffer, &buffer_size, usrptr);
r = token_open(cd, hdr, token, val, type, segment, priority, pin, pin_size, &buffer, &buffer_size, usrptr, true);
if (!r) {
r = LUKS2_keyslot_open_by_token(cd, hdr, token, segment, priority,
buffer, buffer_size, vk);
@@ -669,7 +679,8 @@ static int token_open_priority(struct crypt_device *cd,
return *stored_retval;
}
static int token_open_any(struct crypt_device *cd, struct luks2_hdr *hdr, const char *type, int segment, const char *pin, size_t pin_size, void *usrptr, struct volume_key **vk)
static int token_open_any(struct crypt_device *cd, struct luks2_hdr *hdr, const char *type, int segment,
const char *pin, size_t pin_size, void *usrptr, struct volume_key **vk)
{
json_object *jobj_tokens;
int r, retval = -ENOENT;
@@ -681,41 +692,42 @@ static int token_open_any(struct crypt_device *cd, struct luks2_hdr *hdr, const
if (!type)
usrptr = NULL;
r = token_open_priority(cd, hdr, jobj_tokens, type, segment, CRYPT_SLOT_PRIORITY_PREFER, pin, pin_size, usrptr, &retval, &blocked, vk);
r = token_open_priority(cd, hdr, jobj_tokens, type, segment, CRYPT_SLOT_PRIORITY_PREFER,
pin, pin_size, usrptr, &retval, &blocked, vk);
if (break_loop_retval(r))
return r;
return token_open_priority(cd, hdr, jobj_tokens, type, segment, CRYPT_SLOT_PRIORITY_NORMAL, pin, pin_size, usrptr, &retval, &blocked, vk);
return token_open_priority(cd, hdr, jobj_tokens, type, segment, CRYPT_SLOT_PRIORITY_NORMAL,
pin, pin_size, usrptr, &retval, &blocked, vk);
}
int LUKS2_token_unlock_volume_key(struct crypt_device *cd,
int LUKS2_token_unlock_key(struct crypt_device *cd,
struct luks2_hdr *hdr,
int token,
const char *type,
const char *pin,
size_t pin_size,
uint32_t flags,
int segment,
void *usrptr,
struct volume_key **vk)
{
char *buffer;
size_t buffer_size;
json_object *jobj_token;
int segment, r = -ENOENT;
int r = -ENOENT;
assert(vk);
if (flags & CRYPT_ACTIVATE_ALLOW_UNBOUND_KEY)
segment = CRYPT_ANY_SEGMENT;
else {
if (segment == CRYPT_DEFAULT_SEGMENT)
segment = LUKS2_get_default_segment(hdr);
if (segment < 0)
return -EINVAL;
}
if (segment < 0 && segment != CRYPT_ANY_SEGMENT)
return -EINVAL;
if (token >= 0 && token < LUKS2_TOKENS_MAX) {
if ((jobj_token = LUKS2_get_token_jobj(hdr, token))) {
r = LUKS2_token_open(cd, hdr, token, jobj_token, type, segment, CRYPT_SLOT_PRIORITY_IGNORE, pin, pin_size, &buffer, &buffer_size, usrptr);
r = token_open(cd, hdr, token, jobj_token, type, segment, CRYPT_SLOT_PRIORITY_IGNORE,
pin, pin_size, &buffer, &buffer_size, usrptr, true);
if (!r) {
r = LUKS2_keyslot_open_by_token(cd, hdr, token, segment, CRYPT_SLOT_PRIORITY_IGNORE,
buffer, buffer_size, vk);
@@ -726,7 +738,7 @@ int LUKS2_token_unlock_volume_key(struct crypt_device *cd,
/*
* return priorities (ordered form least to most significant):
* ENOENT - unusable for activation (no token handler, invalid token metadata, not assigned to volume segment, etc)
* EPERM - usable but token provided passphrase did not not unlock any assigned keyslot
* EPERM - usable but token provided passphrase did not unlock any assigned keyslot
* EAGAIN - usable but not ready (token HW is missing)
* ENOANO - ready, but token pin is wrong or missing
*
@@ -751,10 +763,15 @@ int LUKS2_token_open_and_activate(struct crypt_device *cd,
void *usrptr)
{
bool use_keyring;
int keyslot, r;
int keyslot, r, segment;
struct volume_key *vk = NULL;
r = LUKS2_token_unlock_volume_key(cd, hdr, token, type, pin, pin_size, flags, usrptr, &vk);
if (flags & CRYPT_ACTIVATE_ALLOW_UNBOUND_KEY)
segment = CRYPT_ANY_SEGMENT;
else
segment = CRYPT_DEFAULT_SEGMENT;
r = LUKS2_token_unlock_key(cd, hdr, token, type, pin, pin_size, segment, usrptr, &vk);
if (r < 0)
return r;
@@ -871,6 +888,10 @@ int LUKS2_token_assign(struct crypt_device *cd, struct luks2_hdr *hdr,
json_object *jobj_tokens;
int r = 0;
if ((keyslot < 0 && keyslot != CRYPT_ANY_SLOT) || keyslot >= LUKS2_KEYSLOTS_MAX ||
(token < 0 && token != CRYPT_ANY_TOKEN) || token >= LUKS2_TOKENS_MAX)
return -EINVAL;
if (token == CRYPT_ANY_TOKEN) {
json_object_object_get_ex(hdr->jobj, "tokens", &jobj_tokens);
@@ -953,3 +974,70 @@ int LUKS2_token_assignment_copy(struct crypt_device *cd,
return commit ? LUKS2_hdr_write(cd, hdr) : 0;
}
int LUKS2_token_unlock_passphrase(struct crypt_device *cd,
struct luks2_hdr *hdr,
int token,
const char *type,
const char *pin,
size_t pin_size,
void *usrptr,
char **passphrase,
size_t *passphrase_size)
{
char *buffer;
size_t buffer_size;
json_object *jobj_token, *jobj_tokens;
int r = -ENOENT, retval = -ENOENT;
if (!hdr)
return -EINVAL;
if (token >= 0 && token < LUKS2_TOKENS_MAX) {
if ((jobj_token = LUKS2_get_token_jobj(hdr, token)))
r = token_open(cd, hdr, token, jobj_token, type, CRYPT_ANY_SEGMENT, CRYPT_SLOT_PRIORITY_IGNORE,
pin, pin_size, &buffer, &buffer_size, usrptr, false);
} else if (token == CRYPT_ANY_TOKEN) {
json_object_object_get_ex(hdr->jobj, "tokens", &jobj_tokens);
if (!type)
usrptr = NULL;
json_object_object_foreach(jobj_tokens, slot, val) {
token = atoi(slot);
r = token_open(cd, hdr, token, val, type, CRYPT_ANY_SEGMENT, CRYPT_SLOT_PRIORITY_IGNORE,
pin, pin_size, &buffer, &buffer_size, usrptr, false);
/*
* return priorities (ordered form least to most significant):
* ENOENT - unusable for activation (no token handler, invalid token metadata, etc)
* EAGAIN - usable but not ready (token HW is missing)
* ENOANO - ready, but token pin is wrong or missing
*
* success (>= 0) or any other negative errno short-circuits token activation loop
* immediately
*/
if (break_loop_retval(r))
goto out;
update_return_errno(r, &retval);
}
r = retval;
} else
r = -EINVAL;
out:
if (!r) {
*passphrase = crypt_safe_alloc(buffer_size);
if (*passphrase) {
memcpy(*passphrase, buffer, buffer_size);
*passphrase_size = buffer_size;
} else
r = -ENOMEM;
LUKS2_token_buffer_free(cd, token, buffer, buffer_size);
}
if (!r)
return token;
return r;
}

View File

@@ -19,8 +19,6 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <assert.h>
#include "luks2_internal.h"
int keyring_open(struct crypt_device *cd,
@@ -139,3 +137,8 @@ int LUKS2_token_keyring_get(struct luks2_hdr *hdr,
return token;
}
void keyring_buffer_free(void *buffer, size_t buffer_len __attribute__((unused)))
{
crypt_safe_free(buffer);
}

View File

@@ -21,7 +21,6 @@
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <assert.h>
#include <sys/select.h>
#include "libcryptsetup.h"
@@ -171,6 +170,7 @@ err:
return -ENOSYS;
}
/* coverity[ -taint_source : arg-1 ] */
int crypt_random_get(struct crypt_device *ctx, char *buf, size_t len, int quality)
{
int status, rng_type;

File diff suppressed because it is too large Load Diff

View File

@@ -23,7 +23,6 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "libcryptsetup.h"
#include "tcrypt.h"

View File

@@ -59,43 +59,33 @@ uint64_t crypt_getphysmemory_kb(void)
return phys_memory_kb;
}
/* MEMLOCK */
#define DEFAULT_PROCESS_PRIORITY -18
static int _priority;
static int _memlock_count = 0;
// return 1 if memory is locked
int crypt_memlock_inc(struct crypt_device *ctx)
void crypt_process_priority(struct crypt_device *cd, int *priority, bool raise)
{
if (!_memlock_count++) {
log_dbg(ctx, "Locking memory.");
if (mlockall(MCL_CURRENT | MCL_FUTURE) == -1) {
log_dbg(ctx, "Cannot lock memory with mlockall.");
_memlock_count--;
return 0;
}
errno = 0;
if (((_priority = getpriority(PRIO_PROCESS, 0)) == -1) && errno)
log_err(ctx, _("Cannot get process priority."));
int _priority, new_priority;
if (raise) {
_priority = getpriority(PRIO_PROCESS, 0);
if (_priority < 0)
_priority = 0;
if (priority)
*priority = _priority;
/*
* Do not bother checking CAP_SYS_NICE as device activation
* requires CAP_SYSADMIN later anyway.
*/
if (getuid() || geteuid())
new_priority = 0;
else
if (setpriority(PRIO_PROCESS, 0, DEFAULT_PROCESS_PRIORITY))
log_dbg(ctx, "setpriority %d failed: %s",
DEFAULT_PROCESS_PRIORITY, strerror(errno));
}
return _memlock_count ? 1 : 0;
}
new_priority = -18;
int crypt_memlock_dec(struct crypt_device *ctx)
{
if (_memlock_count && (!--_memlock_count)) {
log_dbg(ctx, "Unlocking memory.");
if (munlockall() == -1)
log_err(ctx, _("Cannot unlock memory."));
if (setpriority(PRIO_PROCESS, 0, new_priority))
log_dbg(cd, "Cannot raise process priority.");
} else {
_priority = priority ? *priority : 0;
if (setpriority(PRIO_PROCESS, 0, _priority))
log_dbg(ctx, "setpriority %d failed: %s", _priority, strerror(errno));
log_dbg(cd, "Cannot reset process priority.");
}
return _memlock_count ? 1 : 0;
}
/* Keyfile processing */
@@ -179,7 +169,7 @@ int crypt_keyfile_device_read(struct crypt_device *cd, const char *keyfile,
key_size = DEFAULT_KEYFILE_SIZE_MAXKB * 1024 + 1;
unlimited_read = 1;
/* use 4k for buffer (page divisor but avoid huge pages) */
buflen = 4096 - sizeof(size_t); // sizeof(struct safe_allocation);
buflen = 4096 - 16; /* sizeof(struct safe_allocation); */
} else
buflen = key_size;

View File

@@ -47,6 +47,7 @@ int crypt_benchmark(struct crypt_device *cd,
r = -ENOMEM;
if (posix_memalign(&buffer, crypt_getpagesize(), buffer_size))
goto out;
memset(buffer, 0, buffer_size);
r = crypt_cipher_ivsize(cipher, cipher_mode);
if (r >= 0 && iv_size != (size_t)r) {
@@ -98,7 +99,7 @@ int crypt_benchmark_pbkdf(struct crypt_device *cd,
int (*progress)(uint32_t time_ms, void *usrptr),
void *usrptr)
{
int r;
int r, priority;
const char *kdf_opt;
if (!pbkdf || (!password && password_size))
@@ -112,10 +113,12 @@ int crypt_benchmark_pbkdf(struct crypt_device *cd,
log_dbg(cd, "Running %s(%s) benchmark.", pbkdf->type, kdf_opt);
crypt_process_priority(cd, &priority, true);
r = crypt_pbkdf_perf(pbkdf->type, pbkdf->hash, password, password_size,
salt, salt_size, volume_key_size, pbkdf->time_ms,
pbkdf->max_memory_kb, pbkdf->parallel_threads,
&pbkdf->iterations, &pbkdf->max_memory_kb, progress, usrptr);
crypt_process_priority(cd, &priority, false);
if (!r)
log_dbg(cd, "Benchmark returns %s(%s) %u iterations, %u memory, %u threads (for %zu-bits key).",

View File

@@ -31,6 +31,8 @@
#include "libcryptsetup.h"
#include "utils_crypt.h"
#define MAX_CAPI_LEN_STR "143" /* for sscanf of crypto API string + 16 + \0 */
int crypt_parse_name_and_mode(const char *s, char *cipher, int *key_nums,
char *cipher_mode)
{
@@ -266,3 +268,80 @@ bool crypt_is_cipher_null(const char *cipher_spec)
return false;
return (strstr(cipher_spec, "cipher_null") || !strcmp(cipher_spec, "null"));
}
int crypt_capi_to_cipher(char **org_c, char **org_i, const char *c_dm, const char *i_dm)
{
char cipher[MAX_CAPI_ONE_LEN], mode[MAX_CAPI_ONE_LEN], iv[MAX_CAPI_ONE_LEN],
auth[MAX_CAPI_ONE_LEN], tmp[MAX_CAPI_LEN], dmcrypt_tmp[MAX_CAPI_LEN*2],
capi[MAX_CAPI_LEN+1];
size_t len;
int i;
if (!c_dm)
return -EINVAL;
/* legacy mode */
if (strncmp(c_dm, "capi:", 4)) {
if (!(*org_c = strdup(c_dm)))
return -ENOMEM;
if (i_dm) {
if (!(*org_i = strdup(i_dm))) {
free(*org_c);
*org_c = NULL;
return -ENOMEM;
}
} else
*org_i = NULL;
return 0;
}
/* modes with capi: prefix */
i = sscanf(c_dm, "capi:%" MAX_CAPI_LEN_STR "[^-]-%" MAX_CAPI_ONE_LEN_STR "s", tmp, iv);
if (i != 2)
return -EINVAL;
len = strlen(tmp);
if (len < 2)
return -EINVAL;
if (tmp[len-1] == ')')
tmp[len-1] = '\0';
if (sscanf(tmp, "rfc4309(%" MAX_CAPI_LEN_STR "s", capi) == 1) {
if (!(*org_i = strdup("aead")))
return -ENOMEM;
} else if (sscanf(tmp, "rfc7539(%" MAX_CAPI_LEN_STR "[^,],%" MAX_CAPI_ONE_LEN_STR "s", capi, auth) == 2) {
if (!(*org_i = strdup(auth)))
return -ENOMEM;
} else if (sscanf(tmp, "authenc(%" MAX_CAPI_ONE_LEN_STR "[^,],%" MAX_CAPI_LEN_STR "s", auth, capi) == 2) {
if (!(*org_i = strdup(auth)))
return -ENOMEM;
} else {
if (i_dm) {
if (!(*org_i = strdup(i_dm)))
return -ENOMEM;
} else
*org_i = NULL;
memset(capi, 0, sizeof(capi));
strncpy(capi, tmp, sizeof(capi)-1);
}
i = sscanf(capi, "%" MAX_CAPI_ONE_LEN_STR "[^(](%" MAX_CAPI_ONE_LEN_STR "[^)])", mode, cipher);
if (i == 2)
i = snprintf(dmcrypt_tmp, sizeof(dmcrypt_tmp), "%s-%s-%s", cipher, mode, iv);
else
i = snprintf(dmcrypt_tmp, sizeof(dmcrypt_tmp), "%s-%s", capi, iv);
if (i < 0 || (size_t)i >= sizeof(dmcrypt_tmp)) {
free(*org_i);
*org_i = NULL;
return -EINVAL;
}
if (!(*org_c = strdup(dmcrypt_tmp))) {
free(*org_i);
*org_i = NULL;
return -ENOMEM;
}
return 0;
}

View File

@@ -27,9 +27,12 @@
struct crypt_device;
#define MAX_CIPHER_LEN 32
#define MAX_CIPHER_LEN_STR "31"
#define MAX_KEYFILES 32
#define MAX_CIPHER_LEN 32
#define MAX_CIPHER_LEN_STR "31"
#define MAX_KEYFILES 32
#define MAX_CAPI_ONE_LEN 2 * MAX_CIPHER_LEN
#define MAX_CAPI_ONE_LEN_STR "63" /* for sscanf length + '\0' */
#define MAX_CAPI_LEN 144 /* should be enough to fit whole capi string */
int crypt_parse_name_and_mode(const char *s, char *cipher,
int *key_nums, char *cipher_mode);
@@ -46,4 +49,6 @@ void crypt_log_hex(struct crypt_device *cd,
bool crypt_is_cipher_null(const char *cipher_spec);
int crypt_capi_to_cipher(char **org_c, char **org_i, const char *c_dm, const char *i_dm);
#endif /* _UTILS_CRYPT_H */

View File

@@ -21,7 +21,6 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <assert.h>
#include <string.h>
#include <stdlib.h>
#include <errno.h>
@@ -623,7 +622,10 @@ size_t device_optimal_encryption_sector_size(struct crypt_device *cd, struct dev
phys_block_size = device_block_phys_size_fd(fd);
close(fd);
if (device->block_size >= phys_block_size || phys_block_size <= SECTOR_SIZE || phys_block_size > MAX_SECTOR_SIZE || MISALIGNED(phys_block_size, device->block_size))
if (device->block_size >= phys_block_size ||
phys_block_size <= SECTOR_SIZE ||
phys_block_size > MAX_SECTOR_SIZE ||
MISALIGNED(phys_block_size, device->block_size))
return device->block_size;
return phys_block_size;

View File

@@ -32,7 +32,6 @@
# include <sys/sysmacros.h> /* for major, minor */
#endif
#include <libgen.h>
#include <assert.h>
#include "internal.h"
#include "utils_device_locking.h"
@@ -106,7 +105,7 @@ static int open_lock_dir(struct crypt_device *cd, const char *dir, const char *b
lockdfd = openat(dirfd, base, O_RDONLY | O_NOFOLLOW | O_DIRECTORY | O_CLOEXEC);
if (lockdfd < 0) {
if (errno == ENOENT) {
log_dbg(cd, _("Locking directory %s/%s will be created with default compiled-in permissions."), dir, base);
log_dbg(cd, "Locking directory %s/%s will be created with default compiled-in permissions.", dir, base);
/* success or failure w/ errno == EEXIST either way just try to open the 'base' directory again */
if (mkdirat(dirfd, base, DEFAULT_LUKS2_LOCK_DIR_PERMS) && errno != EEXIST)

View File

@@ -75,6 +75,7 @@ static inline uint32_t act2dmflags(uint32_t act_flags)
#define DM_CRYPT_NO_WORKQUEUE_SUPPORTED (1 << 25) /* dm-crypt suppot for bypassing workqueues */
#define DM_INTEGRITY_FIX_HMAC_SUPPORTED (1 << 26) /* hmac covers also superblock */
#define DM_INTEGRITY_RESET_RECALC_SUPPORTED (1 << 27) /* dm-integrity automatic recalculation supported */
#define DM_VERITY_TASKLETS_SUPPORTED (1 << 28) /* dm-verity tasklets supported */
typedef enum { DM_CRYPT = 0, DM_VERITY, DM_INTEGRITY, DM_LINEAR, DM_ERROR, DM_ZERO, DM_UNKNOWN } dm_target_type;
enum tdirection { TARGET_EMPTY = 0, TARGET_SET, TARGET_QUERY };

View File

@@ -1,55 +0,0 @@
/*
* FIPS mode utilities
*
* Copyright (C) 2011-2022 Red Hat, Inc. All rights reserved.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <unistd.h>
#include <fcntl.h>
#include <errno.h>
#include "utils_fips.h"
#if !ENABLE_FIPS
bool crypt_fips_mode(void) { return false; }
#else
static bool fips_checked = false;
static bool fips_mode = false;
static bool kernel_fips_mode(void)
{
int fd;
char buf[1] = "";
if ((fd = open("/proc/sys/crypto/fips_enabled", O_RDONLY)) >= 0) {
while (read(fd, buf, sizeof(buf)) < 0 && errno == EINTR);
close(fd);
}
return (buf[0] == '1');
}
bool crypt_fips_mode(void)
{
if (fips_checked)
return fips_mode;
fips_mode = kernel_fips_mode() && !access("/etc/system-fips", F_OK);
fips_checked = true;
return fips_mode;
}
#endif /* ENABLE_FIPS */

View File

@@ -1,28 +0,0 @@
/*
* FIPS mode utilities
*
* Copyright (C) 2011-2022 Red Hat, Inc. All rights reserved.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#ifndef _UTILS_FIPS_H
#define _UTILS_FIPS_H
#include <stdbool.h>
bool crypt_fips_mode(void);
#endif /* _UTILS_FIPS_H */

View File

@@ -29,6 +29,7 @@
#include "utils_io.h"
/* coverity[ -taint_source : arg-1 ] */
static ssize_t _read_buffer(int fd, void *buf, size_t length, volatile int *quit)
{
size_t read_size = 0;

View File

@@ -163,7 +163,7 @@ int keyring_get_passphrase(const char *key_desc,
ret = keyctl_read(kid, NULL, 0);
if (ret > 0) {
len = ret;
buf = malloc(len);
buf = crypt_safe_alloc(len);
if (!buf)
return -ENOMEM;
@@ -173,9 +173,7 @@ int keyring_get_passphrase(const char *key_desc,
if (ret < 0) {
err = errno;
if (buf)
crypt_safe_memzero(buf, len);
free(buf);
crypt_safe_free(buf);
return -err;
}

View File

@@ -20,13 +20,17 @@
*/
#include <stdlib.h>
#include <stdbool.h>
#include <string.h>
#include <sys/mman.h>
#include "libcryptsetup.h"
struct safe_allocation {
size_t size;
char data[0];
size_t size;
bool locked;
char data[0] __attribute__((aligned(8)));
};
#define OVERHEAD offsetof(struct safe_allocation, data)
/*
* Replacement for memset(s, 0, n) on stack that can be optimized out
@@ -34,6 +38,9 @@ struct safe_allocation {
*/
void crypt_safe_memzero(void *data, size_t size)
{
if (!data)
return;
#ifdef HAVE_EXPLICIT_BZERO
explicit_bzero(data, size);
#else
@@ -49,15 +56,19 @@ void *crypt_safe_alloc(size_t size)
{
struct safe_allocation *alloc;
if (!size || size > (SIZE_MAX - offsetof(struct safe_allocation, data)))
if (!size || size > (SIZE_MAX - OVERHEAD))
return NULL;
alloc = malloc(size + offsetof(struct safe_allocation, data));
alloc = malloc(size + OVERHEAD);
if (!alloc)
return NULL;
crypt_safe_memzero(alloc, size + OVERHEAD);
alloc->size = size;
crypt_safe_memzero(&alloc->data, size);
/* Ignore failure if it is over limit. */
if (!mlock(alloc, size + OVERHEAD))
alloc->locked = true;
/* coverity[leaked_storage] */
return &alloc->data;
@@ -72,11 +83,16 @@ void crypt_safe_free(void *data)
if (!data)
return;
p = (char *)data - offsetof(struct safe_allocation, data);
p = (char *)data - OVERHEAD;
alloc = (struct safe_allocation *)p;
crypt_safe_memzero(data, alloc->size);
if (alloc->locked) {
munlock(alloc, alloc->size + OVERHEAD);
alloc->locked = false;
}
s = (volatile size_t *)&alloc->size;
*s = 0x55aa55aa;
free(alloc);
@@ -92,7 +108,7 @@ void *crypt_safe_realloc(void *data, size_t size)
if (new_data && data) {
p = (char *)data - offsetof(struct safe_allocation, data);
p = (char *)data - OVERHEAD;
alloc = (struct safe_allocation *)p;
if (size > alloc->size)

View File

@@ -0,0 +1,53 @@
# ===========================================================================
# https://www.gnu.org/software/autoconf-archive/ax_check_compile_flag.html
# ===========================================================================
#
# SYNOPSIS
#
# AX_CHECK_COMPILE_FLAG(FLAG, [ACTION-SUCCESS], [ACTION-FAILURE], [EXTRA-FLAGS], [INPUT])
#
# DESCRIPTION
#
# Check whether the given FLAG works with the current language's compiler
# or gives an error. (Warnings, however, are ignored)
#
# ACTION-SUCCESS/ACTION-FAILURE are shell commands to execute on
# success/failure.
#
# If EXTRA-FLAGS is defined, it is added to the current language's default
# flags (e.g. CFLAGS) when the check is done. The check is thus made with
# the flags: "CFLAGS EXTRA-FLAGS FLAG". This can for example be used to
# force the compiler to issue an error when a bad flag is given.
#
# INPUT gives an alternative input source to AC_COMPILE_IFELSE.
#
# NOTE: Implementation based on AX_CFLAGS_GCC_OPTION. Please keep this
# macro in sync with AX_CHECK_{PREPROC,LINK}_FLAG.
#
# LICENSE
#
# Copyright (c) 2008 Guido U. Draheim <guidod@gmx.de>
# Copyright (c) 2011 Maarten Bosmans <mkbosmans@gmail.com>
#
# Copying and distribution of this file, with or without modification, are
# permitted in any medium without royalty provided the copyright notice
# and this notice are preserved. This file is offered as-is, without any
# warranty.
#serial 6
AC_DEFUN([AX_CHECK_COMPILE_FLAG],
[AC_PREREQ(2.64)dnl for _AC_LANG_PREFIX and AS_VAR_IF
AS_VAR_PUSHDEF([CACHEVAR],[ax_cv_check_[]_AC_LANG_ABBREV[]flags_$4_$1])dnl
AC_CACHE_CHECK([whether _AC_LANG compiler accepts $1], CACHEVAR, [
ax_check_save_flags=$[]_AC_LANG_PREFIX[]FLAGS
_AC_LANG_PREFIX[]FLAGS="$[]_AC_LANG_PREFIX[]FLAGS $4 $1"
AC_COMPILE_IFELSE([m4_default([$5],[AC_LANG_PROGRAM()])],
[AS_VAR_SET(CACHEVAR,[yes])],
[AS_VAR_SET(CACHEVAR,[no])])
_AC_LANG_PREFIX[]FLAGS=$ax_check_save_flags])
AS_VAR_IF(CACHEVAR,yes,
[m4_default([$2], :)],
[m4_default([$3], :)])
AS_VAR_POPDEF([CACHEVAR])dnl
])dnl AX_CHECK_COMPILE_FLAGS

View File

@@ -29,6 +29,7 @@ ADOCFILES = $(ADOCFILES_COMMON) \
man/cryptsetup-config.8.adoc \
man/cryptsetup-tcryptDump.8.adoc \
man/cryptsetup-bitlkDump.8.adoc \
man/cryptsetup-fvault2Dump.8.adoc \
man/cryptsetup-repair.8.adoc \
man/cryptsetup-benchmark.8.adoc \
man/cryptsetup-ssh.8.adoc \
@@ -64,6 +65,7 @@ CRYPTSETUP_MANPAGES = \
man/cryptsetup-config.8 \
man/cryptsetup-tcryptDump.8 \
man/cryptsetup-bitlkDump.8 \
man/cryptsetup-fvault2Dump.8 \
man/cryptsetup-repair.8 \
man/cryptsetup-benchmark.8
@@ -74,6 +76,7 @@ CRYPTSETUP_MANLINKS = \
man/cryptsetup-loopaesOpen.8 \
man/cryptsetup-tcryptOpen.8 \
man/cryptsetup-bitlkOpen.8 \
man/cryptsetup-fvault2Open.8 \
man/cryptsetup-luksErase.8
VERITYSETUP_MANPAGES = man/veritysetup.8

View File

@@ -33,7 +33,7 @@ ifdef::ACTION_ISLUKS[]
Print more information on command execution.
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_ISLUKS,ACTION_LUKSDUMP,ACTION_CONVERT,ACTION_REPAIR,ACTION_REENCRYPT[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSKILLSLOT,ACTION_ISLUKS,ACTION_LUKSDUMP,ACTION_LUKSUUID,ACTION_CONVERT,ACTION_REPAIR,ACTION_REENCRYPT[]
*--type <device-type>*::
ifndef::ACTION_REENCRYPT[]
Specifies required device type, for more info read _BASIC ACTIONS_ section in *cryptsetup*(8).
@@ -45,7 +45,7 @@ endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_TCRYPTDUMP,ACTION_BENCHMARK,ACTION_REENCRYPT[]
*--hash, -h* _<hash-spec>_::
ifdef::ACTION_OPEN[]
ifdef::ACTION_OPEN,ACTION_TCRYPTDUMP[]
Specifies the passphrase hash. Applies to _plain_ and _loopaes_ device types only.
+
For _tcrypt_ device type, it restricts checked PBKDF2 variants when looking for header.
@@ -54,7 +54,7 @@ ifdef::ACTION_LUKSFORMAT[]
Specifies the hash used in the LUKS key setup scheme and volume key
digest.
endif::[]
ifndef::ACTION_REENCRYPT,ACTION_OPEN[]
ifndef::ACTION_REENCRYPT,ACTION_OPEN,ACTION_TCRYPTDUMP[]
The specified hash is used for PBKDF2 and AF splitter.
endif::[]
ifdef::ACTION_REENCRYPT[]
@@ -67,25 +67,21 @@ for new LUKS1 device header.
*LUKS2:* Ignored unless new keyslot pbkdf algorithm is set to PBKDF2 (see --pbkdf).
endif::[]
+
The specified hash name is passed to the compiled-in crypto backend.
Different backends may support different hashes.
ifdef::ACTION_LUKSFORMAT[]
The hash algorithm must provide at least 160 bits of output.
endif::[]
Do not use a non-crypto hash like *xxhash* as this breaks
security.
+
Do not use a non-crypto hash like *xxhash* as this breaks security.
Use _cryptsetup --help_ to show the defaults.
endif::[]
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_REENCRYPT,ACTION_TCRYPTDUMP,ACTION_BENCHMARK[]
*--cipher, -c* _<cipher-spec>_::
ifdef::ACTION_OPEN[]
ifdef::ACTION_OPEN,ACTION_TCRYPTDUMP[]
Set the cipher specification string for _plain_ device type.
+
For _tcrypt_ device type it restricts checked cipher chains when looking for header.
endif::[]
ifndef::ACTION_REENCRYPT,ACTION_OPEN[]
ifndef::ACTION_REENCRYPT,ACTION_OPEN,ACTION_TCRYPTDUMP[]
Set the cipher specification string.
endif::[]
ifdef::ACTION_REENCRYPT[]
@@ -100,6 +96,7 @@ In reencrypt mode, if no new cipher specification is requested, the existing cip
in use. Unless the existing cipher was "cipher_null". In that case default cipher would
be applied as in encrypt mode.
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_REENCRYPT[]
+
_cryptsetup --help_ shows the compiled-in defaults.
+
@@ -110,12 +107,10 @@ of the IV generation. For example, ESSIV needs a hash function, while
For XTS mode you can optionally set a key size of 512 bits with the -s
option. Key size for XTS mode is twice that for other modes for the same
security level.
+
XTS mode requires kernel 2.6.24 or later and plain64 requires kernel
2.6.33 or later. More information can be found in the FAQ.
endif::[]
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_REENCRYPT[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_REPAIR,ACTION_TCRYPTDUMP,ACTION_REENCRYPT[]
*--verify-passphrase, -y*::
When interactively asking for a passphrase, ask for it twice and
complain if both inputs do not match.
@@ -125,28 +120,27 @@ endif::[]
Ignored on input from file or stdin.
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_TCRYPTDUMP,ACTION_REENCRYPT[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_TCRYPTDUMP,ACTION_REENCRYPT,ACTION_REPAIR,ACTION_BITLKDUMP[]
*--key-file, -d* _name_::
Read the passphrase from file.
+
If the name given is "-", then the passphrase will be read from stdin.
In this case, reading will not stop at newline characters.
+
ifdef::ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY[]
The passphrase supplied via --key-file is always the passphrase for existing
keyslot requested by the command.
+
If you want to set a new passphrase via key file, you have to use a
positional argument or parameter --new-keyfile.
+
endif::[]
ifdef::ACTION_OPEN[]
*NOTE:* With _plain_ device type, the passphrase obtained via --key-file option is
passed directly in dm-crypt. Unlike the interactive mode (stdin)
where digest (--hash option) of the passphrase is passed in dm-crypt instead.
+
endif::[]
ifndef::ACTION_REENCRYPT,ACTION_OPEN[]
With LUKS, the passphrase supplied via --key-file is always the existing
passphrase requested by a command, except in the case of _luksFormat_
where --key-file is equivalent to the positional key file argument.
+
If you want to set a new passphrase via key file, you have to use a
positional argument to _luksAddKey_.
+
endif::[]
ifndef::ACTION_REENCRYPT[]
See section _NOTES ON PASSPHRASE PROCESSING_ in *cryptsetup*(8) for more information.
endif::[]
@@ -160,12 +154,12 @@ passphrases.
endif::[]
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_REENCRYPT[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_REENCRYPT,ACTION_REPAIR,ACTION_BITLKDUMP[]
*--keyfile-offset* _value_::
Skip _value_ bytes at the beginning of the key file.
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_REENCRYPT[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_REENCRYPT,ACTION_REPAIR,ACTION_BITLKDUMP[]
*--keyfile-size, -l* _value_::
Read a maximum of _value_ bytes from the key file. The default is to
read the whole file up to the compiled-in maximum that can be queried
@@ -176,16 +170,27 @@ This option is useful to cut trailing newlines, for example. If
--keyfile-offset is also given, the size count starts after the offset.
endif::[]
ifdef::ACTION_LUKSADDKEY[]
*--new-keyfile* _name_::
Read the passphrase for a new keyslot from file.
+
If the name given is "-", then the passphrase will be read from stdin.
In this case, reading will not stop at newline characters.
+
This is alternative method to positional argument when adding new
passphrase via kefile.
endif::[]
ifdef::ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY[]
*--new-keyfile-offset* _value_::
Skip _value_ bytes at the start when adding a new passphrase from key
file with _luksAddKey_.
file.
endif::[]
ifdef::ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY[]
*--new-keyfile-size* _value_::
Read a maximum of _value_ bytes when adding a new passphrase from key
file with _luksAddKey_. The default is to read the whole file up to
file. The default is to read the whole file up to
the compiled-in maximum length that can be queried with --help.
Supplying more than the compiled in maximum aborts the operation. When
--new-keyfile-offset is also given, reading starts after the offset.
@@ -198,7 +203,7 @@ Use a volume key stored in a file.
endif::[]
ifdef::ACTION_FORMAT[]
+
For _luksFormat_ this allows creating a LUKS header with this specific
This allows creating a LUKS header with this specific
volume key. If the volume key was taken from an existing LUKS header and
all other parameters are the same, then the new header decrypts the data
encrypted with the header the volume key was taken from. +
@@ -207,8 +212,9 @@ ifdef::ACTION_LUKSDUMP,ACTION_BITLKDUMP[]
The volume key is stored in a file instead of being printed out to standard output. +
endif::[]
ifdef::ACTION_LUKSADDKEY[]
For _luksAddKey_ this allows adding a new passphrase without having to
know an existing one. +
This allows adding a new keyslot without having to know passphrase to existing one.
It may be also used when no keyslot is active.
+
endif::[]
ifdef::ACTION_OPEN[]
This allows one to open _luks_ and _bitlk_ device types without giving a passphrase. +
@@ -263,8 +269,8 @@ See *NOTES ON RANDOM NUMBER GENERATORS* in *cryptsetup*(8) for more
information. Use _cryptsetup --help_ to show the compiled-in default random
number generator.
+
*WARNING:* In a low-entropy situation (e.g. in an embedded system), both
selections are problematic. Using /dev/urandom can lead to weak keys.
*WARNING:* In a low-entropy situation (e.g. in an embedded system) and older
kernels, both selections are problematic. Using /dev/urandom can lead to weak keys.
Using /dev/random can block a long time, potentially forever, if not
enough entropy can be harvested by the kernel.
endif::[]
@@ -280,9 +286,20 @@ it is requested.
Reencrypt only the LUKS1 header and keyslots. Skips data in-place reencryption.
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSDUMP,ACTION_TOKEN,ACTION_CONFIG,ACTION_TOKEN,ACTION_REENCRYPT[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSDUMP,ACTION_LUKSRESUME,ACTION_TOKEN,ACTION_CONFIG,ACTION_TOKEN,ACTION_REPAIR,ACTION_REENCRYPT[]
*--key-slot, -S <0-N>*::
ifndef::ACTION_OPEN[]
ifdef::ACTION_LUKSADDKEY[]
When used together with parameter --new-key-slot this option allows you to specify which
key slot is selected for unlocking volume key.
+
*NOTE:* This option is ignored if existing volume key gets unlocked
via LUKS2 token (--token-id, --token-type or --token-only parameters) or
when volume key is provided directly via --volume-key-file parameter.
+
*NOTE:* To maintain backward compatibility, without --new-key-slot parameter,
this option allows you to specify which key slot is selected for the new key.
endif::[]
ifndef::ACTION_OPEN,ACTION_LUKSADDKEY[]
For LUKS operations that add key material, this option allows you to
specify which key slot is selected for the new key.
endif::[]
@@ -303,18 +320,40 @@ size and key size, but a valid key slot ID can always be between 0 and
31 for LUKS2.
endif::[]
ifdef::ACTION_LUKSADDKEY[]
*--new-key-slot <0-N>*::
This option allows you to specify which key slot is selected for
the new key.
+
*NOTE:* When used this option affects --key-slot option.
+
The maximum number of key slots depends on the LUKS version. LUKS1 can have up
to 8 key slots. LUKS2 can have up to 32 key slots based on key slot area
size and key size, but a valid key slot ID can always be between 0 and
31 for LUKS2.
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_REENCRYPT,ACTION_BENCHMARK,ACTION_LUKSADDKEY[]
*--key-size, -s* _bits_::
ifndef::ACTION_LUKSADDKEY[]
Sets key size in _bits_. The argument has to be a multiple of 8. The
possible key-sizes are limited by the cipher and mode used.
+
See /proc/crypto for more information. Note that key-size in
/proc/crypto is stated in bytes.
+
endif::[]
ifdef::ACTION_LUKSADDKEY[]
Provide volume key size in _bits_. The argument has to be a multiple of 8.
+
This option is required when parameter --volume-key-file is used to provide
current volume key. Also, it is used when new unbound keyslot is created by
specifying --unbound parameter.
endif::[]
ifdef::ACTION_OPEN[]
This option can be used for _plain_ device type only.
endif::[]
ifndef::ACTION_REENCRYPT,ACTION_OPEN[]
ifndef::ACTION_REENCRYPT,ACTION_OPEN,ACTION_LUKSADDKEY[]
This option can be used for _open --type plain_ or _luksFormat_. All
other LUKS actions will use the key-size specified in the LUKS header.
Use _cryptsetup --help_ to show the compiled-in defaults.
@@ -350,7 +389,7 @@ endif::[]
+
ifndef::ACTION_OPEN[]
The --offset option sets the data offset (payload) of data
device and must be be aligned to 4096-byte sectors (must be multiple of
device and must be aligned to 4096-byte sectors (must be multiple of
8). This option cannot be combined with --align-payload option.
endif::[]
endif::[]
@@ -465,7 +504,7 @@ new LUKS header.
endif::[]
endif::[]
ifdef::ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_REENCRYPT[]
ifdef::ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_REENCRYPT,ACTION_BENCHMARK[]
*--pbkdf-memory <number>*::
Set the memory cost for PBKDF (for Argon2i/id the number represents
kilobytes). Note that it is maximal value, PBKDF benchmark or
@@ -473,7 +512,7 @@ available physical memory can decrease it. This option is not
available for PBKDF2.
endif::[]
ifdef::ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_REENCRYPT[]
ifdef::ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_REENCRYPT,ACTION_BENCHMARK[]
*--pbkdf-parallel <number>*::
Set the parallel cost for PBKDF (number of threads, up to 4). Note
that it is maximal value, it is decreased automatically if CPU online
@@ -520,18 +559,18 @@ numbers are represented in a string format due to need of full 64bit
unsigned integers.
endif::[]
ifdef::ACTION_RESIZE[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_REENCRYPT,ACTION_REPAIR,ACTION_LUKSRESUME,ACTION_RESIZE,ACTION_TCRYPTDUMP,ACTION_BITLKDUMP[]
*--timeout, -t <number of seconds>*::
The number of seconds to wait before timeout on passphrase input via
terminal. It is relevant every time a passphrase is asked, for example
for _open_, _luksFormat_ or _luksAddKey_. It has no effect if used in
conjunction with --key-file. +
terminal. It is relevant every time a passphrase is asked.
It has no effect if used in conjunction with --key-file.
+
This option is useful when the system should not stall if the user
does not input a passphrase, e.g. during boot. The default is a value
of 0 seconds, which means to wait forever.
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_LUKSADDKEY,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_REENCRYPT[]
ifdef::ACTION_OPEN,ACTION_LUKSRESUME,ACTION_REENCRYPT[]
*--tries, -T*::
How often the input of the passphrase shall be retried. The default is 3 tries.
endif::[]
@@ -629,7 +668,7 @@ Do not activate the device, just verify passphrase. The device mapping name is
not mandatory if this option is used.
endif::[]
ifdef::ACTION_OPEN,ACTION_STATUS,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSSUSPEND,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_TOKEN,ACTION_CONVERT,ACTION_CONFIG,ACTION_REENCRYPT,ACTION_CLOSE[]
ifndef::ACTION_BENCHMARK,ACTION_BITLKDUMP[]
*--header <device or file storing the LUKS header>*::
ifndef::ACTION_OPEN[]
Use a detached (separated) metadata device or file where the LUKS
@@ -670,6 +709,9 @@ to a detached file. The passed future file must not exist at the time
of initializing the decryption operation. This frees space in head of data
device so that data can be moved at original LUKS2 header location. Later on
decryption operation continues as if the ordinary detached header was passed.
+
*WARNING:* Never put exported header file in a filesystem on top of device
you are about to decrypt! It would cause a deadlock.
endif::[]
endif::[]
@@ -715,12 +757,12 @@ Removes a previously configured deferred device removal in _close_
command.
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_TOKEN[]
ifdef::ACTION_OPEN,ACTION_LUKSRESUME,ACTION_RESIZE,ACTION_TOKEN[]
*--disable-external-tokens*::
Disable loading of plugins for external LUKS2 tokens.
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSFORMAT,ACTION_LUKSSUSPEND,ACTION_LUKSRESUME,ACTION_LUKSADDKEY,ACTION_LUKSREMOVEKEY,ACTION_LUKSCHANGEKEY,ACTION_LUKSCONVERTKEY,ACTION_LUKSKILLSLOT,ACTION_LUKSDUMP,ACTION_TOKEN,ACTION_REENCRYPT[]
ifndef::ACTION_BENCHMARK,ACTION_BITLKDUMP,ACTION_TCRYPTDUMP[]
*--disable-locks*::
Disable lock protection for metadata on disk. This option is valid
only for LUKS2 and ignored for other formats.
@@ -739,8 +781,7 @@ endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_REFRESH,ACTION_LUKSFORMAT,ACTION_LUKSRESUME,ACTION_TOKEN,ACTION_REENCRYPT[]
*--disable-keyring*::
Do not load volume key in kernel keyring and store it directly in the
dm-crypt target instead. This option is supported only for the LUKS2
format.
dm-crypt target instead. This option is supported only for the LUKS2 type.
endif::[]
ifdef::ACTION_TOKEN[]
@@ -756,23 +797,49 @@ slot is never used, if not explicitly requested by _--key-slot_
option.
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSRESUME,ACTION_TOKEN[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSRESUME,ACTION_TOKEN,ACTION_LUKSADDKEY[]
*--token-id*::
ifndef::ACTION_TOKEN,ACTION_LUKSADDKEY[]
Specify what token to use. If omitted, all available tokens will be checked
before proceeding further with passphrase prompt.
endif::[]
ifdef::ACTION_LUKSADDKEY[]
Specify what token to use when unlocking existing keyslot to get volume key.
endif::[]
ifdef::ACTION_TOKEN[]
Specify token number. If omitted, first unused token id is used when adding or importing
new token.
endif::[]
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSRESUME[]
ifdef::ACTION_LUKSADDKEY[]
*--new-token-id*::
Specify what token to use to get the passphrase for a new keyslot.
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSRESUME,ACTION_LUKSADDKEY[]
*--token-only*::
ifndef::ACTION_LUKSADDKEY[]
Do not proceed further with action if token based keyslot unlock failed. Without the
option, action asks for passphrase to proceed further.
endif::[]
ifdef::ACTION_LUKSADDKEY[]
Use only LUKS2 tokens to unlock existing volume key.
+
*NOTE*: To create a new keyslot using passphrase provided by a token use --new-token-id parameter.
endif::[]
endif::[]
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSRESUME[]
*--token-type*::
Restrict tokens eligible for operation to specific token type (name).
ifdef::ACTION_OPEN,ACTION_RESIZE,ACTION_LUKSRESUME,ACTION_LUKSADDKEY[]
*--token-type* _type_::
ifndef::ACTION_LUKSADDKEY[]
Restrict tokens eligible for operation to specific token _type_.
Mostly useful when no --token-id is specified.
endif::[]
ifdef::ACTION_LUKSADDKEY[]
Specify what token type (all _type_ tokens) to use when unlocking existing keyslot to get volume key.
endif::[]
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSFORMAT,ACTION_REENCRYPT[]
ifndef::ACTION_REENCRYPT[]
@@ -819,7 +886,7 @@ Reencrypt device with new encryption sector size enforced.
+
*WARNING:* Increasing encryption sector size may break hosted filesystem. Do not
run reencryption with --force-offline-reencrypt if unsure what block size
was filesystem formated with.
was filesystem formatted with.
endif::[]
endif::[]
@@ -834,7 +901,7 @@ use it only for accessing incompatible existing disk images from other
systems that require this option.
endif::[]
ifdef::ACTION_REFRESH[]
ifdef::ACTION_OPEN,ACTION_REFRESH[]
*--persistent*::
If used with LUKS2 devices and activation commands like _open_ or
_refresh_, the specified activation flags are persistently written
@@ -880,6 +947,14 @@ option).
For more info, see _AUTHENTICATED DISK ENCRYPTION_ section in *cryptsetup*(8).
endif::[]
ifdef::ACTION_LUKSFORMAT[]
*--integrity-legacy-padding*::
Use inefficient legacy padding.
+
*WARNING*: Do not use this option until you need compatibility with specific
old kernel.
endif::[]
ifdef::ACTION_LUKSFORMAT,ACTION_REENCRYPT[]
*--luks2-metadata-size <size>*::
This option can be used to enlarge the LUKS2 metadata (JSON) area. The
@@ -928,17 +1003,21 @@ aligned to page size and page-cache initiates read of a sector with
invalid integrity tag.
endif::[]
ifdef::ACTION_OPEN,ACTION_LUKSADDKEY,ACTION_LUKSDUMP[]
ifdef::ACTION_OPEN,ACTION_LUKSADDKEY,ACTION_LUKSDUMP,ACTION_TOKEN[]
*--unbound*::
ifndef::ACTION_OPEN[]
Creates new or dumps existing LUKS2 unbound keyslot.
+
ifdef::ACTION_LUKSADDKEY[]
Creates new LUKS2 unbound keyslot.
endif::[]
ifdef::ACTION_LUKSDUMP[]
Dumps existing LUKS2 unbound keyslot.
endif::[]
ifdef::ACTION_OPEN[]
Allowed only only together with --test-passphrase parameter, it allows
to test passphrase for unbound LUKS2 keyslot. Otherwise, unbound keyslot
passphrase can be tested only when specific keyslot is selected via
--key-slot parameter.
Allowed only together with --test-passphrase parameter, it allows one to test
passphrase for unbound LUKS2 keyslot. Otherwise, unbound keyslot passphrase
can be tested only when specific keyslot is selected via --key-slot parameter.
endif::[]
ifdef::ACTION_TOKEN[]
Creates new LUKS2 keyring token assigned to no keyslot. Usable only with _add_ action.
endif::[]
endif::[]

View File

@@ -20,7 +20,10 @@ Benchmarks ciphers and KDF (key derivation function). Without
parameters, it tries to measure few common configurations.
To benchmark other ciphers or modes, you need to specify *--cipher* and
*--key-size* options or *--hash* for KDF test.
*--key-size* options.
To benchmark PBKDF you need to specify *--pbkdf* or *--hash* with optional
cost parameters *--iter-time*, *--pbkdf-memory* or *--pbkdf-parallel*.
*NOTE:* This benchmark uses memory only and is only informative. You
cannot directly predict real storage encryption speed from it.
@@ -31,7 +34,8 @@ are configuring kernel yourself, enable "User-space interface for
symmetric key cipher algorithms" in "Cryptographic API" section
(CRYPTO_USER_API_SKCIPHER .config option).
*<options>* can be [--cipher, --key-size, --hash].
*<options>* can be [--cipher, --key-size, --hash, --pbkdf, --iter-time,
--pbkdf-memory, --pbkdf-parallel].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -18,7 +18,17 @@ cryptsetup-bitlkDump - dump the header information of a BITLK (BitLocker compati
Dump the header information of a BITLK (BitLocker compatible) device.
*<options>* can be [--dump-volume-key --volume-key-file].
If the --dump-volume-key option is used, the BITLK device volume key
is dumped instead of header information. You have to provide password
or keyfile to dump volume key.
Beware that the volume key can be used to decrypt the data stored in
the container without a passphrase.
This means that if the volume key is compromised, the whole device has
to be erased to prevent further access. Use this option carefully.
*<options>* can be [--dump-volume-key, --volume-key-file, --key-file,
--keyfile-offset, --keyfile-size, --timeout].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -20,11 +20,11 @@ Removes the existing mapping <name> and wipes the key from kernel
memory.
For backward compatibility, there are *close* command aliases: *remove*,
*plainClose*, *luksClose*, *loopaesClose*, *tcryptClose* (all behave
exactly the same, device type is determined automatically from the active
device).
*plainClose*, *luksClose*, *loopaesClose*, *tcryptClose*, *bitlkClose*
(all behave exactly the same, device type is determined automatically
from the active device).
*<options>* can be [--deferred] or [--cancel-deferred]
*<options>* can be [--deferred, --cancel-deferred, --header, --disable-locks].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -24,7 +24,7 @@ prefer, ignore) for keyslot (specified by _--key-slot_) or _--label_ and
_--subsystem_.
*<options>* can be [--priority, --label, --subsystem, --key-slot,
--header].
--header, --disable-locks].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -31,7 +31,7 @@ _luks2_.
of a crash during conversion or if a media error occurs. Always create a
header backup before performing this operation!
*<options>* can be [--header, --type].
*<options>* can be [--header, --type, --disable-locks].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -22,5 +22,7 @@ You do not need to provide any password for this operation.
*WARNING:* This operation is irreversible.
*<options>* can be [--header, --disable-locks].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -0,0 +1,34 @@
= cryptsetup-fvault2Dump(8)
:doctype: manpage
:manmanual: Maintenance Commands
:mansource: cryptsetup {release-version}
:man-linkstyle: pass:[blue R < >]
:COMMON_OPTIONS:
:ACTION_BITLKDUMP:
== Name
cryptsetup-fvault2Dump - dump the header information of a FVAULT2 (FileVault2 compatible) device
== SYNOPSIS
*cryptsetup _fvault2Dump_ [<options>] <device>*
== DESCRIPTION
Dump the header information of a FVAULT2 (FileVault2 compatible) device.
If the --dump-volume-key option is used, the FVAULT2 device volume key
is dumped instead of header information. You have to provide password
or keyfile to dump volume key.
Beware that the volume key can be used to decrypt the data stored in
the container without a passphrase.
This means that if the volume key is compromised, the whole device has
to be erased to prevent further access. Use this option carefully.
*<options>* can be [--dump-volume-key, --volume-key-file, --key-file,
--keyfile-offset, --keyfile-size, --timeout].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -16,11 +16,14 @@ cryptsetup-isLuks - check if a device is a LUKS device
== DESCRIPTION
Returns true, if <device> is a LUKS device, false otherwise. Use option
-v to get human-readable feedback. 'Command successful.' means the
device is a LUKS device.
Returns true, if <device> is a LUKS device, false otherwise.
Use option -v to get human-readable feedback.
'Command successful.' means the device is a LUKS device.
By specifying --type you may query for specific LUKS version.
*<options>* can be [--header, --type, --disable-locks].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -16,10 +16,12 @@ cryptsetup-luksAddKey - add a new passphrase
== DESCRIPTION
Adds a new passphrase. An existing passphrase must be supplied
interactively or via --key-file. The new passphrase to be added can be
specified interactively or read from the file given as the positional
argument.
Adds a keyslot protected by a new passphrase. An existing passphrase
must be supplied interactively, via --key-file or LUKS2 token (plugin).
Alternatively to existing passphrase user may pass directly volume key
(via --volume-key-file). The new passphrase to be added can be specified
interactively, read from the file given as the positional argument (also
via --new-keyfile parameter) or via LUKS2 token.
*NOTE:* with --unbound option the action creates new unbound LUKS2
keyslot. The keyslot cannot be used for device activation. If you don't
@@ -31,10 +33,39 @@ that supports per-keyslot parameters. For LUKS1, PBKDF type and hash
algorithm is always the same for all keyslots.
*<options>* can be [--key-file, --keyfile-offset, --keyfile-size,
--new-keyfile-offset, --new-keyfile-size, --key-slot, --volume-key-file,
--force-password, --hash, --header, --disable-locks, --iter-time,
--pbkdf, --pbkdf-force-iterations, --pbkdf-memory, --pbkdf-parallel,
--unbound, --type, --keyslot-cipher, --keyslot-key-size].
--new-keyfile, --new-keyfile-offset, --new-keyfile-size, --key-slot,
--new-key-slot, --volume-key-file, --force-password, --hash, --header,
--disable-locks, --iter-time, --pbkdf, --pbkdf-force-iterations,
--pbkdf-memory, --pbkdf-parallel, --unbound, --type, --keyslot-cipher,
--keyslot-key-size, --key-size, --timeout, --token-id, --token-type,
--token-only, --new-token-id, --verify-passphrase].
include::man/common_options.adoc[]
== EXAMPLES
*NOTE*: When not specified otherwise interactive passphrase prompt is always default method.
Add new keyslot using interactive passphrase prompt for both existing and new passphrase:
*cryptsetup luksAddKey /dev/device*
Add new keyslot using LUKS2 tokens to unlock existing keyslot with interactive passphrase prompt for new passphrase:
*cryptsetup luksAddKey --token-only /dev/device*
Add new keyslot using LUKS2 systemd-tpm2 tokens to unlock existing keyslot with interactive passphrase prompt for new passphrase (systemd-tpm2 token plugin must be available):
*cryptsetup luksAddKey --token-type systemd-tpm2 /dev/device*
Add new keyslot using interactive passphrase prompt for existing keyslot, reading new passphrase from key_file:
*cryptsetup luksAddKey --new-keyfile key_file /dev/device* or
*cryptsetup luksAddKey /dev/device key_file*
Add new keyslot using volume stored in volume_key_file and LUKS2 token in slot 5 to get new keyslot passphrase (token in slot 5 must exist
and respective token plugin must be available):
*cryptsetup luksAddKey --volume-key-file volume_key_file --new-token-id 5 /dev/device*
include::man/common_footer.adoc[]

View File

@@ -40,7 +40,7 @@ algorithm is always the same for all keyslots.
--new-keyfile-offset, --iter-time, --pbkdf, --pbkdf-force-iterations,
--pbkdf-memory, --pbkdf-parallel, --new-keyfile-size, --key-slot,
--force-password, --hash, --header, --disable-locks, --type,
--keyslot-cipher, --keyslot-key-size].
--keyslot-cipher, --keyslot-key-size, --timeout, --verify-passphrase].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -35,7 +35,7 @@ been wiped and make the LUKS container inaccessible.
*<options>* can be [--key-file, --keyfile-offset, --keyfile-size,
--key-slot, --hash, --header, --disable-locks, --iter-time, --pbkdf,
--pbkdf-force-iterations, --pbkdf-memory, --pbkdf-parallel,
--keyslot-cipher, --keyslot-key-size].
--keyslot-cipher, --keyslot-key-size, --timeout, --verify-passphrase].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

View File

@@ -35,12 +35,12 @@ To dump unbound key (LUKS2 format only), --unbound parameter, specific
interactively or via --key-file. Optional --volume-key-file parameter
enables unbound keyslot dump to a file.
To dump LUKS2 JSON metadata (without basic heade information like UUID)
To dump LUKS2 JSON metadata (without basic header information like UUID)
use --dump-json-metadata option.
*<options>* can be [--dump-volume-key, --dump-json-metadata, --key-file,
--keyfile-offset, --keyfile-size, --header, --disable-locks,
--volume-key-file, --type, --unbound, --key-slot].
--volume-key-file, --type, --unbound, --key-slot, --timeout].
*WARNING:* If --dump-volume-key is used with --key-file and the argument
to --key-file is '-', no validation question will be asked and no

View File

@@ -28,19 +28,20 @@ You cannot call luksFormat on a device or filesystem that is mapped or
in use, e.g., mounted filesystem, used in LVM, active RAID member, etc. The
device or filesystem has to be un-mounted in order to call luksFormat.
To use LUKS2, specify _--type luks2_.
To use specific version of LUKS format, use _--type luks1_ or _type luks2_.
*<options>* can be [--hash, --cipher, --verify-passphrase, --key-size,
--key-slot, --key-file (takes precedence over optional second argument),
--keyfile-offset, --keyfile-size, --use-random | --use-urandom, --uuid,
--keyfile-offset, --keyfile-size, --use-random, --use-urandom, --uuid,
--volume-key-file, --iter-time, --header, --pbkdf-force-iterations,
--force-password, --disable-locks].
--force-password, --disable-locks, --timeout, --type, --offset,
--align-payload (deprecated)].
For LUKS2, additional *<options>* can be [--integrity,
--integrity-no-wipe, --sector-size, --label, --subsystem, --pbkdf,
--pbkdf-memory, --pbkdf-parallel, --disable-locks, --disable-keyring,
--luks2-metadata-size, --luks2-keyslots-size, --keyslot-cipher,
--keyslot-key-size].
--keyslot-key-size, --integrity-legacy-padding].
*WARNING:* Doing a luksFormat on an existing LUKS container will make
all data in the old container permanently irretrievable unless you have a

View File

@@ -17,9 +17,11 @@ cryptsetup-luksHeaderBackup - store a binary backup of the LUKS header and keysl
== DESCRIPTION
Stores a binary backup of the LUKS header and keyslot area. +
Note: Using '-' as filename writes the header backup to a file named
*NOTE:* Using '-' as filename writes the header backup to a file named
'-'.
*<options>* can be [--header, --header-backup-file, --disable-locks].
*WARNING:* This backup file and a passphrase valid at the time of backup
allows decryption of the LUKS data area, even if the passphrase was
later changed or removed from the LUKS device. Also note that with a

View File

@@ -18,8 +18,9 @@ cryptsetup-luksHeaderRestore - restore a binary backup of the LUKS header and ke
Restores a binary backup of the LUKS header and keyslot area from the
specified file. +
Note: Using '-' as filename reads the header backup from a file named
'-'.
*NOTE:* Using '-' as filename reads the header backup from a file named '-'.
*<options>* can be [--header, --header-backup-file, --disable-locks].
*WARNING:* Header and keyslots will be replaced, only the passphrases
from the backup will work afterward.

View File

@@ -24,7 +24,7 @@ so. Removing the last passphrase makes a LUKS container permanently
inaccessible.
*<options>* can be [--key-file, --keyfile-offset, --keyfile-size,
--header, --disable-locks, --type].
--header, --disable-locks, --type, --verify-passphrase, --timeout].
*WARNING:* If you read the passphrase from stdin (without further
argument or with '-' as an argument to --key-file), batch-mode (-q) will

View File

@@ -21,7 +21,7 @@ be removed can be specified interactively, as the positional argument or
via --key-file.
*<options>* can be [--key-file, --keyfile-offset, --keyfile-size,
--header, --disable-locks, --type]
--header, --disable-locks, --type, --timeout, --verify-passphrase].
*WARNING:* If you read the passphrase from stdin (without further
argument or with '-' as an argument to --key-file), batch-mode (-q) will

View File

@@ -20,9 +20,10 @@ Resumes a suspended device and reinstates the encryption key. Prompts
interactively for a passphrase if no token is usable (LUKS2 only) or
--key-file is not given.
*<options>* can be [--key-file, --keyfile-size, --header,
--disable-keyring, --disable-locks, --token-id, --token-only,
--token-type, --type]
*<options>* can be [--key-file, --keyfile-size, --keyfile-offset,
--key-slot, --header, --disable-keyring, --disable-locks, --token-id,
--token-only, --token-type, --disable-external-tokens, --type, --tries,
--timeout, --verify-passphrase].
include::man/common_options.adoc[]
include::man/common_footer.adoc[]

Some files were not shown because too many files have changed in this diff Show More