Check wrapper type alignment in both test suites so incidental alignment
can't hide an empty CRYPTOPP_ALIGN_DATA, including in ASan builds.
Clarify that the compiler may fold the existing address checks.
The macro expands to nothing for compilers that are neither MSVC nor
GCC/Clang, and the SIMD backends issue aligned loads against buffers declared
with it, so a silent expansion to nothing would fault at run time. Nothing
verified this so far.
Add TC_IS_ALIGNED next to the existing alignment constants and check both of
them from the platform self-test suites. The probe buffers stay below the
alignment under test because the ABI already aligns larger objects by itself,
which would make the check pass vacuously.
The check is skipped in the Windows driver: a failing self-test there reaches
TC_BUG_CHECK and would bugcheck the machine.
* Crypto: fix portable C code on big-endian CPUs
On big-endian CPUs (e.g. MIPS and PowerPC) the portable C code of
several algorithms assumes a little-endian host, so ciphertext, hashes
and derived keys are wrong and "veracrypt --text --test" fails:
- Twofish: the key-dependent S-box bytes are read back from 32-bit
words through a union, and blocks are loaded/stored as native words.
- Camellia: blocks and keys are always byte-swapped to big-endian.
- Kuznyechik: keys and blocks are loaded/stored as native 64-bit words
while the tables expect the little-endian interpretation.
- SHA-256/SHA-512: message words, length and digest are always
byte-swapped.
- BLAKE2s: the parameter block and message words are read as native
little-endian data. The parameter block is now built from its fields,
so it is right for any parameters, not only the ones VeraCrypt uses.
- Streebog: the existing big-endian code path is never enabled, and
BSWAP64 used by it is not defined (its buffer512 initializer also has
one pair of braces too many). Its add512() also differs from the
little-endian one, which drops a carry on purpose (existing volumes
depend on it); do the same limb arithmetic on big-endian.
- misc.h: the rotate-based bswap_32 (non-Linux, non-Apple, non-MSVC
builds) lacks outer parentheses, so "bswap_32(a) ^ b" is parsed
wrongly, and the fallback bswap_64 does not parenthesise its argument.
- PBKDF2: the block number is always byte-swapped.
Swap only where the host byte order differs from the data, and enable
the Streebog big-endian path. On big-endian hosts the message words,
keys and blocks of SHA-2, BLAKE2s, Twofish and Kuznyechik are read and
written byte-wise (new VcLoad*/VcStore* inline helpers in misc.h), so
these paths also work on misaligned buffers on strict-alignment CPUs.
On little-endian CPUs the code is unchanged: the object files of all
touched sources are byte-identical before and after this change
(checked on x86_64, aarch64 and mipsel). With it, all self-tests pass on
mips (big-endian) under qemu.
Signed-off-by: Ville Takio <ville+git@takio.fi>
* Volume: avoid unaligned 64-bit header and test vector accesses
The volume header (de)serialisation and TestXtsAES read and write 64-bit
fields through casted pointers into byte buffers at offsets that are
only 4-byte aligned (e.g. the header field at offset 12). CPUs that trap
on misaligned access without kernel fix-up (SPARC, MIPS64 on some
systems, qemu-user) then fail with SIGBUS in "veracrypt --test" and when
creating or opening any volume. Use memcpy instead, and have
DeserializeEntryAt check that the whole entry, not only its start, lies
inside the header.
The XTS code also accesses its local byte arrays (whitening values,
data unit number) through uint64 pointers; declare them 8-byte aligned
instead of relying on the compiler's stack layout.
Signed-off-by: Ville Takio <ville+git@takio.fi>
* Volume: test multi-block PBKDF2 output and the Streebog carry case
The PBKDF2 self-tests only check the first 4 bytes of each derivation,
so the block counter of the second and later output blocks is never
checked. Also compare the complete output of a 192-byte derivation for
every PRF, which covers the later blocks and how they are joined, and
hash a message whose block sum hits the carry case of Streebog's
add512(), which has to stay bit-compatible across CPUs. The message
buffer is 8-byte aligned, as the portable Streebog code reads it as
64-bit words. The expected values are those of the existing
little-endian code, and match independent implementations for all five
PRFs (Python hashlib/hmac, OpenSSL for Whirlpool, gostcrypto for
Streebog).
Signed-off-by: Ville Takio <ville+git@takio.fi>
---------
Signed-off-by: Ville Takio <ville+git@takio.fi>
Extend the Unix encryption thread pool to run key-derivation work items and use it when mounting volumes without an explicitly selected KDF. This brings Linux/macOS header PRF autodetection closer to the Windows path while keeping selected-KDF mounts unchanged.
Fixes#1610.
Argon2id includes the requested output length in its computation, so deriving 192 bytes and using a prefix is not equivalent to deriving only the selected cipher's key material length. This differs from PBKDF2, where the prefix property made this detail invisible.
VeraCrypt derives the maximum header key material currently needed by the supported cipher/cascade set, which is 192 bytes, and then uses the required prefix for the selected encryption algorithm. For AES-XTS this means the first 64 bytes of the 192-byte Argon2id output are used.
Make this design rule explicit in code and documentation by introducing ARGON2_HEADER_KEYDATA_SIZE instead of relying implicitly on GetMaxPkcs5OutSize. If a future cipher or cascade requires more than 192 bytes, that must be handled as an explicit format/design change.
Document the 192-byte Argon2id header KDF output requirement so third-party implementations derive the same header key material.
References: https://github.com/veracrypt/VeraCrypt/issues/1614
The cascade order has been updated so that SM4 is applied after the other cipher(s) (e.g., Serpent). This change reflects standard cryptanalytic guidance, which shows that the overall strength of a cascade is limited by the first encryption stage. Given that SM4 uses a 128-bit key, its post-quantum brute-force resistance is lower than ciphers with a 256-bit key (such as Serpent). By placing SM4 last, we ensure that any potential weakness in SM4 cannot reduce the security margin provided by the stronger cipher.