mirror of
https://gitlab.com/cryptsetup/cryptsetup.git
synced 2025-12-09 01:40:00 +01:00
Compare commits
119 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2e97d8f8e8 | ||
|
|
7effba0f71 | ||
|
|
2ad69eba90 | ||
|
|
4d218e4cbd | ||
|
|
a0346a09ce | ||
|
|
f6e85be3ed | ||
|
|
04e921846f | ||
|
|
e37f3728d7 | ||
|
|
2062ece2ab | ||
|
|
a5fa6f1015 | ||
|
|
9bdd5bf4fe | ||
|
|
110ce5607e | ||
|
|
78f938b0e9 | ||
|
|
ad2f50316f | ||
|
|
cf534f3759 | ||
|
|
75c105f853 | ||
|
|
680eb76e45 | ||
|
|
e364041b40 | ||
|
|
de37457a75 | ||
|
|
057db3b3b3 | ||
|
|
461011ad2a | ||
|
|
aa7346bb36 | ||
|
|
5206543902 | ||
|
|
7f93a49cc3 | ||
|
|
bec86e3d5a | ||
|
|
3ba95a822f | ||
|
|
486ec44c3e | ||
|
|
8dc4877697 | ||
|
|
7415c5858d | ||
|
|
8e5411f468 | ||
|
|
3bf40bb8dd | ||
|
|
79956a4d47 | ||
|
|
2d755335de | ||
|
|
d7762c09dd | ||
|
|
957201e758 | ||
|
|
004dc271a4 | ||
|
|
a9b24ccc82 | ||
|
|
c57071a43a | ||
|
|
df27f04f61 | ||
|
|
f3e398afc5 | ||
|
|
65877efe8b | ||
|
|
96acd87f0b | ||
|
|
fcb35d4e73 | ||
|
|
0d47e5eb76 | ||
|
|
f30bbbffe7 | ||
|
|
6b88461553 | ||
|
|
700b558fb6 | ||
|
|
58b5be440f | ||
|
|
626801f7df | ||
|
|
77a345d4cb | ||
|
|
18901fd501 | ||
|
|
5b86cb5cc2 | ||
|
|
ce23225e46 | ||
|
|
09c229fe6c | ||
|
|
db56125708 | ||
|
|
5736b0a114 | ||
|
|
a21c0503f8 | ||
|
|
e52d5f3d98 | ||
|
|
0e96b9d010 | ||
|
|
dcba8c28f2 | ||
|
|
da93a3320b | ||
|
|
53607a0274 | ||
|
|
67d19f3570 | ||
|
|
54c1f71bd3 | ||
|
|
a7e2809466 | ||
|
|
3f66e9fe4b | ||
|
|
f547d0fac3 | ||
|
|
cdf272315e | ||
|
|
31303718da | ||
|
|
4192bdd731 | ||
|
|
c18aa03552 | ||
|
|
b2283f045a | ||
|
|
8e3863aa20 | ||
|
|
79899badd0 | ||
|
|
691b7a63f2 | ||
|
|
154731306b | ||
|
|
d67548adfe | ||
|
|
cfeaaa02fc | ||
|
|
c5270f85d3 | ||
|
|
45931a890d | ||
|
|
1a5c169c06 | ||
|
|
d8fbf43022 | ||
|
|
3be96efe0b | ||
|
|
99a2486b09 | ||
|
|
c3c65ee864 | ||
|
|
db0f5f8d22 | ||
|
|
8b162ca258 | ||
|
|
4f990d5a74 | ||
|
|
1349efa34d | ||
|
|
cf99ecb5a9 | ||
|
|
0d818d0a92 | ||
|
|
42b0ab437a | ||
|
|
a36de633d5 | ||
|
|
8a43d49b89 | ||
|
|
ae9c9cf369 | ||
|
|
db44c27674 | ||
|
|
efa2c7b08b | ||
|
|
a9441043bc | ||
|
|
aaf0cfa3c1 | ||
|
|
2a2444b961 | ||
|
|
2526ec92bd | ||
|
|
9bddc52601 | ||
|
|
1b96e93f91 | ||
|
|
6127b6959f | ||
|
|
330007beb2 | ||
|
|
cbfd48d949 | ||
|
|
f64064fe71 | ||
|
|
f2521889c2 | ||
|
|
642d41970d | ||
|
|
acd069fd27 | ||
|
|
c810b0514e | ||
|
|
e600024908 | ||
|
|
fd5b88449a | ||
|
|
433758e4cb | ||
|
|
5b8f762ab2 | ||
|
|
72db6e4de2 | ||
|
|
2780ccdd62 | ||
|
|
fdcabdfd28 | ||
|
|
40b876f550 |
404
FAQ
404
FAQ
@@ -64,6 +64,13 @@ A. Contributors
|
||||
installers after a complete backup of all LUKS containers has been
|
||||
made.
|
||||
|
||||
UBUNTU INSTALLER: In particular the Ubuntu installer seems to be
|
||||
quite willing to kill LUKS containers in several different ways.
|
||||
Those responsible at Ubuntu seem not to care very much (it is very
|
||||
easy to recognize a LUKS container), so treat the process of
|
||||
installing Ubuntu as a severe hazard to any LUKS container you may
|
||||
have.
|
||||
|
||||
NO WARNING ON NON-INTERACTIVE FORMAT: If you feed cryptsetup from
|
||||
STDIN (e.g. via GnuPG) on LUKS format, it does not give you the
|
||||
warning that you are about to format (and e.g. will lose any
|
||||
@@ -104,8 +111,11 @@ A. Contributors
|
||||
This issue has been acknowledged by the Ubuntu dev team, see here:
|
||||
http://launchpad.net/bugs/420080
|
||||
|
||||
Update 7/2012: I am unsure whether this has been fixed by now, best
|
||||
be careful.
|
||||
Update 4/2013: I am still unsure whether this has been fixed by
|
||||
now, best be careful. They also seem to have added even more LUKS
|
||||
killer functionality to the Ubuntu installer. I can only strongly
|
||||
recommended to not install Ubuntu on a system with existing LUKS
|
||||
containers without complete backups.
|
||||
|
||||
|
||||
* 1.4 My LUKS-device is broken! Help!
|
||||
@@ -136,13 +146,17 @@ A. Contributors
|
||||
|
||||
* 1.5 Who wrote this?
|
||||
|
||||
Current FAQ maintainer is Arno Wagner <arno@wagner.name>. Other
|
||||
contributors are listed at the end. If you want to contribute, send
|
||||
your article, including a descriptive headline, to the maintainer,
|
||||
or the dm-crypt mailing list with something like "FAQ ..." in the
|
||||
subject. You can also send more raw information and have me write
|
||||
the section. Please note that by contributing to this FAQ, you
|
||||
accept the license described below.
|
||||
Current FAQ maintainer is Arno Wagner <arno@wagner.name>. If you
|
||||
want to send me encrypted email, my current PGP key is DSA key
|
||||
CB5D9718, fingerprint 12D6 C03B 1B30 33BB 13CF B774 E35C 5FA1 CB5D
|
||||
9718.
|
||||
|
||||
Other contributors are listed at the end. If you want to contribute,
|
||||
send your article, including a descriptive headline, to the
|
||||
maintainer, or the dm-crypt mailing list with something like "FAQ
|
||||
..." in the subject. You can also send more raw information and
|
||||
have me write the section. Please note that by contributing to this
|
||||
FAQ, you accept the license described below.
|
||||
|
||||
This work is under the "Attribution-Share Alike 3.0 Unported"
|
||||
license, which means distribution is unlimited, you may create
|
||||
@@ -157,14 +171,14 @@ A. Contributors
|
||||
least problems.
|
||||
|
||||
|
||||
* 1.5 Where is the project website?
|
||||
* 1.6 Where is the project website?
|
||||
|
||||
There is the project website at http://code.google.com/p/cryptsetup/
|
||||
Please do not post questions there, nobody will read them. Use
|
||||
the mailing-list instead.
|
||||
|
||||
|
||||
* 1.6 Is there a mailing-list?
|
||||
* 1.7 Is there a mailing-list?
|
||||
|
||||
Instructions on how to subscribe to the mailing-list are at on the
|
||||
project website. People are generally helpful and friendly on the
|
||||
@@ -184,7 +198,7 @@ A. Contributors
|
||||
http://dir.gmane.org/gmane.linux.kernel.device-mapper.dm-crypt
|
||||
|
||||
|
||||
* 1.7 Unsubscribe from the mailing-list
|
||||
* 1.8 Unsubscribe from the mailing-list
|
||||
|
||||
Send mail to dm-crypt-unsubscribe@saout.de from the subscribed
|
||||
account. You will get an email with instructions.
|
||||
@@ -259,6 +273,25 @@ A. Contributors
|
||||
|
||||
Just follow the on-screen instructions.
|
||||
|
||||
Note: Passphrase iteration is determined by cryptsetup depending on
|
||||
CPU power. On a slow device, this may be lower than you want. I
|
||||
recently benchmarked this on a Raspberry Pi and it came out at
|
||||
about 1/15 of the iteration count for a typical PC. If security is
|
||||
paramount, you may want to increase the time spent in iteration, at
|
||||
the cost of a slower unlock later. For the Raspberry Pi, using
|
||||
|
||||
cryptsetup luksFormat -i 15000 <target device>
|
||||
|
||||
gives you an iteration count and security level equal to an average
|
||||
PC for passphrase iteration and master-key iteration. If in doubt,
|
||||
check the iteration counts with
|
||||
|
||||
cryptsetup luksDump <target device>
|
||||
|
||||
and adjust the iteration count accordingly by creating the container
|
||||
again with a different iteration time (the number after '-i' is the
|
||||
iteration time in milicesonds) until your requirements are met.
|
||||
|
||||
05) Map the container. Here it will be mapped to /dev/mapper/c1:
|
||||
cryptsetup luksOpen <target device> c1
|
||||
|
||||
@@ -289,7 +322,63 @@ A. Contributors
|
||||
easy to make, but will compromise your security.
|
||||
|
||||
|
||||
* 2.2 What is the difference between "plain" and LUKS format?
|
||||
* 2.2 How do I set up encrypted swap?
|
||||
|
||||
As things that are confidential can end up in swap (keys,
|
||||
passphrases, etc. are usually protected against being swapped to
|
||||
disk, but other things may not be), it may be advisable to do
|
||||
something about the issue. One option is to run without swap, which
|
||||
generally works well in a desktop-context. It may cause problems
|
||||
in a server-setting or under special circumstances. The solution to
|
||||
that is to encrypt swap with a random key at boot-time.
|
||||
|
||||
NOTE: This is for Debian, and should work for Debian-derived
|
||||
distributions. For others you may have to write your own startup
|
||||
script or use other mechanisms.
|
||||
|
||||
01) Add the swap partition to /etc/crypttab. A line like the following
|
||||
should do it:
|
||||
|
||||
swap /dev/<partition> /dev/urandom swap,noearly
|
||||
|
||||
Warning: While Debian refuses to overwrite partitions with a
|
||||
filesystem or RAID signature on it, if your disk IDs may change
|
||||
(adding or removing disks, failure of disk during boot, etc.), you
|
||||
may want to take additional precautions. Yes, this means that your
|
||||
kernel device names like sda, sdb, ... can change between reboots!
|
||||
This is not a concern if you have only one disk. One possibility is
|
||||
to make sure the partition number is not present on additional
|
||||
disks or also swap there. Another is to encapsulate the swap
|
||||
partition (by making it a 1-disk RAID1 or by using LVM), so that it
|
||||
gets a persistent identifier. Specifying it directly by UUID does
|
||||
not work, unfortunately, as the UUID is part of the swap signature
|
||||
and that is not visible from the outside due to the encryption and
|
||||
in addition changes on each reboot with this setup.
|
||||
|
||||
Note: Use /dev/random if you are paranoid or in a potential
|
||||
low-entropy situation (embedded system, etc.). This may cause the
|
||||
operation to take a long time during boot. If you are in a "no
|
||||
entropy" situation, you cannot encrypt swap securely. In this
|
||||
situation you should find some entropy, also because nothing else
|
||||
using crypto will be secure, like ssh, ssl or GnuPG.
|
||||
|
||||
Note: The "noearly" option makes sure things like LVM, RAID, etc.
|
||||
are running. As swap is non-critical for boot, it is fine to start
|
||||
it late.
|
||||
|
||||
02) Add the swap partition to /etc/fstab. A line like the following
|
||||
should do it:
|
||||
|
||||
/dev/mapper/swap none swap sw 0 0
|
||||
|
||||
That is it. Reboot or start it manually to activate encrypted swap.
|
||||
Manual start would look like this:
|
||||
|
||||
/etc/init.d/crypdisks start
|
||||
swapon /dev/mapper/swap
|
||||
|
||||
|
||||
* 2.3 What is the difference between "plain" and LUKS format?
|
||||
|
||||
First, unless you happen to understand the cryptographic background
|
||||
well, you should use LUKS. It does protect the user from a lot of
|
||||
@@ -309,13 +398,24 @@ A. Contributors
|
||||
|
||||
Side-note: That has limited value against the authorities. In
|
||||
civilized countries, they cannot force you to give up a crypto-key
|
||||
anyways. In the US, the UK and dictatorships around the world,
|
||||
they can force you to give up the keys (using imprisonment or worse
|
||||
to pressure you), and in the worst case, they only need a
|
||||
nebulous "suspicion" about the presence of encrypted data. My
|
||||
advice is to either be ready to give up the keys or to not have
|
||||
anyways. In quite a few countries around the world, they can force
|
||||
you to give up the keys (using imprisonment or worse to pressure
|
||||
you, sometimes without due process), and in the worst case, they
|
||||
only need a nebulous "suspicion" about the presence of encrypted
|
||||
data. Sometimes this applies to everybody, sometimes only when you
|
||||
are suspected of having "illicit data" (definition subject to
|
||||
change) and sometimes specifically when crossing a border. Note
|
||||
that this is going on in countries like the US and the UK, to
|
||||
different degrees and sometimes with courts restricting what the
|
||||
authorities can actually demand.
|
||||
|
||||
My advice is to either be ready to give up the keys or to not have
|
||||
encrypted data when traveling to those countries, especially when
|
||||
crossing the borders.
|
||||
crossing the borders. The latter also means not having any
|
||||
high-entropy (random) data areas on your disk, unless you can
|
||||
explain them and demonstrate that explanation. Hence doing a
|
||||
zero-wipe of all free space, including unused space, may be a good
|
||||
idea.
|
||||
|
||||
Disadvantages are that you do not have all the nice features that
|
||||
the LUKS metadata offers, like multiple passphrases that can be
|
||||
@@ -343,7 +443,7 @@ A. Contributors
|
||||
non-default XTS mode).
|
||||
|
||||
|
||||
* 2.3 Can I encrypt an already existing, non-empty partition to use
|
||||
* 2.4 Can I encrypt an already existing, non-empty partition to use
|
||||
LUKS?
|
||||
|
||||
There is no converter, and it is not really needed. The way to do
|
||||
@@ -358,7 +458,7 @@ A. Contributors
|
||||
to be in a filesystem.
|
||||
|
||||
|
||||
* 2.4 How do I use LUKS with a loop-device?
|
||||
* 2.5 How do I use LUKS with a loop-device?
|
||||
|
||||
This can be very handy for experiments. Setup is just the same as
|
||||
with any block device. If you want, for example, to use a 100MiB
|
||||
@@ -372,7 +472,7 @@ A. Contributors
|
||||
To unmap the file when done, use "losetup -d /dev/loop0".
|
||||
|
||||
|
||||
* 2.5 When I add a new key-slot to LUKS, it asks for a passphrase but
|
||||
* 2.6 When I add a new key-slot to LUKS, it asks for a passphrase but
|
||||
then complains about there not being a key-slot with that
|
||||
passphrase?
|
||||
|
||||
@@ -384,7 +484,7 @@ A. Contributors
|
||||
new key-slot.
|
||||
|
||||
|
||||
* 2.6 Encryption on top of RAID or the other way round?
|
||||
* 2.7 Encryption on top of RAID or the other way round?
|
||||
|
||||
Unless you have special needs, place encryption between RAID and
|
||||
filesystem, i.e. encryption on top of RAID. You can do it the other
|
||||
@@ -393,16 +493,39 @@ A. Contributors
|
||||
not work anymore. Therefore it is better to encrypt the RAID
|
||||
device, e.g. /dev/dm0 .
|
||||
|
||||
This means that the typical layering looks like this:
|
||||
|
||||
* 2.7 How do I read a dm-crypt key from file?
|
||||
Filesystem <- top
|
||||
|
|
||||
Encryption
|
||||
|
|
||||
RAID
|
||||
|
|
||||
Raw partitions
|
||||
|
|
||||
Raw disks <- bottom
|
||||
|
||||
The big advantage is that you can manage the RAID container just
|
||||
like any RAID container, it does not care that what is in it is
|
||||
encrypted.
|
||||
|
||||
Note that the file will still be hashed first, just like keyboard
|
||||
input. Use the --key-file option, like this:
|
||||
|
||||
* 2.8 How do I read a dm-crypt key from file?
|
||||
|
||||
Use the --key-file option, like this:
|
||||
|
||||
cryptsetup create --key-file keyfile e1 /dev/loop0
|
||||
|
||||
This will read the binary key from file, i.e. no hashing or
|
||||
transformation will be applied to the keyfile before its bits are
|
||||
used as key. Extra bits (beyond the length of the key) at the end
|
||||
are ignored. Note that if you read from STDIN, the data will still
|
||||
be hashed, just as a key read interactively from the terminal. See
|
||||
the man-page sections "NOTES ON PASSPHRASE PROCESSING..." for more
|
||||
detail.
|
||||
|
||||
* 2.8 How do I read a LUKS slot key from file?
|
||||
|
||||
* 2.9 How do I read a LUKS slot key from file?
|
||||
|
||||
What you really do here is to read a passphrase from file, just as
|
||||
you would with manual entry of a passphrase for a key-slot. You can
|
||||
@@ -428,7 +551,7 @@ A. Contributors
|
||||
cryptsetup luksOpen --key-file keyfile /dev/loop0 e1
|
||||
|
||||
|
||||
* 2.9 How do I read the LUKS master key from file?
|
||||
* 2.10 How do I read the LUKS master key from file?
|
||||
|
||||
The question you should ask yourself first is why you would want to
|
||||
do this. The only legitimate reason I can think of is if you want
|
||||
@@ -439,7 +562,7 @@ A. Contributors
|
||||
do this here.
|
||||
|
||||
|
||||
* 2.10 What are the security requirements for a key read from file?
|
||||
* 2.11 What are the security requirements for a key read from file?
|
||||
|
||||
A file-stored key or passphrase has the same security requirements
|
||||
as one entered interactively, however you can use random bytes and
|
||||
@@ -451,7 +574,7 @@ A. Contributors
|
||||
head -c 256 /dev/random > keyfile
|
||||
|
||||
|
||||
* 2.11 If I map a journaled file system using dm-crypt/LUKS, does it
|
||||
* 2.12 If I map a journaled file system using dm-crypt/LUKS, does it
|
||||
still provide its usual transactional guarantees?
|
||||
|
||||
Yes, it does, unless a very old kernel is used. The required flags
|
||||
@@ -479,7 +602,7 @@ A. Contributors
|
||||
should improve further and eventually the problem should go away.
|
||||
|
||||
|
||||
* 2.12 Can I use LUKS or cryptsetup with a more secure (external)
|
||||
* 2.13 Can I use LUKS or cryptsetup with a more secure (external)
|
||||
medium for key storage, e.g. TPM or a smartcard?
|
||||
|
||||
Yes, see the answers on using a file-supplied key. You do have to
|
||||
@@ -488,8 +611,12 @@ A. Contributors
|
||||
own tool that in turn gets the key from the more secure key
|
||||
storage.
|
||||
|
||||
For TPM support, you may want to have a look at tpm-luks at
|
||||
https://github.com/shpedoikal/tpm-luks. Note that tpm-luks is not
|
||||
related to the cryptsetup project.
|
||||
|
||||
* 2.13 Can I resize a dm-crypt or LUKS partition?
|
||||
|
||||
* 2.14 Can I resize a dm-crypt or LUKS partition?
|
||||
|
||||
Yes, you can, as neither dm-crypt nor LUKS stores partition size.
|
||||
Whether you should is a different question. Personally I recommend
|
||||
@@ -509,6 +636,59 @@ A. Contributors
|
||||
for that.
|
||||
|
||||
|
||||
* 2.15 How do I Benchmark the Ciphers, Hashes and Modes?
|
||||
|
||||
Since version 1.60 cryptsetup supports the "benchmark" command.
|
||||
Simply run as root:
|
||||
|
||||
cryptsetup benchmark
|
||||
|
||||
It will output first iterations/second for the key-derivation
|
||||
function PBKDF2 parameterized with different hash-functions, and
|
||||
then the raw encryption speed of ciphers with different modes and
|
||||
key-sizes. You can get more than the default benchmarks, see the
|
||||
man-page for the relevant parameters. Note that XTS mode takes two
|
||||
keys, hence the listed key sizes are double that for other modes
|
||||
and half of it is the cipher key, the other half is the XTS key.
|
||||
|
||||
|
||||
* 2.16 How do I Verify I have an Authentic cryptsetup Source Package?
|
||||
|
||||
Current maintainer is Milan Broz and he signs the release packages
|
||||
with his PGP key. The key he currently uses is the "RSA key ID
|
||||
D93E98FC", fingerprint 2A29 1824 3FDE 4664 8D06 86F9 D9B0 577B
|
||||
D93E 98FC. While I have every confidence this really is his key and
|
||||
that he is who he claims to be, don't depend on it if your life is
|
||||
at stake. For that matter, if your life is at stake, don't depend
|
||||
on me being who I claim to be either.
|
||||
|
||||
That said, as cryptsetup is under good version control, a malicious
|
||||
change should be noticed sooner or later, but it may take a while.
|
||||
Also, the attacker model makes compromising the sources in a
|
||||
non-obvious way pretty hard. Sure, you could put the master-key
|
||||
somewhere on disk, but that is rather obvious as soon as somebody
|
||||
looks as there would be data in an empty LUKS container in a place
|
||||
it should not be. Doing this in a more nefarious way, for example
|
||||
hiding the master-key in the salts, would need a look at the
|
||||
sources to be discovered, but I think that somebody would find that
|
||||
sooner or later as well.
|
||||
|
||||
That said, this discussion is really a lot more complicated and
|
||||
longer as an FAQ can sustain. If in doubt, ask on the mailing list.
|
||||
|
||||
|
||||
* 2.17 Is there a concern with 4k Sectors?
|
||||
|
||||
Not from dm-crypt itself. Encryption will be done in 512B blocks,
|
||||
but if the partition and filesystem are aligned correctly and the
|
||||
filesystem uses multiples of 4kiB as block size, the dm-crypt layer
|
||||
will just process 8 x 512B = 4096B at a time with negligible
|
||||
overhead. LUKS does place data at an offset, which is 2MiB per
|
||||
default and will not break alignment. See also Item 6.12 of this
|
||||
FAQ for more details. Note that if your partition or filesystem is
|
||||
misaligned, dm-crypt can make the effect worse though.
|
||||
|
||||
|
||||
3. Common Problems
|
||||
|
||||
|
||||
@@ -617,7 +797,38 @@ A. Contributors
|
||||
diagnosing and (if still possible) repairing this.
|
||||
|
||||
|
||||
* 4.2 Can a bad RAM module cause problems?
|
||||
* 4.2 I cannot unlock my LUKS container! What could be the problem?
|
||||
|
||||
First, make sure you have a correct passphrase. Then make sure you
|
||||
have the correct key-map and correct keyboard. And then make sure
|
||||
you have the correct character set and encoding, see also
|
||||
"PASSPHRASE CHARACTER SET" under Section 1.2.
|
||||
|
||||
If you are sure you are entering the passphrase right, there is the
|
||||
possibility that the respective key-slot has been damaged. There
|
||||
is no way to recover a damaged key-slot, except from a header
|
||||
backup (see Section 6). For security reasons, there is also no
|
||||
checksum in the key-slots that could tell you whether a key-slot has
|
||||
been damaged. The only checksum present allows recognition of a
|
||||
correct passphrase, but that only works if the passphrase is
|
||||
correct and the respective key-slot is intact.
|
||||
|
||||
In order to find out whether a key-slot is damaged one has to look
|
||||
for "non-random looking" data in it. There is a tool that
|
||||
automatizes this in the cryptsetup distribution from version 1.6.0
|
||||
onwards. It is located in misc/keyslot_checker/. Instructions how
|
||||
to use and how to interpret results are in the README file. Note
|
||||
that this tool requires a libcryptsetup from cryptsetup 1.6.0 or
|
||||
later (which means libcryptsetup.so.4.5.0 or later). If the tool
|
||||
complains about missing functions in libcryptsetup, you likely
|
||||
have an earlier version from your distribution still installed. You
|
||||
can either point the symbolic link(s) from libcryptsetup.so.4 to
|
||||
the new version manually, or you can uninstall the distribution
|
||||
version of cryptsetup and re-install that from cryptsetup >= 1.6.0
|
||||
again to fix this.
|
||||
|
||||
|
||||
* 4.3 Can a bad RAM module cause problems?
|
||||
|
||||
LUKS and dm-crypt can give the RAM quite a workout, especially when
|
||||
combined with software RAID. In particular the combination RAID5 +
|
||||
@@ -659,7 +870,7 @@ A. Contributors
|
||||
did a verify.
|
||||
|
||||
|
||||
* 4.3 How do I test RAM?
|
||||
* 4.4 How do I test RAM?
|
||||
|
||||
First you should know that overclocking often makes memory
|
||||
problems worse. So if you overclock (which I strongly recommend
|
||||
@@ -733,8 +944,8 @@ A. Contributors
|
||||
is easier than it actually is is fine. An attacker may still have
|
||||
vastly higher cost than estimated here.
|
||||
|
||||
LUKS uses SHA1 for hasing per default. The claim in the reference is
|
||||
63 billion tries/second for SHA1. We will leave aside the check
|
||||
LUKS uses SHA1 for hashing per default. The claim in the reference
|
||||
is 63 billion tries/second for SHA1. We will leave aside the check
|
||||
whether a try actually decrypts a key-slot. Now, the machine has 25
|
||||
GPUs, which I will estimate at an overall lifetime cost of USD/EUR
|
||||
1000 each, and an useful lifetime of 2 years. (This is on the low
|
||||
@@ -1181,7 +1392,9 @@ A. Contributors
|
||||
|
||||
XTS mode is potentially even more secure than cbc-essiv (but only if
|
||||
cbc-essiv is insecure in your scenario). It is a NIST standard and
|
||||
used, e.g. in Truecrypt. At the moment, if you want to use it, you
|
||||
used, e.g. in Truecrypt. From version 1.6.0 of cryptsetup onwards,
|
||||
aes-xts-plain64 is the default for LUKS. If you want to use it
|
||||
with a cryptsetup before version 1.6.0 or with plain dm-crypt, you
|
||||
have to specify it manually as "aes-xts-plain", i.e.
|
||||
|
||||
cryptsetup -c aes-xts-plain luksFormat <device>
|
||||
@@ -1272,7 +1485,7 @@ A. Contributors
|
||||
foot, you can figure out how to do it yourself.
|
||||
|
||||
|
||||
* 5.19 What about SSDs or Flash Drives?
|
||||
* 5.19 What about SSDs, Flash and Hybrid Drives?
|
||||
|
||||
The problem is that you cannot reliably erase parts of these
|
||||
devices, mainly due to wear-leveling and possibly defect
|
||||
@@ -1286,7 +1499,7 @@ A. Contributors
|
||||
done in some fashion so that larger writes do not cause a lot of
|
||||
small internal updates.
|
||||
|
||||
The thing is that the mappings between outside-adressable sectors
|
||||
The thing is that the mappings between outside-addressable sectors
|
||||
and inside sectors is arbitrary (and the vendors are not talking).
|
||||
Also the discarded sectors are not necessarily erased immediately.
|
||||
They may linger a long time.
|
||||
@@ -1315,28 +1528,107 @@ A. Contributors
|
||||
|
||||
If you trust the device vendor (you probably should not...) you can
|
||||
try an ATA "secure erase" command for SSDs. That does not work for
|
||||
USB keys though. And if it finishes after a few seconds, it was
|
||||
possibly faked by the SSD.
|
||||
USB keys though and may or may not be secure for a hybrid drive. If
|
||||
it finishes on an SSD after a few seconds, it was possibly faked.
|
||||
Unfortunately, for hybrid drives that indicator does not work, as
|
||||
the drive may well take the time to truly erase the magnetic part,
|
||||
but only mark the SSD/Flash part as erased while data is still in
|
||||
there.
|
||||
|
||||
If you can do without password management and are fine with doing
|
||||
physical destruction for permenently deleting data (allways after
|
||||
physical destruction for permanently deleting data (always after
|
||||
one or several full overwrites!), you can use plain dm-crypt or
|
||||
LUKS.
|
||||
|
||||
If you want or need the original LUKS security features to work,
|
||||
If you want or need all the original LUKS security features to work,
|
||||
you can use a detached LUKS header and put that on a conventional,
|
||||
magnetic disk. That leaves potentially old encrypted data in the
|
||||
pools on the disk, but otherwise you get LUKS with the same
|
||||
security as on a magnetic disk.
|
||||
|
||||
If you are concerned about your laptop being stolen, you are likely
|
||||
fine using LUKS on an SSD. An attacker would need to have access
|
||||
to an old passphrase (and the key-slot for this old passphrase
|
||||
would actually need to still be somewhere in the SSD) for your
|
||||
data to be at risk. So unless you pasted your old passphrase all
|
||||
over the Internet or the attacker has knowledge of it from some
|
||||
other source and does a targetted laptop theft to get at your
|
||||
data, you should be fine.
|
||||
fine using LUKS on an SSD or hybrid drive. An attacker would need
|
||||
to have access to an old passphrase (and the key-slot for this old
|
||||
passphrase would actually need to still be somewhere in the SSD)
|
||||
for your data to be at risk. So unless you pasted your old
|
||||
passphrase all over the Internet or the attacker has knowledge of
|
||||
it from some other source and does a targeted laptop theft to get
|
||||
at your data, you should be fine.
|
||||
|
||||
|
||||
* 5.20 LUKS is broken! It uses SHA-1!
|
||||
|
||||
No, it is not. SHA-1 is (academically) broken for finding
|
||||
collisions, but not for using it in a key-derivation function. And
|
||||
that collision vulnerability is for non-iterated use only. And you
|
||||
need the hash-value in verbatim.
|
||||
|
||||
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 master key, breaking everything. So
|
||||
basically, this SHA-1 vulnerability allows you to open a LUKS
|
||||
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 broken for a specific different use. The way the mechanism
|
||||
is used matters very much. A hash that is broken for one use can be
|
||||
completely secure for other uses and here it is.
|
||||
|
||||
|
||||
* 5.21 Why is there no "Nuke-Option"?
|
||||
|
||||
A "Nuke-Option" or "Kill-switch" is a password that when entered
|
||||
upon unlocking instead wipes the header and all passwords. So when
|
||||
somebody forces you to enter your password, you can destroy the
|
||||
data instead.
|
||||
|
||||
While this sounds attractive at first glance, it does not make sense
|
||||
once a real security analysis is done. One problem is that you have
|
||||
to have some kind of HSM (Hardware Security Module) in order to
|
||||
implement it securely. In the movies, a HSM starts to smoke and
|
||||
melt once the Nuke-Option has been activated. In reality, it just
|
||||
wipes some battery-backed RAM cells. A proper HSM costs something
|
||||
like 20'000...100'000 EUR/USD and there a Nuke-Option may make some
|
||||
sense. BTW, a chipcard or a TPM is not a HSM, although some
|
||||
vendors are promoting that myth.
|
||||
|
||||
Now, a proper HSMs will have a wipe option but not a Nuke-Option,
|
||||
i.e. you can explicitly wipe the HSM, but by a different process
|
||||
than unlocking it takes. Why is that? Simple: If somebody can force
|
||||
you to reveal passwords, then they can also do bad things to you if
|
||||
you do not or if you enter a nuke password instead. Think locking
|
||||
you up for a few years for "destroying evidence" or for far longer
|
||||
and without trial for being a "terrorist suspect". No HSM maker
|
||||
will want to expose its customers to that risk.
|
||||
|
||||
Now think of the typical LUKS application scenario, i.e. disk
|
||||
encryption. Usually the ones forcing you to hand over your password
|
||||
will have access to the disk as well, and, if they have any real
|
||||
suspicion, they will mirror your disk before entering anything
|
||||
supplied by you. This neatly negates any Nuke-Option. If they have
|
||||
no suspicion (just harassing people that cross some border for
|
||||
example), the Nuke-Option would work, but see above about likely
|
||||
negative consequences and remember that a Nuke-Option may not work
|
||||
reliably on SSD and hybrid drives anyways.
|
||||
|
||||
Hence my advice is to never take data that you do not want to reveal
|
||||
into any such situation in the first place. There is no need to
|
||||
transfer data on physical carriers today. The Internet makes it
|
||||
quite possible to transfer data between arbitrary places and modern
|
||||
encryption makes it secure. If you do it right, nobody will even be
|
||||
able to identify source or destination. (How to do that is out of
|
||||
scope of this document. It does require advanced skills in this age
|
||||
of pervasive surveillance.)
|
||||
|
||||
Hence, LUKS has not kill option because it would do much more harm
|
||||
than good.
|
||||
|
||||
Still, if you have a good use-case (i.e. non-abstract real-world
|
||||
situation) where a Nuke-Option would actually be beneficial, please
|
||||
let me know.
|
||||
|
||||
|
||||
6. Backup and Data Recovery
|
||||
@@ -1617,7 +1909,7 @@ http://code.google.com/p/cryptsetup/source/browse/misc/luks-header-from-active
|
||||
change the password, you basically have to create a second
|
||||
encrypted device with the new passphrase and copy your data over.
|
||||
On the plus side, if you accidentally overwrite any part of a
|
||||
dm-crypt device, the damage will be limited to the are you
|
||||
dm-crypt device, the damage will be limited to the area you
|
||||
overwrote.
|
||||
|
||||
|
||||
@@ -1889,6 +2181,16 @@ http://code.google.com/p/cryptsetup/source/browse/misc/luks-header-from-active
|
||||
not be used anymore as well. My advice would be to drop SLED 10.
|
||||
|
||||
|
||||
* 8.3 Gcrypt after 1.5.3 breaks Whirlpool
|
||||
|
||||
It is the other way round: In gcrypt 1.5.3 and before Whirlpool is
|
||||
broken and it was fixed in the next version. If you selected
|
||||
whirlpool as hash on creation of a LUKS container, it does not work
|
||||
anymore with the fixed library. Currently, the only work-around is
|
||||
to decrypt with the old version. This also shows one risk of using
|
||||
rarely used settings.
|
||||
|
||||
|
||||
9. References and Further Reading
|
||||
|
||||
|
||||
|
||||
2
README
2
README
@@ -18,7 +18,7 @@ MAILING LIST:
|
||||
|
||||
DOWNLOAD:
|
||||
|
||||
http://code.google.com/p/cryptsetup/downloads/
|
||||
https://www.kernel.org/pub/linux/utils/cryptsetup/
|
||||
|
||||
SOURCE CODE:
|
||||
|
||||
|
||||
12
TODO
12
TODO
@@ -4,5 +4,13 @@ Version 1.7:
|
||||
- TRIM for keyslots
|
||||
- Do we need crypt_data_path() - path to data device (if differs)?
|
||||
- Resync ETA time is not accurate, calculate it better (last minute window?).
|
||||
- Crypt benchmark cannot ttest ECB mode.
|
||||
- Log doesn't work yet in early binary start (FIPS message).
|
||||
- Crypt benchmark cannot test ECB mode.
|
||||
- crypto backend should initialise itself only once (debug log)
|
||||
- Some crypt backends are inefective fo PBKDF2 (missing fast key reset)
|
||||
Add optimisation to internal PBKDF2 (hash HMAC key in advance).
|
||||
- Kernel backend doesn't allow PBKDF2 key size > 20480 bytes
|
||||
(should be fixed with optimisation above).
|
||||
- Add test vectors to internal PBKDF2 code.
|
||||
- Add support for Nettle PBKDF2.
|
||||
- Extend existing LUKS header to use another KDF? (https://password-hashing.net/)
|
||||
- Fix all crazy automake warnings (or switch to Cmake).
|
||||
|
||||
@@ -78,7 +78,7 @@ autopoint --force $AP_OPTS
|
||||
libtoolize --force --copy
|
||||
aclocal -I m4 $AL_OPTS
|
||||
autoheader $AH_OPTS
|
||||
automake --add-missing --gnu $AM_OPTS
|
||||
automake --add-missing --copy --gnu $AM_OPTS
|
||||
autoconf $AC_OPTS
|
||||
|
||||
if test x$NOCONFIGURE = x; then
|
||||
|
||||
37
configure.ac
37
configure.ac
@@ -1,17 +1,24 @@
|
||||
AC_PREREQ([2.67])
|
||||
AC_INIT([cryptsetup],[1.6.0])
|
||||
AC_INIT([cryptsetup],[1.6.4])
|
||||
|
||||
dnl library version from <major>.<minor>.<release>[-<suffix>]
|
||||
LIBCRYPTSETUP_VERSION=$(echo $PACKAGE_VERSION | cut -f1 -d-)
|
||||
LIBCRYPTSETUP_VERSION_INFO=9:0:5
|
||||
dnl library file name for FIPS selfcheck
|
||||
LIBCRYPTSETUP_VERSION_FIPS="libcryptsetup.so.4"
|
||||
FIPS_MODULE_FILE="/etc/system-fips"
|
||||
|
||||
AC_CONFIG_SRCDIR(src/cryptsetup.c)
|
||||
AC_CONFIG_MACRO_DIR([m4])
|
||||
|
||||
AC_CONFIG_HEADERS([config.h:config.h.in])
|
||||
AM_INIT_AUTOMAKE(dist-bzip2)
|
||||
|
||||
# We do not want to run test in parallel. Really.
|
||||
# http://lists.gnu.org/archive/html/automake/2013-01/msg00060.html
|
||||
|
||||
# For old automake use this
|
||||
#AM_INIT_AUTOMAKE(dist-bzip2)
|
||||
AM_INIT_AUTOMAKE([dist-bzip2 1.12 serial-tests])
|
||||
|
||||
if test "x$prefix" = "xNONE"; then
|
||||
sysconfdir=/etc
|
||||
@@ -32,7 +39,7 @@ PKG_PROG_PKG_CONFIG
|
||||
AC_HEADER_DIRENT
|
||||
AC_HEADER_STDC
|
||||
AC_CHECK_HEADERS(fcntl.h malloc.h inttypes.h sys/ioctl.h sys/mman.h \
|
||||
ctype.h unistd.h locale.h)
|
||||
ctype.h unistd.h locale.h byteswap.h endian.h)
|
||||
|
||||
AC_CHECK_HEADERS(uuid/uuid.h,,[AC_MSG_ERROR([You need the uuid library.])])
|
||||
AC_CHECK_HEADER(libdevmapper.h,,[AC_MSG_ERROR([You need the device-mapper library.])])
|
||||
@@ -42,13 +49,18 @@ AC_CHECK_LIB(uuid, uuid_clear, ,[AC_MSG_ERROR([You need the uuid library.])])
|
||||
AC_SUBST(UUID_LIBS, $LIBS)
|
||||
LIBS=$saved_LIBS
|
||||
|
||||
AC_CHECK_FUNCS([posix_memalign])
|
||||
AC_SEARCH_LIBS([clock_gettime],[rt posix4])
|
||||
AC_CHECK_FUNCS([posix_memalign clock_gettime])
|
||||
|
||||
if test "x$enable_largefile" = "xno" ; then
|
||||
AC_MSG_ERROR([Building with --disable-largefile is not supported, it can cause data corruption.])
|
||||
fi
|
||||
|
||||
AC_C_CONST
|
||||
AC_C_BIGENDIAN
|
||||
AC_TYPE_OFF_T
|
||||
AC_SYS_LARGEFILE
|
||||
|
||||
AC_FUNC_FSEEKO
|
||||
AC_PROG_GCC_TRADITIONAL
|
||||
|
||||
dnl ==========================================================================
|
||||
@@ -74,6 +86,8 @@ if test "x$with_fips" = "xyes"; then
|
||||
AC_DEFINE(ENABLE_FIPS, 1, [Enable FIPS mode restrictions])
|
||||
AC_DEFINE_UNQUOTED(LIBCRYPTSETUP_VERSION_FIPS, ["$LIBCRYPTSETUP_VERSION_FIPS"],
|
||||
[library file name for FIPS selfcheck])
|
||||
AC_DEFINE_UNQUOTED(FIPS_MODULE_FILE, ["$FIPS_MODULE_FILE"],
|
||||
[file checked to determine if running in FIPS mode])
|
||||
|
||||
if test "x$enable_static" = "xyes" -o "x$enable_static_cryptsetup" = "xyes" ; then
|
||||
AC_MSG_ERROR([Static build is not compatible with FIPS.])
|
||||
@@ -118,8 +132,12 @@ AC_DEFUN([CONFIGURE_GCRYPT], [
|
||||
fi
|
||||
dnl Check if we can use gcrypt PBKDF2 (1.6.0 supports empty password)
|
||||
AC_ARG_ENABLE([gcrypt-pbkdf2], AS_HELP_STRING([--enable-gcrypt-pbkdf2],[force enable internal gcrypt PBKDF2]),
|
||||
[use_internal_pbkdf2=0],
|
||||
[AM_PATH_LIBGCRYPT([1.6.0], [use_internal_pbkdf2=0], [use_internal_pbkdf2=1])])
|
||||
if test "x$enableval" = "xyes"; then
|
||||
[use_internal_pbkdf2=0]
|
||||
else
|
||||
[use_internal_pbkdf2=1]
|
||||
fi,
|
||||
[AM_PATH_LIBGCRYPT([1.6.1], [use_internal_pbkdf2=0], [use_internal_pbkdf2=1])])
|
||||
AM_PATH_LIBGCRYPT($GCRYPT_REQ_VERSION,,[AC_MSG_ERROR([You need the gcrypt library.])])
|
||||
|
||||
if test x$enable_static_cryptsetup = xyes; then
|
||||
@@ -149,8 +167,8 @@ AC_DEFUN([CONFIGURE_OPENSSL], [
|
||||
if test x$enable_static_cryptsetup = xyes; then
|
||||
saved_PKG_CONFIG=$PKG_CONFIG
|
||||
PKG_CONFIG="$PKG_CONFIG --static"
|
||||
PKG_CHECK_MODULES([OPENSSL], [openssl])
|
||||
CRYPTO_STATIC_LIBS=$OPENSSL_LIBS
|
||||
PKG_CHECK_MODULES([OPENSSL_STATIC], [openssl])
|
||||
CRYPTO_STATIC_LIBS=$OPENSSL_STATIC_LIBS
|
||||
PKG_CONFIG=$saved_PKG_CONFIG
|
||||
fi
|
||||
NO_FIPS([])
|
||||
@@ -337,6 +355,7 @@ AC_SUBST([CRYPTO_STATIC_LIBS])
|
||||
AC_SUBST([LIBCRYPTSETUP_VERSION])
|
||||
AC_SUBST([LIBCRYPTSETUP_VERSION_INFO])
|
||||
AC_SUBST([LIBCRYPTSETUP_VERSION_FIPS])
|
||||
AC_SUBST([FIPS_MODULE_FILE])
|
||||
|
||||
dnl ==========================================================================
|
||||
AC_ARG_ENABLE([dev-random], AS_HELP_STRING([--enable-dev-random],
|
||||
|
||||
32
docs/v1.6.1-ReleaseNotes
Normal file
32
docs/v1.6.1-ReleaseNotes
Normal file
@@ -0,0 +1,32 @@
|
||||
Cryptsetup 1.6.1 Release Notes
|
||||
==============================
|
||||
|
||||
Changes since version 1.6.0
|
||||
|
||||
* Fix loop-AES keyfile parsing.
|
||||
Loop-AES keyfile should be text keyfile, reject keyfiles which
|
||||
are not properly terminated.
|
||||
|
||||
* Fix passphrase pool overflow for too long TCRYPT passphrase.
|
||||
(Maximal TCRYPT passphrase length is 64 characters.)
|
||||
|
||||
* Return EPERM (translated to exit code 2) for too long TCRYPT passphrase.
|
||||
|
||||
* Fix deactivation of device when failed underlying node disappeared.
|
||||
|
||||
* Fix API deactivate call for TCRYPT format and NULL context parameter.
|
||||
|
||||
* Improve keyslot checker example documentation.
|
||||
|
||||
* Report error message if deactivation fails and device is still busy.
|
||||
|
||||
* Make passphrase prompts more consistent (and remove "LUKS" form prompt).
|
||||
|
||||
* Fix some missing headers (compilation failed with alternative libc).
|
||||
|
||||
* Remove not functional API UUID support for plain & loopaes devices.
|
||||
(not persistent activation UUID).
|
||||
|
||||
* Properly cleanup devices on interrupt in api-test.
|
||||
|
||||
* Support all tests run if kernel is in FIPS mode.
|
||||
25
docs/v1.6.2-ReleaseNotes
Normal file
25
docs/v1.6.2-ReleaseNotes
Normal file
@@ -0,0 +1,25 @@
|
||||
Cryptsetup 1.6.2 Release Notes
|
||||
==============================
|
||||
|
||||
Changes since version 1.6.1
|
||||
|
||||
* Print error and fail if more device arguments are present for isLuks command.
|
||||
|
||||
* 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).
|
||||
|
||||
* Print a warning if system encryption is used and device is a partition.
|
||||
(TCRYPT system encryption uses whole device argument.)
|
||||
|
||||
* Disallow explicit small payload offset for LUKS detached header.
|
||||
LUKS detached header only allows data payload 0 (whole data device is used)
|
||||
or explicit offset larger than header + keyslots size.
|
||||
|
||||
* Fix boundary condition for verity device that caused failure for certain device sizes.
|
||||
|
||||
* Various fixes to documentation, including update FAQ, default modes
|
||||
and TCRYPT description.
|
||||
|
||||
* Workaround for some recent changes in automake (serial-tests).
|
||||
50
docs/v1.6.3-ReleaseNotes
Normal file
50
docs/v1.6.3-ReleaseNotes
Normal file
@@ -0,0 +1,50 @@
|
||||
Cryptsetup 1.6.3 Release Notes
|
||||
==============================
|
||||
|
||||
Changes since version 1.6.2
|
||||
|
||||
* Fix cryptsetup reencryption tool to work properly
|
||||
with devices using 4kB sectors.
|
||||
|
||||
* Always use page size if running through loop device,
|
||||
this fixes failures for external LUKS header and
|
||||
filesystem requiring 4kB block size.
|
||||
|
||||
* Fix TCRYPT system encryption mapping for multiple partitions.
|
||||
Since this commit, one can use partition directly as device parameter.
|
||||
If you need to activate such partition from image in file,
|
||||
please first use map partitioned loop device (losetup -P)
|
||||
on image.
|
||||
(Cryptsetup require partition offsets visible in kernel sysfs
|
||||
in this mode.)
|
||||
|
||||
* Support activation of old TrueCrypt containers using CBC mode
|
||||
and whitening (created in TrueCrypt version < 4.1).
|
||||
This requires Linux kernel 3.13 or later.
|
||||
(Containers with cascade CBC ciphers are not supported.)
|
||||
|
||||
* Properly display keys in dump --dump-master-key command
|
||||
for TrueCrypt CBC containers.
|
||||
|
||||
* Rewrite cipher benchmark loop which was unreliable
|
||||
on very fast machines.
|
||||
|
||||
* Add warning if LUKS device was activated using non-cryptsetup
|
||||
library which did not set UUID properly (e.g. cryptmount).
|
||||
(Some commands, like luksSuspend, are not available then.)
|
||||
|
||||
* Support length limitation also for plain (no hash) length.
|
||||
This can be used for mapping problematic cryptosystems which
|
||||
wipes some key (losetup sometimes set last 32 byte to zero,
|
||||
which can be now configured as --hash plain:31 parameter).
|
||||
|
||||
* Fix hash limit if parameter is not a number.
|
||||
(The whole key was set to zero instead of command failure.)
|
||||
|
||||
* Unify --key-slot behavior in cryptsetup_reencrypt tool.
|
||||
|
||||
* Update dracut example scripts for system reencryption on first boot.
|
||||
|
||||
* Add command line option --tcrypt-backup to access TCRYPT backup header.
|
||||
|
||||
* Fix static compilation with OpenSSL.
|
||||
57
docs/v1.6.4-ReleaseNotes
Normal file
57
docs/v1.6.4-ReleaseNotes
Normal file
@@ -0,0 +1,57 @@
|
||||
Cryptsetup 1.6.4 Release Notes
|
||||
==============================
|
||||
|
||||
Changes since version 1.6.3
|
||||
|
||||
* Implement new erase (with alias luksErase) command.
|
||||
|
||||
The erase cryptsetup command can be used to permanently erase
|
||||
all keyslots and make the LUKS container inaccessible.
|
||||
(The only way to unlock such device is to use LUKS header backup
|
||||
created before erase command was used.)
|
||||
|
||||
You do not need to provide any password for this operation.
|
||||
|
||||
This operation is irreversible.
|
||||
|
||||
* Add internal "whirlpool_gcryptbug hash" for accessing flawed
|
||||
Whirlpool hash in gcrypt (requires gcrypt 1.6.1 or above).
|
||||
|
||||
The gcrypt version of Whirlpool hash algorithm was flawed in some
|
||||
situations.
|
||||
|
||||
This means that if you used Whirlpool in LUKS header and upgraded
|
||||
to new gcrypt library your LUKS container become inaccessible.
|
||||
|
||||
Please refer to cryptsetup FAQ for detail how to fix this situation.
|
||||
|
||||
* Allow to use --disable-gcrypt-pbkdf2 during configuration
|
||||
to force use internal PBKDF2 code.
|
||||
|
||||
* Require gcrypt 1.6.1 for imported implementation of PBKDF2
|
||||
(PBKDF2 in gcrypt 1.6.0 is too slow).
|
||||
|
||||
* Add --keep-key to cryptsetup-reencrypt.
|
||||
|
||||
This allows change of LUKS header hash (and iteration count) without
|
||||
the need to reencrypt the whole data area.
|
||||
(Reencryption of LUKS header only without master key change.)
|
||||
|
||||
* By default verify new passphrase in luksChangeKey and luksAddKey
|
||||
commands (if input is from terminal).
|
||||
|
||||
* Fix memory leak in Nettle crypto backend.
|
||||
|
||||
* Support --tries option even for TCRYPT devices in cryptsetup.
|
||||
|
||||
* Support --allow-discards option even for TCRYPT devices.
|
||||
(Note that this could destroy hidden volume and it is not suggested
|
||||
by original TrueCrypt security model.)
|
||||
|
||||
* Link against -lrt for clock_gettime to fix undefined reference
|
||||
to clock_gettime error (introduced in 1.6.2).
|
||||
|
||||
* Fix misleading error message when some algorithms are not available.
|
||||
|
||||
* Count system time in PBKDF2 benchmark if kernel returns no self usage info.
|
||||
(Workaround to broken getrusage() syscall with some hypervisors.)
|
||||
@@ -5,7 +5,7 @@ moduledir = $(libdir)/cryptsetup
|
||||
pkgconfigdir = $(libdir)/pkgconfig
|
||||
pkgconfig_DATA = libcryptsetup.pc
|
||||
|
||||
AM_CPPFLAGS = \
|
||||
AM_CPPFLAGS = -include config.h \
|
||||
-I$(top_srcdir) \
|
||||
-I$(top_srcdir)/lib/crypto_backend \
|
||||
-I$(top_srcdir)/lib/luks1 \
|
||||
@@ -16,10 +16,7 @@ AM_CPPFLAGS = \
|
||||
-DLIBDIR=\""$(libdir)"\" \
|
||||
-DPREFIX=\""$(prefix)"\" \
|
||||
-DSYSCONFDIR=\""$(sysconfdir)"\" \
|
||||
-DVERSION=\""$(VERSION)"\" \
|
||||
-D_GNU_SOURCE \
|
||||
-D_LARGEFILE64_SOURCE \
|
||||
-D_FILE_OFFSET_BITS=64
|
||||
-DVERSION=\""$(VERSION)"\"
|
||||
|
||||
lib_LTLIBRARIES = libcryptsetup.la
|
||||
|
||||
@@ -32,11 +29,11 @@ common_ldadd = \
|
||||
|
||||
libcryptsetup_la_DEPENDENCIES = $(common_ldadd) libcryptsetup.sym
|
||||
|
||||
libcryptsetup_la_LDFLAGS = \
|
||||
libcryptsetup_la_LDFLAGS = $(AM_LDFLAGS) -no-undefined \
|
||||
-Wl,--version-script=$(top_srcdir)/lib/libcryptsetup.sym \
|
||||
-version-info @LIBCRYPTSETUP_VERSION_INFO@
|
||||
|
||||
libcryptsetup_la_CFLAGS = -Wall @CRYPTO_CFLAGS@
|
||||
libcryptsetup_la_CFLAGS = -Wall $(AM_CFLAGS) @CRYPTO_CFLAGS@
|
||||
|
||||
libcryptsetup_la_LIBADD = \
|
||||
@UUID_LIBS@ \
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
*/
|
||||
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "libcryptsetup.h"
|
||||
@@ -83,7 +83,11 @@ int crypt_plain_hash(struct crypt_device *ctx __attribute__((unused)),
|
||||
/* hash[:hash_length] */
|
||||
if ((s = strchr(hash_name_buf, ':'))) {
|
||||
*s = '\0';
|
||||
hash_size = atoi(++s);
|
||||
s++;
|
||||
if (!*s || sscanf(s, "%zd", &hash_size) != 1) {
|
||||
log_dbg("Hash length is not a number");
|
||||
return -EINVAL;
|
||||
}
|
||||
if (hash_size > key_size) {
|
||||
log_dbg("Hash length %zd > key length %zd",
|
||||
hash_size, key_size);
|
||||
@@ -95,7 +99,16 @@ int crypt_plain_hash(struct crypt_device *ctx __attribute__((unused)),
|
||||
pad_size = 0;
|
||||
}
|
||||
|
||||
r = hash(hash_name_buf, hash_size, key, passphrase_size, passphrase);
|
||||
/* No hash, copy passphrase directly */
|
||||
if (!strcmp(hash_name_buf, "plain")) {
|
||||
if (passphrase_size < hash_size) {
|
||||
log_dbg("Too short plain passphrase.");
|
||||
return -EINVAL;
|
||||
}
|
||||
memcpy(key, passphrase, hash_size);
|
||||
r = 0;
|
||||
} else
|
||||
r = hash(hash_name_buf, hash_size, key, passphrase_size, passphrase);
|
||||
|
||||
if (r == 0 && pad_size)
|
||||
memset(key + hash_size, 0, pad_size);
|
||||
|
||||
@@ -2,7 +2,7 @@ moduledir = $(libdir)/cryptsetup
|
||||
|
||||
noinst_LTLIBRARIES = libcrypto_backend.la
|
||||
|
||||
libcrypto_backend_la_CFLAGS = -Wall @CRYPTO_CFLAGS@
|
||||
libcrypto_backend_la_CFLAGS = $(AM_CFLAGS) -Wall @CRYPTO_CFLAGS@
|
||||
|
||||
libcrypto_backend_la_SOURCES = crypto_backend.h \
|
||||
crypto_cipher_kernel.c pbkdf_check.c crc32.c
|
||||
@@ -27,4 +27,4 @@ if CRYPTO_INTERNAL_PBKDF2
|
||||
libcrypto_backend_la_SOURCES += pbkdf2_generic.c
|
||||
endif
|
||||
|
||||
AM_CPPFLAGS = -D_GNU_SOURCE -I$(top_srcdir)/lib
|
||||
AM_CPPFLAGS = -include config.h -I$(top_srcdir)/lib
|
||||
|
||||
@@ -23,7 +23,6 @@
|
||||
|
||||
#include <stdint.h>
|
||||
#include <string.h>
|
||||
#include "config.h"
|
||||
|
||||
struct crypt_device;
|
||||
struct crypt_hash;
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
|
||||
static int crypto_backend_initialised = 0;
|
||||
static int crypto_backend_secmem = 1;
|
||||
static int crypto_backend_whirlpool_bug = -1;
|
||||
static char version[64];
|
||||
|
||||
struct crypt_hash {
|
||||
@@ -42,6 +43,44 @@ struct crypt_hmac {
|
||||
int hash_len;
|
||||
};
|
||||
|
||||
/*
|
||||
* Test for wrong Whirlpool variant,
|
||||
* Ref: http://lists.gnupg.org/pipermail/gcrypt-devel/2014-January/002889.html
|
||||
*/
|
||||
static void crypt_hash_test_whirlpool_bug(void)
|
||||
{
|
||||
struct crypt_hash *h;
|
||||
char buf[2] = "\0\0", hash_out1[64], hash_out2[64];
|
||||
int r;
|
||||
|
||||
if (crypto_backend_whirlpool_bug >= 0)
|
||||
return;
|
||||
|
||||
crypto_backend_whirlpool_bug = 0;
|
||||
if (crypt_hash_init(&h, "whirlpool"))
|
||||
return;
|
||||
|
||||
/* One shot */
|
||||
if ((r = crypt_hash_write(h, &buf[0], 2)) ||
|
||||
(r = crypt_hash_final(h, hash_out1, 64))) {
|
||||
crypt_hash_destroy(h);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Split buf (crypt_hash_final resets hash state) */
|
||||
if ((r = crypt_hash_write(h, &buf[0], 1)) ||
|
||||
(r = crypt_hash_write(h, &buf[1], 1)) ||
|
||||
(r = crypt_hash_final(h, hash_out2, 64))) {
|
||||
crypt_hash_destroy(h);
|
||||
return;
|
||||
}
|
||||
|
||||
crypt_hash_destroy(h);
|
||||
|
||||
if (memcmp(hash_out1, hash_out2, 64))
|
||||
crypto_backend_whirlpool_bug = 1;
|
||||
}
|
||||
|
||||
int crypt_backend_init(struct crypt_device *ctx)
|
||||
{
|
||||
if (crypto_backend_initialised)
|
||||
@@ -70,10 +109,15 @@ int crypt_backend_init(struct crypt_device *ctx)
|
||||
gcry_control (GCRYCTL_INITIALIZATION_FINISHED, 0);
|
||||
}
|
||||
|
||||
snprintf(version, 64, "gcrypt %s%s",
|
||||
gcry_check_version(NULL),
|
||||
crypto_backend_secmem ? "" : ", secmem disabled");
|
||||
crypto_backend_initialised = 1;
|
||||
crypt_hash_test_whirlpool_bug();
|
||||
|
||||
snprintf(version, 64, "gcrypt %s%s%s",
|
||||
gcry_check_version(NULL),
|
||||
crypto_backend_secmem ? "" : ", secmem disabled",
|
||||
crypto_backend_whirlpool_bug > 0 ? ", flawed whirlpool" : ""
|
||||
);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -87,6 +131,23 @@ uint32_t crypt_backend_flags(void)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const char *crypt_hash_compat_name(const char *name, unsigned int *flags)
|
||||
{
|
||||
const char *hash_name = name;
|
||||
|
||||
/* "whirlpool_gcryptbug" is out shortcut to flawed whirlpool
|
||||
* in libgcrypt < 1.6.0 */
|
||||
if (name && !strcasecmp(name, "whirlpool_gcryptbug")) {
|
||||
#if GCRYPT_VERSION_NUMBER >= 0x010601
|
||||
if (flags)
|
||||
*flags |= GCRY_MD_FLAG_BUGEMU1;
|
||||
#endif
|
||||
hash_name = "whirlpool";
|
||||
}
|
||||
|
||||
return hash_name;
|
||||
}
|
||||
|
||||
/* HASH */
|
||||
int crypt_hash_size(const char *name)
|
||||
{
|
||||
@@ -94,7 +155,7 @@ int crypt_hash_size(const char *name)
|
||||
|
||||
assert(crypto_backend_initialised);
|
||||
|
||||
hash_id = gcry_md_map_name(name);
|
||||
hash_id = gcry_md_map_name(crypt_hash_compat_name(name, NULL));
|
||||
if (!hash_id)
|
||||
return -EINVAL;
|
||||
|
||||
@@ -104,6 +165,7 @@ int crypt_hash_size(const char *name)
|
||||
int crypt_hash_init(struct crypt_hash **ctx, const char *name)
|
||||
{
|
||||
struct crypt_hash *h;
|
||||
unsigned int flags = 0;
|
||||
|
||||
assert(crypto_backend_initialised);
|
||||
|
||||
@@ -111,13 +173,13 @@ int crypt_hash_init(struct crypt_hash **ctx, const char *name)
|
||||
if (!h)
|
||||
return -ENOMEM;
|
||||
|
||||
h->hash_id = gcry_md_map_name(name);
|
||||
h->hash_id = gcry_md_map_name(crypt_hash_compat_name(name, &flags));
|
||||
if (!h->hash_id) {
|
||||
free(h);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (gcry_md_open(&h->hd, h->hash_id, 0)) {
|
||||
if (gcry_md_open(&h->hd, h->hash_id, flags)) {
|
||||
free(h);
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -173,6 +235,7 @@ int crypt_hmac_init(struct crypt_hmac **ctx, const char *name,
|
||||
const void *buffer, size_t length)
|
||||
{
|
||||
struct crypt_hmac *h;
|
||||
unsigned int flags = GCRY_MD_FLAG_HMAC;
|
||||
|
||||
assert(crypto_backend_initialised);
|
||||
|
||||
@@ -180,13 +243,13 @@ int crypt_hmac_init(struct crypt_hmac **ctx, const char *name,
|
||||
if (!h)
|
||||
return -ENOMEM;
|
||||
|
||||
h->hash_id = gcry_md_map_name(name);
|
||||
h->hash_id = gcry_md_map_name(crypt_hash_compat_name(name, &flags));
|
||||
if (!h->hash_id) {
|
||||
free(h);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (gcry_md_open(&h->hd, h->hash_id, GCRY_MD_FLAG_HMAC)) {
|
||||
if (gcry_md_open(&h->hd, h->hash_id, flags)) {
|
||||
free(h);
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -261,15 +324,17 @@ int crypt_pbkdf(const char *kdf, const char *hash,
|
||||
char *key, size_t key_length,
|
||||
unsigned int iterations)
|
||||
{
|
||||
const char *hash_name = crypt_hash_compat_name(hash, NULL);
|
||||
|
||||
#if USE_INTERNAL_PBKDF2
|
||||
if (!kdf || strncmp(kdf, "pbkdf2", 6))
|
||||
return -EINVAL;
|
||||
|
||||
return pkcs5_pbkdf2(hash, password, password_length, salt, salt_length,
|
||||
return pkcs5_pbkdf2(hash_name, password, password_length, salt, salt_length,
|
||||
iterations, key_length, key);
|
||||
|
||||
#else /* USE_INTERNAL_PBKDF2 */
|
||||
int hash_id = gcry_md_map_name(hash);
|
||||
int hash_id = gcry_md_map_name(hash_name);
|
||||
int kdf_id;
|
||||
|
||||
if (!hash_id)
|
||||
|
||||
@@ -265,8 +265,8 @@ int crypt_hmac_final(struct crypt_hmac *ctx, char *buffer, size_t length)
|
||||
int crypt_hmac_destroy(struct crypt_hmac *ctx)
|
||||
{
|
||||
memset(ctx->key, 0, ctx->key_length);
|
||||
memset(ctx, 0, sizeof(*ctx));
|
||||
free(ctx->key);
|
||||
memset(ctx, 0, sizeof(*ctx));
|
||||
free(ctx);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -25,12 +25,24 @@
|
||||
|
||||
static long time_ms(struct rusage *start, struct rusage *end)
|
||||
{
|
||||
int count_kernel_time = 0;
|
||||
long ms;
|
||||
|
||||
if (crypt_backend_flags() & CRYPT_BACKEND_KERNEL)
|
||||
count_kernel_time = 1;
|
||||
|
||||
/*
|
||||
* FIXME: if there is no self usage info, count system time.
|
||||
* This seem like getrusage() bug in some hypervisors...
|
||||
*/
|
||||
if (!end->ru_utime.tv_sec && !start->ru_utime.tv_sec &&
|
||||
!end->ru_utime.tv_usec && !start->ru_utime.tv_usec)
|
||||
count_kernel_time = 1;
|
||||
|
||||
ms = (end->ru_utime.tv_sec - start->ru_utime.tv_sec) * 1000;
|
||||
ms += (end->ru_utime.tv_usec - start->ru_utime.tv_usec) / 1000;
|
||||
|
||||
if (crypt_backend_flags() & CRYPT_BACKEND_KERNEL) {
|
||||
if (count_kernel_time) {
|
||||
ms += (end->ru_stime.tv_sec - start->ru_stime.tv_sec) * 1000;
|
||||
ms += (end->ru_stime.tv_usec - start->ru_stime.tv_usec) / 1000;
|
||||
}
|
||||
|
||||
@@ -24,10 +24,6 @@
|
||||
#ifndef INTERNAL_H
|
||||
#define INTERNAL_H
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdarg.h>
|
||||
#include <unistd.h>
|
||||
@@ -96,7 +92,11 @@ struct device *crypt_data_device(struct crypt_device *cd);
|
||||
int crypt_confirm(struct crypt_device *cd, const char *msg);
|
||||
|
||||
char *crypt_lookup_dev(const char *dev_id);
|
||||
int crypt_sysfs_get_rotational(int major, int minor, int *rotational);
|
||||
int crypt_dev_is_rotational(int major, int minor);
|
||||
int crypt_dev_is_partition(const char *dev_path);
|
||||
char *crypt_get_partition_device(const char *dev_path, uint64_t offset, uint64_t size);
|
||||
char *crypt_get_base_device(const char *dev_path);
|
||||
uint64_t crypt_dev_partition_offset(const char *dev_path);
|
||||
|
||||
ssize_t write_blockwise(int fd, int bsize, void *buf, size_t count);
|
||||
ssize_t read_blockwise(int fd, int bsize, void *_buf, size_t count);
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
* Copyright (C) 2004, Christophe Saout <christophe@saout.de>
|
||||
* Copyright (C) 2004-2007, Clemens Fruhwirth <clemens@endorphin.org>
|
||||
* Copyright (C) 2009-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2012, Milan Broz
|
||||
* Copyright (C) 2009-2014, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -393,7 +393,7 @@ struct crypt_params_verity {
|
||||
*/
|
||||
struct crypt_params_tcrypt {
|
||||
const char *passphrase; /**< passphrase to unlock header (input only) */
|
||||
size_t passphrase_size; /**< passphrase size (input only) */
|
||||
size_t passphrase_size; /**< passphrase size (input only, max length is 64) */
|
||||
const char **keyfiles; /**< keyfile paths to unlock header (input only) */
|
||||
unsigned int keyfiles_count;/**< keyfiles count (input only) */
|
||||
const char *hash_name; /**< hash function for PBKDF */
|
||||
@@ -1019,6 +1019,9 @@ int crypt_get_verity_info(struct crypt_device *cd,
|
||||
* @param decryption_mbs measured decryption speed in MiB/s
|
||||
*
|
||||
* @return @e 0 on success or negative errno value otherwise.
|
||||
*
|
||||
* @note If encryption_buffer_size is too small and encryption time
|
||||
* cannot be properly measured, -ERANGE is returned.
|
||||
*/
|
||||
int crypt_benchmark(struct crypt_device *cd,
|
||||
const char *cipher,
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include <fcntl.h>
|
||||
#include <linux/fs.h>
|
||||
#include <uuid/uuid.h>
|
||||
#include <sys/utsname.h>
|
||||
|
||||
#include "internal.h"
|
||||
|
||||
@@ -99,6 +100,18 @@ static void set_dm_error(int level,
|
||||
|
||||
static int _dm_simple(int task, const char *name, int udev_wait);
|
||||
|
||||
static int _dm_satisfies_version(unsigned target_maj, unsigned target_min,
|
||||
unsigned actual_maj, unsigned actual_min)
|
||||
{
|
||||
if (actual_maj > target_maj)
|
||||
return 1;
|
||||
|
||||
if (actual_maj == target_maj && actual_min >= target_min)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void _dm_set_crypt_compat(const char *dm_version, unsigned crypt_maj,
|
||||
unsigned crypt_min, unsigned crypt_patch)
|
||||
{
|
||||
@@ -110,24 +123,27 @@ static void _dm_set_crypt_compat(const char *dm_version, unsigned crypt_maj,
|
||||
log_dbg("Detected dm-crypt version %i.%i.%i, dm-ioctl version %u.%u.%u.",
|
||||
crypt_maj, crypt_min, crypt_patch, dm_maj, dm_min, dm_patch);
|
||||
|
||||
if (crypt_maj >= 1 && crypt_min >= 2)
|
||||
if (_dm_satisfies_version(1, 2, crypt_maj, crypt_min))
|
||||
_dm_crypt_flags |= DM_KEY_WIPE_SUPPORTED;
|
||||
else
|
||||
log_dbg("Suspend and resume disabled, no wipe key support.");
|
||||
|
||||
if (crypt_maj >= 1 && crypt_min >= 10)
|
||||
if (_dm_satisfies_version(1, 10, crypt_maj, crypt_min))
|
||||
_dm_crypt_flags |= DM_LMK_SUPPORTED;
|
||||
|
||||
if (dm_maj >= 4 && dm_min >= 20)
|
||||
if (_dm_satisfies_version(4, 20, dm_maj, dm_min))
|
||||
_dm_crypt_flags |= DM_SECURE_SUPPORTED;
|
||||
|
||||
/* not perfect, 2.6.33 supports with 1.7.0 */
|
||||
if (crypt_maj >= 1 && crypt_min >= 8)
|
||||
if (_dm_satisfies_version(1, 8, crypt_maj, crypt_min))
|
||||
_dm_crypt_flags |= DM_PLAIN64_SUPPORTED;
|
||||
|
||||
if (crypt_maj >= 1 && crypt_min >= 11)
|
||||
if (_dm_satisfies_version(1, 11, crypt_maj, crypt_min))
|
||||
_dm_crypt_flags |= DM_DISCARDS_SUPPORTED;
|
||||
|
||||
if (_dm_satisfies_version(1, 13, crypt_maj, crypt_min))
|
||||
_dm_crypt_flags |= DM_TCW_SUPPORTED;
|
||||
|
||||
/* Repeat test if dm-crypt is not present */
|
||||
if (crypt_maj > 0)
|
||||
_dm_crypt_checked = 1;
|
||||
@@ -143,6 +159,16 @@ static void _dm_set_verity_compat(const char *dm_version, unsigned verity_maj,
|
||||
verity_maj, verity_min, verity_patch);
|
||||
}
|
||||
|
||||
static void _dm_kernel_info(void)
|
||||
{
|
||||
struct utsname uts;
|
||||
|
||||
if (!uname(&uts))
|
||||
log_dbg("Detected kernel %s %s %s.",
|
||||
uts.sysname, uts.release, uts.machine);
|
||||
|
||||
}
|
||||
|
||||
static int _dm_check_versions(void)
|
||||
{
|
||||
struct dm_task *dmt;
|
||||
@@ -153,6 +179,8 @@ static int _dm_check_versions(void)
|
||||
if (_dm_crypt_checked)
|
||||
return 1;
|
||||
|
||||
_dm_kernel_info();
|
||||
|
||||
/* Shut up DM while checking */
|
||||
_quiet_log = 1;
|
||||
|
||||
@@ -493,14 +521,19 @@ int dm_remove_device(struct crypt_device *cd, const char *name,
|
||||
* CRYPT-LUKS1-00000000000000000000000000000000-name
|
||||
* CRYPT-TEMP-name
|
||||
*/
|
||||
static void dm_prepare_uuid(const char *name, const char *type, const char *uuid, char *buf, size_t buflen)
|
||||
static int dm_prepare_uuid(const char *name, const char *type, const char *uuid, char *buf, size_t buflen)
|
||||
{
|
||||
char *ptr, uuid2[UUID_LEN] = {0};
|
||||
uuid_t uu;
|
||||
unsigned i = 0;
|
||||
|
||||
/* Remove '-' chars */
|
||||
if (uuid && !uuid_parse(uuid, uu)) {
|
||||
if (uuid) {
|
||||
if (uuid_parse(uuid, uu) < 0) {
|
||||
log_dbg("Requested UUID %s has invalid format.", uuid);
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (ptr = uuid2, i = 0; i < UUID_LEN; i++)
|
||||
if (uuid[i] != '-') {
|
||||
*ptr = uuid[i];
|
||||
@@ -516,6 +549,8 @@ static void dm_prepare_uuid(const char *name, const char *type, const char *uuid
|
||||
log_dbg("DM-UUID is %s", buf);
|
||||
if (i >= buflen)
|
||||
log_err(NULL, _("DM-UUID for device %s was truncated.\n"), name);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _dm_create_device(const char *name, const char *type,
|
||||
@@ -542,7 +577,8 @@ static int _dm_create_device(const char *name, const char *type,
|
||||
if (!dm_task_set_name(dmt, name))
|
||||
goto out_no_removal;
|
||||
} else {
|
||||
dm_prepare_uuid(name, type, uuid, dev_uuid, sizeof(dev_uuid));
|
||||
if (!dm_prepare_uuid(name, type, uuid, dev_uuid, sizeof(dev_uuid)))
|
||||
goto out_no_removal;
|
||||
|
||||
if (!(dmt = dm_task_create(DM_DEVICE_CREATE)))
|
||||
goto out_no_removal;
|
||||
|
||||
@@ -2,15 +2,13 @@ moduledir = $(libdir)/cryptsetup
|
||||
|
||||
noinst_LTLIBRARIES = libloopaes.la
|
||||
|
||||
libloopaes_la_CFLAGS = -Wall @CRYPTO_CFLAGS@
|
||||
libloopaes_la_CFLAGS = -Wall $(AM_CFLAGS) @CRYPTO_CFLAGS@
|
||||
|
||||
libloopaes_la_SOURCES = \
|
||||
loopaes.c \
|
||||
loopaes.h
|
||||
|
||||
AM_CPPFLAGS = -D_GNU_SOURCE \
|
||||
-D_LARGEFILE64_SOURCE \
|
||||
-D_FILE_OFFSET_BITS=64 \
|
||||
AM_CPPFLAGS = -include config.h \
|
||||
-I$(top_srcdir)/lib \
|
||||
-I$(top_srcdir)/lib/crypto_backend
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* loop-AES compatible volume handling
|
||||
*
|
||||
* Copyright (C) 2011-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2011-2012, Milan Broz
|
||||
* Copyright (C) 2011-2013, Milan Broz
|
||||
*
|
||||
* This file is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
@@ -75,16 +75,16 @@ static int hash_keys(struct crypt_device *cd,
|
||||
const char *hash_override,
|
||||
const char **input_keys,
|
||||
unsigned int keys_count,
|
||||
unsigned int key_len_output)
|
||||
unsigned int key_len_output,
|
||||
unsigned int key_len_input)
|
||||
{
|
||||
const char *hash_name;
|
||||
char tweak, *key_ptr;
|
||||
unsigned i, key_len_input;
|
||||
unsigned int i;
|
||||
int r;
|
||||
|
||||
hash_name = hash_override ?: get_hash(key_len_output);
|
||||
tweak = get_tweak(keys_count);
|
||||
key_len_input = strlen(input_keys[0]);
|
||||
|
||||
if (!keys_count || !key_len_output || !hash_name || !key_len_input) {
|
||||
log_err(cd, _("Key processing error (using hash %s).\n"),
|
||||
@@ -134,7 +134,8 @@ int LOOPAES_parse_keyfile(struct crypt_device *cd,
|
||||
size_t buffer_len)
|
||||
{
|
||||
const char *keys[LOOPAES_KEYS_MAX];
|
||||
unsigned i, key_index, key_len, offset;
|
||||
unsigned int key_lengths[LOOPAES_KEYS_MAX];
|
||||
unsigned int i, key_index, key_len, offset;
|
||||
|
||||
log_dbg("Parsing loop-AES keyfile of size %d.", buffer_len);
|
||||
|
||||
@@ -154,33 +155,45 @@ int LOOPAES_parse_keyfile(struct crypt_device *cd,
|
||||
|
||||
offset = 0;
|
||||
key_index = 0;
|
||||
key_lengths[0] = 0;
|
||||
while (offset < buffer_len && key_index < LOOPAES_KEYS_MAX) {
|
||||
keys[key_index++] = &buffer[offset];
|
||||
while (offset < buffer_len && buffer[offset])
|
||||
keys[key_index] = &buffer[offset];
|
||||
key_lengths[key_index] = 0;;
|
||||
while (offset < buffer_len && buffer[offset]) {
|
||||
offset++;
|
||||
key_lengths[key_index]++;
|
||||
}
|
||||
if (offset == buffer_len) {
|
||||
log_dbg("Unterminated key #%d in keyfile.", key_index);
|
||||
log_err(cd, _("Incompatible loop-AES keyfile detected.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
while (offset < buffer_len && !buffer[offset])
|
||||
offset++;
|
||||
key_index++;
|
||||
}
|
||||
|
||||
/* All keys must be the same length */
|
||||
key_len = key_index ? strlen(keys[0]) : 0;
|
||||
key_len = key_lengths[0];
|
||||
for (i = 0; i < key_index; i++)
|
||||
if (key_len != strlen(keys[i])) {
|
||||
if (!key_lengths[i] || (key_lengths[i] != key_len)) {
|
||||
log_dbg("Unexpected length %d of key #%d (should be %d).",
|
||||
strlen(keys[i]), i, key_len);
|
||||
key_lengths[i], i, key_len);
|
||||
key_len = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
log_dbg("Keyfile: %d keys of length %d.", key_index, key_len);
|
||||
if (offset != buffer_len || key_len == 0 ||
|
||||
(key_index != 1 && key_index !=64 && key_index != 65)) {
|
||||
log_err(cd, _("Incompatible loop-AES keyfile detected.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
log_dbg("Keyfile: %d keys of length %d.", key_index, key_len);
|
||||
|
||||
*keys_count = key_index;
|
||||
return hash_keys(cd, vk, hash, keys, key_index, crypt_get_volume_key_size(cd));
|
||||
return hash_keys(cd, vk, hash, keys, key_index,
|
||||
crypt_get_volume_key_size(cd), key_len);
|
||||
}
|
||||
|
||||
int LOOPAES_activate(struct crypt_device *cd,
|
||||
@@ -195,7 +208,6 @@ int LOOPAES_activate(struct crypt_device *cd,
|
||||
int r;
|
||||
struct crypt_dm_active_device dmd = {
|
||||
.target = DM_CRYPT,
|
||||
.uuid = crypt_get_uuid(cd),
|
||||
.size = 0,
|
||||
.flags = flags,
|
||||
.data_device = crypt_data_device(cd),
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* loop-AES compatible volume handling
|
||||
*
|
||||
* Copyright (C) 2011-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2011-2012, Milan Broz
|
||||
* Copyright (C) 2011-2013, Milan Broz
|
||||
*
|
||||
* This file is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
@@ -23,7 +23,6 @@
|
||||
#define _LOOPAES_H
|
||||
|
||||
#include <unistd.h>
|
||||
#include "config.h"
|
||||
|
||||
struct crypt_device;
|
||||
struct volume_key;
|
||||
|
||||
@@ -2,7 +2,7 @@ moduledir = $(libdir)/cryptsetup
|
||||
|
||||
noinst_LTLIBRARIES = libluks1.la
|
||||
|
||||
libluks1_la_CFLAGS = -Wall @CRYPTO_CFLAGS@
|
||||
libluks1_la_CFLAGS = -Wall $(AM_CFLAGS) @CRYPTO_CFLAGS@
|
||||
|
||||
libluks1_la_SOURCES = \
|
||||
af.c \
|
||||
@@ -11,9 +11,7 @@ libluks1_la_SOURCES = \
|
||||
af.h \
|
||||
luks.h
|
||||
|
||||
AM_CPPFLAGS = -D_GNU_SOURCE \
|
||||
-D_LARGEFILE64_SOURCE \
|
||||
-D_FILE_OFFSET_BITS=64 \
|
||||
AM_CPPFLAGS = -include config.h \
|
||||
-I$(top_srcdir)/lib \
|
||||
-I$(top_srcdir)/lib/crypto_backend
|
||||
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
*
|
||||
* Copyright (C) 2004-2006, Clemens Fruhwirth <clemens@endorphin.org>
|
||||
* Copyright (C) 2009-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2013, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -153,6 +154,7 @@ int LUKS_hdr_backup(
|
||||
{
|
||||
struct device *device = crypt_metadata_device(ctx);
|
||||
int r = 0, devfd = -1;
|
||||
ssize_t hdr_size;
|
||||
ssize_t buffer_size;
|
||||
char *buffer = NULL;
|
||||
|
||||
@@ -160,15 +162,19 @@ int LUKS_hdr_backup(
|
||||
if (r)
|
||||
return r;
|
||||
|
||||
buffer_size = LUKS_device_sectors(hdr->keyBytes) << SECTOR_SHIFT;
|
||||
hdr_size = LUKS_device_sectors(hdr->keyBytes) << SECTOR_SHIFT;
|
||||
buffer_size = size_round_up(hdr_size, crypt_getpagesize());
|
||||
|
||||
buffer = crypt_safe_alloc(buffer_size);
|
||||
if (!buffer || buffer_size < LUKS_ALIGN_KEYSLOTS) {
|
||||
if (!buffer || hdr_size < LUKS_ALIGN_KEYSLOTS || hdr_size > buffer_size) {
|
||||
r = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
|
||||
log_dbg("Storing backup of header (%u bytes) and keyslot area (%u bytes).",
|
||||
sizeof(*hdr), buffer_size - LUKS_ALIGN_KEYSLOTS);
|
||||
sizeof(*hdr), hdr_size - LUKS_ALIGN_KEYSLOTS);
|
||||
|
||||
log_dbg("Output backup file size: %u bytes.", buffer_size);
|
||||
|
||||
devfd = device_open(device, O_RDONLY);
|
||||
if(devfd == -1) {
|
||||
@@ -177,7 +183,7 @@ int LUKS_hdr_backup(
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (read_blockwise(devfd, device_block_size(device), buffer, buffer_size) < buffer_size) {
|
||||
if (read_blockwise(devfd, device_block_size(device), buffer, hdr_size) < hdr_size) {
|
||||
r = -EIO;
|
||||
goto out;
|
||||
}
|
||||
@@ -594,6 +600,28 @@ int LUKS_write_phdr(struct luks_phdr *hdr,
|
||||
return r;
|
||||
}
|
||||
|
||||
/* Check that kernel supports requested cipher by decryption of one sector */
|
||||
static int LUKS_check_cipher(struct luks_phdr *hdr, struct crypt_device *ctx)
|
||||
{
|
||||
int r;
|
||||
struct volume_key *empty_key;
|
||||
char buf[SECTOR_SIZE];
|
||||
|
||||
log_dbg("Checking if cipher %s-%s is usable.", hdr->cipherName, hdr->cipherMode);
|
||||
|
||||
empty_key = crypt_alloc_volume_key(hdr->keyBytes, NULL);
|
||||
if (!empty_key)
|
||||
return -ENOMEM;
|
||||
|
||||
r = LUKS_decrypt_from_storage(buf, sizeof(buf),
|
||||
hdr->cipherName, hdr->cipherMode,
|
||||
empty_key, 0, ctx);
|
||||
|
||||
crypt_free_volume_key(empty_key);
|
||||
memset(buf, 0, sizeof(buf));
|
||||
return r;
|
||||
}
|
||||
|
||||
int LUKS_generate_phdr(struct luks_phdr *header,
|
||||
const struct volume_key *vk,
|
||||
const char *cipherName, const char *cipherMode, const char *hashSpec,
|
||||
@@ -605,7 +633,7 @@ int LUKS_generate_phdr(struct luks_phdr *header,
|
||||
int detached_metadata_device,
|
||||
struct crypt_device *ctx)
|
||||
{
|
||||
unsigned int i=0;
|
||||
unsigned int i = 0, hdr_sectors = LUKS_device_sectors(vk->keylength);
|
||||
size_t blocksPerStripeSet, currentSector;
|
||||
int r;
|
||||
uuid_t partitionUuid;
|
||||
@@ -615,6 +643,13 @@ int LUKS_generate_phdr(struct luks_phdr *header,
|
||||
if (alignPayload == 0 && !detached_metadata_device)
|
||||
alignPayload = DEFAULT_DISK_ALIGNMENT / SECTOR_SIZE;
|
||||
|
||||
if (alignPayload && detached_metadata_device && alignPayload < hdr_sectors) {
|
||||
log_err(ctx, _("Data offset for detached LUKS header must be "
|
||||
"either 0 or higher than header size (%d sectors).\n"),
|
||||
hdr_sectors);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (crypt_hmac_size(hashSpec) < LUKS_DIGESTSIZE) {
|
||||
log_err(ctx, _("Requested LUKS hash %s is not supported.\n"), hashSpec);
|
||||
return -EINVAL;
|
||||
@@ -640,6 +675,10 @@ int LUKS_generate_phdr(struct luks_phdr *header,
|
||||
|
||||
LUKS_fix_header_compatible(header);
|
||||
|
||||
r = LUKS_check_cipher(header, ctx);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
log_dbg("Generating LUKS header version %d using hash %s, %s, %s, MK %d bytes",
|
||||
header->version, header->hashSpec ,header->cipherName, header->cipherMode,
|
||||
header->keyBytes);
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
#include <assert.h>
|
||||
#include <sys/select.h>
|
||||
|
||||
#include "libcryptsetup.h"
|
||||
#include "internal.h"
|
||||
|
||||
180
lib/setup.c
180
lib/setup.c
@@ -4,7 +4,7 @@
|
||||
* Copyright (C) 2004, Christophe Saout <christophe@saout.de>
|
||||
* Copyright (C) 2004-2007, Clemens Fruhwirth <clemens@endorphin.org>
|
||||
* Copyright (C) 2009-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2012, Milan Broz
|
||||
* Copyright (C) 2009-2014, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -60,14 +60,12 @@ struct crypt_device {
|
||||
struct crypt_params_plain hdr;
|
||||
char *cipher;
|
||||
char *cipher_mode;
|
||||
char *uuid;
|
||||
unsigned int key_size;
|
||||
} plain;
|
||||
struct { /* used in CRYPT_LOOPAES */
|
||||
struct crypt_params_loopaes hdr;
|
||||
char *cipher;
|
||||
char *cipher_mode;
|
||||
char *uuid;
|
||||
unsigned int key_size;
|
||||
} loopaes;
|
||||
struct { /* used in CRYPT_VERITY */
|
||||
@@ -185,8 +183,6 @@ int init_crypto(struct crypt_device *ctx)
|
||||
{
|
||||
int r;
|
||||
|
||||
crypt_fips_libcryptsetup_check(ctx);
|
||||
|
||||
r = crypt_random_init(ctx);
|
||||
if (r < 0) {
|
||||
log_err(ctx, _("Cannot initialize crypto RNG backend.\n"));
|
||||
@@ -261,6 +257,23 @@ static int isTCRYPT(const char *type)
|
||||
return (type && !strcmp(CRYPT_TCRYPT, type));
|
||||
}
|
||||
|
||||
static int onlyLUKS(struct crypt_device *cd)
|
||||
{
|
||||
int r = 0;
|
||||
|
||||
if (cd && !cd->type) {
|
||||
log_err(cd, _("Cannot determine device type. Incompatible activation of device?\n"));
|
||||
r = -EINVAL;
|
||||
}
|
||||
if (!cd || !isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
r = -EINVAL;
|
||||
}
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
|
||||
/* keyslot helpers */
|
||||
static int keyslot_verify_or_find_empty(struct crypt_device *cd, int *keyslot)
|
||||
{
|
||||
@@ -329,7 +342,6 @@ int PLAIN_activate(struct crypt_device *cd,
|
||||
enum devcheck device_check;
|
||||
struct crypt_dm_active_device dmd = {
|
||||
.target = DM_CRYPT,
|
||||
.uuid = crypt_get_uuid(cd),
|
||||
.size = size,
|
||||
.flags = flags,
|
||||
.data_device = crypt_data_device(cd),
|
||||
@@ -364,10 +376,6 @@ int PLAIN_activate(struct crypt_device *cd,
|
||||
|
||||
r = dm_create_device(cd, name, CRYPT_PLAIN, &dmd, 0);
|
||||
|
||||
// FIXME
|
||||
if (!cd->u.plain.uuid && dm_query_device(cd, name, DM_ACTIVE_UUID, &dmd) >= 0)
|
||||
cd->u.plain.uuid = CONST_CAST(char*)dmd.uuid;
|
||||
|
||||
free(dm_cipher);
|
||||
return r;
|
||||
}
|
||||
@@ -713,9 +721,10 @@ static int _init_by_name_crypt(struct crypt_device *cd, const char *name)
|
||||
DM_ACTIVE_CRYPT_KEYSIZE, &dmd);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
if (r > 0)
|
||||
r = 0;
|
||||
|
||||
if (isPLAIN(cd->type)) {
|
||||
cd->u.plain.uuid = dmd.uuid ? strdup(dmd.uuid) : NULL;
|
||||
cd->u.plain.hdr.hash = NULL; /* no way to get this */
|
||||
cd->u.plain.hdr.offset = dmd.u.crypt.offset;
|
||||
cd->u.plain.hdr.skip = dmd.u.crypt.iv_offset;
|
||||
@@ -727,7 +736,6 @@ static int _init_by_name_crypt(struct crypt_device *cd, const char *name)
|
||||
cd->u.plain.cipher_mode = strdup(cipher_mode);
|
||||
}
|
||||
} else if (isLOOPAES(cd->type)) {
|
||||
cd->u.loopaes.uuid = dmd.uuid ? strdup(dmd.uuid) : NULL;
|
||||
cd->u.loopaes.hdr.offset = dmd.u.crypt.offset;
|
||||
|
||||
r = crypt_parse_name_and_mode(dmd.u.crypt.cipher, cipher,
|
||||
@@ -758,8 +766,12 @@ static int _init_by_name_crypt(struct crypt_device *cd, const char *name)
|
||||
free(cd->type);
|
||||
cd->type = NULL;
|
||||
r = 0;
|
||||
goto out;
|
||||
}
|
||||
} else {
|
||||
log_dbg("LUKS device header not available.");
|
||||
free(cd->type);
|
||||
cd->type = NULL;
|
||||
r = 0;
|
||||
}
|
||||
} else if (isTCRYPT(cd->type)) {
|
||||
r = TCRYPT_init_by_name(cd, name, &dmd, &cd->device,
|
||||
@@ -784,14 +796,15 @@ static int _init_by_name_verity(struct crypt_device *cd, const char *name)
|
||||
|
||||
r = dm_query_device(cd, name,
|
||||
DM_ACTIVE_DEVICE |
|
||||
DM_ACTIVE_UUID |
|
||||
DM_ACTIVE_VERITY_HASH_DEVICE |
|
||||
DM_ACTIVE_VERITY_PARAMS, &dmd);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
if (r > 0)
|
||||
r = 0;
|
||||
|
||||
if (isVERITY(cd->type)) {
|
||||
cd->u.verity.uuid = dmd.uuid ? strdup(dmd.uuid) : NULL;
|
||||
cd->u.verity.uuid = NULL; // FIXME
|
||||
cd->u.verity.hdr.flags = CRYPT_VERITY_NO_HEADER; //FIXME
|
||||
cd->u.verity.hdr.data_size = params.data_size;
|
||||
cd->u.verity.root_hash_size = dmd.u.verity.root_hash_size;
|
||||
@@ -810,7 +823,6 @@ static int _init_by_name_verity(struct crypt_device *cd, const char *name)
|
||||
}
|
||||
out:
|
||||
device_free(dmd.data_device);
|
||||
free(CONST_CAST(void*)dmd.uuid);
|
||||
return r;
|
||||
}
|
||||
|
||||
@@ -920,6 +932,11 @@ static int _crypt_format_plain(struct crypt_device *cd,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (uuid) {
|
||||
log_err(cd, _("UUID is not supported for this crypt type.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (!(cd->type = strdup(CRYPT_PLAIN)))
|
||||
return -ENOMEM;
|
||||
|
||||
@@ -931,8 +948,6 @@ static int _crypt_format_plain(struct crypt_device *cd,
|
||||
cd->u.plain.cipher = strdup(cipher);
|
||||
cd->u.plain.cipher_mode = strdup(cipher_mode);
|
||||
|
||||
if (uuid)
|
||||
cd->u.plain.uuid = strdup(uuid);
|
||||
|
||||
if (params && params->hash)
|
||||
cd->u.plain.hdr.hash = strdup(params->hash);
|
||||
@@ -1042,6 +1057,11 @@ static int _crypt_format_loopaes(struct crypt_device *cd,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (uuid) {
|
||||
log_err(cd, _("UUID is not supported for this crypt type.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (!(cd->type = strdup(CRYPT_LOOPAES)))
|
||||
return -ENOMEM;
|
||||
|
||||
@@ -1049,9 +1069,6 @@ static int _crypt_format_loopaes(struct crypt_device *cd,
|
||||
|
||||
cd->u.loopaes.cipher = strdup(cipher ?: DEFAULT_LOOPAES_CIPHER);
|
||||
|
||||
if (uuid)
|
||||
cd->u.loopaes.uuid = strdup(uuid);
|
||||
|
||||
if (params && params->hash)
|
||||
cd->u.loopaes.hdr.hash = strdup(params->hash);
|
||||
|
||||
@@ -1288,7 +1305,7 @@ int crypt_resize(struct crypt_device *cd, const char *name, uint64_t new_size)
|
||||
int r;
|
||||
|
||||
/* Device context type must be initialised */
|
||||
if (!cd->type || !crypt_get_uuid(cd))
|
||||
if (!cd->type)
|
||||
return -EINVAL;
|
||||
|
||||
log_dbg("Resizing device %s to %" PRIu64 " sectors.", name, new_size);
|
||||
@@ -1413,11 +1430,9 @@ void crypt_free(struct crypt_device *cd)
|
||||
free(CONST_CAST(void*)cd->u.plain.hdr.hash);
|
||||
free(cd->u.plain.cipher);
|
||||
free(cd->u.plain.cipher_mode);
|
||||
free(cd->u.plain.uuid);
|
||||
} else if (isLOOPAES(cd->type)) {
|
||||
free(CONST_CAST(void*)cd->u.loopaes.hdr.hash);
|
||||
free(cd->u.loopaes.cipher);
|
||||
free(cd->u.loopaes.uuid);
|
||||
} else if (isVERITY(cd->type)) {
|
||||
free(CONST_CAST(void*)cd->u.verity.hdr.hash_name);
|
||||
free(CONST_CAST(void*)cd->u.verity.hdr.salt);
|
||||
@@ -1440,11 +1455,9 @@ int crypt_suspend(struct crypt_device *cd,
|
||||
|
||||
log_dbg("Suspending volume %s.", name);
|
||||
|
||||
if (!cd || !isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
r = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
ci = crypt_status(NULL, name);
|
||||
if (ci < CRYPT_ACTIVE) {
|
||||
@@ -1485,11 +1498,9 @@ int crypt_resume_by_passphrase(struct crypt_device *cd,
|
||||
|
||||
log_dbg("Resuming volume %s.", name);
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
r = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = dm_status_suspended(cd, name);
|
||||
if (r < 0)
|
||||
@@ -1515,7 +1526,7 @@ int crypt_resume_by_passphrase(struct crypt_device *cd,
|
||||
log_err(cd, _("Error during resuming device %s.\n"), name);
|
||||
} else
|
||||
r = keyslot;
|
||||
out:
|
||||
|
||||
crypt_free_volume_key(vk);
|
||||
return r < 0 ? r : keyslot;
|
||||
}
|
||||
@@ -1534,11 +1545,9 @@ int crypt_resume_by_keyfile_offset(struct crypt_device *cd,
|
||||
|
||||
log_dbg("Resuming volume %s.", name);
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
r = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = dm_status_suspended(cd, name);
|
||||
if (r < 0)
|
||||
@@ -1600,10 +1609,9 @@ int crypt_keyslot_add_by_passphrase(struct crypt_device *cd,
|
||||
"new passphrase %sprovided.",
|
||||
passphrase ? "" : "not ", new_passphrase ? "" : "not ");
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = keyslot_verify_or_find_empty(cd, &keyslot);
|
||||
if (r)
|
||||
@@ -1649,14 +1657,15 @@ int crypt_keyslot_add_by_passphrase(struct crypt_device *cd,
|
||||
|
||||
r = LUKS_set_key(keyslot, new_password, new_passwordLen,
|
||||
&cd->u.luks1.hdr, vk, cd->iteration_time, &cd->u.luks1.PBKDF2_per_sec, cd);
|
||||
if(r < 0) goto out;
|
||||
if(r < 0)
|
||||
goto out;
|
||||
|
||||
r = 0;
|
||||
out:
|
||||
if (!new_passphrase)
|
||||
crypt_safe_free(new_password);
|
||||
crypt_free_volume_key(vk);
|
||||
return r ?: keyslot;
|
||||
return r < 0 ? r : keyslot;
|
||||
}
|
||||
|
||||
int crypt_keyslot_change_by_passphrase(struct crypt_device *cd,
|
||||
@@ -1668,15 +1677,14 @@ int crypt_keyslot_change_by_passphrase(struct crypt_device *cd,
|
||||
size_t new_passphrase_size)
|
||||
{
|
||||
struct volume_key *vk = NULL;
|
||||
int r = -EINVAL;
|
||||
int r;
|
||||
|
||||
log_dbg("Changing passphrase from old keyslot %d to new %d.",
|
||||
keyslot_old, keyslot_new);
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = LUKS_open_key_with_hdr(keyslot_old, passphrase, passphrase_size,
|
||||
&cd->u.luks1.hdr, &vk, cd);
|
||||
@@ -1706,10 +1714,10 @@ int crypt_keyslot_change_by_passphrase(struct crypt_device *cd,
|
||||
|
||||
if (keyslot_old == keyslot_new) {
|
||||
if (r >= 0)
|
||||
log_verbose(cd, _("Key slot %d changed.\n"), r);
|
||||
log_verbose(cd, _("Key slot %d changed.\n"), keyslot_new);
|
||||
} else {
|
||||
if (r >= 0) {
|
||||
log_verbose(cd, _("Replaced with key slot %d.\n"), r);
|
||||
log_verbose(cd, _("Replaced with key slot %d.\n"), keyslot_new);
|
||||
r = crypt_keyslot_destroy(cd, keyslot_old);
|
||||
}
|
||||
}
|
||||
@@ -1717,7 +1725,7 @@ int crypt_keyslot_change_by_passphrase(struct crypt_device *cd,
|
||||
log_err(cd, _("Failed to swap new key slot.\n"));
|
||||
out:
|
||||
crypt_free_volume_key(vk);
|
||||
return r ?: keyslot_new;
|
||||
return r < 0 ? r : keyslot_new;
|
||||
}
|
||||
|
||||
int crypt_keyslot_add_by_keyfile_offset(struct crypt_device *cd,
|
||||
@@ -1737,10 +1745,9 @@ int crypt_keyslot_add_by_keyfile_offset(struct crypt_device *cd,
|
||||
log_dbg("Adding new keyslot, existing keyfile %s, new keyfile %s.",
|
||||
keyfile ?: "[none]", new_keyfile ?: "[none]");
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = keyslot_verify_or_find_empty(cd, &keyslot);
|
||||
if (r)
|
||||
@@ -1813,15 +1820,14 @@ int crypt_keyslot_add_by_volume_key(struct crypt_device *cd,
|
||||
size_t passphrase_size)
|
||||
{
|
||||
struct volume_key *vk = NULL;
|
||||
int r = -EINVAL;
|
||||
int r;
|
||||
char *new_password = NULL; size_t new_passwordLen;
|
||||
|
||||
log_dbg("Adding new keyslot %d using volume key.", keyslot);
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (volume_key)
|
||||
vk = crypt_alloc_volume_key(volume_key_size, volume_key);
|
||||
@@ -1861,13 +1867,13 @@ out:
|
||||
int crypt_keyslot_destroy(struct crypt_device *cd, int keyslot)
|
||||
{
|
||||
crypt_keyslot_info ki;
|
||||
int r;
|
||||
|
||||
log_dbg("Destroying keyslot %d.", keyslot);
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
ki = crypt_keyslot_status(cd, keyslot);
|
||||
if (ki == CRYPT_SLOT_INVALID) {
|
||||
@@ -2146,6 +2152,7 @@ int crypt_activate_by_volume_key(struct crypt_device *cd,
|
||||
|
||||
int crypt_deactivate(struct crypt_device *cd, const char *name)
|
||||
{
|
||||
struct crypt_device *fake_cd = NULL;
|
||||
int r;
|
||||
|
||||
if (!name)
|
||||
@@ -2153,16 +2160,24 @@ int crypt_deactivate(struct crypt_device *cd, const char *name)
|
||||
|
||||
log_dbg("Deactivating volume %s.", name);
|
||||
|
||||
if (!cd)
|
||||
dm_backend_init();
|
||||
if (!cd) {
|
||||
r = crypt_init_by_name(&fake_cd, name);
|
||||
if (r < 0)
|
||||
return r;
|
||||
cd = fake_cd;
|
||||
}
|
||||
|
||||
switch (crypt_status(cd, name)) {
|
||||
case CRYPT_ACTIVE:
|
||||
case CRYPT_BUSY:
|
||||
if (cd && isTCRYPT(cd->type))
|
||||
if (isTCRYPT(cd->type))
|
||||
r = TCRYPT_deactivate(cd, name);
|
||||
else
|
||||
r = dm_remove_device(cd, name, 0, 0);
|
||||
if (r < 0 && crypt_status(cd, name) == CRYPT_BUSY) {
|
||||
log_err(cd, _("Device %s is still in use.\n"), name);
|
||||
r = -EBUSY;
|
||||
}
|
||||
break;
|
||||
case CRYPT_INACTIVE:
|
||||
log_err(cd, _("Device %s is not active.\n"), name);
|
||||
@@ -2173,8 +2188,7 @@ int crypt_deactivate(struct crypt_device *cd, const char *name)
|
||||
r = -EINVAL;
|
||||
}
|
||||
|
||||
if (!cd)
|
||||
dm_backend_exit();
|
||||
crypt_free(fake_cd);
|
||||
|
||||
return r;
|
||||
}
|
||||
@@ -2230,10 +2244,9 @@ int crypt_volume_key_verify(struct crypt_device *cd,
|
||||
struct volume_key *vk;
|
||||
int r;
|
||||
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
return -EINVAL;
|
||||
}
|
||||
r = onlyLUKS(cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
vk = crypt_alloc_volume_key(volume_key_size, volume_key);
|
||||
if (!vk)
|
||||
@@ -2452,12 +2465,6 @@ const char *crypt_get_uuid(struct crypt_device *cd)
|
||||
if (isLUKS(cd->type))
|
||||
return cd->u.luks1.hdr.uuid;
|
||||
|
||||
if (isPLAIN(cd->type))
|
||||
return cd->u.plain.uuid;
|
||||
|
||||
if (isLOOPAES(cd->type))
|
||||
return cd->u.loopaes.uuid;
|
||||
|
||||
if (isVERITY(cd->type))
|
||||
return cd->u.verity.uuid;
|
||||
|
||||
@@ -2530,10 +2537,8 @@ uint64_t crypt_get_iv_offset(struct crypt_device *cd)
|
||||
|
||||
crypt_keyslot_info crypt_keyslot_status(struct crypt_device *cd, int keyslot)
|
||||
{
|
||||
if (!isLUKS(cd->type)) {
|
||||
log_err(cd, _("This operation is supported only for LUKS device.\n"));
|
||||
if (onlyLUKS(cd) < 0)
|
||||
return CRYPT_SLOT_INVALID;
|
||||
}
|
||||
|
||||
return LUKS_keyslot_info(&cd->u.luks1.hdr, keyslot);
|
||||
}
|
||||
@@ -2607,3 +2612,8 @@ int crypt_get_active_device(struct crypt_device *cd, const char *name,
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __attribute__((constructor)) libcryptsetup_ctor(void)
|
||||
{
|
||||
crypt_fips_libcryptsetup_check();
|
||||
}
|
||||
|
||||
@@ -2,15 +2,13 @@ moduledir = $(libdir)/cryptsetup
|
||||
|
||||
noinst_LTLIBRARIES = libtcrypt.la
|
||||
|
||||
libtcrypt_la_CFLAGS = -Wall @CRYPTO_CFLAGS@
|
||||
libtcrypt_la_CFLAGS = -Wall $(AM_CFLAGS) @CRYPTO_CFLAGS@
|
||||
|
||||
libtcrypt_la_SOURCES = \
|
||||
tcrypt.c \
|
||||
tcrypt.h
|
||||
|
||||
AM_CPPFLAGS = -D_GNU_SOURCE \
|
||||
-D_LARGEFILE64_SOURCE \
|
||||
-D_FILE_OFFSET_BITS=64 \
|
||||
AM_CPPFLAGS = -include config.h \
|
||||
-I$(top_srcdir)/lib \
|
||||
-I$(top_srcdir)/lib/crypto_backend
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* TCRYPT (TrueCrypt-compatible) volume handling
|
||||
*
|
||||
* Copyright (C) 2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2012, Milan Broz
|
||||
* Copyright (C) 2012-2014, Milan Broz
|
||||
*
|
||||
* This file is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
@@ -51,6 +51,7 @@ struct tcrypt_alg {
|
||||
unsigned int iv_size;
|
||||
unsigned int key_offset;
|
||||
unsigned int iv_offset; /* or tweak key offset */
|
||||
unsigned int key_extra_size;
|
||||
};
|
||||
|
||||
struct tcrypt_algs {
|
||||
@@ -66,101 +67,107 @@ struct tcrypt_algs {
|
||||
static struct tcrypt_algs tcrypt_cipher[] = {
|
||||
/* XTS mode */
|
||||
{0,1,64,"aes","xts-plain64",
|
||||
{{"aes", 64,16,0,32}}},
|
||||
{{"aes", 64,16,0,32,0}}},
|
||||
{0,1,64,"serpent","xts-plain64",
|
||||
{{"serpent",64,16,0,32}}},
|
||||
{{"serpent",64,16,0,32,0}}},
|
||||
{0,1,64,"twofish","xts-plain64",
|
||||
{{"twofish",64,16,0,32}}},
|
||||
{{"twofish",64,16,0,32,0}}},
|
||||
{0,2,128,"twofish-aes","xts-plain64",
|
||||
{{"twofish",64,16, 0,64},
|
||||
{"aes", 64,16,32,96}}},
|
||||
{{"twofish",64,16, 0,64,0},
|
||||
{"aes", 64,16,32,96,0}}},
|
||||
{0,3,192,"serpent-twofish-aes","xts-plain64",
|
||||
{{"serpent",64,16, 0, 96},
|
||||
{"twofish",64,16,32,128},
|
||||
{"aes", 64,16,64,160}}},
|
||||
{{"serpent",64,16, 0, 96,0},
|
||||
{"twofish",64,16,32,128,0},
|
||||
{"aes", 64,16,64,160,0}}},
|
||||
{0,2,128,"aes-serpent","xts-plain64",
|
||||
{{"aes", 64,16, 0,64},
|
||||
{"serpent",64,16,32,96}}},
|
||||
{{"aes", 64,16, 0,64,0},
|
||||
{"serpent",64,16,32,96,0}}},
|
||||
{0,3,192,"aes-twofish-serpent","xts-plain64",
|
||||
{{"aes", 64,16, 0, 96},
|
||||
{"twofish",64,16,32,128},
|
||||
{"serpent",64,16,64,160}}},
|
||||
{{"aes", 64,16, 0, 96,0},
|
||||
{"twofish",64,16,32,128,0},
|
||||
{"serpent",64,16,64,160,0}}},
|
||||
{0,2,128,"serpent-twofish","xts-plain64",
|
||||
{{"serpent",64,16, 0,64},
|
||||
{"twofish",64,16,32,96}}},
|
||||
{{"serpent",64,16, 0,64,0},
|
||||
{"twofish",64,16,32,96,0}}},
|
||||
|
||||
/* LRW mode */
|
||||
{0,1,48,"aes","lrw-benbi",
|
||||
{{"aes", 48,16,32,0}}},
|
||||
{{"aes", 48,16,32,0,0}}},
|
||||
{0,1,48,"serpent","lrw-benbi",
|
||||
{{"serpent",48,16,32,0}}},
|
||||
{{"serpent",48,16,32,0,0}}},
|
||||
{0,1,48,"twofish","lrw-benbi",
|
||||
{{"twofish",48,16,32,0}}},
|
||||
{{"twofish",48,16,32,0,0}}},
|
||||
{0,2,96,"twofish-aes","lrw-benbi",
|
||||
{{"twofish",48,16,32,0},
|
||||
{"aes", 48,16,64,0}}},
|
||||
{{"twofish",48,16,32,0,0},
|
||||
{"aes", 48,16,64,0,0}}},
|
||||
{0,3,144,"serpent-twofish-aes","lrw-benbi",
|
||||
{{"serpent",48,16,32,0},
|
||||
{"twofish",48,16,64,0},
|
||||
{"aes", 48,16,96,0}}},
|
||||
{{"serpent",48,16,32,0,0},
|
||||
{"twofish",48,16,64,0,0},
|
||||
{"aes", 48,16,96,0,0}}},
|
||||
{0,2,96,"aes-serpent","lrw-benbi",
|
||||
{{"aes", 48,16,32,0},
|
||||
{"serpent",48,16,64,0}}},
|
||||
{{"aes", 48,16,32,0,0},
|
||||
{"serpent",48,16,64,0,0}}},
|
||||
{0,3,144,"aes-twofish-serpent","lrw-benbi",
|
||||
{{"aes", 48,16,32,0},
|
||||
{"twofish",48,16,64,0},
|
||||
{"serpent",48,16,96,0}}},
|
||||
{{"aes", 48,16,32,0,0},
|
||||
{"twofish",48,16,64,0,0},
|
||||
{"serpent",48,16,96,0,0}}},
|
||||
{0,2,96,"serpent-twofish", "lrw-benbi",
|
||||
{{"serpent",48,16,32,0},
|
||||
{"twofish",48,16,64,0}}},
|
||||
{{"serpent",48,16,32,0,0},
|
||||
{"twofish",48,16,64,0,0}}},
|
||||
|
||||
/* Kernel LRW block size is fixed to 16 bytes for GF(2^128)
|
||||
* thus cannot be used with blowfish where block is 8 bytes.
|
||||
* There also no GF(2^64) support.
|
||||
{1,1,64,"blowfish_le","lrw-benbi",
|
||||
{{"blowfish_le",64,8,32,0}}},
|
||||
{{"blowfish_le",64,8,32,0,0}}},
|
||||
{1,2,112,"blowfish_le-aes","lrw-benbi",
|
||||
{{"blowfish_le",64, 8,32,0},
|
||||
{"aes", 48,16,88,0}}},
|
||||
{{"blowfish_le",64, 8,32,0,0},
|
||||
{"aes", 48,16,88,0,0}}},
|
||||
{1,3,160,"serpent-blowfish_le-aes","lrw-benbi",
|
||||
{{"serpent", 48,16, 32,0},
|
||||
{"blowfish_le",64, 8, 64,0},
|
||||
{"aes", 48,16,120,0}}},*/
|
||||
/* CBC + "outer" CBC (both with whitening) */
|
||||
{1,1,32,"aes","cbc-tcrypt",
|
||||
{{"aes", 32,16,32,0}}},
|
||||
{1,1,32,"serpent","cbc-tcrypt",
|
||||
{{"serpent",32,16,32,0}}},
|
||||
{1,1,32,"twofish","cbc-tcrypt",
|
||||
{{"twofish",32,16,32,0}}},
|
||||
{1,2,64,"twofish-aes","cbci-tcrypt",
|
||||
{{"twofish",32,16,32,0},
|
||||
{"aes", 32,16,64,0}}},
|
||||
{1,3,96,"serpent-twofish-aes","cbci-tcrypt",
|
||||
{{"serpent",32,16,32,0},
|
||||
{"twofish",32,16,64,0},
|
||||
{"aes", 32,16,96,0}}},
|
||||
{1,2,64,"aes-serpent","cbci-tcrypt",
|
||||
{{"aes", 32,16,32,0},
|
||||
{"serpent",32,16,64,0}}},
|
||||
{1,3,96,"aes-twofish-serpent", "cbci-tcrypt",
|
||||
{{"aes", 32,16,32,0},
|
||||
{"twofish",32,16,64,0},
|
||||
{"serpent",32,16,96,0}}},
|
||||
{1,2,64,"serpent-twofish", "cbci-tcrypt",
|
||||
{{"serpent",32,16,32,0},
|
||||
{"twofish",32,16,64,0}}},
|
||||
{1,1,16,"cast5","cbc-tcrypt",
|
||||
{{"cast5", 16,8,32,0}}},
|
||||
{1,1,24,"des3_ede","cbc-tcrypt",
|
||||
{{"des3_ede",24,8,32,0}}},
|
||||
{1,1,56,"blowfish_le","cbc-tcrypt",
|
||||
{{"blowfish_le",56,8,32,0}}},
|
||||
{1,2,88,"blowfish_le-aes","cbc-tcrypt",
|
||||
{{"blowfish_le",56, 8,32,0},
|
||||
{"aes", 32,16,88,0}}},
|
||||
{1,3,120,"serpent-blowfish_le-aes","cbc-tcrypt",
|
||||
{{"serpent", 32,16, 32,0},
|
||||
{"blowfish_le",56, 8, 64,0},
|
||||
{"aes", 32,16,120,0}}},
|
||||
{{"serpent", 48,16, 32,0,0},
|
||||
{"blowfish_le",64, 8, 64,0,0},
|
||||
{"aes", 48,16,120,0,0}}},*/
|
||||
|
||||
/*
|
||||
* CBC + "outer" CBC (both with whitening)
|
||||
* chain_key_size: alg_keys_bytes + IV_seed_bytes + whitening_bytes
|
||||
*/
|
||||
{1,1,32+16+16,"aes","cbc-tcw",
|
||||
{{"aes", 32,16,32,0,32}}},
|
||||
{1,1,32+16+16,"serpent","cbc-tcw",
|
||||
{{"serpent",32,16,32,0,32}}},
|
||||
{1,1,32+16+16,"twofish","cbc-tcw",
|
||||
{{"twofish",32,16,32,0,32}}},
|
||||
{1,2,64+16+16,"twofish-aes","cbci-tcrypt",
|
||||
{{"twofish",32,16,32,0,0},
|
||||
{"aes", 32,16,64,0,32}}},
|
||||
{1,3,96+16+16,"serpent-twofish-aes","cbci-tcrypt",
|
||||
{{"serpent",32,16,32,0,0},
|
||||
{"twofish",32,16,64,0,0},
|
||||
{"aes", 32,16,96,0,32}}},
|
||||
{1,2,64+16+16,"aes-serpent","cbci-tcrypt",
|
||||
{{"aes", 32,16,32,0,0},
|
||||
{"serpent",32,16,64,0,32}}},
|
||||
{1,3,96+16+16,"aes-twofish-serpent", "cbci-tcrypt",
|
||||
{{"aes", 32,16,32,0,0},
|
||||
{"twofish",32,16,64,0,0},
|
||||
{"serpent",32,16,96,0,32}}},
|
||||
{1,2,64+16+16,"serpent-twofish", "cbci-tcrypt",
|
||||
{{"serpent",32,16,32,0,0},
|
||||
{"twofish",32,16,64,0,32}}},
|
||||
{1,1,16+8+16,"cast5","cbc-tcw",
|
||||
{{"cast5", 16,8,32,0,24}}},
|
||||
{1,1,24+8+16,"des3_ede","cbc-tcw",
|
||||
{{"des3_ede",24,8,32,0,24}}},
|
||||
{1,1,56+8+16,"blowfish_le","cbc-tcrypt",
|
||||
{{"blowfish_le",56,8,32,0,24}}},
|
||||
{1,2,88+16+16,"blowfish_le-aes","cbc-tcrypt",
|
||||
{{"blowfish_le",56, 8,32,0,0},
|
||||
{"aes", 32,16,88,0,32}}},
|
||||
{1,3,120+16+16,"serpent-blowfish_le-aes","cbc-tcrypt",
|
||||
{{"serpent", 32,16, 32,0,0},
|
||||
{"blowfish_le",56, 8, 64,0,0},
|
||||
{"aes", 32,16,120,0,32}}},
|
||||
{}
|
||||
};
|
||||
|
||||
@@ -289,6 +296,9 @@ static void TCRYPT_copy_key(struct tcrypt_alg *alg, const char *mode,
|
||||
memcpy(&out_key[ks2], key, TCRYPT_LRW_IKEY_LEN);
|
||||
} else if (!strncmp(mode, "cbc", 3)) {
|
||||
memcpy(out_key, &key[alg->key_offset], alg->key_size);
|
||||
/* IV + whitening */
|
||||
memcpy(&out_key[alg->key_size], &key[alg->iv_offset],
|
||||
alg->key_extra_size);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -485,6 +495,12 @@ static int TCRYPT_init_hdr(struct crypt_device *cd,
|
||||
else
|
||||
passphrase_size = params->passphrase_size;
|
||||
|
||||
if (params->passphrase_size > TCRYPT_KEY_POOL_LEN) {
|
||||
log_err(cd, _("Maximum TCRYPT passphrase length (%d) exceeded.\n"),
|
||||
TCRYPT_KEY_POOL_LEN);
|
||||
return -EPERM;
|
||||
}
|
||||
|
||||
/* Calculate pool content from keyfiles */
|
||||
for (i = 0; i < params->keyfiles_count; i++) {
|
||||
r = TCRYPT_pool_keyfile(cd, pwd, params->keyfiles[i]);
|
||||
@@ -520,13 +536,13 @@ static int TCRYPT_init_hdr(struct crypt_device *cd,
|
||||
r = TCRYPT_decrypt_hdr(cd, hdr, key, legacy_modes);
|
||||
if (r == -ENOENT) {
|
||||
skipped++;
|
||||
continue;
|
||||
r = -EPERM;
|
||||
}
|
||||
if (r != -EPERM)
|
||||
break;
|
||||
}
|
||||
|
||||
if ((skipped && skipped == i) || r == -ENOTSUP) {
|
||||
if ((r < 0 && r != -EPERM && skipped && skipped == i) || r == -ENOTSUP) {
|
||||
log_err(cd, _("Required kernel crypto interface not available.\n"));
|
||||
#ifdef ENABLE_AF_ALG
|
||||
log_err(cd, _("Ensure you have algif_skcipher kernel module loaded.\n"));
|
||||
@@ -557,8 +573,9 @@ int TCRYPT_read_phdr(struct crypt_device *cd,
|
||||
struct tcrypt_phdr *hdr,
|
||||
struct crypt_params_tcrypt *params)
|
||||
{
|
||||
struct device *device = crypt_metadata_device(cd);
|
||||
struct device *base_device, *device = crypt_metadata_device(cd);
|
||||
ssize_t hdr_size = sizeof(struct tcrypt_phdr);
|
||||
char *base_device_path;
|
||||
int devfd = 0, r, bs;
|
||||
|
||||
assert(sizeof(struct tcrypt_phdr) == 512);
|
||||
@@ -570,7 +587,23 @@ int TCRYPT_read_phdr(struct crypt_device *cd,
|
||||
if (bs < 0)
|
||||
return bs;
|
||||
|
||||
devfd = device_open(device, O_RDONLY);
|
||||
if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER &&
|
||||
crypt_dev_is_partition(device_path(device))) {
|
||||
base_device_path = crypt_get_base_device(device_path(device));
|
||||
|
||||
log_dbg("Reading TCRYPT system header from device %s.", base_device_path ?: "?");
|
||||
if (!base_device_path)
|
||||
return -EINVAL;
|
||||
|
||||
r = device_alloc(&base_device, base_device_path);
|
||||
if (r < 0)
|
||||
return r;
|
||||
devfd = device_open(base_device, O_RDONLY);
|
||||
free(base_device_path);
|
||||
device_free(base_device);
|
||||
} else
|
||||
devfd = device_open(device, O_RDONLY);
|
||||
|
||||
if (devfd == -1) {
|
||||
log_err(cd, _("Cannot open device %s.\n"), device_path(device));
|
||||
return -EINVAL;
|
||||
@@ -579,8 +612,9 @@ int TCRYPT_read_phdr(struct crypt_device *cd,
|
||||
r = -EIO;
|
||||
if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER) {
|
||||
if (lseek(devfd, TCRYPT_HDR_SYSTEM_OFFSET, SEEK_SET) >= 0 &&
|
||||
read_blockwise(devfd, bs, hdr, hdr_size) == hdr_size)
|
||||
read_blockwise(devfd, bs, hdr, hdr_size) == hdr_size) {
|
||||
r = TCRYPT_init_hdr(cd, hdr, params);
|
||||
}
|
||||
} else if (params->flags & CRYPT_TCRYPT_HIDDEN_HEADER) {
|
||||
if (params->flags & CRYPT_TCRYPT_BACKUP_HEADER) {
|
||||
if (lseek(devfd, TCRYPT_HDR_HIDDEN_OFFSET_BCK, SEEK_END) >= 0 &&
|
||||
@@ -630,10 +664,13 @@ int TCRYPT_activate(struct crypt_device *cd,
|
||||
uint32_t flags)
|
||||
{
|
||||
char cipher[MAX_CIPHER_LEN], dm_name[PATH_MAX], dm_dev_name[PATH_MAX];
|
||||
struct device *device = NULL;
|
||||
char *part_path;
|
||||
struct device *device = NULL, *part_device = NULL;
|
||||
unsigned int i;
|
||||
int r;
|
||||
uint32_t req_flags;
|
||||
struct tcrypt_algs *algs;
|
||||
enum devcheck device_check;
|
||||
struct crypt_dm_active_device dmd = {
|
||||
.target = DM_CRYPT,
|
||||
.size = 0,
|
||||
@@ -661,22 +698,55 @@ int TCRYPT_activate(struct crypt_device *cd,
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
if (strstr(params->mode, "-tcw"))
|
||||
req_flags = DM_TCW_SUPPORTED;
|
||||
else
|
||||
req_flags = DM_PLAIN64_SUPPORTED;
|
||||
|
||||
algs = TCRYPT_get_algs(params->cipher, params->mode);
|
||||
if (!algs)
|
||||
return -EINVAL;
|
||||
|
||||
if (params->flags & CRYPT_TCRYPT_HIDDEN_HEADER)
|
||||
if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER)
|
||||
dmd.size = 0;
|
||||
else if (params->flags & CRYPT_TCRYPT_HIDDEN_HEADER)
|
||||
dmd.size = hdr->d.hidden_volume_size / hdr->d.sector_size;
|
||||
else
|
||||
dmd.size = hdr->d.volume_size / hdr->d.sector_size;
|
||||
|
||||
r = device_block_adjust(cd, dmd.data_device, DEV_EXCL,
|
||||
if (dmd.flags & CRYPT_ACTIVATE_SHARED)
|
||||
device_check = DEV_SHARED;
|
||||
else
|
||||
device_check = DEV_EXCL;
|
||||
|
||||
if ((params->flags & CRYPT_TCRYPT_SYSTEM_HEADER) &&
|
||||
!crypt_dev_is_partition(device_path(dmd.data_device))) {
|
||||
part_path = crypt_get_partition_device(device_path(dmd.data_device),
|
||||
dmd.u.crypt.offset, dmd.size);
|
||||
if (part_path) {
|
||||
if (!device_alloc(&part_device, part_path)) {
|
||||
log_verbose(cd, _("Activating TCRYPT system encryption for partition %s.\n"),
|
||||
part_path);
|
||||
dmd.data_device = part_device;
|
||||
dmd.u.crypt.offset = 0;
|
||||
}
|
||||
free(part_path);
|
||||
} else
|
||||
/*
|
||||
* System encryption use the whole device mapping, there can
|
||||
* be active partitions.
|
||||
*/
|
||||
device_check = DEV_SHARED;
|
||||
}
|
||||
|
||||
r = device_block_adjust(cd, dmd.data_device, device_check,
|
||||
dmd.u.crypt.offset, &dmd.size, &dmd.flags);
|
||||
if (r)
|
||||
return r;
|
||||
|
||||
/* Frome here, key size for every cipher must be the same */
|
||||
dmd.u.crypt.vk = crypt_alloc_volume_key(algs->cipher[0].key_size, NULL);
|
||||
dmd.u.crypt.vk = crypt_alloc_volume_key(algs->cipher[0].key_size +
|
||||
algs->cipher[0].key_extra_size, NULL);
|
||||
if (!dmd.u.crypt.vk)
|
||||
return -ENOMEM;
|
||||
|
||||
@@ -716,11 +786,12 @@ int TCRYPT_activate(struct crypt_device *cd,
|
||||
break;
|
||||
}
|
||||
|
||||
if (r < 0 && !(dm_flags() & DM_PLAIN64_SUPPORTED)) {
|
||||
log_err(cd, _("Kernel doesn't support plain64 IV.\n"));
|
||||
if (r < 0 && !(dm_flags() & req_flags)) {
|
||||
log_err(cd, _("Kernel doesn't support TCRYPT compatible mapping.\n"));
|
||||
r = -ENOTSUP;
|
||||
}
|
||||
|
||||
device_free(part_device);
|
||||
crypt_free_volume_key(dmd.u.crypt.vk);
|
||||
return r;
|
||||
}
|
||||
@@ -870,8 +941,11 @@ uint64_t TCRYPT_get_data_offset(struct crypt_device *cd,
|
||||
goto hdr_offset;
|
||||
|
||||
/* Mapping through whole device, not partition! */
|
||||
if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER)
|
||||
if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER) {
|
||||
if (crypt_dev_is_partition(device_path(crypt_metadata_device(cd))))
|
||||
return 0;
|
||||
goto hdr_offset;
|
||||
}
|
||||
|
||||
if (params->mode && !strncmp(params->mode, "xts", 3)) {
|
||||
if (hdr->d.version < 3)
|
||||
@@ -901,15 +975,21 @@ hdr_offset:
|
||||
|
||||
uint64_t TCRYPT_get_iv_offset(struct crypt_device *cd,
|
||||
struct tcrypt_phdr *hdr,
|
||||
struct crypt_params_tcrypt *params
|
||||
)
|
||||
struct crypt_params_tcrypt *params)
|
||||
{
|
||||
if (params->mode && !strncmp(params->mode, "xts", 3))
|
||||
return TCRYPT_get_data_offset(cd, hdr, params);
|
||||
else if (params->mode && !strncmp(params->mode, "lrw", 3))
|
||||
return 0;
|
||||
uint64_t iv_offset;
|
||||
|
||||
return hdr->d.mk_offset / hdr->d.sector_size;
|
||||
if (params->mode && !strncmp(params->mode, "xts", 3))
|
||||
iv_offset = TCRYPT_get_data_offset(cd, hdr, params);
|
||||
else if (params->mode && !strncmp(params->mode, "lrw", 3))
|
||||
iv_offset = 0;
|
||||
else
|
||||
iv_offset = hdr->d.mk_offset / hdr->d.sector_size;
|
||||
|
||||
if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER)
|
||||
iv_offset += crypt_dev_partition_offset(device_path(crypt_metadata_device(cd)));
|
||||
|
||||
return iv_offset;
|
||||
}
|
||||
|
||||
int TCRYPT_get_volume_key(struct crypt_device *cd,
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* TCRYPT (TrueCrypt-compatible) header defitinion
|
||||
*
|
||||
* Copyright (C) 2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2012, Milan Broz
|
||||
* Copyright (C) 2012-2014, Milan Broz
|
||||
*
|
||||
* This file is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* libcryptsetup - cryptsetup library, cipher bechmark
|
||||
*
|
||||
* Copyright (C) 2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2012, Milan Broz
|
||||
* Copyright (C) 2012-2013, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -21,8 +21,7 @@
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/resource.h>
|
||||
#include <time.h>
|
||||
|
||||
#include "internal.h"
|
||||
|
||||
@@ -32,6 +31,12 @@
|
||||
*/
|
||||
#define CIPHER_BLOCK_BYTES 65536
|
||||
|
||||
/*
|
||||
* If the measured value is lower, encrypted buffer is probably too small
|
||||
* and calculated values are not reliable.
|
||||
*/
|
||||
#define CIPHER_TIME_MIN_MS 0.001
|
||||
|
||||
/*
|
||||
* The whole test depends on Linux kernel usermode crypto API for now.
|
||||
* (The same implementations are used in dm-crypt though.)
|
||||
@@ -47,19 +52,15 @@ struct cipher_perf {
|
||||
size_t buffer_size;
|
||||
};
|
||||
|
||||
static long time_ms(struct rusage *start, struct rusage *end)
|
||||
static int time_ms(struct timespec *start, struct timespec *end, double *ms)
|
||||
{
|
||||
long ms = 0;
|
||||
double start_ms, end_ms;
|
||||
|
||||
/* For kernel backend, we need to measure only tim in kernel.
|
||||
ms = (end->ru_utime.tv_sec - start->ru_utime.tv_sec) * 1000;
|
||||
ms += (end->ru_utime.tv_usec - start->ru_utime.tv_usec) / 1000;
|
||||
*/
|
||||
start_ms = start->tv_sec * 1000.0 + start->tv_nsec / (1000.0 * 1000);
|
||||
end_ms = end->tv_sec * 1000.0 + end->tv_nsec / (1000.0 * 1000);
|
||||
|
||||
ms += (end->ru_stime.tv_sec - start->ru_stime.tv_sec) * 1000;
|
||||
ms += (end->ru_stime.tv_usec - start->ru_stime.tv_usec) / 1000;
|
||||
|
||||
return ms;
|
||||
*ms = end_ms - start_ms;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int cipher_perf_one(struct cipher_perf *cp, char *buf,
|
||||
@@ -98,26 +99,39 @@ static int cipher_perf_one(struct cipher_perf *cp, char *buf,
|
||||
|
||||
return r;
|
||||
}
|
||||
static long cipher_measure(struct cipher_perf *cp, char *buf,
|
||||
size_t buf_size, int encrypt)
|
||||
static int cipher_measure(struct cipher_perf *cp, char *buf,
|
||||
size_t buf_size, int encrypt, double *ms)
|
||||
{
|
||||
struct rusage rstart, rend;
|
||||
struct timespec start, end;
|
||||
int r;
|
||||
|
||||
if (getrusage(RUSAGE_SELF, &rstart) < 0)
|
||||
/*
|
||||
* Using getrusage would be better here but the precision
|
||||
* is not adequate, so better stick with CLOCK_MONOTONIC
|
||||
*/
|
||||
if (clock_gettime(CLOCK_MONOTONIC, &start) < 0)
|
||||
return -EINVAL;
|
||||
|
||||
r = cipher_perf_one(cp, buf, buf_size, encrypt);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (getrusage(RUSAGE_SELF, &rend) < 0)
|
||||
if (clock_gettime(CLOCK_MONOTONIC, &end) < 0)
|
||||
return -EINVAL;
|
||||
|
||||
return time_ms(&rstart, &rend);
|
||||
r = time_ms(&start, &end, ms);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (*ms < CIPHER_TIME_MIN_MS) {
|
||||
log_dbg("Measured cipher runtime (%1.6f) is too low.", *ms);
|
||||
return -ERANGE;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static double speed_mbs(unsigned long bytes, unsigned long ms)
|
||||
static double speed_mbs(unsigned long bytes, double ms)
|
||||
{
|
||||
double speed = bytes, s = ms / 1000.;
|
||||
|
||||
@@ -127,32 +141,32 @@ static double speed_mbs(unsigned long bytes, unsigned long ms)
|
||||
static int cipher_perf(struct cipher_perf *cp,
|
||||
double *encryption_mbs, double *decryption_mbs)
|
||||
{
|
||||
long ms_enc, ms_dec, ms;
|
||||
int repeat_enc, repeat_dec;
|
||||
double ms_enc, ms_dec, ms;
|
||||
int r, repeat_enc, repeat_dec;
|
||||
void *buf = NULL;
|
||||
|
||||
if (posix_memalign(&buf, crypt_getpagesize(), cp->buffer_size))
|
||||
return -ENOMEM;
|
||||
|
||||
ms_enc = 0;
|
||||
ms_enc = 0.0;
|
||||
repeat_enc = 1;
|
||||
while (ms_enc < 1000) {
|
||||
ms = cipher_measure(cp, buf, cp->buffer_size, 1);
|
||||
if (ms < 0) {
|
||||
while (ms_enc < 1000.0) {
|
||||
r = cipher_measure(cp, buf, cp->buffer_size, 1, &ms);
|
||||
if (r < 0) {
|
||||
free(buf);
|
||||
return (int)ms;
|
||||
return r;
|
||||
}
|
||||
ms_enc += ms;
|
||||
repeat_enc++;
|
||||
}
|
||||
|
||||
ms_dec = 0;
|
||||
ms_dec = 0.0;
|
||||
repeat_dec = 1;
|
||||
while (ms_dec < 1000) {
|
||||
ms = cipher_measure(cp, buf, cp->buffer_size, 0);
|
||||
if (ms < 0) {
|
||||
while (ms_dec < 1000.0) {
|
||||
r = cipher_measure(cp, buf, cp->buffer_size, 0, &ms);
|
||||
if (r < 0) {
|
||||
free(buf);
|
||||
return (int)ms;
|
||||
return r;
|
||||
}
|
||||
ms_dec += ms;
|
||||
repeat_dec++;
|
||||
|
||||
@@ -24,10 +24,9 @@
|
||||
#define _UTILS_CRYPT_H
|
||||
|
||||
#include <unistd.h>
|
||||
#include "config.h"
|
||||
|
||||
#define MAX_CIPHER_LEN 32
|
||||
#define MAX_CIPHER_LEN_STR "32"
|
||||
#define MAX_CIPHER_LEN_STR "31"
|
||||
#define MAX_KEYFILES 32
|
||||
|
||||
struct crypt_device;
|
||||
|
||||
@@ -221,7 +221,7 @@ int device_block_size(struct device *device)
|
||||
if (fstat(fd, &st) < 0)
|
||||
goto out;
|
||||
|
||||
if (S_ISREG(st.st_mode)) {
|
||||
if (S_ISREG(st.st_mode) || device->file_path) {
|
||||
r = (int)crypt_getpagesize();
|
||||
goto out;
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
* Copyright (C) 2004, Christophe Saout <christophe@saout.de>
|
||||
* Copyright (C) 2004-2007, Clemens Fruhwirth <clemens@endorphin.org>
|
||||
* Copyright (C) 2009-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2012, Milan Broz
|
||||
* Copyright (C) 2009-2013, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -28,12 +28,10 @@
|
||||
#include <dirent.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
#include <limits.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/types.h>
|
||||
#include "utils_dm.h"
|
||||
|
||||
char *crypt_lookup_dev(const char *dev_id);
|
||||
int crypt_sysfs_get_rotational(int major, int minor, int *rotational);
|
||||
#include "internal.h"
|
||||
|
||||
static char *__lookup_dev(char *path, dev_t dev, int dir_level, const int max_level)
|
||||
{
|
||||
@@ -169,16 +167,12 @@ char *crypt_lookup_dev(const char *dev_id)
|
||||
return devpath;
|
||||
}
|
||||
|
||||
int crypt_sysfs_get_rotational(int major, int minor, int *rotational)
|
||||
static int _read_uint64(const char *sysfs_path, uint64_t *value)
|
||||
{
|
||||
char path[PATH_MAX], tmp[64] = {0};
|
||||
char tmp[64] = {0};
|
||||
int fd, r;
|
||||
|
||||
if (snprintf(path, sizeof(path), "/sys/dev/block/%d:%d/queue/rotational",
|
||||
major, minor) < 0)
|
||||
return 0;
|
||||
|
||||
if ((fd = open(path, O_RDONLY)) < 0)
|
||||
if ((fd = open(sysfs_path, O_RDONLY)) < 0)
|
||||
return 0;
|
||||
r = read(fd, tmp, sizeof(tmp));
|
||||
close(fd);
|
||||
@@ -186,8 +180,185 @@ int crypt_sysfs_get_rotational(int major, int minor, int *rotational)
|
||||
if (r <= 0)
|
||||
return 0;
|
||||
|
||||
if (sscanf(tmp, "%d", rotational) != 1)
|
||||
if (sscanf(tmp, "%" PRIu64, value) != 1)
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _sysfs_get_uint64(int major, int minor, uint64_t *value, const char *attr)
|
||||
{
|
||||
char path[PATH_MAX];
|
||||
|
||||
if (snprintf(path, sizeof(path), "/sys/dev/block/%d:%d/%s",
|
||||
major, minor, attr) < 0)
|
||||
return 0;
|
||||
|
||||
return _read_uint64(path, value);
|
||||
}
|
||||
|
||||
static int _path_get_uint64(const char *sysfs_path, uint64_t *value, const char *attr)
|
||||
{
|
||||
char path[PATH_MAX];
|
||||
|
||||
if (snprintf(path, sizeof(path), "%s/%s",
|
||||
sysfs_path, attr) < 0)
|
||||
return 0;
|
||||
|
||||
return _read_uint64(path, value);
|
||||
}
|
||||
|
||||
int crypt_dev_is_rotational(int major, int minor)
|
||||
{
|
||||
uint64_t val;
|
||||
|
||||
if (!_sysfs_get_uint64(major, minor, &val, "queue/rotational"))
|
||||
return 1; /* if failed, expect rotational disk */
|
||||
|
||||
return val ? 1 : 0;
|
||||
}
|
||||
|
||||
int crypt_dev_is_partition(const char *dev_path)
|
||||
{
|
||||
uint64_t val;
|
||||
struct stat st;
|
||||
|
||||
if (stat(dev_path, &st) < 0)
|
||||
return 0;
|
||||
|
||||
if (!S_ISBLK(st.st_mode))
|
||||
return 0;
|
||||
|
||||
if (!_sysfs_get_uint64(major(st.st_rdev), minor(st.st_rdev),
|
||||
&val, "partition"))
|
||||
return 0;
|
||||
|
||||
return val ? 1 : 0;
|
||||
}
|
||||
|
||||
uint64_t crypt_dev_partition_offset(const char *dev_path)
|
||||
{
|
||||
uint64_t val;
|
||||
struct stat st;
|
||||
|
||||
if (!crypt_dev_is_partition(dev_path))
|
||||
return 0;
|
||||
|
||||
if (stat(dev_path, &st) < 0)
|
||||
return 0;
|
||||
|
||||
if (!_sysfs_get_uint64(major(st.st_rdev), minor(st.st_rdev),
|
||||
&val, "start"))
|
||||
return 0;
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
/* Try to find partition which match offset and size on top level device */
|
||||
char *crypt_get_partition_device(const char *dev_path, uint64_t offset, uint64_t size)
|
||||
{
|
||||
char link[PATH_MAX], path[PATH_MAX], part_path[PATH_MAX], *devname;
|
||||
char *result = NULL;
|
||||
struct stat st;
|
||||
size_t devname_len;
|
||||
ssize_t len;
|
||||
struct dirent *entry;
|
||||
DIR *dir;
|
||||
uint64_t part_offset, part_size;
|
||||
|
||||
if (stat(dev_path, &st) < 0)
|
||||
return NULL;
|
||||
|
||||
if (!S_ISBLK(st.st_mode))
|
||||
return NULL;
|
||||
|
||||
if (snprintf(path, sizeof(path), "/sys/dev/block/%d:%d",
|
||||
major(st.st_rdev), minor(st.st_rdev)) < 0)
|
||||
return NULL;
|
||||
|
||||
len = readlink(path, link, sizeof(link) - 1);
|
||||
if (len < 0)
|
||||
return NULL;
|
||||
|
||||
/* Get top level disk name for sysfs search */
|
||||
link[len] = '\0';
|
||||
devname = strrchr(link, '/');
|
||||
if (!devname)
|
||||
return NULL;
|
||||
devname++;
|
||||
|
||||
/* DM devices do not use kernel partitions. */
|
||||
if (dm_is_dm_kernel_name(devname))
|
||||
return NULL;
|
||||
|
||||
dir = opendir(path);
|
||||
if (!dir)
|
||||
return NULL;
|
||||
|
||||
devname_len = strlen(devname);
|
||||
while((entry = readdir(dir))) {
|
||||
if (strncmp(entry->d_name, devname, devname_len))
|
||||
continue;
|
||||
|
||||
if (snprintf(part_path, sizeof(part_path), "%s/%s",
|
||||
path, entry->d_name) < 0)
|
||||
continue;
|
||||
|
||||
if (stat(part_path, &st) < 0)
|
||||
continue;
|
||||
|
||||
if (S_ISDIR(st.st_mode)) {
|
||||
if (!_path_get_uint64(part_path, &part_offset, "start") ||
|
||||
!_path_get_uint64(part_path, &part_size, "size"))
|
||||
continue;
|
||||
if (part_offset == offset && part_size == size &&
|
||||
snprintf(part_path, sizeof(part_path), "/dev/%s",
|
||||
entry->d_name) > 0) {
|
||||
result = strdup(part_path);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
closedir(dir);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/* Try to find base device from partition */
|
||||
char *crypt_get_base_device(const char *dev_path)
|
||||
{
|
||||
char link[PATH_MAX], path[PATH_MAX], part_path[PATH_MAX], *devname;
|
||||
struct stat st;
|
||||
ssize_t len;
|
||||
|
||||
if (!crypt_dev_is_partition(dev_path))
|
||||
return NULL;
|
||||
|
||||
if (stat(dev_path, &st) < 0)
|
||||
return NULL;
|
||||
|
||||
if (snprintf(path, sizeof(path), "/sys/dev/block/%d:%d",
|
||||
major(st.st_rdev), minor(st.st_rdev)) < 0)
|
||||
return NULL;
|
||||
|
||||
len = readlink(path, link, sizeof(link) - 1);
|
||||
if (len < 0)
|
||||
return NULL;
|
||||
|
||||
/* Get top level disk name for sysfs search */
|
||||
link[len] = '\0';
|
||||
devname = strrchr(link, '/');
|
||||
if (!devname)
|
||||
return NULL;
|
||||
*devname = '\0';
|
||||
devname = strrchr(link, '/');
|
||||
if (!devname)
|
||||
return NULL;
|
||||
devname++;
|
||||
|
||||
if (dm_is_dm_kernel_name(devname))
|
||||
return NULL;
|
||||
|
||||
snprintf(part_path, sizeof(part_path), "/dev/%s", devname);
|
||||
return strdup(part_path);
|
||||
}
|
||||
|
||||
@@ -39,6 +39,7 @@ struct device;
|
||||
#define DM_PLAIN64_SUPPORTED (1 << 3) /* plain64 IV */
|
||||
#define DM_DISCARDS_SUPPORTED (1 << 4) /* discards/TRIM option is supported */
|
||||
#define DM_VERITY_SUPPORTED (1 << 5) /* dm-verity target supported */
|
||||
#define DM_TCW_SUPPORTED (1 << 6) /* tcw (TCRYPT CBC with whitening) */
|
||||
uint32_t dm_flags(void);
|
||||
|
||||
#define DM_ACTIVE_DEVICE (1 << 0)
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/*
|
||||
* FIPS mode utilities
|
||||
*
|
||||
* Copyright (C) 2011-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2011-2013, 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
|
||||
@@ -19,45 +19,35 @@
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include "libcryptsetup.h"
|
||||
#include "nls.h"
|
||||
#include "utils_fips.h"
|
||||
#include "config.h"
|
||||
|
||||
#if !ENABLE_FIPS
|
||||
int crypt_fips_mode(void) { return 0; }
|
||||
void crypt_fips_libcryptsetup_check(struct crypt_device *cd) {}
|
||||
void crypt_fips_self_check(struct crypt_device *cd) {}
|
||||
void crypt_fips_libcryptsetup_check(void) {}
|
||||
#else
|
||||
#include <fipscheck.h>
|
||||
|
||||
int crypt_fips_mode(void)
|
||||
{
|
||||
return FIPSCHECK_kernel_fips_mode();
|
||||
return FIPSCHECK_kernel_fips_mode() && !access(FIPS_MODULE_FILE, F_OK);
|
||||
}
|
||||
|
||||
static void crypt_fips_verify(struct crypt_device *cd,
|
||||
const char *name, const char *function)
|
||||
static void crypt_fips_verify(const char *name, const char *function)
|
||||
{
|
||||
if (!crypt_fips_mode())
|
||||
return;
|
||||
|
||||
if (!FIPSCHECK_verify(name, function)) {
|
||||
crypt_log(cd, CRYPT_LOG_ERROR, _("FIPS checksum verification failed.\n"));
|
||||
fputs(_("FIPS checksum verification failed.\n"), stderr);
|
||||
_exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
crypt_log(cd, CRYPT_LOG_VERBOSE, _("Running in FIPS mode.\n"));
|
||||
}
|
||||
|
||||
void crypt_fips_libcryptsetup_check(struct crypt_device *cd)
|
||||
void crypt_fips_libcryptsetup_check(void)
|
||||
{
|
||||
crypt_fips_verify(cd, LIBCRYPTSETUP_VERSION_FIPS, "crypt_init");
|
||||
}
|
||||
|
||||
void crypt_fips_self_check(struct crypt_device *cd)
|
||||
{
|
||||
crypt_fips_verify(cd, NULL, NULL);
|
||||
crypt_fips_verify(LIBCRYPTSETUP_VERSION_FIPS, "crypt_init");
|
||||
}
|
||||
#endif /* ENABLE_FIPS */
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/*
|
||||
* FIPS mode utilities
|
||||
*
|
||||
* Copyright (C) 2011-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2011-2013, 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
|
||||
@@ -24,7 +24,6 @@
|
||||
struct crypt_device;
|
||||
|
||||
int crypt_fips_mode(void);
|
||||
void crypt_fips_libcryptsetup_check(struct crypt_device *cd);
|
||||
void crypt_fips_self_check(struct crypt_device *cd);
|
||||
void crypt_fips_libcryptsetup_check(void);
|
||||
|
||||
#endif /* _UTILS_FIPS_H */
|
||||
|
||||
@@ -124,7 +124,7 @@ int crypt_wipe(struct device *device,
|
||||
{
|
||||
struct stat st;
|
||||
char *buffer;
|
||||
int devfd, flags, rotational, bsize;
|
||||
int devfd, flags, bsize;
|
||||
ssize_t written;
|
||||
|
||||
if (!size || size % SECTOR_SIZE || (size > MAXIMUM_WIPE_BYTES)) {
|
||||
@@ -139,14 +139,12 @@ int crypt_wipe(struct device *device,
|
||||
}
|
||||
|
||||
if (type == CRYPT_WIPE_DISK && S_ISBLK(st.st_mode)) {
|
||||
rotational = 0;
|
||||
if (!crypt_sysfs_get_rotational(major(st.st_rdev),
|
||||
minor(st.st_rdev),
|
||||
&rotational))
|
||||
rotational = 1;
|
||||
log_dbg("Rotational flag is %d.", rotational);
|
||||
if (!rotational)
|
||||
if (!crypt_dev_is_rotational(major(st.st_rdev),
|
||||
minor(st.st_rdev))) {
|
||||
type = CRYPT_WIPE_SSD;
|
||||
log_dbg("Non-rotational device, using SSD wipe mode.");
|
||||
} else
|
||||
log_dbg("Rotational device, using normal wipe mode.");
|
||||
}
|
||||
|
||||
bsize = device_block_size(device);
|
||||
|
||||
@@ -2,15 +2,13 @@ moduledir = $(libdir)/cryptsetup
|
||||
|
||||
noinst_LTLIBRARIES = libverity.la
|
||||
|
||||
libverity_la_CFLAGS = -Wall @CRYPTO_CFLAGS@
|
||||
libverity_la_CFLAGS = -Wall $(AM_CFLAGS) @CRYPTO_CFLAGS@
|
||||
|
||||
libverity_la_SOURCES = \
|
||||
verity_hash.c \
|
||||
verity.c \
|
||||
verity.h
|
||||
|
||||
AM_CPPFLAGS = -D_GNU_SOURCE \
|
||||
-D_LARGEFILE64_SOURCE \
|
||||
-D_FILE_OFFSET_BITS=64 \
|
||||
AM_CPPFLAGS = -include config.h \
|
||||
-I$(top_srcdir)/lib \
|
||||
-I$(top_srcdir)/lib/crypto_backend
|
||||
|
||||
@@ -22,7 +22,6 @@
|
||||
#define _VERITY_H
|
||||
|
||||
#include <unistd.h>
|
||||
#include "config.h"
|
||||
|
||||
#define VERITY_MAX_HASH_TYPE 1
|
||||
#define VERITY_BLOCK_SIZE_OK(x) ((x) % 512 || (x) < 512 || \
|
||||
|
||||
@@ -220,7 +220,7 @@ static int VERITY_create_or_verify_hash(struct crypt_device *cd,
|
||||
off_t hash_level_block[VERITY_MAX_LEVELS];
|
||||
off_t hash_level_size[VERITY_MAX_LEVELS];
|
||||
off_t data_file_blocks, s;
|
||||
size_t hash_per_block, hash_per_block_bits;
|
||||
size_t hash_per_block_bits;
|
||||
off_t data_device_size = 0, hash_device_size = 0;
|
||||
uint64_t dev_size;
|
||||
int levels, i, r;
|
||||
@@ -251,7 +251,6 @@ static int VERITY_create_or_verify_hash(struct crypt_device *cd,
|
||||
}
|
||||
|
||||
hash_per_block_bits = get_bits_down(hash_block_size / digest_size);
|
||||
hash_per_block = 1 << hash_per_block_bits;
|
||||
if (!hash_per_block_bits)
|
||||
return -EINVAL;
|
||||
|
||||
@@ -271,8 +270,7 @@ static int VERITY_create_or_verify_hash(struct crypt_device *cd,
|
||||
for (i = levels - 1; i >= 0; i--) {
|
||||
hash_level_block[i] = hash_position;
|
||||
// verity position of block data_file_blocks at level i
|
||||
s = data_file_blocks >> (i * hash_per_block_bits);
|
||||
s = (s + hash_per_block - 1) / hash_per_block;
|
||||
s = (data_file_blocks + ((off_t)1 << ((i + 1) * hash_per_block_bits)) - 1) >> ((i + 1) * hash_per_block_bits);
|
||||
hash_level_size[i] = s;
|
||||
if ((hash_position + s) < hash_position ||
|
||||
(hash_position + s) < 0) {
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
.TH CRYPTSETUP-REENCRYPT "8" "June 2012" "cryptsetup-reencrypt" "Maintenance Commands"
|
||||
.TH CRYPTSETUP-REENCRYPT "8" "December 2013" "cryptsetup-reencrypt" "Maintenance Commands"
|
||||
.SH NAME
|
||||
cryptsetup-reencrypt - tool for offline LUKS device re-encryption
|
||||
.SH SYNOPSIS
|
||||
@@ -56,7 +56,7 @@ Set the cipher specification string.
|
||||
.B "\-\-key-size, \-s \fI<bits>\fR"
|
||||
Set 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.
|
||||
The possible key-sizes are limited by the cipher and mode used.
|
||||
|
||||
If you are increasing key size, there must be enough space in the LUKS header
|
||||
for enlarged keyslots (data offset must be large enough) or reencryption
|
||||
@@ -67,6 +67,9 @@ you can destructively shrink device with \-\-reduce-device-size option.
|
||||
.TP
|
||||
.B "\-\-hash, \-h \fI<hash-spec>\fR"
|
||||
Specifies the hash used in the LUKS key setup scheme and volume key digest.
|
||||
|
||||
NOTE: if this parameter is not specified, default hash algorithm is always used
|
||||
for new device header.
|
||||
.TP
|
||||
.B "\-\-iter-time, \-i \fI<milliseconds>\fR"
|
||||
The number of milliseconds to spend with PBKDF2 passphrase processing for the
|
||||
@@ -100,6 +103,12 @@ Read a maximum of \fIvalue\fR bytes from the key file.
|
||||
Default is to read the whole file up to the compiled-in
|
||||
maximum.
|
||||
.TP
|
||||
.B "\-\-keep-key"
|
||||
Do not change encryption key, just reencrypt the LUKS header and keyslots.
|
||||
|
||||
This option can be combined only with \fI\-\-hash\fR or \fI\-\-iter-time\fR
|
||||
options.
|
||||
.TP
|
||||
.B "\-\-tries, \-T"
|
||||
Number of retries for invalid passphrase entry.
|
||||
.TP
|
||||
@@ -200,9 +209,9 @@ Please attach the output of the failed command with the
|
||||
.SH AUTHORS
|
||||
Cryptsetup-reencrypt was written by Milan Broz <gmazyland@gmail.com>.
|
||||
.SH COPYRIGHT
|
||||
Copyright \(co 2012 Milan Broz
|
||||
Copyright \(co 2012-2014 Milan Broz
|
||||
.br
|
||||
Copyright \(co 2012 Red Hat, Inc.
|
||||
Copyright \(co 2012-2013 Red Hat, Inc.
|
||||
|
||||
This is free software; see the source for copying conditions. There is NO
|
||||
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
|
||||
286
man/cryptsetup.8
286
man/cryptsetup.8
@@ -1,4 +1,4 @@
|
||||
.TH CRYPTSETUP "8" "May 2012" "cryptsetup" "Maintenance Commands"
|
||||
.TH CRYPTSETUP "8" "December 2013" "cryptsetup" "Maintenance Commands"
|
||||
.SH NAME
|
||||
cryptsetup - manage plain dm-crypt and LUKS encrypted volumes
|
||||
.SH SYNOPSIS
|
||||
@@ -10,6 +10,10 @@ device-mapper mappings. These include plain dm-crypt volumes and
|
||||
LUKS volumes. The difference is that LUKS uses a metadata header
|
||||
and can hence offer more features than plain dm-crypt. On the other
|
||||
hand, the header is visible and vulnerable to damage.
|
||||
|
||||
In addition, cryptsetup provides limited support for the use of
|
||||
historic loopaes volumes and for TruerCrypt compatible volumes.
|
||||
|
||||
.SH PLAIN DM-CRYPT OR LUKS?
|
||||
.PP
|
||||
Unless you understand the cryptographic background well, use LUKS.
|
||||
@@ -51,27 +55,27 @@ secure wiping by just overwriting header and key-slot area.
|
||||
|
||||
\fBPreviously used partitions:\fR If a partition was previously used,
|
||||
it is a very good idea to wipe filesystem signatures, data, etc. before
|
||||
creating a LUKS or plain dm-crypt container on it.
|
||||
For a quick removal of filesystem signatures, use "wipefs". Take care
|
||||
though that this may not remove everything. In particular md (RAID)
|
||||
signatures at the end of a device may survive. It also does not
|
||||
remove data. For a full wipe, overwrite the whole partition before
|
||||
creating a LUKS or plain dm-crypt container on it.
|
||||
For a quick removal of filesystem signatures, use "wipefs". Take care
|
||||
though that this may not remove everything. In particular md (RAID)
|
||||
signatures at the end of a device may survive. It also does not
|
||||
remove data. For a full wipe, overwrite the whole partition before
|
||||
container creation. If you do not know how to to that, the
|
||||
cryptsetup FAQ describes several options.
|
||||
|
||||
.SH BASIC COMMANDS
|
||||
The following are valid actions for all supported device types.
|
||||
|
||||
\fIopen\fR <name> <device> \-\-type <device_type>
|
||||
\fIopen\fR <device> <name> \-\-type <device_type>
|
||||
.IP
|
||||
Opens (creates a mapping) with <name> backed by device <device>.
|
||||
Opens (creates a mapping with) <name> backed by device <device>.
|
||||
|
||||
Device type can be \fIplain\fR, \fIluks\fR (default), \fIloopaes\fR
|
||||
or \fItcrypt\fR.
|
||||
|
||||
For backward compatibility there are \fBopen\fR command aliases:
|
||||
|
||||
\fBcreate\fR: open \-\-type plain <device> <name>\fR switched arguments)
|
||||
\fBcreate\fR (argument-order <name> <device>): open \-\-type plain
|
||||
.br
|
||||
\fBplainOpen\fR: open \-\-type plain
|
||||
.br
|
||||
@@ -82,7 +86,9 @@ For backward compatibility there are \fBopen\fR command aliases:
|
||||
\fBtcryptOpen\fR: open \-\-type tcrypt
|
||||
|
||||
\fB<options>\fR are type specific and are described below
|
||||
for individual device types.
|
||||
for individual device types. For \fBcreate\fR, the order of the <name>
|
||||
and <device> options is inverted for historical reasons, all other
|
||||
aliases use the standard \fB<device> <name>\fR order.
|
||||
.PP
|
||||
\fIclose\fR <name>
|
||||
.IP
|
||||
@@ -109,7 +115,7 @@ sectors of the raw device are represented in the mapped device.
|
||||
Plain dm-crypt encrypts the device sector-by-sector with a
|
||||
single, non-salted hash of the passphrase. No checks
|
||||
are performed, no metadata is used. There is no formatting operation.
|
||||
When the raw device is mapped (created), the usual device operations
|
||||
When the raw device is mapped (opened), the usual device operations
|
||||
can be used on the mapped device, including filesystem creation.
|
||||
Mapped devices usually reside in /dev/mapper/<name>.
|
||||
|
||||
@@ -119,7 +125,7 @@ The following are valid plain device type actions:
|
||||
.br
|
||||
\fIcreate\fR <name> <device> (\fBOBSOLETE syntax\fR)
|
||||
.IP
|
||||
Creates a mapping with <name> backed by device <device>.
|
||||
Opens (creates a mapping with) <name> backed by device <device>.
|
||||
|
||||
\fB<options>\fR can be [\-\-hash, \-\-cipher, \-\-verify-passphrase,
|
||||
\-\-key-file, \-\-keyfile-offset, \-\-key-size, \-\-offset, \-\-skip, \-\-size,
|
||||
@@ -159,7 +165,7 @@ The following are valid LUKS actions:
|
||||
\fIluksFormat\fR <device> [<key file>]
|
||||
.IP
|
||||
Initializes a LUKS partition and sets the initial passphrase
|
||||
(for key-slot 0),
|
||||
(for key-slot 0),
|
||||
either via prompting or via <key file>. Note that
|
||||
if the second argument is present, then the passphrase
|
||||
is taken from the file given there, without the need
|
||||
@@ -170,10 +176,12 @@ from stdin and the safety-question being skipped.
|
||||
|
||||
You can only call luksFormat on a LUKS device that is not mapped.
|
||||
|
||||
\fB<options>\fR can be [\-\-cipher, \-\-verify-passphrase, \-\-key-size,
|
||||
\-\-key-slot, \-\-key-file (takes precedence over optional second argument),
|
||||
\-\-keyfile-offset, \-\-keyfile-size, \-\-use-random | \-\-use-urandom,
|
||||
\-\-uuid, \-\-master-key-file].
|
||||
\fB<options>\fR 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, \-\-master\-key\-file, \-\-iter\-time, \-\-header,
|
||||
\-\-force\-password].
|
||||
|
||||
\fBWARNING:\fR Doing a luksFormat on an existing LUKS container will
|
||||
make all data the old container permanently irretrievable, unless
|
||||
@@ -191,9 +199,9 @@ prompts for it interactively.
|
||||
The <device> parameter can be also specified by LUKS UUID in the
|
||||
format UUID=<uuid>, which uses the symlinks in /dev/disk/by-uuid.
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-keyfile-offset,
|
||||
\-\-keyfile-size, \-\-readonly, \-\-test-passphrase,
|
||||
\-\-allow-discards, \-\-header, \-\-key-slot, \-\-master-key-file].
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-keyfile\-offset,
|
||||
\-\-keyfile\-size, \-\-readonly, \-\-test\-passphrase,
|
||||
\-\-allow\-discards, \-\-header, \-\-key-slot, \-\-master\-key\-file].
|
||||
.PP
|
||||
\fIluksSuspend\fR <name>
|
||||
.IP
|
||||
@@ -215,7 +223,7 @@ the mapped device.
|
||||
Resumes a suspended device and reinstates the encryption key.
|
||||
Prompts interactively for a passphrase if \-\-key-file is not given.
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-keyfile-size, \-\-header]
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-keyfile\-size, \-\-header]
|
||||
.PP
|
||||
\fIluksAddKey\fR <device> [<key file with new key>]
|
||||
.IP
|
||||
@@ -224,9 +232,10 @@ interactively or via \-\-key-file.
|
||||
The new passphrase to be added can be specified interactively
|
||||
or read from the file given as positional argument.
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-keyfile-offset,
|
||||
\-\-keyfile-size, \-\-new-keyfile-offset,
|
||||
\-\-new-keyfile-size, \-\-key-slot, \-\-master-key-file].
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-keyfile\-offset,
|
||||
\-\-keyfile\-size, \-\-new\-keyfile\-offset,
|
||||
\-\-new\-keyfile\-size, \-\-key\-slot, \-\-master\-key\-file,
|
||||
\-\-iter\-time, \-\-force\-password].
|
||||
.PP
|
||||
\fIluksRemoveKey\fR <device> [<key file with passphrase to be removed>]
|
||||
.IP
|
||||
@@ -234,12 +243,12 @@ Removes the supplied passphrase from the LUKS device. The
|
||||
passphrase to be removed can be specified interactively,
|
||||
as positional argument or via \-\-key-file.
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-keyfile-offset,
|
||||
\-\-keyfile-size]
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-keyfile\-offset,
|
||||
\-\-keyfile\-size]
|
||||
|
||||
\fBWARNING:\fR If you read the passphrase from stdin
|
||||
(without further argument or with '-' as argument
|
||||
to \-\-key-file), batch-mode (-q) will be implicitely
|
||||
(without further argument or with '-' as argument
|
||||
to \-\-key\-file), batch-mode (-q) will be implicitely
|
||||
switched on and no warning will be given when you remove the
|
||||
last remaining passphrase from a LUKS container. Removing
|
||||
the last passphrase makes the LUKS container permanently
|
||||
@@ -248,7 +257,7 @@ inaccessible.
|
||||
\fIluksChangeKey\fR <device> [<new key file>]
|
||||
.IP
|
||||
Changes an existing passphrase. The passphrase
|
||||
to be changed must be supplied interactively or via \-\-key-file.
|
||||
to be changed must be supplied interactively or via \-\-key\-file.
|
||||
The new passphrase can be supplied interactively or in
|
||||
a file given as positional argument.
|
||||
|
||||
@@ -266,9 +275,9 @@ during this operation can cause the overwrite to fail after
|
||||
the old passphrase has been wiped and make the LUKS container
|
||||
inaccessible.
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-keyfile-offset,
|
||||
\-\-keyfile-size, \-\-new-keyfile-offset,
|
||||
\-\-new-keyfile-size, \-\-key-slot].
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-keyfile\-offset,
|
||||
\-\-keyfile\-size, \-\-new\-keyfile\-offset,
|
||||
\-\-new\-keyfile\-size, \-\-key\-slot, \-\-force\-password].
|
||||
.PP
|
||||
\fIluksKillSlot\fR <device> <key slot number>
|
||||
.IP
|
||||
@@ -278,7 +287,8 @@ This command can remove the last remaining key-slot, but requires
|
||||
an interactive confirmation when doing so. Removing the last
|
||||
passphrase makes a LUKS container permanently inaccessible.
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-keyfile-offset, \-\-keyfile-size].
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-keyfile\-offset,
|
||||
\-\-keyfile\-size].
|
||||
|
||||
\fBWARNING:\fR If you read the passphrase from stdin
|
||||
(without further argument or with '-' as argument
|
||||
@@ -288,6 +298,15 @@ last remaining passphrase from a LUKS container. Removing
|
||||
the last passphrase makes the LUKS container permanently
|
||||
inaccessible.
|
||||
.PP
|
||||
\fIerase\fR <device>
|
||||
.br
|
||||
\fIluksErase\fR <device>
|
||||
.IP
|
||||
Erase all keyslots and make the LUKS container permanently inaccessible.
|
||||
You do not need to provide any password for this operation.
|
||||
|
||||
\fBWARNING:\fR This operation is irreversible.
|
||||
.PP
|
||||
\fIluksUUID\fR <device>
|
||||
.IP
|
||||
Print the UUID of a LUKS device.
|
||||
@@ -304,7 +323,7 @@ means the device is a LUKS device.
|
||||
.IP
|
||||
Dump the header information of a LUKS device.
|
||||
|
||||
If the \-\-dump-master-key option is used, the LUKS device master key is
|
||||
If the \-\-dump\-master\-key option is used, the LUKS device master key is
|
||||
dumped instead of the keyslot info. Beware that the master key cannot be
|
||||
changed and can be used to decrypt the data stored in the LUKS container
|
||||
without a passphrase and even without the LUKS header. This means
|
||||
@@ -312,16 +331,16 @@ that if the master key is compromised, the whole device has to be
|
||||
erased to prevent further access. Use this option carefully.
|
||||
|
||||
In order to dump the master key, a passphrase has to be supplied,
|
||||
either interactively or via \-\-key-file.
|
||||
either interactively or via \-\-key\-file.
|
||||
|
||||
\fB<options>\fR can be [\-\-dump-master-key, \-\-key-file,
|
||||
\-\-keyfile-offset, \-\-keyfile-size].
|
||||
\fB<options>\fR can be [\-\-dump\-master\-key, \-\-key\-file,
|
||||
\-\-keyfile\-offset, \-\-keyfile\-size].
|
||||
|
||||
\fBWARNING:\fR If \-\-dump-master-key is used with \-\-key-file
|
||||
and the argument to \-\-key-file is '-', no validation question
|
||||
\fBWARNING:\fR If \-\-dump\-master\-key is used with \-\-key\-file
|
||||
and the argument to \-\-key\-file is '-', no validation question
|
||||
will be asked and no warning given.
|
||||
.PP
|
||||
\fIluksHeaderBackup\fR <device> \-\-header-backup-file <file>
|
||||
\fIluksHeaderBackup\fR <device> \-\-header\-backup\-file <file>
|
||||
.IP
|
||||
Stores a binary backup of the LUKS header and keyslot area.
|
||||
.br
|
||||
@@ -338,7 +357,7 @@ addition or overwrite the encrypted data area as well.
|
||||
The second option is less secure, as some sectors
|
||||
can survive, e.g. due to defect management.
|
||||
.PP
|
||||
\fIluksHeaderRestore\fR <device> \-\-header-backup-file <file>
|
||||
\fIluksHeaderRestore\fR <device> \-\-header\-backup\-file <file>
|
||||
.IP
|
||||
Restores a binary backup of the LUKS header and keyslot area
|
||||
from the specified file.
|
||||
@@ -356,18 +375,19 @@ the backup will also be written to it.
|
||||
cryptsetup supports mapping loop-AES encrypted partition using
|
||||
a compatibility mode.
|
||||
.PP
|
||||
\fIopen\fR \-\-type loopaes <device> <name> \-\-key-file <keyfile>
|
||||
\fIopen\fR \-\-type loopaes <device> <name> \-\-key\-file <keyfile>
|
||||
.br
|
||||
\fIloopaesOpen\fR <device> <name> \-\-key-file <keyfile> (\fBold syntax\fR)
|
||||
\fIloopaesOpen\fR <device> <name> \-\-key\-file <keyfile> (\fBold syntax\fR)
|
||||
.IP
|
||||
Opens the loop-AES <device> and sets up a mapping <name>.
|
||||
|
||||
If the key file is encrypted with GnuPG, then you have to use
|
||||
\-\-key-file=- and decrypt it before use, e.g. like this:
|
||||
\-\-key\-file=\- and decrypt it before use, e.g. like this:
|
||||
.br
|
||||
gpg \-\-decrypt <keyfile> | cryptsetup loopaesOpen \-\-key-file=- <device> <name>
|
||||
gpg \-\-decrypt <keyfile> | cryptsetup loopaesOpen \-\-key\-file=\-
|
||||
<device> <name>
|
||||
|
||||
Use \fB\-\-keyfile-size\fR to specify the proper key length if needed.
|
||||
Use \fB\-\-keyfile\-size\fR to specify the proper key length if needed.
|
||||
|
||||
Use \fB\-\-offset\fR to specify device offset. Note that the units
|
||||
need to be specified in number of 512 byte sectors.
|
||||
@@ -381,8 +401,8 @@ Use \fB\-\-hash\fR to override the default hash function for
|
||||
passphrase hashing (otherwise it is detected according to key
|
||||
size).
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-key-size, \-\-offset, \-\-skip,
|
||||
\-\-hash, \-\-readonly, \-\-allow-discards].
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-key\-size, \-\-offset, \-\-skip,
|
||||
\-\-hash, \-\-readonly, \-\-allow\-discards].
|
||||
.PP
|
||||
See also section 7 of the FAQ and \fBhttp://loop-aes.sourceforge.net\fR
|
||||
for more information regarding loop-AES.
|
||||
@@ -412,39 +432,68 @@ The \fBtcryptDump\fR command should work for all recognized TCRYPT devices
|
||||
and doesn't require superuser privilege.
|
||||
|
||||
To map system device (device with boot loader where the whole encrypted
|
||||
system resides) use \fB\-\-tcrypt-system\fR option. Use the whole
|
||||
device not the system partition as the device parameter.
|
||||
system resides) use \fB\-\-tcrypt\-system\fR option.
|
||||
You can use partition device as the parameter (parameter must be real partition
|
||||
device, not image in file), then only this partition is mapped.
|
||||
|
||||
If you have whole TCRYPT device as a file image and you want to map multiple
|
||||
partition encrypted with system encryption, please create loopback mapping
|
||||
with partitions first (\fBlosetup -P\fR, see \fPlosetup(8)\fR man page for more info),
|
||||
and use loop partition as the device parameter.
|
||||
|
||||
If you use whole base device as parameter, one device for the whole system
|
||||
encryption is mapped. This mode is available only for backward compatibility
|
||||
with older cryptsetup versions which mapped TCRYPT system encryption
|
||||
using whole device.
|
||||
|
||||
To use hidden header (and map hidden device, if available),
|
||||
use \fB\-\-tcrypt-hidden\fR option.
|
||||
use \fB\-\-tcrypt\-hidden\fR option.
|
||||
|
||||
To explicitly use backup (secondary) header, use \fB\-\-tcrypt\-backup\fR
|
||||
option.
|
||||
|
||||
\fBNOTE:\fR There is no protection for a hidden volume if
|
||||
the outer volume is mounted. The reason is that if there
|
||||
were any protection, it would require some metadata describing
|
||||
what to protect in the outer volume and the hidden volume would
|
||||
become detectable.
|
||||
|
||||
.PP
|
||||
\fIopen\fR \-\-type tcrypt <device> <name>
|
||||
.br
|
||||
\fItcryptOpen\fR <device> <name> (\fBold syntax\fR)
|
||||
.IP
|
||||
Opens the TCRYPT (a TrueCrypt-compatible) <device> and sets up a mapping <name>.
|
||||
Opens the TCRYPT (a TrueCrypt-compatible) <device> and sets up
|
||||
a mapping <name>.
|
||||
|
||||
\fB<options>\fR can be [\-\-key-file, \-\-tcrypt-hidden, \-\-tcrypt-system,
|
||||
\-\-readonly, \-\-test-passphrase].
|
||||
\fB<options>\fR can be [\-\-key\-file, \-\-tcrypt\-hidden,
|
||||
\-\-tcrypt\-system, \-\-tcrypt\-backup, \-\-readonly, \-\-test\-passphrase,
|
||||
\-\-allow-discards].
|
||||
|
||||
The keyfile parameter allows combination of file content with the
|
||||
passphrase and can be repeated. Note that using keyfiles is compatible
|
||||
with TCRYPT and is different from LUKS keyfile logic.
|
||||
|
||||
\fBWARNING:\fR Option \fB\-\-allow\-discards\fR cannot be combined with
|
||||
option \fB\-\-tcrypt\-hidden\fR. For normal mapping it can cause
|
||||
\fBdestruction of hidden volume\fR (hidden volume appears as unused space
|
||||
for outer volume so this space can be discarded).
|
||||
|
||||
.PP
|
||||
\fItcryptDump\fR <device>
|
||||
.IP
|
||||
Dump the header information of a TCRYPT device.
|
||||
|
||||
If the \-\-dump-master-key option is used, the TCRYPT device master key is
|
||||
dumped instead of TCRYPT header info. Beware that the master key
|
||||
If the \-\-dump\-master\-key option is used, the TCRYPT device master key
|
||||
is dumped instead of TCRYPT header info. Beware that the master key
|
||||
(or concatenated master keys if cipher chain is used)
|
||||
can be used to decrypt the data stored in the TCRYPT container without
|
||||
a passphrase.
|
||||
This means that if the master key is compromised, the whole device has
|
||||
to be erased to prevent further access. Use this option carefully.
|
||||
|
||||
\fB<options>\fR can be [\-\-dump-master-key, \-\-key-file, \-\-tcrypt-hidden,
|
||||
\-\-tcrypt-system].
|
||||
\fB<options>\fR can be [\-\-dump\-master\-key, \-\-key\-file,
|
||||
\-\-tcrypt\-hidden, \-\-tcrypt\-system, \-\-tcrypt\-backup].
|
||||
|
||||
The keyfile parameter allows combination of file content with the
|
||||
passphrase and can be repeated.
|
||||
@@ -475,7 +524,7 @@ 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 \fB\-\-cipher\fR
|
||||
and \fB\-\-key-size\fR options or \fB\-\-hash\fR for KDF test.
|
||||
and \fB\-\-key\-size\fR options or \fB\-\-hash\fR for KDF test.
|
||||
|
||||
\fBNOTE:\fR This benchmark is using memory only and is only informative.
|
||||
You cannot directly predict real storage encryption speed from it.
|
||||
@@ -486,7 +535,7 @@ If you are configuring kernel yourself, enable
|
||||
"User-space interface for symmetric key cipher algorithms" in
|
||||
"Cryptographic API" section (CRYPTO_USER_API_SKCIPHER .config option).
|
||||
|
||||
\fB<options>\fR can be [\-\-cipher, \-\-key-size, \-\-hash].
|
||||
\fB<options>\fR can be [\-\-cipher, \-\-key\-size, \-\-hash].
|
||||
.SH OPTIONS
|
||||
.TP
|
||||
.B "\-\-verbose, \-v"
|
||||
@@ -496,15 +545,17 @@ Print more information on command execution.
|
||||
Run in debug mode with full diagnostic logs. Debug output
|
||||
lines are always prefixed by '#'.
|
||||
.TP
|
||||
.B "\-\-hash, \-h \fI<hash-spec>\fR"
|
||||
Specifies the passphrase hash for \fIopen\fR (for plain and loopaes device types).
|
||||
.B "\-\-hash, \-h \fI<hash\-spec>\fR"
|
||||
Specifies the passphrase hash for \fIopen\fR (for plain and
|
||||
loopaes device types).
|
||||
|
||||
Specifies the hash used in the LUKS key setup scheme and volume key digest
|
||||
for \fIluksFormat\fR.
|
||||
for \fIluksFormat\fR. The specified hash is used as hash-parameter
|
||||
for PBKDF2 and for the AF splitter.
|
||||
|
||||
The specified hash name is passed to the compiled-in crypto backend.
|
||||
Different backends may support different hashes.
|
||||
For \fIluksFormat\fR, the hash
|
||||
For \fIluksFormat\fR, the hash
|
||||
algorithm must provide at least 160 bits of output, which
|
||||
excludes, e.g., MD5. Do not use a non-crypto hash like
|
||||
\fB"crc32"\fR as this breaks security.
|
||||
@@ -515,16 +566,20 @@ Values compatible with old version of cryptsetup are
|
||||
|
||||
Use \fIcryptsetup \-\-help\fR to show the defaults.
|
||||
.TP
|
||||
.B "\-\-cipher, \-c \fI<cipher-spec>\fR"
|
||||
.B "\-\-cipher, \-c \fI<cipher\-spec>\fR"
|
||||
Set the cipher specification string.
|
||||
|
||||
\fIcryptsetup \-\-help\fR shows the compiled-in defaults.
|
||||
The current default in the distributed sources is
|
||||
"aes-cbc-essiv:sha256" for both plain dm-crypt and LUKS.
|
||||
"aes-cbc-essiv:sha256" for plain dm-crypt and
|
||||
"aes-xts-plain64" for LUKS.
|
||||
|
||||
For XTS mode (a possible future default), use "aes-xts-plain"
|
||||
or better "aes-xts-plain64"
|
||||
as cipher specification and optionally set a key size of
|
||||
If a hash is part of the cipher spefification, then it is
|
||||
used as part of the IV generation. For example, ESSIV
|
||||
needs a hash function, while "plain64" does not and
|
||||
hence none is specified.
|
||||
|
||||
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.
|
||||
@@ -536,7 +591,7 @@ kernel 2.6.33 or later. More information can be found in the FAQ.
|
||||
When interactively asking for a passphrase, ask for it twice
|
||||
and complain if both inputs do not match. Advised when creating
|
||||
a regular mapping for the first time, or when running
|
||||
\fIluksFormat\fR. Ignores on input from file or stdin.
|
||||
\fIluksFormat\fR. Ignored on input from file or stdin.
|
||||
.TP
|
||||
.B "\-\-key-file, \-d \fIname\fR"
|
||||
Read the passphrase from file.
|
||||
@@ -544,9 +599,9 @@ 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.
|
||||
|
||||
With LUKS, passphrases supplied via \-\-key-file are always
|
||||
With LUKS, passphrases supplied via \-\-key\-file are always
|
||||
the existing passphrases requested by a command, except in
|
||||
the case of \fIluksFormat\fR where \-\-key-file is equivalent
|
||||
the case of \fIluksFormat\fR 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
|
||||
@@ -554,37 +609,37 @@ use a positional argument to \fIluksAddKey\fR.
|
||||
|
||||
See section \fBNOTES ON PASSPHRASE PROCESSING\fR for more information.
|
||||
.TP
|
||||
.B "\-\-keyfile-offset \fIvalue\fR"
|
||||
.B "\-\-keyfile\-offset \fIvalue\fR"
|
||||
Skip \fIvalue\fR bytes at the beginning of the key file.
|
||||
Works with all commands that accepts key files.
|
||||
.TP
|
||||
.B "\-\-keyfile-size, \-l \fIvalue\fR"
|
||||
.B "\-\-keyfile\-size, \-l \fIvalue\fR"
|
||||
Read a maximum of \fIvalue\fR bytes from the key file.
|
||||
Default is to read the whole file up to the compiled-in
|
||||
maximum that can be queried with \-\-help. Supplying more
|
||||
data than the compiled-in maximum aborts the operation.
|
||||
|
||||
This option is useful
|
||||
to cut trailing newlines, for example. If \-\-keyfile-offset
|
||||
to cut trailing newlines, for example. If \-\-keyfile\-offset
|
||||
is also given, the size count starts after the offset.
|
||||
Works with all commands that accepts key files.
|
||||
.TP
|
||||
.B "\-\-new-keyfile-offset \fIvalue\fR"
|
||||
.B "\-\-new\-keyfile\-offset \fIvalue\fR"
|
||||
Skip \fIvalue\fR bytes at the start when
|
||||
adding a new passphrase from key file with
|
||||
\fIluksAddKey\fR.
|
||||
.TP
|
||||
.B "\-\-new-keyfile-size \fIvalue\fR"
|
||||
.B "\-\-new\-keyfile\-size \fIvalue\fR"
|
||||
Read a maximum of \fIvalue\fR bytes when adding
|
||||
a new passphrase from key file with \fIluksAddKey\fR.
|
||||
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
|
||||
When \-\-new\-keyfile\-offset is also given, reading starts
|
||||
after the offset.
|
||||
.TP
|
||||
.B "\-\-master-key-file"
|
||||
.B "\-\-master\-key\-file"
|
||||
Use a master key stored in a file.
|
||||
|
||||
For \fIluksFormat\fR this
|
||||
@@ -594,20 +649,25 @@ LUKS header and all other parameters are the same,
|
||||
then the new header decrypts the data encrypted with the
|
||||
header the master key was taken from.
|
||||
|
||||
\fBWARNING:\fR If you create your own master key, you
|
||||
need to make sure to do it right. Otherwise you can end
|
||||
up with a low-entropy or otherwise partially predictable
|
||||
master key which will compromise security.
|
||||
|
||||
For \fIluksAddKey\fR this allows adding a new passphrase
|
||||
without having to know an exiting one.
|
||||
|
||||
For \fIopen\fR this allows to open the LUKS device
|
||||
without giving a passphrase.
|
||||
.TP
|
||||
.B "\-\-dump-master-key"
|
||||
.B "\-\-dump\-master\-key"
|
||||
For \fIluksDump\fR this option includes the master key in the displayed
|
||||
information. Use with care, as the master key can be used to
|
||||
bypass the passphrases, see also option \-\-master-key-file.
|
||||
bypass the passphrases, see also option \-\-master\-key\-file.
|
||||
.TP
|
||||
.B "\-\-use-random"
|
||||
.B "\-\-use\-random"
|
||||
.TP
|
||||
.B "\-\-use-urandom"
|
||||
.B "\-\-use\-urandom"
|
||||
For \fIluksFormat\fR these options define which kernel random number
|
||||
generator will be used to create the master key (which is a
|
||||
long-term key).
|
||||
@@ -623,7 +683,7 @@ Using /dev/random can block a long time, potentially
|
||||
forever, if not enough entropy can be harvested by
|
||||
the kernel.
|
||||
.TP
|
||||
.B "\-\-key-slot, \-S <0-7>"
|
||||
.B "\-\-key\-slot, \-S <0\-7>"
|
||||
For LUKS operations that add key material, this options allows you
|
||||
to specify which key slot is selected for the new key.
|
||||
This option can be used for \fIluksFormat\fR,
|
||||
@@ -634,7 +694,7 @@ specific key-slot to compare the passphrase against.
|
||||
If the given passphrase would only match a different key-slot,
|
||||
the operation fails.
|
||||
.TP
|
||||
.B "\-\-key-size, \-s <bits>"
|
||||
.B "\-\-key\-size, \-s <bits>"
|
||||
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.
|
||||
@@ -657,17 +717,14 @@ This option is only relevant for the \fIopen\fR action with plain
|
||||
or loopaes device types.
|
||||
.TP
|
||||
.B "\-\-skip, \-p <number of 512 byte sectors>"
|
||||
How many sectors of the encrypted data to skip at the beginning.
|
||||
Start offset used in IV calculation in 512-byte sectors
|
||||
(how many sectors of the encrypted data to skip at the beginning).
|
||||
This option is only relevant for the \fIopen\fR action with plain
|
||||
or loopaes device types.
|
||||
|
||||
This is different from the \-\-offset options with respect to
|
||||
the sector numbers used in IV calculation.
|
||||
Using \-\-offset will shift the IV calculation by the same negative amount.
|
||||
Hence, if \-\-offset \fIn\fR, sector \fIn\fR will get a sector
|
||||
number of \fI0\fR for the IV calculation.
|
||||
Using \-\-skip causes sector \fIn\fR to also be the first sector
|
||||
of the mapped device, but with its number for IV generation is \fIn\fR.
|
||||
Hence, if \-\-offset \fIn\fR, and \-\-skip \fIs\fR, sector \fIn\fR
|
||||
(the first sector of encrypted device) will get a sector number
|
||||
of \fIs\fR for the IV calculation.
|
||||
.TP
|
||||
.B "\-\-readonly, \-r"
|
||||
set up a read-only mapping.
|
||||
@@ -675,17 +732,17 @@ set up a read-only mapping.
|
||||
.B "\-\-shared"
|
||||
Creates an additional mapping for one common
|
||||
ciphertext device. Arbitrary mappings are supported.
|
||||
This option is only relevant for the
|
||||
This option is only relevant for the
|
||||
\fIopen \-\-type plain\fR action. Use \-\-offset, \-\-size and \-\-skip to
|
||||
specify the mapped area.
|
||||
.TP
|
||||
.B "\-\-iter-time, \-i <number of milliseconds>"
|
||||
.B "\-\-iter\-time, \-i <number of milliseconds>"
|
||||
The number of milliseconds to spend with PBKDF2 passphrase processing.
|
||||
This option is only relevant for LUKS operations that set or change
|
||||
passphrases, such as \fIluksFormat\fR or \fIluksAddKey\fR.
|
||||
Specifying 0 as parameter selects the compiled-in default.
|
||||
.TP
|
||||
.B "\-\-batch-mode, \-q"
|
||||
.B "\-\-batch\-mode, \-q"
|
||||
Suppresses all confirmation questions. Use with care!
|
||||
|
||||
If the \-y option is not specified, this option also switches off
|
||||
@@ -697,7 +754,7 @@ via terminal. It is relevant every time a passphrase is asked,
|
||||
for example for \fIopen\fR, \fIluksFormat\fR or \fIluksAddKey\fR.
|
||||
It has no effect if used in conjunction with \-\-key-file.
|
||||
.br
|
||||
This option is useful when the system
|
||||
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.
|
||||
@@ -709,7 +766,7 @@ every time a passphrase is asked, for example for
|
||||
\fIopen\fR, \fIluksFormat\fR or \fIluksAddKey\fR.
|
||||
The default is 3 tries.
|
||||
.TP
|
||||
.B "\-\-align-payload <number of 512 byte sectors>"
|
||||
.B "\-\-align\-payload <number of 512 byte sectors>"
|
||||
Align payload at a boundary of \fIvalue\fR 512-byte sectors.
|
||||
This option is relevant for \fIluksFormat\fR.
|
||||
|
||||
@@ -729,7 +786,7 @@ used with the \fIluksUUID\fR command.
|
||||
The UUID must be provided in the standard UUID format,
|
||||
e.g. 12345678-1234-1234-1234-123456789abc.
|
||||
.TP
|
||||
.B "\-\-allow-discards\fR"
|
||||
.B "\-\-allow\-discards\fR"
|
||||
Allow the use of discard (TRIM) requests for device.
|
||||
This option is only relevant for \fIopen\fR action.
|
||||
|
||||
@@ -743,7 +800,7 @@ later. If in doubt, do no use it.
|
||||
A kernel version of 3.1 or later is needed. For earlier kernels
|
||||
this option is ignored.
|
||||
.TP
|
||||
.B "\-\-test-passphrase\fR"
|
||||
.B "\-\-test\-passphrase\fR"
|
||||
Do not activate device, just verify passphrase.
|
||||
This option is only relevant for \fIopen\fR action (the device
|
||||
mapping name is not mandatory if this option is used).
|
||||
@@ -753,7 +810,7 @@ Use a detached (separated) metadata device or file where the
|
||||
LUKS header is stored. This options allows to store ciphertext
|
||||
and LUKS header on different devices.
|
||||
|
||||
This option is only relevant for LUKS devices and can be
|
||||
This option is only relevant for LUKS devices and can be
|
||||
used with the \fIluksFormat\fR, \fIopen\fR, \fIluksSuspend\fR,
|
||||
\fIluksResume\fR, \fIstatus\fR and \fIresize\fR commands.
|
||||
|
||||
@@ -765,7 +822,7 @@ For other commands that change the LUKS header (e.g. \fIluksAddKey\fR),
|
||||
specify the device or file with the LUKS header directly as the
|
||||
LUKS device.
|
||||
|
||||
If used with \fIluksFormat\fR, the \-\-align-payload option is taken
|
||||
If used with \fIluksFormat\fR, the \-\-align\-payload option is taken
|
||||
as absolute sector alignment on ciphertext device and can be zero.
|
||||
|
||||
\fBWARNING:\fR There is no check whether the ciphertext device specified
|
||||
@@ -773,7 +830,7 @@ actually belongs to the header given. In fact you can specify an
|
||||
arbitrary device as the ciphertext device for \fIopen\fR
|
||||
with the \-\-header option. Use with care.
|
||||
.TP
|
||||
.B "\-\-force-password\fR"
|
||||
.B "\-\-force\-password\fR"
|
||||
Do not use password quality checking for new LUKS passwords.
|
||||
|
||||
This option applies only to \fIluksFormat\fR, \fIluksAddKey\fR and
|
||||
@@ -806,7 +863,7 @@ low-entropy passphrases are easy to attack in plain mode.
|
||||
first newline, i.e. '\\n'.
|
||||
The input without the newline character is processed with
|
||||
the default hash or the hash specified with \-\-hash.
|
||||
The has result will be truncated to the key size
|
||||
The hash result will be truncated to the key size
|
||||
of the used cipher, or the size specified with \-s.
|
||||
|
||||
\fBFrom stdin\fR: Reading will continue until a newline (or until
|
||||
@@ -831,7 +888,7 @@ directly specifying a binary key.
|
||||
No warning will be given if the amount of data read from stdin is
|
||||
less than the key size.
|
||||
|
||||
\fBFrom a key file\fR: It will be truncated to the
|
||||
\fBFrom a key file\fR: It will be truncated to the
|
||||
key size of the used cipher or the size given by \-s
|
||||
and directly used as binary key.
|
||||
if the key file is shorter than the key, cryptsetup
|
||||
@@ -849,13 +906,13 @@ the newline character.
|
||||
\fBFrom stdin\fR:
|
||||
LUKS will read passphrases from stdin up to the
|
||||
first newline character or the compiled-in
|
||||
maximum key file length. If \-\-keyfile-size is
|
||||
maximum key file length. If \-\-keyfile\-size is
|
||||
given, it is ignored.
|
||||
|
||||
\fBFrom key file\fR:
|
||||
The complete keyfile is read up to the compiled-in
|
||||
maximum size. Newline characters do not terminate the
|
||||
input. The \-\-keyfile-size option can be used to limit
|
||||
input. The \-\-keyfile\-size option can be used to limit
|
||||
what is read.
|
||||
|
||||
\fBPassphrase processing\fR:
|
||||
@@ -869,7 +926,12 @@ used key length, higher iteration times will not increase security.
|
||||
|
||||
The default setting of one second is sufficient for most
|
||||
practical cases. The only exception is a low-entropy
|
||||
passphrase used on a slow device.
|
||||
passphrase used on a device with a slow CPU, as this will
|
||||
result in a low iteration count. On a slow device it may
|
||||
be advisable to increase the iteration time using the
|
||||
\-\-iter\-time option in order to obtain a higher
|
||||
iteration count. This does slow down all later luksOpen
|
||||
operations accordingly.
|
||||
.SH INCOHERENT BEHAVIOR FOR INVALID PASSPHRASES/KEYS
|
||||
LUKS checks for a valid passphrase when an encrypted partition
|
||||
is unlocked. The behavior of plain dm-crypt is different.
|
||||
@@ -905,12 +967,12 @@ and for wiping deleted keyslots.
|
||||
|
||||
The second type is used for the volume (master) key. You can switch
|
||||
between using /dev/random and /dev/urandom here, see
|
||||
\fP\-\-use-random\fR and \fP\-\-use-urandom\fR
|
||||
\fP\-\-use\-random\fR and \fP\-\-use\-urandom\fR
|
||||
options. Using /dev/random on a system without enough entropy sources
|
||||
can cause \fPluksFormat\fR to block until the requested amount of
|
||||
random data is gathered. In a low-entropy situation (embedded system),
|
||||
this can take a very long time and potentially forever. At the same
|
||||
time, using /dev/urandom in a low-entropy situation will
|
||||
time, using /dev/urandom in a low-entropy situation will
|
||||
produce low-quality keys. This is a serious problem, but solving
|
||||
it is out of scope for a mere man-page.
|
||||
See \fPurandom(4)\fR for more information.
|
||||
@@ -956,9 +1018,9 @@ Copyright \(co 2004-2006 Clemens Fruhwirth
|
||||
.br
|
||||
Copyright \(co 2009-2012 Red Hat, Inc.
|
||||
.br
|
||||
Copyright \(co 2009-2012 Milan Broz
|
||||
Copyright \(co 2009-2014 Milan Broz
|
||||
.br
|
||||
Copyright \(co 2012 Arno Wagner
|
||||
Copyright \(co 2012-2014 Arno Wagner
|
||||
|
||||
This is free software; see the source for copying conditions. There is NO
|
||||
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
.TH VERITYSETUP "8" "June 2012" "veritysetup" "Maintenance Commands"
|
||||
.TH VERITYSETUP "8" "December 2013" "veritysetup" "Maintenance Commands"
|
||||
.SH NAME
|
||||
veritysetup - manage dm-verity (block level verification) volumes
|
||||
.SH SYNOPSIS
|
||||
@@ -130,7 +130,9 @@ The first implementation of veritysetup was written by Chrome OS authors.
|
||||
This version is based on verification code written by Mikulas Patocka <mpatocka@redhat.com>
|
||||
and rewritten for libcryptsetup by Milan Broz <gmazyland@gmail.com>.
|
||||
.SH COPYRIGHT
|
||||
Copyright \(co 2012 Red Hat, Inc.
|
||||
Copyright \(co 2012-2013 Red Hat, Inc.
|
||||
.br
|
||||
Copyright \(co 2012-2013 Milan Broz
|
||||
|
||||
This is free software; see the source for copying conditions. There is NO
|
||||
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
|
||||
17
misc/11-dm-crypt.rules
Normal file
17
misc/11-dm-crypt.rules
Normal file
@@ -0,0 +1,17 @@
|
||||
# Old udev rules historically used in device-mapper.
|
||||
# No need to install these until you have some weird configuration.
|
||||
# (Code internally set the same flags.)
|
||||
|
||||
ACTION!="add|change", GOTO="crypt_end"
|
||||
ENV{DM_UDEV_RULES_VSN}!="?*", GOTO="crypt_end"
|
||||
|
||||
ENV{DM_UUID}=="CRYPT-TEMP-?*", GOTO="crypt_disable"
|
||||
ENV{DM_UUID}!="?*", ENV{DM_NAME}=="temporary-cryptsetup-?*", GOTO="crypt_disable"
|
||||
GOTO="crypt_end"
|
||||
|
||||
LABEL="crypt_disable"
|
||||
ENV{DM_UDEV_DISABLE_SUBSYSTEM_RULES_FLAG}="1"
|
||||
ENV{DM_UDEV_DISABLE_DISK_RULES_FLAG}="1"
|
||||
ENV{DM_UDEV_DISABLE_OTHER_RULES_FLAG}="1"
|
||||
|
||||
LABEL="crypt_end"
|
||||
@@ -2,13 +2,28 @@ Example of simple dracut module for reencryption of system
|
||||
LUKS drive on-the-fly.
|
||||
|
||||
Install in /usr/[share|lib]/dracut/modules.d/90reencrypt, then
|
||||
rebuild intramfs "with dracut -f -a reencrypt".
|
||||
build special intramfs "with dracut -a reencrypt -o crypt".
|
||||
Reencrypt module doesn't work (has a conflict) with crypt module as
|
||||
of now. After successfull reencryption reboot using original initramfs.
|
||||
|
||||
Dracut then recognize argument rd_REENCRYPT=name:size,
|
||||
e.g. rd_REENCRYPT=sda2:52G means only 52G of device
|
||||
Dracut then recognize argument rd.luks.reencrypt=name:size,
|
||||
e.g. rd.luks.reencrypt=sda2:52G means only 52G of device
|
||||
will be reencrypted (default is whole device).
|
||||
(Name is kernel name of device.)
|
||||
|
||||
Also, you may specify keyslot which you want to use for reencryption,
|
||||
rd.luks.reencrypt_keyslot=<keyslot_number>. Bear in mind that if you
|
||||
use this option, all other keyslots will be deactivated.
|
||||
|
||||
Another argument, rd.luks.reencrypt_key=/dev/sda:/path/to/keyfile
|
||||
can be used to read password for specific keyslot from device containing
|
||||
filesystem with a keyfile (file with a password). If you omit reencrypt_key
|
||||
argument, reencryption would work only in case a LUKS container has
|
||||
exactly one keyslot activated.
|
||||
|
||||
Arguments rd.luks.reencrypt_keyslot and rd.luks.reencrypt_key are not
|
||||
mandatory.
|
||||
|
||||
Note that reencryption context is stored in ramdisk, any
|
||||
fail can mean complete lost of data!
|
||||
|
||||
|
||||
@@ -7,16 +7,23 @@ check() {
|
||||
|
||||
depends() {
|
||||
echo dm rootfs-block
|
||||
return 0
|
||||
}
|
||||
|
||||
installkernel() {
|
||||
instmods dm_crypt =crypto
|
||||
# requires hostonly='' override so that loop module is pulled in initramfs
|
||||
# even if not loaded in actual kernel. dracut bug?
|
||||
hostonly='' instmods dm_crypt =crypto loop
|
||||
}
|
||||
|
||||
install() {
|
||||
if dracut_module_included crypt; then
|
||||
derror "'reencrypt' can't be installed together with 'crypt'."
|
||||
derror "Add '-o crypt' option to install reencrypt module."
|
||||
return 1
|
||||
fi
|
||||
|
||||
dracut_install cryptsetup-reencrypt
|
||||
|
||||
inst_hook cmdline 30 "$moddir/parse-reencrypt.sh"
|
||||
inst_simple "$moddir"/reencrypt.sh /sbin/reencrypt
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,14 +1,19 @@
|
||||
#!/bin/sh
|
||||
|
||||
REENC=$(getargs rd_REENCRYPT=)
|
||||
REENC=$(getargs rd.luks.reencrypt=)
|
||||
REENC_DEV=$(echo $REENC | sed 's/:.*//')
|
||||
REENC_SIZE=$(echo $REENC | sed -n 's/.*://p')
|
||||
|
||||
REENC_KEY=$(getargs rd_REENCRYPT_KEY=)
|
||||
REENC_KEY=$(getargs rd.luks.reencrypt_key=)
|
||||
if [ -z "$REENC_KEY" ] ; then
|
||||
REENC_KEY=none
|
||||
fi
|
||||
|
||||
REENC_SLOT=$(getargs rd.luks.reencrypt_keyslot=)
|
||||
if [ -z "$REENC_SLOT" ] ; then
|
||||
REENC_SLOT=any
|
||||
fi
|
||||
|
||||
if [ -n "$REENC_DEV" ] ; then
|
||||
{
|
||||
printf 'SUBSYSTEM!="block", GOTO="reenc_end"\n'
|
||||
@@ -16,7 +21,7 @@ if [ -n "$REENC_DEV" ] ; then
|
||||
printf 'KERNEL!="%s", GOTO="reenc_end"\n' $REENC_DEV
|
||||
printf 'ENV{ID_FS_TYPE}=="crypto_LUKS", RUN+="/sbin/initqueue \
|
||||
--unique --onetime --name crypt-reencrypt-%%k \
|
||||
/sbin/reencrypt $env{DEVNAME} %s"\n' "$REENC_KEY $REENC_SIZE"
|
||||
/sbin/reencrypt $env{DEVNAME} %s"\n' "$REENC_KEY $REENC_SLOT $REENC_SIZE"
|
||||
printf 'LABEL="reenc_end"\n'
|
||||
} > /etc/udev/rules.d/69-reencryption.rules
|
||||
fi
|
||||
|
||||
@@ -1,10 +1,12 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# $1=$device [$2=keyfile|none [$3=size]]
|
||||
# $1=$device [$2=keyfile|none [$3=keyslot|any [$4=size]]]
|
||||
#
|
||||
|
||||
[ -d /sys/module/dm_crypt ] || modprobe dm_crypt
|
||||
|
||||
[ -d /sys/module/loop ] || modprobe loop
|
||||
|
||||
[ -f /tmp/reencrypted ] && exit 0
|
||||
|
||||
. /lib/dracut-lib.sh
|
||||
@@ -17,8 +19,12 @@ else
|
||||
fi
|
||||
|
||||
PARAMS="$device -T 1 --use-fsync -B 32"
|
||||
if [ -n "$3" ]; then
|
||||
PARAMS="$PARAMS --device-size $3"
|
||||
if [ "$3" != "any" ]; then
|
||||
PARAMS="$PARAMS -S $3"
|
||||
fi
|
||||
|
||||
if [ -n "$4" ]; then
|
||||
PARAMS="$PARAMS --device-size $4"
|
||||
fi
|
||||
|
||||
reenc_readkey() {
|
||||
@@ -34,25 +40,40 @@ reenc_readkey() {
|
||||
|
||||
reenc_run() {
|
||||
local cwd=$(pwd)
|
||||
local _prompt="LUKS password for REENCRYPTING $device"
|
||||
cd /tmp
|
||||
if [ "$1" = "none" ] ; then
|
||||
if [ "$2" != "any" ]; then
|
||||
_prompt="$_prompt, using keyslot $2"
|
||||
fi
|
||||
/bin/plymouth ask-for-password \
|
||||
--prompt "LUKS password for REENCRYPTING $device" \
|
||||
--prompt "$_prompt" \
|
||||
--command="/sbin/cryptsetup-reencrypt $PARAMS"
|
||||
else
|
||||
info "REENCRYPT using key $1"
|
||||
reenc_readkey "$1" | /sbin/cryptsetup-reencrypt -d - $PARAMS
|
||||
fi
|
||||
_ret=$?
|
||||
cd $cwd
|
||||
}
|
||||
|
||||
info "REENCRYPT $device requested"
|
||||
# flock against other interactive activities
|
||||
{ flock -s 9;
|
||||
reenc_run $2
|
||||
} 9>/.console.lock
|
||||
reenc_run $2 $3
|
||||
} 9>/.console_lock
|
||||
|
||||
# do not ask again
|
||||
>> /tmp/reencrypted
|
||||
if [ $_ret -eq 0 ]; then
|
||||
# do not ask again
|
||||
>> /tmp/reencrypted
|
||||
warn "Reencryption of device $device has finished successfully. Use previous"
|
||||
warn "initramfs image (without reencrypt module) to boot the system. When"
|
||||
warn "you leave the emergency shell, the system will reboot."
|
||||
|
||||
exit 0
|
||||
emergency_shell -n "(reboot)"
|
||||
[ -x /usr/bin/systemctl ] && /usr/bin/systemctl reboot
|
||||
[ -x /sbin/shutdown ] && /sbin/shutdown -r now
|
||||
fi
|
||||
|
||||
# panic the kernel otherwise
|
||||
exit 1
|
||||
|
||||
@@ -12,8 +12,10 @@ Installation
|
||||
============
|
||||
|
||||
1. Install the version of cryptsetup the tool came with.
|
||||
2. Compile with
|
||||
gcc -lm -lcryptsetup chk_luks_keyslots.c -o chk_luks_keyslots
|
||||
2. Compile with "make"
|
||||
|
||||
Manual compile can be done with
|
||||
gcc -lm -lcryptsetup chk_luks_keyslots.c -o chk_luks_keyslots
|
||||
|
||||
Usage
|
||||
=====
|
||||
@@ -21,8 +23,8 @@ Usage
|
||||
Call chk_luks_keyslots without arguments for an option summary.
|
||||
|
||||
|
||||
Example of a good keyslot area:
|
||||
-------------------------------
|
||||
Example of a good keyslot area with keys 0 and 2 in use:
|
||||
--------------------------------------------------------
|
||||
|
||||
root> ./chk_luks_keyslots /dev/loop0
|
||||
|
||||
@@ -31,17 +33,17 @@ parameters (commandline and LUKS header):
|
||||
threshold: 0.900000
|
||||
|
||||
- processing keyslot 0: start: 0x001000 end: 0x020400
|
||||
- processing keyslot 1: start: 0x021000 end: 0x040400
|
||||
- processing keyslot 1: keyslot not in use
|
||||
- processing keyslot 2: start: 0x041000 end: 0x060400
|
||||
- processing keyslot 3: start: 0x061000 end: 0x080400
|
||||
- processing keyslot 4: start: 0x081000 end: 0x0a0400
|
||||
- processing keyslot 5: start: 0x0a1000 end: 0x0c0400
|
||||
- processing keyslot 6: start: 0x0c1000 end: 0x0e0400
|
||||
- processing keyslot 7: start: 0x0e1000 end: 0x100400
|
||||
- processing keyslot 3: keyslot not in use
|
||||
- processing keyslot 4: keyslot not in use
|
||||
- processing keyslot 5: keyslot not in use
|
||||
- processing keyslot 6: keyslot not in use
|
||||
- processing keyslot 7: keyslot not in use
|
||||
|
||||
|
||||
Example of a fault in slot 8 at offset 0x100200:
|
||||
-----------------------------
|
||||
Same example of a fault in slot 2 at offset 0x50000:
|
||||
----------------------------------------------------
|
||||
|
||||
root>./chk_luks_keyslots /dev/loop2
|
||||
|
||||
@@ -50,14 +52,14 @@ parameters (commandline and LUKS header):
|
||||
threshold: 0.900000
|
||||
|
||||
- processing keyslot 0: start: 0x001000 end: 0x020400
|
||||
- processing keyslot 1: start: 0x021000 end: 0x040400
|
||||
- processing keyslot 1: keyslot not in use
|
||||
- processing keyslot 2: start: 0x041000 end: 0x060400
|
||||
- processing keyslot 3: start: 0x061000 end: 0x080400
|
||||
- processing keyslot 4: start: 0x081000 end: 0x0a0400
|
||||
- processing keyslot 5: start: 0x0a1000 end: 0x0c0400
|
||||
- processing keyslot 6: start: 0x0c1000 end: 0x0e0400
|
||||
- processing keyslot 7: start: 0x0e1000 end: 0x100400
|
||||
low entropy at: 0x100200 entropy: 0.846546
|
||||
low entropy at: 0x050000 entropy: 0.549165
|
||||
- processing keyslot 3: keyslot not in use
|
||||
- processing keyslot 4: keyslot not in use
|
||||
- processing keyslot 5: keyslot not in use
|
||||
- processing keyslot 6: keyslot not in use
|
||||
- processing keyslot 7: keyslot not in use
|
||||
|
||||
|
||||
Same as last, but verbose:
|
||||
@@ -69,48 +71,48 @@ parameters (commandline and LUKS header):
|
||||
threshold: 0.900000
|
||||
|
||||
- processing keyslot 0: start: 0x001000 end: 0x020400
|
||||
- processing keyslot 1: start: 0x021000 end: 0x040400
|
||||
- processing keyslot 1: keyslot not in use
|
||||
- processing keyslot 2: start: 0x041000 end: 0x060400
|
||||
- processing keyslot 3: start: 0x061000 end: 0x080400
|
||||
- processing keyslot 4: start: 0x081000 end: 0x0a0400
|
||||
- processing keyslot 5: start: 0x0a1000 end: 0x0c0400
|
||||
- processing keyslot 6: start: 0x0c1000 end: 0x0e0400
|
||||
- processing keyslot 7: start: 0x0e1000 end: 0x100400
|
||||
low entropy at: 0x100200 entropy: 0.846546
|
||||
low entropy at: 0x050000 entropy: 0.549165
|
||||
Binary dump:
|
||||
0x100200 BD 0E C7 A8 7D EF 04 F6 AF 83 DF 74 94 FE 04 56 ....}......t...V
|
||||
0x100210 3B 64 BD 68 A9 F6 CF 3C 37 CD 66 B7 17 4D 63 2B ;d.h...<7.f..Mc+
|
||||
0x100220 8F 6E 74 7E 96 7A 2B 27 32 1B F0 80 37 5A 9A 41 .nt~.z+'2...7Z.A
|
||||
0x100230 4A 6E CB C0 CF 39 95 45 92 90 E1 0B E6 08 EE 2A Jn...9.E.......*
|
||||
0x100240 FA 66 6D 67 49 89 76 B1 41 CD 24 57 AA 65 F7 69 .fmgI.v.A.$W.e.i
|
||||
0x100250 33 16 A7 C7 61 3D 43 B7 74 D6 86 83 1D 19 BF 85 3...a=C.t.......
|
||||
0x100260 E4 22 3E 16 66 1C B0 1E 11 0D D4 26 37 AD A4 02 .">.f......&7...
|
||||
0x100270 40 77 9A 5A B8 40 39 E3 A3 A0 96 08 4D 57 C5 0C @w.Z.@9.....MW..
|
||||
0x100280 D4 74 89 45 FA 93 F7 FE A7 9D D3 99 43 77 8E 35 .t.E........Cw.5
|
||||
0x100290 E0 55 90 3E 91 29 EA DB 5C 13 19 C9 83 CE D8 0C .U.>.)..\.......
|
||||
0x1002a0 85 7F 96 26 60 16 A0 0B E1 F9 01 13 1E 59 83 98 ...&`........Y..
|
||||
0x1002b0 06 B5 1D 6F B6 81 9D 60 58 70 15 30 29 42 32 C6 ...o...`Xp.0)B2.
|
||||
0x1002c0 A7 55 64 00 65 ED 41 1C B4 C1 C7 10 E1 8E 60 B0 .Ud.e.A.......`.
|
||||
0x1002d0 F0 9E 9C 40 5A 84 92 8D 21 F0 B8 2D 61 4E 21 9D ...@Z...!..-aN!.
|
||||
0x1002e0 FA B8 18 D3 47 A4 4F D4 AB 73 C0 93 F3 8E 9A 95 ....G.O..s......
|
||||
0x1002f0 A4 F1 6D EB 36 85 F4 F7 62 BA 26 D5 15 57 0D 0C ..m.6...b.&..W..
|
||||
0x100300 C9 4E 19 F2 5B 5A F5 54 B8 F4 B5 57 72 08 1B 7A .N..[Z.T...Wr..z
|
||||
0x100310 C3 66 7F 82 1E 75 92 C2 E9 97 64 5E F7 FB A9 05 .f...u....d^....
|
||||
0x100320 CF 30 C8 6A D1 35 9B 9D 22 52 22 46 0E 4B DE 53 .0.j.5.."R"F.K.S
|
||||
0x100330 68 C8 DA 5F C7 CA 31 D0 C9 B4 57 CF 0F 1F 4B 9C h.._..1...W...K.
|
||||
0x100340 DF 0C F8 7C F2 E3 32 52 3C 0D D2 DC 5C CF F0 00 ...|..2R<...\...
|
||||
0x100350 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 XXXXXXXXXXXXXXXX
|
||||
0x100360 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 XXXXXXXXXXXXXXXX
|
||||
0x100370 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 XXXXXXXXXXXXXXXX
|
||||
0x100380 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 XXXXXXXXXXXXXXXX
|
||||
0x100390 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 XXXXXXXXXXXXXXXX
|
||||
0x1003a0 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 58 XXXXXXXXXXXXXXXX
|
||||
0x1003b0 B4 81 7A F0 BE 38 7E 00 A4 61 41 06 ED 7B 40 D9 ..z..8~..aA..{@.
|
||||
0x1003c0 BF 58 51 C9 CD 37 78 4D 4D B3 6E B4 7D 86 3C CB .XQ..7xMM.n.}.<.
|
||||
0x1003d0 D5 39 2E FC 78 B1 3E DE C0 7F 55 25 65 71 AD 2A .9..x.>...U%eq.*
|
||||
0x1003e0 1E 68 D3 3B 78 17 5F D2 08 93 50 88 D8 0A 75 4F .h.;x._...P...uO
|
||||
0x1003f0 E5 AA 26 0F B4 F7 F5 88 65 2B E4 92 18 08 32 9E ..&.....e+....2.
|
||||
0x050000 54 68 69 73 20 69 73 20 61 20 74 65 73 74 2D 73 This is a test-s
|
||||
0x050010 65 63 74 6F 72 20 66 6F 72 20 63 68 6B 5F 6C 75 ector for chk_lu
|
||||
0x050020 6B 73 5F 6B 65 79 73 6C 6F 74 73 20 74 68 65 20 ks_keyslots the
|
||||
0x050030 71 75 69 63 6B 20 62 72 6F 77 6E 20 66 6F 78 20 quick brown fox
|
||||
0x050040 6A 75 6D 70 73 20 6F 76 65 72 20 74 68 65 20 6C jumps over the l
|
||||
0x050050 61 7A 79 20 64 6F 67 20 74 68 65 20 71 75 69 63 azy dog the quic
|
||||
0x050060 6B 20 62 72 6F 77 6E 20 66 6F 78 20 6A 75 6D 70 k brown fox jump
|
||||
0x050070 73 20 6F 76 65 72 20 74 68 65 20 6C 61 7A 79 20 s over the lazy
|
||||
0x050080 64 6F 67 20 74 68 65 20 71 75 69 63 6B 20 62 72 dog the quick br
|
||||
0x050090 6F 77 6E 20 66 6F 78 20 6A 75 6D 70 73 20 6F 76 own fox jumps ov
|
||||
0x0500a0 65 72 20 74 68 65 20 6C 61 7A 79 20 64 6F 67 20 er the lazy dog
|
||||
0x0500b0 74 68 65 20 71 75 69 63 6B 20 62 72 6F 77 6E 20 the quick brown
|
||||
0x0500c0 66 6F 78 20 6A 75 6D 70 73 20 6F 76 65 72 20 74 fox jumps over t
|
||||
0x0500d0 68 65 20 6C 61 7A 79 20 64 6F 67 20 74 68 65 20 he lazy dog the
|
||||
0x0500e0 71 75 69 63 6B 20 62 72 6F 77 6E 20 66 6F 78 20 quick brown fox
|
||||
0x0500f0 6A 75 6D 70 73 20 6F 76 65 72 20 74 68 65 20 6C jumps over the l
|
||||
0x050100 61 7A 79 20 64 6F 67 20 74 68 65 20 71 75 69 63 azy dog the quic
|
||||
0x050110 6B 20 62 72 6F 77 6E 20 66 6F 78 20 6A 75 6D 70 k brown fox jump
|
||||
0x050120 73 20 6F 76 65 72 20 74 68 65 20 6C 61 7A 79 20 s over the lazy
|
||||
0x050130 64 6F 67 20 74 68 65 20 71 75 69 63 6B 20 62 72 dog the quick br
|
||||
0x050140 6F 77 6E 20 66 6F 78 20 6A 75 6D 70 73 20 6F 76 own fox jumps ov
|
||||
0x050150 65 72 20 74 68 65 20 6C 61 7A 79 20 64 6F 67 20 er the lazy dog
|
||||
0x050160 74 68 65 20 71 75 69 63 6B 20 62 72 6F 77 6E 20 the quick brown
|
||||
0x050170 66 6F 78 20 6A 75 6D 70 73 20 6F 76 65 72 20 74 fox jumps over t
|
||||
0x050180 68 65 20 6C 61 7A 79 20 64 6F 67 20 74 68 65 20 he lazy dog the
|
||||
0x050190 71 75 69 63 6B 20 62 72 6F 77 6E 20 66 6F 78 20 quick brown fox
|
||||
0x0501a0 6A 75 6D 70 73 20 6F 76 65 72 20 74 68 65 20 6C jumps over the l
|
||||
0x0501b0 61 7A 79 20 64 6F 67 20 74 68 65 20 71 75 69 63 azy dog the quic
|
||||
0x0501c0 6B 20 62 72 6F 77 6E 20 66 6F 78 20 6A 75 6D 70 k brown fox jump
|
||||
0x0501d0 73 20 6F 76 65 72 20 74 68 65 20 6C 61 7A 79 20 s over the lazy
|
||||
0x0501e0 64 6F 67 20 74 68 65 20 71 75 69 63 6B 20 62 72 dog the quick br
|
||||
0x0501f0 6F 77 6E 20 66 6F 78 20 6A 75 6D 70 73 20 6F 76 own fox jumps ov
|
||||
|
||||
- processing keyslot 3: keyslot not in use
|
||||
- processing keyslot 4: keyslot not in use
|
||||
- processing keyslot 5: keyslot not in use
|
||||
- processing keyslot 6: keyslot not in use
|
||||
- processing keyslot 7: keyslot not in use
|
||||
|
||||
----
|
||||
Copyright (C) 2012, Arno Wagner <arno@wagner.name>
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
cs
|
||||
de
|
||||
es
|
||||
fi
|
||||
fr
|
||||
id
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
AM_CPPFLAGS = -I$(top_srcdir)/lib $(PYTHON_INCLUDES)
|
||||
AM_CPPFLAGS = -include $(top_srcdir)/config.h -I$(top_srcdir)/lib $(PYTHON_INCLUDES)
|
||||
EXTRA_DIST = pycryptsetup-test.py
|
||||
CLEANFILES = *.img
|
||||
|
||||
@@ -9,7 +9,7 @@ pyexec_LTLIBRARIES = pycryptsetup.la
|
||||
|
||||
pycryptsetup_la_SOURCES = pycryptsetup.c
|
||||
pycryptsetup_la_CPPFLAGS = $(AM_CPPFLAGS) $(PYTHON_CPPFLAGS) -fno-strict-aliasing
|
||||
pycryptsetup_la_LDFLAGS = -avoid-version -module
|
||||
pycryptsetup_la_LDFLAGS = -avoid-version -module -shared -export-dynamic
|
||||
pycryptsetup_la_LIBADD = $(top_builddir)/lib/libcryptsetup.la -lpython$(PYTHON_VERSION)
|
||||
else
|
||||
all:
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
AM_CPPFLAGS = \
|
||||
AM_CPPFLAGS = -include config.h \
|
||||
-I$(top_srcdir) \
|
||||
-I$(top_srcdir)/lib \
|
||||
-DDATADIR=\""$(datadir)"\" \
|
||||
@@ -6,8 +6,7 @@ AM_CPPFLAGS = \
|
||||
-DLIBDIR=\""$(libdir)"\" \
|
||||
-DPREFIX=\""$(prefix)"\" \
|
||||
-DSYSCONFDIR=\""$(sysconfdir)"\" \
|
||||
-DVERSION=\""$(VERSION)"\" \
|
||||
-D_GNU_SOURCE
|
||||
-DVERSION=\""$(VERSION)"\"
|
||||
|
||||
# cryptsetup
|
||||
cryptsetup_SOURCES = \
|
||||
@@ -25,7 +24,7 @@ cryptsetup_LDADD = \
|
||||
@FIPSCHECK_LIBS@ \
|
||||
@PWQUALITY_LIBS@
|
||||
|
||||
cryptsetup_CFLAGS = -Wall
|
||||
cryptsetup_CFLAGS = $(AM_CFLAGS) -Wall
|
||||
|
||||
sbin_PROGRAMS=cryptsetup
|
||||
|
||||
@@ -33,7 +32,7 @@ if STATIC_TOOLS
|
||||
sbin_PROGRAMS += cryptsetup.static
|
||||
cryptsetup_static_SOURCES = $(cryptsetup_SOURCES)
|
||||
cryptsetup_static_CFLAGS = $(cryptsetup_CFLAGS)
|
||||
cryptsetup_static_LDFLAGS = -all-static
|
||||
cryptsetup_static_LDFLAGS = $(AM_LDFLAGS) -all-static
|
||||
cryptsetup_static_LDADD = $(cryptsetup_LDADD) \
|
||||
@CRYPTO_STATIC_LIBS@ \
|
||||
@PWQUALITY_STATIC_LIBS@ \
|
||||
@@ -63,7 +62,7 @@ if STATIC_TOOLS
|
||||
sbin_PROGRAMS += veritysetup.static
|
||||
veritysetup_static_SOURCES = $(veritysetup_SOURCES)
|
||||
veritysetup_static_CFLAGS = $(veritysetup_CFLAGS)
|
||||
veritysetup_static_LDFLAGS = -all-static
|
||||
veritysetup_static_LDFLAGS = $(AM_LDFLAGS) -all-static
|
||||
veritysetup_static_LDADD = $(veritysetup_LDADD) \
|
||||
@CRYPTO_STATIC_LIBS@ \
|
||||
@DEVMAPPER_STATIC_LIBS@ \
|
||||
@@ -88,7 +87,7 @@ if STATIC_TOOLS
|
||||
sbin_PROGRAMS += cryptsetup-reencrypt.static
|
||||
cryptsetup_reencrypt_static_SOURCES = $(cryptsetup_reencrypt_SOURCES)
|
||||
cryptsetup_reencrypt_static_CFLAGS = $(cryptsetup_reencrypt_CFLAGS)
|
||||
cryptsetup_reencrypt_static_LDFLAGS = -all-static
|
||||
cryptsetup_reencrypt_static_LDFLAGS = $(AM_LDFLAGS) -all-static
|
||||
cryptsetup_reencrypt_static_LDADD = $(cryptsetup_reencrypt_LDADD) \
|
||||
@CRYPTO_STATIC_LIBS@ \
|
||||
@DEVMAPPER_STATIC_LIBS@ \
|
||||
|
||||
206
src/cryptsetup.c
206
src/cryptsetup.c
@@ -4,7 +4,7 @@
|
||||
* Copyright (C) 2004, Christophe Saout <christophe@saout.de>
|
||||
* Copyright (C) 2004-2007, Clemens Fruhwirth <clemens@endorphin.org>
|
||||
* Copyright (C) 2009-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2012, Milan Broz
|
||||
* Copyright (C) 2009-2014, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -60,6 +60,7 @@ static int opt_allow_discards = 0;
|
||||
static int opt_test_passphrase = 0;
|
||||
static int opt_tcrypt_hidden = 0;
|
||||
static int opt_tcrypt_system = 0;
|
||||
static int opt_tcrypt_backup = 0;
|
||||
|
||||
static const char **action_argv;
|
||||
static int action_argc;
|
||||
@@ -208,6 +209,50 @@ out:
|
||||
return r;
|
||||
}
|
||||
|
||||
static int tcrypt_load(struct crypt_device *cd, struct crypt_params_tcrypt *params)
|
||||
{
|
||||
int r, tries = opt_tries, eperm = 0;
|
||||
|
||||
do {
|
||||
/* TCRYPT header is encrypted, get passphrase now */
|
||||
r = tools_get_key(_("Enter passphrase: "),
|
||||
CONST_CAST(char**)¶ms->passphrase,
|
||||
¶ms->passphrase_size, 0, 0, NULL, opt_timeout,
|
||||
_verify_passphrase(0), 0, cd);
|
||||
if (r < 0)
|
||||
continue;
|
||||
|
||||
if (opt_tcrypt_hidden)
|
||||
params->flags |= CRYPT_TCRYPT_HIDDEN_HEADER;
|
||||
|
||||
if (opt_tcrypt_system)
|
||||
params->flags |= CRYPT_TCRYPT_SYSTEM_HEADER;
|
||||
|
||||
if (opt_tcrypt_backup)
|
||||
params->flags |= CRYPT_TCRYPT_BACKUP_HEADER;
|
||||
|
||||
r = crypt_load(cd, CRYPT_TCRYPT, params);
|
||||
|
||||
if (r == -EPERM) {
|
||||
log_err(_("No device header detected with this passphrase.\n"));
|
||||
eperm = 1;
|
||||
}
|
||||
|
||||
if (r < 0) {
|
||||
crypt_safe_free(CONST_CAST(char*)params->passphrase);
|
||||
params->passphrase = NULL;
|
||||
params->passphrase_size = 0;
|
||||
}
|
||||
check_signal(&r);
|
||||
} while (r == -EPERM && (--tries > 0));
|
||||
|
||||
/* Report wrong passphrase if at least one try failed */
|
||||
if (eperm && r == -EPIPE)
|
||||
r = -EPERM;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int action_open_tcrypt(void)
|
||||
{
|
||||
struct crypt_device *cd = NULL;
|
||||
@@ -225,33 +270,19 @@ static int action_open_tcrypt(void)
|
||||
if ((r = crypt_init(&cd, action_argv[0])))
|
||||
goto out;
|
||||
|
||||
/* TCRYPT header is encrypted, get passphrase now */
|
||||
r = tools_get_key(_("Enter passphrase: "),
|
||||
CONST_CAST(char**)¶ms.passphrase,
|
||||
¶ms.passphrase_size, 0, 0, NULL, opt_timeout,
|
||||
_verify_passphrase(0), 0, cd);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
if (opt_tcrypt_hidden)
|
||||
params.flags |= CRYPT_TCRYPT_HIDDEN_HEADER;
|
||||
|
||||
if (opt_tcrypt_system)
|
||||
params.flags |= CRYPT_TCRYPT_SYSTEM_HEADER;
|
||||
|
||||
r = crypt_load(cd, CRYPT_TCRYPT, ¶ms);
|
||||
check_signal(&r);
|
||||
r = tcrypt_load(cd, ¶ms);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
if (opt_readonly)
|
||||
flags |= CRYPT_ACTIVATE_READONLY;
|
||||
|
||||
if (opt_allow_discards)
|
||||
flags |= CRYPT_ACTIVATE_ALLOW_DISCARDS;
|
||||
|
||||
if (activated_name)
|
||||
r = crypt_activate_by_volume_key(cd, activated_name, NULL, 0, flags);
|
||||
out:
|
||||
if (r == -EPERM)
|
||||
log_err(_("No device header detected with this passphrase.\n"));
|
||||
crypt_free(cd);
|
||||
crypt_safe_free(CONST_CAST(char*)params.passphrase);
|
||||
return r;
|
||||
@@ -312,22 +343,7 @@ static int action_tcryptDump(void)
|
||||
if ((r = crypt_init(&cd, action_argv[0])))
|
||||
goto out;
|
||||
|
||||
/* TCRYPT header is encrypted, get passphrase now */
|
||||
r = tools_get_key(_("Enter passphrase: "),
|
||||
CONST_CAST(char**)¶ms.passphrase,
|
||||
¶ms.passphrase_size, 0, 0, NULL, opt_timeout,
|
||||
_verify_passphrase(0), 0, cd);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
if (opt_tcrypt_hidden)
|
||||
params.flags |= CRYPT_TCRYPT_HIDDEN_HEADER;
|
||||
|
||||
if (opt_tcrypt_system)
|
||||
params.flags |= CRYPT_TCRYPT_SYSTEM_HEADER;
|
||||
|
||||
r = crypt_load(cd, CRYPT_TCRYPT, ¶ms);
|
||||
check_signal(&r);
|
||||
r = tcrypt_load(cd, ¶ms);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
@@ -336,8 +352,6 @@ static int action_tcryptDump(void)
|
||||
else
|
||||
r = crypt_dump(cd);
|
||||
out:
|
||||
if (r == -EPERM)
|
||||
log_err(_("No device header detected with this passphrase.\n"));
|
||||
crypt_free(cd);
|
||||
crypt_safe_free(CONST_CAST(char*)params.passphrase);
|
||||
return r;
|
||||
@@ -453,6 +467,29 @@ static int action_benchmark_kdf(const char *hash)
|
||||
return r;
|
||||
}
|
||||
|
||||
static int benchmark_cipher_loop(const char *cipher, const char *cipher_mode,
|
||||
size_t volume_key_size, size_t iv_size,
|
||||
double *encryption_mbs, double *decryption_mbs)
|
||||
{
|
||||
int r, buffer_size = 1024 * 1024;
|
||||
|
||||
do {
|
||||
r = crypt_benchmark(NULL, cipher, cipher_mode,
|
||||
volume_key_size, iv_size, buffer_size,
|
||||
encryption_mbs, decryption_mbs);
|
||||
if (r == -ERANGE) {
|
||||
if (buffer_size < 1024 * 1024 * 65)
|
||||
buffer_size *= 2;
|
||||
else {
|
||||
log_err(_("Result of benchmark is not reliable.\n"));
|
||||
r = -ENOENT;
|
||||
}
|
||||
}
|
||||
} while (r == -ERANGE);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int action_benchmark(void)
|
||||
{
|
||||
static struct {
|
||||
@@ -482,7 +519,6 @@ static int action_benchmark(void)
|
||||
double enc_mbr = 0, dec_mbr = 0;
|
||||
int key_size = (opt_key_size ?: DEFAULT_PLAIN_KEYBITS);
|
||||
int iv_size = 16, skipped = 0;
|
||||
int buffer_size = 1024 * 1024;
|
||||
char *c;
|
||||
int i, r;
|
||||
|
||||
@@ -504,9 +540,9 @@ static int action_benchmark(void)
|
||||
strstr(cipher, "cast5"))
|
||||
iv_size = 8;
|
||||
|
||||
r = crypt_benchmark(NULL, cipher, cipher_mode,
|
||||
key_size / 8, iv_size, buffer_size,
|
||||
&enc_mbr, &dec_mbr);
|
||||
r = benchmark_cipher_loop(cipher, cipher_mode,
|
||||
key_size / 8, iv_size,
|
||||
&enc_mbr, &dec_mbr);
|
||||
if (!r) {
|
||||
log_std(N_("# Algorithm | Key | Encryption | Decryption\n"));
|
||||
log_std("%8s-%s %4db %6.1f MiB/s %6.1f MiB/s\n",
|
||||
@@ -521,9 +557,9 @@ static int action_benchmark(void)
|
||||
break;
|
||||
}
|
||||
for (i = 0; bciphers[i].cipher; i++) {
|
||||
r = crypt_benchmark(NULL, bciphers[i].cipher, bciphers[i].mode,
|
||||
r = benchmark_cipher_loop(bciphers[i].cipher, bciphers[i].mode,
|
||||
bciphers[i].key_size, bciphers[i].iv_size,
|
||||
buffer_size, &enc_mbr, &dec_mbr);
|
||||
&enc_mbr, &dec_mbr);
|
||||
check_signal(&r);
|
||||
if (r == -ENOTSUP || r == -EINTR)
|
||||
break;
|
||||
@@ -657,7 +693,7 @@ static int action_luksFormat(void)
|
||||
else if (opt_urandom)
|
||||
crypt_set_rng_type(cd, CRYPT_RNG_URANDOM);
|
||||
|
||||
r = tools_get_key(_("Enter LUKS passphrase: "), &password, &passwordLen,
|
||||
r = tools_get_key(_("Enter passphrase: "), &password, &passwordLen,
|
||||
opt_keyfile_offset, opt_keyfile_size, opt_key_file,
|
||||
opt_timeout, _verify_passphrase(1), 1, cd);
|
||||
if (r < 0)
|
||||
@@ -828,7 +864,7 @@ static int action_luksKillSlot(void)
|
||||
if (!opt_batch_mode) {
|
||||
r = verify_keyslot(cd, opt_key_slot,
|
||||
_("This is the last keyslot. Device will become unusable after purging this key."),
|
||||
_("Enter any remaining LUKS passphrase: "),
|
||||
_("Enter any remaining passphrase: "),
|
||||
opt_key_file, opt_keyfile_offset, opt_keyfile_size);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
@@ -856,7 +892,7 @@ static int action_luksRemoveKey(void)
|
||||
if ((r = crypt_load(cd, CRYPT_LUKS1, NULL)))
|
||||
goto out;
|
||||
|
||||
r = tools_get_key(_("Enter LUKS passphrase to be deleted: "),
|
||||
r = tools_get_key(_("Enter passphrase to be deleted: "),
|
||||
&password, &passwordLen,
|
||||
opt_keyfile_offset, opt_keyfile_size, opt_key_file,
|
||||
opt_timeout,
|
||||
@@ -925,7 +961,7 @@ static int action_luksAddKey(void)
|
||||
opt_key_file, opt_keyfile_size, opt_keyfile_offset,
|
||||
opt_new_key_file, opt_new_keyfile_size, opt_new_keyfile_offset);
|
||||
} else {
|
||||
r = tools_get_key(_("Enter any passphrase: "),
|
||||
r = tools_get_key(_("Enter any existing passphrase: "),
|
||||
&password, &password_size, 0, 0, NULL,
|
||||
opt_timeout, _verify_passphrase(0), 0, cd);
|
||||
|
||||
@@ -941,7 +977,7 @@ static int action_luksAddKey(void)
|
||||
|
||||
r = tools_get_key(_("Enter new passphrase for key slot: "),
|
||||
&password_new, &password_new_size, 0, 0, NULL,
|
||||
opt_timeout, _verify_passphrase(0), 1, cd);
|
||||
opt_timeout, _verify_passphrase(1), 1, cd);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
@@ -974,7 +1010,7 @@ static int action_luksChangeKey(void)
|
||||
if (opt_iteration_time)
|
||||
crypt_set_iteration_time(cd, opt_iteration_time);
|
||||
|
||||
r = tools_get_key(_("Enter LUKS passphrase to be changed: "),
|
||||
r = tools_get_key(_("Enter passphrase to be changed: "),
|
||||
&password, &password_size,
|
||||
opt_keyfile_offset, opt_keyfile_size, opt_key_file,
|
||||
opt_timeout, _verify_passphrase(0), 0, cd);
|
||||
@@ -988,11 +1024,11 @@ static int action_luksChangeKey(void)
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
r = tools_get_key(_("Enter new LUKS passphrase: "),
|
||||
r = tools_get_key(_("Enter new passphrase: "),
|
||||
&password_new, &password_new_size,
|
||||
opt_new_keyfile_offset, opt_new_keyfile_size,
|
||||
opt_new_key_file,
|
||||
opt_timeout, _verify_passphrase(0), 1, cd);
|
||||
opt_timeout, _verify_passphrase(1), 1, cd);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
@@ -1010,6 +1046,12 @@ static int action_isLuks(void)
|
||||
struct crypt_device *cd = NULL;
|
||||
int r;
|
||||
|
||||
/* FIXME: argc > max should be checked for other operations as well */
|
||||
if (action_argc > 1) {
|
||||
log_err(_("Only one device argument for isLuks operation is supported.\n"));
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
if ((r = crypt_init(&cd, action_argv[0])))
|
||||
goto out;
|
||||
|
||||
@@ -1067,7 +1109,7 @@ static int luksDump_with_volume_key(struct crypt_device *cd)
|
||||
if (!vk)
|
||||
return -ENOMEM;
|
||||
|
||||
r = tools_get_key(_("Enter LUKS passphrase: "), &password, &passwordLen,
|
||||
r = tools_get_key(_("Enter passphrase: "), &password, &passwordLen,
|
||||
opt_keyfile_offset, opt_keyfile_size, opt_key_file,
|
||||
opt_timeout, 0, 0, cd);
|
||||
if (r < 0)
|
||||
@@ -1227,6 +1269,47 @@ args:
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
static int action_luksErase(void)
|
||||
{
|
||||
struct crypt_device *cd = NULL;
|
||||
crypt_keyslot_info ki;
|
||||
char *msg = NULL;
|
||||
int i, r;
|
||||
|
||||
if ((r = crypt_init(&cd, uuid_or_device(action_argv[0]))))
|
||||
goto out;
|
||||
|
||||
crypt_set_confirm_callback(cd, yesDialog, NULL);
|
||||
|
||||
if ((r = crypt_load(cd, CRYPT_LUKS1, NULL)))
|
||||
goto out;
|
||||
|
||||
if(asprintf(&msg, _("This operation will erase all keyslots on device %s.\n"
|
||||
"Device will become unusable after this operation."),
|
||||
uuid_or_device(action_argv[0])) == -1) {
|
||||
r = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (!yesDialog(msg, NULL)) {
|
||||
r = -EPERM;
|
||||
goto out;
|
||||
}
|
||||
|
||||
for (i = 0; i < crypt_keyslot_max(CRYPT_LUKS1); i++) {
|
||||
ki = crypt_keyslot_status(cd, i);
|
||||
if (ki == CRYPT_SLOT_ACTIVE || ki == CRYPT_SLOT_ACTIVE_LAST) {
|
||||
r = crypt_keyslot_destroy(cd, i);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
out:
|
||||
free(msg);
|
||||
crypt_free(cd);
|
||||
return r;
|
||||
}
|
||||
|
||||
static struct action_type {
|
||||
const char *type;
|
||||
int (*handler)(void);
|
||||
@@ -1241,6 +1324,7 @@ static struct action_type {
|
||||
{ "status", action_status, 1, 0, N_("<name>"), N_("show device status") },
|
||||
{ "benchmark", action_benchmark, 0, 0, N_("<name>"), N_("benchmark cipher") },
|
||||
{ "repair", action_luksRepair, 1, 1, N_("<device>"), N_("try to repair on-disk metadata") },
|
||||
{ "erase", action_luksErase , 1, 1, N_("<device>"), N_("erase all keyslots (remove encryption key)") },
|
||||
{ "luksFormat", action_luksFormat, 1, 1, N_("<device> [<new key file>]"), N_("formats a LUKS device") },
|
||||
{ "luksAddKey", action_luksAddKey, 1, 1, N_("<device> [<new key file>]"), N_("add key to LUKS device") },
|
||||
{ "luksRemoveKey",action_luksRemoveKey,1, 1, N_("<device> [<key file>]"), N_("removes supplied key or key file from LUKS device") },
|
||||
@@ -1384,6 +1468,7 @@ int main(int argc, const char **argv)
|
||||
{ "test-passphrase", '\0', POPT_ARG_NONE, &opt_test_passphrase, 0, N_("Do not activate device, just check passphrase."), NULL },
|
||||
{ "tcrypt-hidden", '\0', POPT_ARG_NONE, &opt_tcrypt_hidden, 0, N_("Use hidden header (hidden TCRYPT device)."), NULL },
|
||||
{ "tcrypt-system", '\0', POPT_ARG_NONE, &opt_tcrypt_system, 0, N_("Device is system TCRYPT drive (with bootloader)."), NULL },
|
||||
{ "tcrypt-backup", '\0', POPT_ARG_NONE, &opt_tcrypt_backup, 0, N_("Use backup (secondary) TCRYPT header."), NULL },
|
||||
{ "type", 'M', POPT_ARG_STRING, &opt_type, 0, N_("Type of device metadata: luks, plain, loopaes, tcrypt."), NULL },
|
||||
{ "force-password", '\0', POPT_ARG_NONE, &opt_force_password, 0, N_("Disable password quality check (if enabled)."), NULL },
|
||||
POPT_TABLEEND
|
||||
@@ -1399,7 +1484,8 @@ int main(int argc, const char **argv)
|
||||
bindtextdomain(PACKAGE, LOCALEDIR);
|
||||
textdomain(PACKAGE);
|
||||
|
||||
crypt_fips_self_check(NULL);
|
||||
if (crypt_fips_mode())
|
||||
crypt_log(NULL, CRYPT_LOG_VERBOSE, _("Running in FIPS mode.\n"));
|
||||
|
||||
popt_context = poptGetContext(PACKAGE, argc, argv, popt_options, 0);
|
||||
poptSetOtherOptionHelp(popt_context,
|
||||
@@ -1490,6 +1576,9 @@ int main(int argc, const char **argv)
|
||||
!strcmp(aname, "loopaesClose") ||
|
||||
!strcmp(aname, "tcryptClose")) {
|
||||
aname = "close";
|
||||
} else if (!strcmp(aname, "luksErase")) {
|
||||
aname = "erase";
|
||||
opt_type = "luks";
|
||||
}
|
||||
|
||||
for(action = action_types; action->type; action++)
|
||||
@@ -1500,7 +1589,7 @@ int main(int argc, const char **argv)
|
||||
usage(popt_context, EXIT_FAILURE, _("Unknown action."),
|
||||
poptGetInvocationName(popt_context));
|
||||
|
||||
if(action_argc < action->required_action_argc)
|
||||
if (action_argc < action->required_action_argc)
|
||||
help_args(action, popt_context);
|
||||
|
||||
/* FIXME: rewrite this from scratch */
|
||||
@@ -1585,10 +1674,15 @@ int main(int argc, const char **argv)
|
||||
_("Option --offset is supported only for open of plain and loopaes devices.\n"),
|
||||
poptGetInvocationName(popt_context));
|
||||
|
||||
if ((opt_tcrypt_hidden || opt_tcrypt_system) && strcmp(aname, "tcryptDump") &&
|
||||
if ((opt_tcrypt_hidden || opt_tcrypt_system || opt_tcrypt_backup) && strcmp(aname, "tcryptDump") &&
|
||||
(strcmp(aname, "open") || strcmp(opt_type, "tcrypt")))
|
||||
usage(popt_context, EXIT_FAILURE,
|
||||
_("Option --tcrypt-hidden or --tcrypt-system is supported only for TCRYPT device.\n"),
|
||||
_("Option --tcrypt-hidden, --tcrypt-system or --tcrypt-backup is supported only for TCRYPT device.\n"),
|
||||
poptGetInvocationName(popt_context));
|
||||
|
||||
if (opt_tcrypt_hidden && opt_allow_discards)
|
||||
usage(popt_context, EXIT_FAILURE,
|
||||
_("Option --tcrypt-hidden cannot be combined with --allow-discards.\n"),
|
||||
poptGetInvocationName(popt_context));
|
||||
|
||||
if (opt_debug) {
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
* Copyright (C) 2004, Christophe Saout <christophe@saout.de>
|
||||
* Copyright (C) 2004-2007, Clemens Fruhwirth <clemens@endorphin.org>
|
||||
* Copyright (C) 2009-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2012, Milan Broz
|
||||
* Copyright (C) 2009-2014, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -24,11 +24,6 @@
|
||||
#ifndef CRYPTSETUP_H
|
||||
#define CRYPTSETUP_H
|
||||
|
||||
#define _LARGEFILE64_SOURCE
|
||||
#define _FILE_OFFSET_BITS 64
|
||||
|
||||
#include <config.h>
|
||||
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
/*
|
||||
* cryptsetup-reencrypt - crypt utility for offline re-encryption
|
||||
*
|
||||
* Copyright (C) 2012, Milan Broz All rights reserved.
|
||||
* Copyright (C) 2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2012-2014, Milan Broz 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
|
||||
@@ -47,6 +47,7 @@ static int opt_tries = 3;
|
||||
static int opt_key_slot = CRYPT_ANY_SLOT;
|
||||
static int opt_key_size = 0;
|
||||
static int opt_new = 0;
|
||||
static int opt_keep_key = 0;
|
||||
|
||||
static const char *opt_reduce_size_str = NULL;
|
||||
static uint64_t opt_reduce_size = 0;
|
||||
@@ -122,6 +123,12 @@ static int alignment(int fd)
|
||||
return alignment;
|
||||
}
|
||||
|
||||
static size_t pagesize(void)
|
||||
{
|
||||
long r = sysconf(_SC_PAGESIZE);
|
||||
return r < 0 ? 4096 : (size_t)r;
|
||||
}
|
||||
|
||||
/* Depends on the first two fields of LUKS1 header format, magic and version */
|
||||
static int device_check(struct reenc_ctx *rc, header_magic set_magic)
|
||||
{
|
||||
@@ -129,6 +136,7 @@ static int device_check(struct reenc_ctx *rc, header_magic set_magic)
|
||||
int r, devfd;
|
||||
ssize_t s;
|
||||
uint16_t version;
|
||||
size_t buf_size = pagesize();
|
||||
|
||||
devfd = open(rc->device, O_RDWR | O_EXCL | O_DIRECT);
|
||||
if (devfd == -1) {
|
||||
@@ -146,14 +154,14 @@ static int device_check(struct reenc_ctx *rc, header_magic set_magic)
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (posix_memalign((void *)&buf, alignment(devfd), SECTOR_SIZE)) {
|
||||
if (posix_memalign((void *)&buf, alignment(devfd), buf_size)) {
|
||||
log_err(_("Allocation of aligned memory failed.\n"));
|
||||
r = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
|
||||
s = read(devfd, buf, SECTOR_SIZE);
|
||||
if (s < 0 || s != SECTOR_SIZE) {
|
||||
s = read(devfd, buf, buf_size);
|
||||
if (s < 0 || s != buf_size) {
|
||||
log_err(_("Cannot read device %s.\n"), rc->device);
|
||||
r = -EIO;
|
||||
goto out;
|
||||
@@ -184,8 +192,8 @@ static int device_check(struct reenc_ctx *rc, header_magic set_magic)
|
||||
if (!r) {
|
||||
if (lseek(devfd, 0, SEEK_SET) == -1)
|
||||
goto out;
|
||||
s = write(devfd, buf, SECTOR_SIZE);
|
||||
if (s < 0 || s != SECTOR_SIZE) {
|
||||
s = write(devfd, buf, buf_size);
|
||||
if (s < 0 || s != buf_size) {
|
||||
log_err(_("Cannot write device %s.\n"), rc->device);
|
||||
r = -EIO;
|
||||
}
|
||||
@@ -193,7 +201,7 @@ static int device_check(struct reenc_ctx *rc, header_magic set_magic)
|
||||
log_dbg("LUKS signature check failed for %s.", rc->device);
|
||||
out:
|
||||
if (buf)
|
||||
memset(buf, 0, SECTOR_SIZE);
|
||||
memset(buf, 0, buf_size);
|
||||
free(buf);
|
||||
close(devfd);
|
||||
return r;
|
||||
@@ -417,7 +425,8 @@ out:
|
||||
|
||||
static int create_new_header(struct reenc_ctx *rc, const char *cipher,
|
||||
const char *cipher_mode, const char *uuid,
|
||||
int key_size, struct crypt_params_luks1 *params)
|
||||
const char *key, int key_size,
|
||||
struct crypt_params_luks1 *params)
|
||||
{
|
||||
struct crypt_device *cd_new = NULL;
|
||||
int i, r;
|
||||
@@ -434,7 +443,7 @@ static int create_new_header(struct reenc_ctx *rc, const char *cipher,
|
||||
crypt_set_iteration_time(cd_new, opt_iteration_time);
|
||||
|
||||
if ((r = crypt_format(cd_new, CRYPT_LUKS1, cipher, cipher_mode,
|
||||
uuid, NULL, key_size, params)))
|
||||
uuid, key, key_size, params)))
|
||||
goto out;
|
||||
log_verbose(_("New LUKS header for device %s created.\n"), rc->device);
|
||||
|
||||
@@ -457,6 +466,8 @@ static int backup_luks_headers(struct reenc_ctx *rc)
|
||||
struct crypt_device *cd = NULL;
|
||||
struct crypt_params_luks1 params = {0};
|
||||
char cipher [MAX_CIPHER_LEN], cipher_mode[MAX_CIPHER_LEN];
|
||||
char *old_key = NULL;
|
||||
size_t old_key_size;
|
||||
int r;
|
||||
|
||||
log_dbg("Creating LUKS header backup for device %s.", rc->device);
|
||||
@@ -487,14 +498,30 @@ static int backup_luks_headers(struct reenc_ctx *rc)
|
||||
}
|
||||
}
|
||||
|
||||
if (opt_keep_key) {
|
||||
log_dbg("Keeping key from old header.");
|
||||
old_key_size = crypt_get_volume_key_size(cd);
|
||||
old_key = crypt_safe_alloc(old_key_size);
|
||||
if (!old_key) {
|
||||
r = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
r = crypt_volume_key_get(cd, CRYPT_ANY_SLOT, old_key, &old_key_size,
|
||||
rc->p[rc->keyslot].password, rc->p[rc->keyslot].passwordLen);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
}
|
||||
|
||||
r = create_new_header(rc,
|
||||
opt_cipher ? cipher : crypt_get_cipher(cd),
|
||||
opt_cipher ? cipher_mode : crypt_get_cipher_mode(cd),
|
||||
crypt_get_uuid(cd),
|
||||
old_key,
|
||||
opt_key_size ? opt_key_size / 8 : crypt_get_volume_key_size(cd),
|
||||
¶ms);
|
||||
out:
|
||||
crypt_free(cd);
|
||||
crypt_safe_free(old_key);
|
||||
if (r)
|
||||
log_err(_("Creation of LUKS backup headers failed.\n"));
|
||||
return r;
|
||||
@@ -539,8 +566,8 @@ static int backup_fake_header(struct reenc_ctx *rc)
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
r = crypt_keyslot_add_by_volume_key(cd_new, 0, NULL, 0,
|
||||
rc->p[0].password, rc->p[0].passwordLen);
|
||||
r = crypt_keyslot_add_by_volume_key(cd_new, rc->keyslot, NULL, 0,
|
||||
rc->p[rc->keyslot].password, rc->p[rc->keyslot].passwordLen);
|
||||
if (r < 0)
|
||||
goto out;
|
||||
|
||||
@@ -552,7 +579,7 @@ static int backup_fake_header(struct reenc_ctx *rc)
|
||||
r = create_new_header(rc,
|
||||
opt_cipher ? cipher : DEFAULT_LUKS1_CIPHER,
|
||||
opt_cipher ? cipher_mode : DEFAULT_LUKS1_MODE,
|
||||
NULL,
|
||||
NULL, NULL,
|
||||
(opt_key_size ? opt_key_size : DEFAULT_LUKS1_KEYBITS) / 8,
|
||||
¶ms);
|
||||
out:
|
||||
@@ -844,15 +871,14 @@ static int initialize_uuid(struct reenc_ctx *rc)
|
||||
static int init_passphrase1(struct reenc_ctx *rc, struct crypt_device *cd,
|
||||
const char *msg, int slot_to_check, int check)
|
||||
{
|
||||
int r = -EINVAL, slot, retry_count;
|
||||
|
||||
slot = (slot_to_check == CRYPT_ANY_SLOT) ? 0 : slot_to_check;
|
||||
char *password;
|
||||
int r = -EINVAL, retry_count;
|
||||
size_t passwordLen;
|
||||
|
||||
retry_count = opt_tries ?: 1;
|
||||
while (retry_count--) {
|
||||
set_int_handler(0);
|
||||
r = crypt_get_key(msg, &rc->p[slot].password,
|
||||
&rc->p[slot].passwordLen,
|
||||
r = crypt_get_key(msg, &password, &passwordLen,
|
||||
0, 0, NULL /*opt_key_file*/,
|
||||
0, 0, cd);
|
||||
if (r < 0)
|
||||
@@ -864,42 +890,49 @@ static int init_passphrase1(struct reenc_ctx *rc, struct crypt_device *cd,
|
||||
set_int_block(1);
|
||||
if (check)
|
||||
r = crypt_activate_by_passphrase(cd, NULL, slot_to_check,
|
||||
rc->p[slot].password, rc->p[slot].passwordLen, 0);
|
||||
password, passwordLen, 0);
|
||||
else
|
||||
r = slot;
|
||||
r = (slot_to_check == CRYPT_ANY_SLOT) ? 0 : slot_to_check;
|
||||
|
||||
if (r < 0) {
|
||||
crypt_safe_free(rc->p[slot].password);
|
||||
rc->p[slot].password = NULL;
|
||||
rc->p[slot].passwordLen = 0;
|
||||
crypt_safe_free(password);
|
||||
password = NULL;
|
||||
passwordLen = 0;
|
||||
}
|
||||
if (r < 0 && r != -EPERM)
|
||||
return r;
|
||||
if (r >= 0) {
|
||||
rc->keyslot = slot;
|
||||
rc->keyslot = r;
|
||||
rc->p[r].password = password;
|
||||
rc->p[r].passwordLen = passwordLen;
|
||||
break;
|
||||
}
|
||||
log_err(_("No key available with this passphrase.\n"));
|
||||
}
|
||||
|
||||
password = NULL;
|
||||
passwordLen = 0;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int init_keyfile(struct reenc_ctx *rc, struct crypt_device *cd, int slot_check)
|
||||
{
|
||||
int r, slot;
|
||||
char *password;
|
||||
int r;
|
||||
size_t passwordLen;
|
||||
|
||||
slot = (slot_check == CRYPT_ANY_SLOT) ? 0 : slot_check;
|
||||
r = crypt_get_key(NULL, &rc->p[slot].password, &rc->p[slot].passwordLen,
|
||||
opt_keyfile_offset, opt_keyfile_size, opt_key_file, 0, 0, cd);
|
||||
r = crypt_get_key(NULL, &password, &passwordLen, opt_keyfile_offset,
|
||||
opt_keyfile_size, opt_key_file, 0, 0, cd);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = crypt_activate_by_passphrase(cd, NULL, slot_check,
|
||||
rc->p[slot].password, rc->p[slot].passwordLen, 0);
|
||||
r = crypt_activate_by_passphrase(cd, NULL, slot_check, password,
|
||||
passwordLen, 0);
|
||||
|
||||
/*
|
||||
* Allow keyslot only if it is last slot or if user explicitly
|
||||
* specify whch slot to use (IOW others will be disabled).
|
||||
* specify which slot to use (IOW others will be disabled).
|
||||
*/
|
||||
if (r >= 0 && opt_key_slot == CRYPT_ANY_SLOT &&
|
||||
crypt_keyslot_status(cd, r) != CRYPT_SLOT_ACTIVE_LAST) {
|
||||
@@ -909,14 +942,17 @@ static int init_keyfile(struct reenc_ctx *rc, struct crypt_device *cd, int slot_
|
||||
}
|
||||
|
||||
if (r < 0) {
|
||||
crypt_safe_free(rc->p[slot].password);
|
||||
rc->p[slot].password = NULL;
|
||||
rc->p[slot].passwordLen = 0;
|
||||
crypt_safe_free(password);
|
||||
if (r == -EPERM)
|
||||
log_err(_("No key available with this passphrase.\n"));
|
||||
return r;
|
||||
} else
|
||||
rc->keyslot = slot;
|
||||
} else {
|
||||
rc->keyslot = r;
|
||||
rc->p[r].password = password;
|
||||
rc->p[r].passwordLen = passwordLen;
|
||||
}
|
||||
|
||||
password = NULL;
|
||||
passwordLen = 0;
|
||||
|
||||
return r;
|
||||
}
|
||||
@@ -931,7 +967,7 @@ static int initialize_passphrase(struct reenc_ctx *rc, const char *device)
|
||||
log_dbg("Passhrases initialization.");
|
||||
|
||||
if (opt_new && !rc->in_progress) {
|
||||
r = init_passphrase1(rc, cd, _("Enter new LUKS passphrase: "), 0, 0);
|
||||
r = init_passphrase1(rc, cd, _("Enter new passphrase: "), opt_key_slot, 0);
|
||||
return r > 0 ? 0 : r;
|
||||
}
|
||||
|
||||
@@ -942,17 +978,22 @@ static int initialize_passphrase(struct reenc_ctx *rc, const char *device)
|
||||
return r;
|
||||
}
|
||||
|
||||
if (opt_key_slot != CRYPT_ANY_SLOT)
|
||||
snprintf(msg, sizeof(msg),
|
||||
_("Enter passphrase for key slot %u: "), opt_key_slot);
|
||||
else
|
||||
snprintf(msg, sizeof(msg), _("Enter any existing passphrase: "));
|
||||
|
||||
if (opt_key_file) {
|
||||
r = init_keyfile(rc, cd, opt_key_slot);
|
||||
} else if (rc->in_progress) {
|
||||
r = init_passphrase1(rc, cd, _("Enter any LUKS passphrase: "),
|
||||
CRYPT_ANY_SLOT, 1);
|
||||
} else if (rc->in_progress || opt_key_slot != CRYPT_ANY_SLOT) {
|
||||
r = init_passphrase1(rc, cd, msg, opt_key_slot, 1);
|
||||
} else for (i = 0; i < MAX_SLOT; i++) {
|
||||
ki = crypt_keyslot_status(cd, i);
|
||||
if (ki != CRYPT_SLOT_ACTIVE && ki != CRYPT_SLOT_ACTIVE_LAST)
|
||||
continue;
|
||||
|
||||
snprintf(msg, sizeof(msg), _("Enter LUKS passphrase for key slot %u: "), i);
|
||||
snprintf(msg, sizeof(msg), _("Enter passphrase for key slot %u: "), i);
|
||||
r = init_passphrase1(rc, cd, msg, i, 1);
|
||||
if (r < 0)
|
||||
break;
|
||||
@@ -1066,11 +1107,15 @@ static int run_reencrypt(const char *device)
|
||||
goto out;
|
||||
}
|
||||
|
||||
if ((r = activate_luks_headers(&rc)))
|
||||
goto out;
|
||||
if (!opt_keep_key) {
|
||||
log_dbg("Running data area reencryption.");
|
||||
if ((r = activate_luks_headers(&rc)))
|
||||
goto out;
|
||||
|
||||
if ((r = copy_data(&rc)))
|
||||
goto out;
|
||||
if ((r = copy_data(&rc)))
|
||||
goto out;
|
||||
} else
|
||||
log_dbg("Keeping existing key, skipping data area reencryption.");
|
||||
|
||||
r = restore_luks_header(&rc);
|
||||
out:
|
||||
@@ -1109,6 +1154,7 @@ int main(int argc, const char **argv)
|
||||
{ "cipher", 'c', POPT_ARG_STRING, &opt_cipher, 0, N_("The cipher used to encrypt the disk (see /proc/crypto)"), NULL },
|
||||
{ "key-size", 's', POPT_ARG_INT, &opt_key_size, 0, N_("The size of the encryption key"), N_("BITS") },
|
||||
{ "hash", 'h', POPT_ARG_STRING, &opt_hash, 0, N_("The hash used to create the encryption key from the passphrase"), NULL },
|
||||
{ "keep-key", '\0', POPT_ARG_NONE, &opt_keep_key, 0, N_("Do not change key, no data area reencryption."), NULL },
|
||||
{ "key-file", 'd', POPT_ARG_STRING, &opt_key_file, 0, N_("Read the key from a file."), NULL },
|
||||
{ "iter-time", 'i', POPT_ARG_INT, &opt_iteration_time, 0, N_("PBKDF2 iteration time for LUKS (in ms)"), N_("msecs") },
|
||||
{ "batch-mode", 'q', POPT_ARG_NONE, &opt_batch_mode, 0, N_("Do not ask for confirmation"), NULL },
|
||||
@@ -1214,6 +1260,10 @@ int main(int argc, const char **argv)
|
||||
usage(popt_context, EXIT_FAILURE, _("Option --new must be used together with --reduce-device-size."),
|
||||
poptGetInvocationName(popt_context));
|
||||
|
||||
if (opt_keep_key && ((!opt_hash && !opt_iteration_time) || opt_cipher || opt_new))
|
||||
usage(popt_context, EXIT_FAILURE, _("Option --keep-key can be used only with --hash or --iter-time."),
|
||||
poptGetInvocationName(popt_context));
|
||||
|
||||
if (opt_debug) {
|
||||
opt_verbose = 1;
|
||||
crypt_set_debug_level(-1);
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* Password quality check wrapper
|
||||
*
|
||||
* Copyright (C) 2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2012, Milan Broz
|
||||
* Copyright (C) 2012-2014, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
* Copyright (C) 2004, Christophe Saout <christophe@saout.de>
|
||||
* Copyright (C) 2004-2007, Clemens Fruhwirth <clemens@endorphin.org>
|
||||
* Copyright (C) 2009-2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2012, Milan Broz
|
||||
* Copyright (C) 2009-2014, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
/*
|
||||
* veritysetup - setup cryptographic volumes for dm-verity
|
||||
*
|
||||
* Copyright (C) 2012, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2012-2013, Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2012-2013, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
||||
@@ -16,6 +16,7 @@ TESTS += reencryption-compat-test
|
||||
endif
|
||||
|
||||
EXTRA_DIST = compatimage.img.bz2 compatv10image.img.bz2 \
|
||||
img_fs_ext4.img.bz2 img_fs_xfs.img.bz2 \
|
||||
valid_header_file.bz2 \
|
||||
evil_hdr-payload_overwrite.bz2 \
|
||||
evil_hdr-stripes_payload_dmg.bz2 \
|
||||
@@ -33,12 +34,13 @@ clean-local:
|
||||
-rm -rf tcrypt-images
|
||||
|
||||
differ_SOURCES = differ.c
|
||||
differ_CFLAGS = -Wall -O2
|
||||
differ_CFLAGS = $(AM_CFLAGS) -Wall -O2
|
||||
|
||||
api_test_SOURCES = api-test.c $(top_srcdir)/lib/utils_loop.c
|
||||
api_test_LDADD = ../lib/libcryptsetup.la
|
||||
api_test_LDFLAGS = -static
|
||||
api_test_CFLAGS = -g -Wall -O0 -I$(top_srcdir)/lib/ -I$(top_srcdir)/lib/luks1
|
||||
api_test_LDFLAGS = $(AM_LDFLAGS) -static
|
||||
api_test_CFLAGS = -g -Wall -O0 $(AM_CFLAGS) -I$(top_srcdir)/lib/ -I$(top_srcdir)/lib/luks1
|
||||
api_test_CPPFLAGS = $(AM_CPPFLAGS) -include config.h
|
||||
|
||||
check_PROGRAMS = api-test differ
|
||||
|
||||
|
||||
@@ -3,11 +3,16 @@
|
||||
CRYPTSETUP="../src/cryptsetup"
|
||||
DEV=""
|
||||
DEV_STACKED="luks0xbabe"
|
||||
MNT_DIR="./mnt_luks"
|
||||
PWD1="93R4P4pIqAH8"
|
||||
PWD2="mymJeD8ivEhE"
|
||||
|
||||
cleanup() {
|
||||
udevadm settle >/dev/null 2>&1
|
||||
if [ -d "$MNT_DIR" ] ; then
|
||||
umount -f $MNT_DIR 2>/dev/null
|
||||
rmdir $MNT_DIR 2>/dev/null
|
||||
fi
|
||||
[ -b /dev/mapper/$DEV_STACKED ] && dmsetup remove $DEV_STACKED >/dev/null 2>&1
|
||||
rmmod scsi_debug 2>/dev/null
|
||||
sleep 2
|
||||
@@ -15,12 +20,18 @@ cleanup() {
|
||||
|
||||
fail()
|
||||
{
|
||||
echo "FAIL"
|
||||
[ -n "$1" ] && echo "$1"
|
||||
if [ -n "$1" ] ; then echo "FAIL $1" ; else echo "FAIL" ; fi
|
||||
cleanup
|
||||
exit 100
|
||||
}
|
||||
|
||||
skip()
|
||||
{
|
||||
echo "TEST SKIPPED: $1"
|
||||
cleanup
|
||||
exit 0
|
||||
}
|
||||
|
||||
add_device() {
|
||||
modprobe scsi_debug $@
|
||||
if [ $? -ne 0 ] ; then
|
||||
@@ -198,3 +209,18 @@ format_null 512 4040 8
|
||||
format_null 512 4096 128
|
||||
format_null 512 4096 2048
|
||||
cleanup
|
||||
|
||||
echo "# Create enterprise-class 4K drive with fs and LUKS images."
|
||||
# loop device here presents 512 block but images have 4k block
|
||||
# cryptsetup should properly use 4k block on direct-io
|
||||
add_device dev_size_mb=16 sector_size=4096 physblk_exp=0 num_tgts=1
|
||||
for file in $(ls img_fs_*.img.bz2) ; do
|
||||
echo "Format using fs image $file."
|
||||
bzip2 -d -c $file | dd of=$DEV bs=1M 2>/dev/null || fail "bad image"
|
||||
[ ! -d $MNT_DIR ] && mkdir $MNT_DIR
|
||||
mount $DEV $MNT_DIR || skip "Mounting image is not available."
|
||||
echo $PWD1 | $CRYPTSETUP luksFormat -i 1 $MNT_DIR/luks.img || fail
|
||||
echo $PWD2 | $CRYPTSETUP luksFormat -i 1 $MNT_DIR/luks.img --header $MNT_DIR/luks_header.img || fail
|
||||
umount $MNT_DIR
|
||||
done
|
||||
cleanup
|
||||
|
||||
186
tests/api-test.c
186
tests/api-test.c
@@ -1,8 +1,8 @@
|
||||
/*
|
||||
* cryptsetup library API check functions
|
||||
*
|
||||
* Copyright (C) 2009-2012 Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2012, Milan Broz
|
||||
* Copyright (C) 2009-2013 Red Hat, Inc. All rights reserved.
|
||||
* Copyright (C) 2009-2013, Milan Broz
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
@@ -27,6 +27,7 @@
|
||||
#include <linux/fs.h>
|
||||
#include <errno.h>
|
||||
#include <assert.h>
|
||||
#include <signal.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <libdevmapper.h>
|
||||
@@ -84,12 +85,16 @@
|
||||
|
||||
static int _debug = 0;
|
||||
static int _verbose = 1;
|
||||
static int _fips_mode = 0;
|
||||
|
||||
static int _quit = 0;
|
||||
|
||||
static char global_log[4096];
|
||||
static int global_lines = 0;
|
||||
|
||||
static char *DEVICE_1 = NULL;
|
||||
static char *DEVICE_2 = NULL;
|
||||
static char *DEVICE_3 = NULL;
|
||||
static char *THE_LOOP_DEV = NULL;
|
||||
|
||||
static char *tmp_file_1 = NULL;
|
||||
@@ -114,6 +119,27 @@ static int device_size(const char *device, uint64_t *size)
|
||||
return r;
|
||||
}
|
||||
|
||||
static int fips_mode(void)
|
||||
{
|
||||
int fd;
|
||||
char buf = 0;
|
||||
|
||||
if (access("/etc/system-fips", F_OK))
|
||||
return 0;
|
||||
|
||||
fd = open("/proc/sys/crypto/fips_enabled", O_RDONLY);
|
||||
|
||||
if (fd < 0)
|
||||
return 0;
|
||||
|
||||
if (read(fd, &buf, 1) != 1)
|
||||
buf = '0';
|
||||
|
||||
close(fd);
|
||||
|
||||
return (buf == '1');
|
||||
}
|
||||
|
||||
static int get_luks_offsets(int metadata_device,
|
||||
size_t keylength,
|
||||
unsigned int alignpayload_sec,
|
||||
@@ -224,7 +250,7 @@ static int _prepare_keyfile(const char *name, const char *passphrase, int size)
|
||||
{
|
||||
int fd, r;
|
||||
|
||||
fd = open(name, O_RDWR | O_CREAT | O_TRUNC, S_IRUSR);
|
||||
fd = open(name, O_RDWR | O_CREAT | O_TRUNC, S_IRUSR|S_IWUSR);
|
||||
if (fd != -1) {
|
||||
r = write(fd, passphrase, size);
|
||||
close(fd);
|
||||
@@ -349,6 +375,9 @@ static void _cleanup(void)
|
||||
if (crypt_loop_device(DEVICE_2))
|
||||
crypt_loop_detach(DEVICE_2);
|
||||
|
||||
if (crypt_loop_device(DEVICE_3))
|
||||
crypt_loop_detach(DEVICE_3);
|
||||
|
||||
_system("rm -f " IMAGE_EMPTY, 0);
|
||||
_system("rm -f " IMAGE1, 0);
|
||||
|
||||
@@ -369,6 +398,7 @@ static void _cleanup(void)
|
||||
free(THE_LOOP_DEV);
|
||||
free(DEVICE_1);
|
||||
free(DEVICE_2);
|
||||
free(DEVICE_3);
|
||||
}
|
||||
|
||||
static int _setup(void)
|
||||
@@ -433,6 +463,12 @@ static int _setup(void)
|
||||
fd = crypt_loop_attach(DEVICE_2, IMAGE_EMPTY, 0, 0, &ro);
|
||||
close(fd);
|
||||
}
|
||||
if (!DEVICE_3)
|
||||
DEVICE_3 = crypt_loop_get_device();
|
||||
if (!DEVICE_3) {
|
||||
printf("Cannot find free loop device.\n");
|
||||
return 1;
|
||||
}
|
||||
/* Keymaterial offset is less than 8 sectors */
|
||||
_system(" [ ! -e " EVL_HEADER_1 " ] && bzip2 -dk " EVL_HEADER_1 ".bz2", 1);
|
||||
/* keymaterial offset aims into payload area */
|
||||
@@ -451,6 +487,11 @@ static int _setup(void)
|
||||
|
||||
_system("modprobe dm-crypt", 0);
|
||||
_system("modprobe dm-verity", 0);
|
||||
|
||||
_fips_mode = fips_mode();
|
||||
if (_debug)
|
||||
printf("FIPS MODE: %d\n", _fips_mode);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -496,6 +537,12 @@ static void xlog(const char *msg, const char *tst, const char *func, int line, c
|
||||
else
|
||||
printf(" [%s,%s:%d] %s\n", msg, func, line, tst);
|
||||
}
|
||||
if (_quit) {
|
||||
if (_verbose)
|
||||
printf("Interrupted by a signal.\n");
|
||||
_cleanup();
|
||||
exit(-1);
|
||||
}
|
||||
}
|
||||
|
||||
/* crypt_device context must be "cd" to parse error properly here */
|
||||
@@ -505,8 +552,8 @@ static void xlog(const char *msg, const char *tst, const char *func, int line, c
|
||||
#define FAIL_(x, y) do { xlog("(fail) ", #x, __FUNCTION__, __LINE__, y); \
|
||||
check_ko((x), __LINE__, __FUNCTION__); \
|
||||
} while(0)
|
||||
#define EQ_(x, y) do { xlog("(equal) ", #x " == " #y, __FUNCTION__, __LINE__, NULL); \
|
||||
int64_t _x = (x), _y = (y); \
|
||||
#define EQ_(x, y) do { int64_t _x = (x), _y = (y); \
|
||||
xlog("(equal) ", #x " == " #y, __FUNCTION__, __LINE__, NULL); \
|
||||
if (_x != _y) check_equal(__LINE__, __FUNCTION__, _x, _y); \
|
||||
} while(0)
|
||||
#define RUN_(x, y) do { printf("%s: %s\n", #x, (y)); x(); } while (0)
|
||||
@@ -760,14 +807,16 @@ static void AddDevicePlain(void)
|
||||
EQ_(crypt_status(cd, CDEVICE_1), CRYPT_ACTIVE);
|
||||
|
||||
// retrieve volume key check
|
||||
memset(key2, 0, key_size);
|
||||
key_size--;
|
||||
// small buffer
|
||||
FAIL_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key2, &key_size, passphrase, strlen(passphrase)), "small buffer");
|
||||
key_size++;
|
||||
OK_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key2, &key_size, passphrase, strlen(passphrase)));
|
||||
if (!_fips_mode) {
|
||||
memset(key2, 0, key_size);
|
||||
key_size--;
|
||||
// small buffer
|
||||
FAIL_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key2, &key_size, passphrase, strlen(passphrase)), "small buffer");
|
||||
key_size++;
|
||||
OK_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key2, &key_size, passphrase, strlen(passphrase)));
|
||||
|
||||
OK_(memcmp(key, key2, key_size));
|
||||
OK_(memcmp(key, key2, key_size));
|
||||
}
|
||||
OK_(strcmp(cipher, crypt_get_cipher(cd)));
|
||||
OK_(strcmp(cipher_mode, crypt_get_cipher_mode(cd)));
|
||||
EQ_((int)key_size, crypt_get_volume_key_size(cd));
|
||||
@@ -899,16 +948,18 @@ static void UseLuksDevice(void)
|
||||
EQ_((int)key_size, crypt_get_volume_key_size(cd));
|
||||
EQ_(1032, crypt_get_data_offset(cd));
|
||||
|
||||
EQ_(0, crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key, &key_size, KEY1, strlen(KEY1)));
|
||||
OK_(crypt_volume_key_verify(cd, key, key_size));
|
||||
OK_(crypt_activate_by_volume_key(cd, NULL, key, key_size, 0));
|
||||
OK_(crypt_activate_by_volume_key(cd, CDEVICE_1, key, key_size, 0));
|
||||
EQ_(crypt_status(cd, CDEVICE_1), CRYPT_ACTIVE);
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
if (!_fips_mode) {
|
||||
EQ_(0, crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key, &key_size, KEY1, strlen(KEY1)));
|
||||
OK_(crypt_volume_key_verify(cd, key, key_size));
|
||||
OK_(crypt_activate_by_volume_key(cd, NULL, key, key_size, 0));
|
||||
OK_(crypt_activate_by_volume_key(cd, CDEVICE_1, key, key_size, 0));
|
||||
EQ_(crypt_status(cd, CDEVICE_1), CRYPT_ACTIVE);
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
|
||||
key[1] = ~key[1];
|
||||
FAIL_(crypt_volume_key_verify(cd, key, key_size), "key mismatch");
|
||||
FAIL_(crypt_activate_by_volume_key(cd, CDEVICE_1, key, key_size, 0), "key mismatch");
|
||||
key[1] = ~key[1];
|
||||
FAIL_(crypt_volume_key_verify(cd, key, key_size), "key mismatch");
|
||||
FAIL_(crypt_activate_by_volume_key(cd, CDEVICE_1, key, key_size, 0), "key mismatch");
|
||||
}
|
||||
crypt_free(cd);
|
||||
}
|
||||
|
||||
@@ -1130,10 +1181,12 @@ static void AddDeviceLuks(void)
|
||||
EQ_(7, crypt_activate_by_passphrase(cd, NULL, 7, passphrase2, strlen(passphrase2), 0));
|
||||
EQ_(6, crypt_keyslot_change_by_passphrase(cd, CRYPT_ANY_SLOT, 6, passphrase2, strlen(passphrase2), passphrase, strlen(passphrase)));
|
||||
|
||||
EQ_(6, crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key2, &key_size, passphrase, strlen(passphrase)));
|
||||
OK_(crypt_volume_key_verify(cd, key2, key_size));
|
||||
if (!_fips_mode) {
|
||||
EQ_(6, crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key2, &key_size, passphrase, strlen(passphrase)));
|
||||
OK_(crypt_volume_key_verify(cd, key2, key_size));
|
||||
|
||||
OK_(memcmp(key, key2, key_size));
|
||||
OK_(memcmp(key, key2, key_size));
|
||||
}
|
||||
OK_(strcmp(cipher, crypt_get_cipher(cd)));
|
||||
OK_(strcmp(cipher_mode, crypt_get_cipher_mode(cd)));
|
||||
EQ_((int)key_size, crypt_get_volume_key_size(cd));
|
||||
@@ -1271,8 +1324,8 @@ static void LuksHeaderRestore(void)
|
||||
|
||||
// volume key_size mismatch
|
||||
OK_(crypt_init(&cd, DMDIR L_DEVICE_OK));
|
||||
memcpy(key2, key, key_size - 1);
|
||||
OK_(crypt_format(cd, CRYPT_LUKS1, cipher, cipher_mode, NULL, key2, key_size - 1, ¶ms));
|
||||
memcpy(key2, key, key_size / 2);
|
||||
OK_(crypt_format(cd, CRYPT_LUKS1, cipher, cipher_mode, NULL, key2, key_size / 2, ¶ms));
|
||||
FAIL_(crypt_header_restore(cd, CRYPT_LUKS1, VALID_HEADER), "Volume keysize mismatch");
|
||||
crypt_free(cd);
|
||||
|
||||
@@ -1386,6 +1439,7 @@ static void LuksHeaderBackup(void)
|
||||
.data_alignment = 2048,
|
||||
};
|
||||
char key[128];
|
||||
int fd, ro = O_RDONLY;
|
||||
|
||||
const char *mk_hex = "bb21158c733229347bd4e681891e213d94c685be6a5b84818afe7a78a6de7a1a";
|
||||
size_t key_size = strlen(mk_hex) / 2;
|
||||
@@ -1393,6 +1447,8 @@ static void LuksHeaderBackup(void)
|
||||
const char *cipher_mode = "cbc-essiv:sha256";
|
||||
uint64_t r_payload_offset;
|
||||
|
||||
const char *passphrase = PASSPHRASE;
|
||||
|
||||
crypt_decode_key(key, mk_hex, key_size);
|
||||
|
||||
OK_(get_luks_offsets(0, key_size, params.data_alignment, 0, NULL, &r_payload_offset));
|
||||
@@ -1402,6 +1458,8 @@ static void LuksHeaderBackup(void)
|
||||
OK_(crypt_init(&cd, DMDIR L_DEVICE_OK));
|
||||
OK_(crypt_format(cd, CRYPT_LUKS1, cipher, cipher_mode, NULL, key, key_size, ¶ms));
|
||||
OK_(crypt_activate_by_volume_key(cd, CDEVICE_1, key, key_size, 0));
|
||||
EQ_(crypt_keyslot_add_by_volume_key(cd, 7, key, key_size, passphrase, strlen(passphrase)), 7);
|
||||
EQ_(crypt_keyslot_add_by_volume_key(cd, 0, key, key_size, passphrase, strlen(passphrase)), 0);
|
||||
OK_(crypt_header_backup(cd, CRYPT_LUKS1, BACKUP_FILE));
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
crypt_free(cd);
|
||||
@@ -1415,6 +1473,43 @@ static void LuksHeaderBackup(void)
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
crypt_free(cd);
|
||||
|
||||
// exercise luksOpen using backup header in file
|
||||
OK_(crypt_init(&cd, BACKUP_FILE));
|
||||
OK_(crypt_load(cd, CRYPT_LUKS1, NULL));
|
||||
OK_(crypt_set_data_device(cd, DMDIR L_DEVICE_OK));
|
||||
EQ_(crypt_activate_by_passphrase(cd, CDEVICE_1, 0, passphrase, strlen(passphrase), 0), 0);
|
||||
EQ_(crypt_status(cd, CDEVICE_1), CRYPT_ACTIVE);
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
crypt_free(cd);
|
||||
|
||||
OK_(crypt_init(&cd, BACKUP_FILE));
|
||||
OK_(crypt_load(cd, CRYPT_LUKS1, NULL));
|
||||
OK_(crypt_set_data_device(cd, DMDIR L_DEVICE_OK));
|
||||
EQ_(crypt_activate_by_passphrase(cd, CDEVICE_1, 7, passphrase, strlen(passphrase), 0), 7);
|
||||
EQ_(crypt_status(cd, CDEVICE_1), CRYPT_ACTIVE);
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
crypt_free(cd);
|
||||
|
||||
// exercise luksOpen using backup header on block device
|
||||
fd = crypt_loop_attach(DEVICE_3, BACKUP_FILE, 0, 0, &ro);
|
||||
close(fd);
|
||||
OK_(fd < 0);
|
||||
OK_(crypt_init(&cd, DEVICE_3));
|
||||
OK_(crypt_load(cd, CRYPT_LUKS1, NULL));
|
||||
OK_(crypt_set_data_device(cd, DMDIR L_DEVICE_OK));
|
||||
EQ_(crypt_activate_by_passphrase(cd, CDEVICE_1, 0, passphrase, strlen(passphrase), 0), 0);
|
||||
EQ_(crypt_status(cd, CDEVICE_1), CRYPT_ACTIVE);
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
crypt_free(cd);
|
||||
|
||||
OK_(crypt_init(&cd, DEVICE_3));
|
||||
OK_(crypt_load(cd, CRYPT_LUKS1, NULL));
|
||||
OK_(crypt_set_data_device(cd, DMDIR L_DEVICE_OK));
|
||||
EQ_(crypt_activate_by_passphrase(cd, CDEVICE_1, 7, passphrase, strlen(passphrase), 0), 7);
|
||||
EQ_(crypt_status(cd, CDEVICE_1), CRYPT_ACTIVE);
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
crypt_free(cd);
|
||||
|
||||
_cleanup_dmdevices();
|
||||
}
|
||||
|
||||
@@ -1713,6 +1808,7 @@ static void TcryptTest(void)
|
||||
};
|
||||
double enc_mbr = 0, dec_mbr = 0;
|
||||
const char *tcrypt_dev = "tcrypt-images/tck_5-sha512-xts-aes";
|
||||
const char *tcrypt_dev2 = "tcrypt-images/tc_5-sha512-xts-serpent-twofish-aes";
|
||||
size_t key_size = 64;
|
||||
char key[key_size], key_def[key_size];
|
||||
const char *key_hex =
|
||||
@@ -1743,12 +1839,14 @@ static void TcryptTest(void)
|
||||
EQ_(256, crypt_get_data_offset(cd));
|
||||
|
||||
memset(key, 0, key_size);
|
||||
key_size--;
|
||||
// small buffer
|
||||
FAIL_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key, &key_size, NULL, 0), "small buffer");
|
||||
key_size++;
|
||||
OK_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key, &key_size, NULL, 0));
|
||||
OK_(memcmp(key, key_def, key_size));
|
||||
if (!_fips_mode) {
|
||||
key_size--;
|
||||
// small buffer
|
||||
FAIL_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key, &key_size, NULL, 0), "small buffer");
|
||||
key_size++;
|
||||
OK_(crypt_volume_key_get(cd, CRYPT_ANY_SLOT, key, &key_size, NULL, 0));
|
||||
OK_(memcmp(key, key_def, key_size));
|
||||
}
|
||||
|
||||
reset_log();
|
||||
crypt_set_log_callback(cd, &new_log, NULL);
|
||||
@@ -1780,6 +1878,18 @@ static void TcryptTest(void)
|
||||
|
||||
OK_(crypt_deactivate(cd, CDEVICE_1));
|
||||
crypt_free(cd);
|
||||
|
||||
OK_(crypt_init(&cd, tcrypt_dev2));
|
||||
params.keyfiles = NULL;
|
||||
params.keyfiles_count = 0;
|
||||
OK_(crypt_load(cd, CRYPT_TCRYPT, ¶ms));
|
||||
OK_(crypt_activate_by_volume_key(cd, CDEVICE_1, NULL, 0, CRYPT_ACTIVATE_READONLY));
|
||||
crypt_free(cd);
|
||||
|
||||
// Deactivate the whole chain
|
||||
EQ_(crypt_status(NULL, CDEVICE_1 "_1"), CRYPT_BUSY);
|
||||
OK_(crypt_deactivate(NULL, CDEVICE_1));
|
||||
EQ_(crypt_status(NULL, CDEVICE_1 "_1"), CRYPT_INACTIVE);
|
||||
}
|
||||
|
||||
// Check that gcrypt is properly initialised in format
|
||||
@@ -1788,7 +1898,7 @@ static void NonFIPSAlg(void)
|
||||
struct crypt_device *cd;
|
||||
struct crypt_params_luks1 params = {0};
|
||||
char key[128] = "";
|
||||
size_t key_size = 128;
|
||||
size_t key_size = 128 / 8;
|
||||
const char *cipher = "aes";
|
||||
const char *cipher_mode = "cbc-essiv:sha256";
|
||||
int ret;
|
||||
@@ -1817,8 +1927,14 @@ static void NonFIPSAlg(void)
|
||||
crypt_free(cd);
|
||||
}
|
||||
|
||||
static void int_handler(int sig __attribute__((__unused__)))
|
||||
{
|
||||
_quit++;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
struct sigaction sa = { .sa_handler = int_handler };
|
||||
int i;
|
||||
|
||||
if (getuid() != 0) {
|
||||
@@ -1833,6 +1949,10 @@ int main(int argc, char *argv[])
|
||||
_debug = _verbose = 1;
|
||||
}
|
||||
|
||||
/* Handle interrupt properly */
|
||||
sigaction(SIGINT, &sa, NULL);
|
||||
sigaction(SIGTERM, &sa, NULL);
|
||||
|
||||
_cleanup();
|
||||
if (_setup())
|
||||
goto out;
|
||||
|
||||
@@ -39,6 +39,7 @@ KEY_MATERIAL5_EXT="S331776-395264"
|
||||
TEST_UUID="12345678-1234-1234-1234-123456789abc"
|
||||
|
||||
LOOPDEV=$(losetup -f 2>/dev/null)
|
||||
[ -f /etc/system-fips ] && FIPS_MODE=$(cat /proc/sys/crypto/fips_enabled 2>/dev/null)
|
||||
|
||||
function remove_mapping()
|
||||
{
|
||||
@@ -63,6 +64,12 @@ function fail()
|
||||
exit 2
|
||||
}
|
||||
|
||||
function can_fail_fips()
|
||||
{
|
||||
# Ignore this fail if running in FIPS mode
|
||||
[ -z "$FIPS_MODE" -o "$FIPS_MODE" -eq 0 ] && fail $1
|
||||
}
|
||||
|
||||
function skip()
|
||||
{
|
||||
[ -n "$1" ] && echo "$1"
|
||||
@@ -390,8 +397,8 @@ echo $PWD1 | $CRYPTSETUP luksAddKey $LOOPDEV -d $KEY1 || fail
|
||||
$CRYPTSETUP luksDump $LOOPDEV | grep -q "Key Slot 0: ENABLED" || fail
|
||||
$CRYPTSETUP luksDump $LOOPDEV | grep -q $TEST_UUID || fail
|
||||
echo $PWDW | $CRYPTSETUP luksDump $LOOPDEV --dump-master-key 2>/dev/null && fail
|
||||
echo $PWD1 | $CRYPTSETUP luksDump $LOOPDEV --dump-master-key | grep -q "MK dump:" || fail
|
||||
$CRYPTSETUP luksDump -q $LOOPDEV --dump-master-key -d $KEY1 | grep -q "MK dump:" || fail
|
||||
echo $PWD1 | $CRYPTSETUP luksDump $LOOPDEV --dump-master-key | grep -q "MK dump:" || can_fail_fips
|
||||
$CRYPTSETUP luksDump -q $LOOPDEV --dump-master-key -d $KEY1 | grep -q "MK dump:" || can_fail_fips
|
||||
|
||||
prepare "[22] remove disappeared device" wipe
|
||||
dmsetup create $DEV_NAME --table "0 5000 linear $LOOPDEV 2" || fail
|
||||
@@ -520,6 +527,8 @@ $CRYPTSETUP luksOpen -S 5 -d $KEY1 $LOOPDEV $DEV_NAME && fail
|
||||
prepare "[28] Detached LUKS header" wipe
|
||||
dd if=/dev/zero of=$HEADER_IMG bs=1M count=4 >/dev/null 2>&1
|
||||
echo $PWD1 | $CRYPTSETUP luksFormat -i1 $LOOPDEV --header $HEADER_IMG || fail
|
||||
echo $PWD1 | $CRYPTSETUP luksFormat -i1 $LOOPDEV --header $HEADER_IMG --align-payload 1 >/dev/null 2>&1 && fail
|
||||
echo $PWD1 | $CRYPTSETUP luksFormat -i1 $LOOPDEV --header $HEADER_IMG --align-payload 8192 || fail
|
||||
echo $PWD1 | $CRYPTSETUP luksFormat -i1 $LOOPDEV --header $HEADER_IMG --align-payload 0 || fail
|
||||
echo $PWD1 | $CRYPTSETUP luksOpen $LOOPDEV --header $HEADER_IMG $DEV_NAME || fail
|
||||
$CRYPTSETUP -q resize $DEV_NAME --size 100 --header $HEADER_IMG || fail
|
||||
@@ -537,5 +546,14 @@ $CRYPTSETUP -q repair $LOOPDEV >/dev/null 2>&1 || fail
|
||||
$CRYPTSETUP luksOpen -d $KEY1 $LOOPDEV $DEV_NAME || fail
|
||||
$CRYPTSETUP luksClose $DEV_NAME || fail
|
||||
|
||||
prepare "[30] LUKS erase" wipe
|
||||
$CRYPTSETUP -q luksFormat -i1 $LOOPDEV $KEY5 --key-slot 5 || fail
|
||||
$CRYPTSETUP luksAddKey -S 1 -d $KEY5 $LOOPDEV $KEY1 || fail
|
||||
$CRYPTSETUP luksDump $LOOPDEV | grep -q "Key Slot 1: ENABLED" || fail
|
||||
$CRYPTSETUP luksDump $LOOPDEV | grep -q "Key Slot 5: ENABLED" || fail
|
||||
$CRYPTSETUP luksErase -q $LOOPDEV || fail
|
||||
$CRYPTSETUP luksDump $LOOPDEV | grep -q "Key Slot 1: DISABLED" || fail
|
||||
$CRYPTSETUP luksDump $LOOPDEV | grep -q "Key Slot 5: DISABLED" || fail
|
||||
|
||||
remove_mapping
|
||||
exit 0
|
||||
|
||||
BIN
tests/img_fs_ext4.img.bz2
Normal file
BIN
tests/img_fs_ext4.img.bz2
Normal file
Binary file not shown.
BIN
tests/img_fs_xfs.img.bz2
Normal file
BIN
tests/img_fs_xfs.img.bz2
Normal file
Binary file not shown.
@@ -20,6 +20,12 @@ cleanup() {
|
||||
exit $1
|
||||
}
|
||||
|
||||
function fail()
|
||||
{
|
||||
echo " $1 [FAILED]"
|
||||
cleanup 2
|
||||
}
|
||||
|
||||
crypt_key() # hash keysize pwd/file name outkey [limit]
|
||||
{
|
||||
DEV2=$DEV_NAME"_x"
|
||||
@@ -50,8 +56,13 @@ crypt_key() # hash keysize pwd/file name outkey [limit]
|
||||
$CRYPTSETUP create -c $MODE -d $4 -h $1 -s $2 $DEV2 /dev/mapper/$DEV_NAME 2>/dev/null
|
||||
ret=$?
|
||||
;;
|
||||
failpwd)
|
||||
echo -e -n "$4" | $CRYPTSETUP create -c $MODE -h $1 -s $2 $LIMIT $DEV2 /dev/mapper/$DEV_NAME 2>/dev/null && fail "Expecting failure"
|
||||
echo " [OK]"
|
||||
return
|
||||
;;
|
||||
*)
|
||||
fail
|
||||
fail ""
|
||||
;;
|
||||
esac
|
||||
|
||||
@@ -107,6 +118,9 @@ crypt_key unknown* 256 file /dev/zero 00000000000000000000000000000000000000000
|
||||
crypt_key sha256:20 256 pwd "xxx" cd2eb0837c9b4c962c22d2ff8b5441b7b4580588000000000000000000000000
|
||||
crypt_key sha256:32 256 pwd "xxx" cd2eb0837c9b4c962c22d2ff8b5441b7b45805887f051d39bf133b583baf6860
|
||||
|
||||
crypt_key sha256: 256 failpwd "xxx" x
|
||||
crypt_key sha256:xx 256 failpwd "xxx" x
|
||||
|
||||
# key file, 80 chars
|
||||
echo -n -e "0123456789abcdef\n\x01\x00\x03\xff\xff\r\xff\xff\n\r" \
|
||||
"2352j3rkjhadcfasc823rqaw7e1 3dq sdq3d 2dkjqw3h2=====" >$KEY_FILE
|
||||
@@ -121,6 +135,12 @@ crypt_key sha256 512 file $KEY_FILE $KEY_FILE_HEX
|
||||
crypt_key plain 128 cat /dev/zero 00000000000000000000000000000000 16
|
||||
crypt_key plain 128 cat /dev/zero 00000000000000000000000000000000 17
|
||||
crypt_key plain 128 cat $KEY_FILE ${KEY_FILE_HEX:0:28}0000 14
|
||||
|
||||
# limiting plain (no hash)
|
||||
crypt_key plain 256 pwd "xxxxxxxx" 7878787878787878000000000000000000000000000000000000000000000000
|
||||
crypt_key plain:2 256 pwd "xxxxxxxx" 7878000000000000000000000000000000000000000000000000000000000000
|
||||
crypt_key plain:9 256 failpwd "xxxxxxxx" x
|
||||
|
||||
crypt_key sha256 128 cat $KEY_FILE a82c9227cc54c7475620ce85ba1fca1e 14
|
||||
crypt_key sha256:14 128 cat $KEY_FILE a82c9227cc54c7475620ce85ba1f0000 14
|
||||
|
||||
|
||||
@@ -6,16 +6,27 @@ REENC=../src/cryptsetup-reencrypt
|
||||
DEV_NAME=reenc9768
|
||||
DEV_NAME2=reenc1273
|
||||
IMG=reenc-data
|
||||
ORIG_IMG=reenc-data-orig
|
||||
KEY1=key1
|
||||
PWD1="93R4P4pIqAH8"
|
||||
PWD2="1cND4319812f"
|
||||
PWD3="1-9Qu5Ejfnqv"
|
||||
|
||||
|
||||
function del_scsi_device()
|
||||
{
|
||||
rmmod scsi_debug 2>/dev/null
|
||||
sleep 2
|
||||
}
|
||||
|
||||
function remove_mapping()
|
||||
{
|
||||
[ -b /dev/mapper/$DEV_NAME2 ] && dmsetup remove $DEV_NAME2
|
||||
[ -b /dev/mapper/$DEV_NAME ] && dmsetup remove $DEV_NAME
|
||||
[ ! -z "$LOOPDEV1" ] && losetup -d $LOOPDEV1 >/dev/null 2>&1
|
||||
rm -f $IMG $KEY1 >/dev/null 2>&1
|
||||
rm -f $IMG $ORIG_IMG $KEY1 >/dev/null 2>&1
|
||||
LOOPDEV1=""
|
||||
del_scsi_device
|
||||
}
|
||||
|
||||
function fail()
|
||||
@@ -32,12 +43,25 @@ function skip()
|
||||
exit 0
|
||||
}
|
||||
|
||||
function add_scsi_device() {
|
||||
del_scsi_device
|
||||
modprobe scsi_debug $@
|
||||
if [ $? -ne 0 ] ; then
|
||||
echo "This kernel seems to not support proper scsi_debug module, test skipped."
|
||||
exit 0
|
||||
fi
|
||||
|
||||
sleep 2
|
||||
SCSI_DEV="/dev/"$(grep scsi_debug /sys/block/*/device/model | cut -f4 -d /)
|
||||
[ -b $SCSI_DEV ] || fail "Cannot find $SCSI_DEV."
|
||||
}
|
||||
|
||||
function open_crypt()
|
||||
{
|
||||
if [ -n "$1" ] ; then
|
||||
echo "$1" | $CRYPTSETUP luksOpen $LOOPDEV1 $DEV_NAME || fail
|
||||
else
|
||||
$CRYPTSETUP luksOpen -d key1 $LOOPDEV1 $DEV_NAME || fail
|
||||
$CRYPTSETUP luksOpen -d $KEY1 $LOOPDEV1 $DEV_NAME || fail
|
||||
fi
|
||||
}
|
||||
|
||||
@@ -80,6 +104,63 @@ function check_hash() # $1 pwd, $2 hash
|
||||
$CRYPTSETUP remove $DEV_NAME || fail
|
||||
}
|
||||
|
||||
function backup_orig()
|
||||
{
|
||||
sync
|
||||
losetup -d $LOOPDEV1
|
||||
cp $IMG $ORIG_IMG
|
||||
losetup $LOOPDEV1 $IMG
|
||||
}
|
||||
|
||||
function rollback()
|
||||
{
|
||||
sync
|
||||
losetup -d $LOOPDEV1
|
||||
cp $ORIG_IMG $IMG
|
||||
losetup $LOOPDEV1 $IMG
|
||||
}
|
||||
|
||||
function check_slot() #space separeted list of ENABLED key slots
|
||||
{
|
||||
local _KS0=DISABLED
|
||||
local _KS1=$_KS0 _KS2=$_KS0 _KS3=$_KS0 _KS4=$_KS0 _KS5=$_KS0 _KS6=$_KS0 _KS7=$_KS0
|
||||
local _tmp
|
||||
|
||||
for _tmp in $*; do
|
||||
eval _KS$_tmp=ENABLED
|
||||
done
|
||||
|
||||
local _out=$($CRYPTSETUP luksDump $LOOPDEV1 | grep -e "Key Slot" | cut -d ' ' -f 4)
|
||||
|
||||
local _i=0
|
||||
for _tmp in $_out; do
|
||||
eval local _orig="\${_KS${_i}}"
|
||||
if [ "$_tmp" != "$_orig" ]; then
|
||||
echo "Keyslot $_i is $_tmp, expected result: $_orig"
|
||||
return 1
|
||||
fi
|
||||
_i=$[_i+1]
|
||||
done
|
||||
|
||||
return 0
|
||||
}
|
||||
|
||||
function simple_scsi_reenc()
|
||||
{
|
||||
echo -n "$1"
|
||||
echo $PWD1 | $CRYPTSETUP luksFormat -i1 $SCSI_DEV || fail
|
||||
|
||||
echo $PWD1 | $CRYPTSETUP luksOpen $SCSI_DEV $DEV_NAME || fail
|
||||
HASH=$(sha256sum /dev/mapper/$DEV_NAME | cut -d' ' -f 1)
|
||||
$CRYPTSETUP luksClose $DEV_NAME || fail
|
||||
|
||||
echo $PWD1 | $REENC -q -i 1 $SCSI_DEV || fail
|
||||
|
||||
echo $PWD1 | $CRYPTSETUP luksOpen $SCSI_DEV $DEV_NAME || fail
|
||||
check_hash_dev /dev/mapper/$DEV_NAME $HASH
|
||||
$CRYPTSETUP luksClose $DEV_NAME || fail
|
||||
}
|
||||
|
||||
[ $(id -u) != 0 ] && skip "WARNING: You must be root to run this test, test skipped."
|
||||
[ ! -x "$REENC" ] && skip "Cannot find $REENC, test skipped."
|
||||
|
||||
@@ -112,12 +193,15 @@ echo $PWD1 | $REENC $LOOPDEV1 -q -i 1 || fail
|
||||
check_hash $PWD1 $HASH2
|
||||
|
||||
echo "[3] Reencryption with keyfile"
|
||||
echo $PWD1 | $CRYPTSETUP -q luksFormat -d key1 -c aes-cbc-essiv:sha256 -s 128 -i 1 --align-payload 4096 $LOOPDEV1 || fail
|
||||
echo $PWD1 | $CRYPTSETUP -q luksFormat -d $KEY1 -c aes-cbc-essiv:sha256 -s 128 -i 1 --align-payload 4096 $LOOPDEV1 || fail
|
||||
wipe
|
||||
check_hash "" $HASH1
|
||||
echo $PWD1 | $CRYPTSETUP -q luksAddKey -d key1 $LOOPDEV1 || fail
|
||||
$REENC $LOOPDEV1 -d key1 -S 0 -i 1 -q || fail
|
||||
echo $PWD1 | $CRYPTSETUP -q luksAddKey -d $KEY1 $LOOPDEV1 || fail
|
||||
$REENC $LOOPDEV1 -d $KEY1 -i 1 -q 2>/dev/null && fail
|
||||
$REENC $LOOPDEV1 -d $KEY1 -S 0 -i 1 -q || fail
|
||||
check_hash "" $HASH1
|
||||
check_slot 0 || fail "Only keyslot 0 expected to be enabled"
|
||||
$REENC $LOOPDEV1 -d $KEY1 -i 1 -q || fail
|
||||
# FIXME echo $PWD1 | $REENC ...
|
||||
|
||||
echo "[4] Encryption of not yet encrypted device"
|
||||
@@ -131,5 +215,56 @@ dmsetup remove $DEV_NAME2 || fail
|
||||
echo $PWD1 | $REENC $LOOPDEV1 -c aes-cbc-essiv:sha256 -s 128 --new --reduce-device-size "$OFFSET"S -q
|
||||
check_hash $PWD1 $HASH3
|
||||
|
||||
echo "[5] Reencryption using specific keyslot"
|
||||
echo $PWD2 | $CRYPTSETUP -q luksFormat -i 1 $LOOPDEV1 || fail
|
||||
echo -e "$PWD2\n$PWD1" | $CRYPTSETUP -q luksAddKey -i 1 -S 1 $LOOPDEV1 || fail
|
||||
echo -e "$PWD2\n$PWD2" | $CRYPTSETUP -q luksAddKey -i 1 -S 2 $LOOPDEV1 || fail
|
||||
echo -e "$PWD2\n$PWD1" | $CRYPTSETUP -q luksAddKey -i 1 -S 3 $LOOPDEV1 || fail
|
||||
echo -e "$PWD2\n$PWD2" | $CRYPTSETUP -q luksAddKey -i 1 -S 4 $LOOPDEV1 || fail
|
||||
echo -e "$PWD2\n$PWD1" | $CRYPTSETUP -q luksAddKey -i 1 -S 5 $LOOPDEV1 || fail
|
||||
echo -e "$PWD2\n$PWD2" | $CRYPTSETUP -q luksAddKey -i 1 -S 6 $LOOPDEV1 || fail
|
||||
echo -e "$PWD2\n$PWD3" | $CRYPTSETUP -q luksAddKey -i 1 -S 7 $LOOPDEV1 || fail
|
||||
backup_orig
|
||||
echo $PWD2 | $REENC -i 1 -S 0 -q $LOOPDEV1 || fail
|
||||
check_slot 0 || fail "Only keyslot 0 expected to be enabled"
|
||||
wipe $PWD2
|
||||
rollback
|
||||
echo $PWD1 | $REENC -i 1 -S 1 -q $LOOPDEV1 || fail
|
||||
check_slot 1 || fail "Only keyslot 1 expected to be enabled"
|
||||
wipe $PWD1
|
||||
rollback
|
||||
echo $PWD2 | $REENC -i 1 -S 6 -q $LOOPDEV1 || fail
|
||||
check_slot 6 || fail "Only keyslot 6 expected to be enabled"
|
||||
wipe $PWD2
|
||||
rollback
|
||||
echo $PWD3 | $REENC -i 1 -S 7 -q $LOOPDEV1 || fail
|
||||
check_slot 7 || fail "Only keyslot 7 expected to be enabled"
|
||||
wipe $PWD3
|
||||
rollback
|
||||
|
||||
echo "[6] Reencryption using all active keyslots"
|
||||
echo -e "$PWD2\n$PWD1\n$PWD2\n$PWD1\n$PWD2\n$PWD1\n$PWD2\n$PWD3" | $REENC -q $LOOPDEV1 || fail
|
||||
check_slot 0 1 2 3 4 5 6 7 || fail "All keyslots expected to be enabled"
|
||||
|
||||
echo "[7] Reencryption of block devices with different block size"
|
||||
add_scsi_device sector_size=512 dev_size_mb=8
|
||||
simple_scsi_reenc "[512 sector]"
|
||||
add_scsi_device sector_size=4096 dev_size_mb=8
|
||||
simple_scsi_reenc "[4096 sector]"
|
||||
add_scsi_device sector_size=512 physblk_exp=3 dev_size_mb=8
|
||||
simple_scsi_reenc "[4096/512 sector]"
|
||||
echo "[OK]"
|
||||
|
||||
echo "[8] Header only reencryption (hash and iteration time)"
|
||||
echo $PWD1 | $CRYPTSETUP -q luksFormat --hash sha1 $LOOPDEV1 || fail
|
||||
wipe $PWD1
|
||||
check_hash $PWD1 $HASH1
|
||||
echo $PWD1 | $REENC $LOOPDEV1 -q --keep-key --hash sha256 --iter-time 1
|
||||
check_hash $PWD1 $HASH1
|
||||
echo $PWD1 | $REENC $LOOPDEV1 -q --keep-key --hash sha512
|
||||
check_hash $PWD1 $HASH1
|
||||
echo $PWD1 | $REENC $LOOPDEV1 -q --keep-key --iter-time 1
|
||||
check_hash $PWD1 $HASH1
|
||||
|
||||
remove_mapping
|
||||
exit 0
|
||||
|
||||
@@ -65,6 +65,7 @@ function test_required()
|
||||
}
|
||||
|
||||
test_required
|
||||
export LANG=C
|
||||
|
||||
[ ! -d $TST_DIR ] && tar xjf tcrypt-images.tar.bz2
|
||||
|
||||
@@ -95,10 +96,11 @@ if [ $(id -u) != 0 ]; then
|
||||
exit 0
|
||||
fi
|
||||
|
||||
echo "ACTIVATION FS UUID CHECK (LRW/XTS modes only)"
|
||||
for file in $(ls $TST_DIR/tc_*-lrw-* $TST_DIR/tc_*-xts-*) ; do
|
||||
echo "ACTIVATION FS UUID CHECK"
|
||||
for file in $(ls $TST_DIR/tc_*) ; do
|
||||
echo -n " $file"
|
||||
echo $PASSWORD | $CRYPTSETUP tcryptOpen -r $file $MAP || fail
|
||||
out=$(echo $PASSWORD | $CRYPTSETUP tcryptOpen -r $file $MAP 2>/dev/null)
|
||||
[ $? -ne 0 ] && ( echo "$out" | grep -q -v "TCRYPT legacy mode" ) && echo " [N/A]" && continue
|
||||
$CRYPTSETUP status $MAP >/dev/null || fail
|
||||
$CRYPTSETUP status /dev/mapper/$MAP >/dev/null || fail
|
||||
UUID=$(lsblk -n -o UUID /dev/mapper/$MAP)
|
||||
@@ -107,10 +109,11 @@ for file in $(ls $TST_DIR/tc_*-lrw-* $TST_DIR/tc_*-xts-*) ; do
|
||||
echo " [OK]"
|
||||
done
|
||||
|
||||
echo "ACTIVATION FS UUID (HIDDEN) CHECK (LRW/XTS modes only)"
|
||||
for file in $(ls $TST_DIR/tc_*-lrw-*-hidden $TST_DIR/tc_*-xts-*-hidden) ; do
|
||||
echo "ACTIVATION FS UUID (HIDDEN) CHECK"
|
||||
for file in $(ls $TST_DIR/tc_*-hidden) ; do
|
||||
echo -n " $file"
|
||||
echo $PASSWORD_HIDDEN | $CRYPTSETUP tcryptOpen -r $file $MAP --tcrypt-hidden || fail
|
||||
out=$(echo $PASSWORD_HIDDEN | $CRYPTSETUP tcryptOpen -r $file $MAP --tcrypt-hidden 2>/dev/null)
|
||||
[ $? -ne 0 ] && ( echo "$out" | grep -q -v "TCRYPT legacy mode" ) && echo " [N/A]" && continue
|
||||
UUID=$(lsblk -n -o UUID /dev/mapper/$MAP)
|
||||
$CRYPTSETUP remove $MAP || fail
|
||||
[ "$UUID" != "CAFE-BABE" ] && fail "UUID check failed."
|
||||
|
||||
Binary file not shown.
Reference in New Issue
Block a user