This commit finishes the removal of support for direct access to key
slots in psa_crypto.c.
This marks the end of the necessary phase of the transition to key
handles. The code should subsequently be refactored to move key slot
management from psa_crypto.c to psa_crypto_slot_management.c.
Switch from the direct use of slot numbers to handles allocated by
psa_allocate_key.
This commit does not affect persistent key tests except for the one
test function in test_suite_psa_crypto that uses persistent keys
(persistent_key_load_key_from_storage).
The general principle for each function is:
* Change `psa_key_slot_t slot` to `psa_key_handle_t handle`.
* Call psa_allocate_key() before setting the policy of the slot,
or before creating key material in functions that don't set a policy.
* Some PSA_ERROR_EMPTY_SLOT errors become PSA_ERROR_INVALID_HANDLE
because there is now a distinction between not having a valid
handle, and having a valid handle to a slot that doesn't contain key
material.
* In tests that use symmetric keys, calculate the max_bits parameters
of psa_allocate_key() from the key data size. In tests where the key
may be asymmetric, call an auxiliary macro KEY_BITS_FROM_DATA which
returns an overapproximation. There's no good way to find a good
value for max_bits with the API, I think the API should be tweaked.
Implement psa_allocate_key, psa_open_key, psa_create_key,
psa_close_key.
Add support for keys designated to handles to psa_get_key_slot, and
thereby to the whole API.
Allocated and non-allocated keys can coexist. This is a temporary
stage in order to transition from the use of direct slot numbers to
allocated handles only. Once all the tests and sample programs have
been migrated to use handles, the implementation will be simplified
and made more robust with support for handles only.
Add missing compilation guards that broke the build if either GCM or
CCM was not defined.
Add missing guards on test cases that require GCM or CBC.
The build and tests now pass for any subset of {MBEDTLS_CCM_C,
MBEDTLS_GCM_C}. There are still unused variables warnings if neither
is defined.
Allow use of persistent keys, including configuring them, importing and
exporting them, and destroying them.
When getting a slot using psa_get_key_slot, there are 3 scenarios that
can occur if the keys lifetime is persistent:
1. Key type is PSA_KEY_TYPE_NONE, no persistent storage entry:
- The key slot is treated as a standard empty key slot
2. Key type is PSA_KEY_TYPE_NONE, persistent storage entry exists:
- Attempt to load the key from persistent storage
3. Key type is not PSA_KEY_TYPE_NONE:
- As checking persistent storage on every use of the key could
be expensive, the persistent key is assumed to be saved in
persistent storage, the in-memory key is continued to be used.
There was no test case of ECDH with anything other than
PSA_ALG_SELECT_RAW. Exercise the code path from ECDH through a
"proper" KDF.
ECDH shared secret copied from an existing test, HKDF output
calculated with Cryptodome.
In ECDH key agreement, allow a public key with the OID id-ECDH, not
just a public key with the OID id-ecPublicKey.
Public keys with the OID id-ECDH are not permitted by psa_import_key,
at least for now. There would be no way to use the key for a key
agreement operation anyway in the current API.
Add test cases that do key agreement with raw selection in pieces, to
validate that selection works even when the application doesn't read
everything in one chunk.
A key selection algorithm is similar to a key derivation algorithm in
that it takes a secret input and produces a secret output stream.
However, unlike key derivation algorithms, there is no expectation
that the input cannot be reconstructed from the output. Key selection
algorithms are exclusively meant to be used on the output of a key
agreement algorithm to select chunks of the shared secret.
On key import and key generation, for RSA, reject key sizes that are
not a multiple of 8. Such keys are not well-supported in Mbed TLS and
are hardly ever used in practice.
The previous commit removed support for non-byte-aligned keys at the
PSA level. This commit actively rejects such keys and adds
corresponding tests (test keys generated with "openssl genrsa").
Simplify the test case "PSA export a slot after a failed import of an
EC keypair": use an invalid private value for the specified curve. Now
the dependencies match the test data, so this fixes curves.pl.
Update some test data from the asymmetric_apis_coverage branch that
wasn't updated to the new format from the
psa-asymmetric-format-raw_private_key branch.
1. New test for testing bad order of hash function calls.
2. Removed test hash_update_bad_paths since it's test scenario
was moved to the new test.
3. Moved some scenarios from test hash_verify_bad_paths to
the new test.
1. Rename hash_bad_paths to hash_verify_bad_paths
2. Add test hash_update_bad_paths
3. Add test hash_finish_bad_paths
The different scenarios tested as part of hash_bad_paths are
moved to the relevant test.
streamline the API for the test test_derive_invalid_generator_state: by removing
the key_data parameter.
This parameter is not important for test flow and can be hard-coded.
Add boundary test cases for private key validity for a short
Weierstrass curve (0 < d < n).
Remove obsolete test cases "valid key but wrong curve". With the new
format, the private key representation does not contain an encoding of
the curve.
In preparation for the import/export format change for private
elliptic curve keys from RFC 5915 to the raw secret value, transform the
test data to the new format.
Tests will not pass until the implementation has been changed to the
new format and some test cases and test functions have been adjusted.
I used the script below to look for lines containing a
PSA_KEY_TYPE_ECC_KEYPAIR and change the first hex string in the
line with an ASN.1 header that looks like the beginning of an RFC 5915
ECPrivateKey. This always happens to be a private key input.
perl -a -F: -i -pe 'sub pad { local ($_) = @_; s/^00// if length == $digits + 2; die if length > $digits; sprintf("\"%0${digits}s\"", $_) } if ($F[0] !~ /\W/ && /:PSA_KEY_TYPE_ECC_KEYPAIR\( *PSA_ECC_CURVE_[A-Z_]+([0-9]+)/) {$digits = int(($1+7)/8)*2; s/"30(?:[0-7].|81..|82....)02010104(..)([0-9a-f]+)"/pad(substr($2, 0, hex($1)*2))/ie}' tests/suites/test_suite_psa_crypto.data