/* BEGIN_HEADER */
#include "test/psa_crypto_helpers.h"
#include "psa/crypto_se_driver.h"

#include "psa_crypto_se.h"
#include "psa_crypto_storage.h"

/** The location and lifetime used for tests that use a single driver. */
#define TEST_DRIVER_LOCATION 1
#define TEST_SE_PERSISTENT_LIFETIME                             \
    ( PSA_KEY_LIFETIME_FROM_PERSISTENCE_AND_LOCATION(           \
        PSA_KEY_PERSISTENCE_DEFAULT, TEST_DRIVER_LOCATION ) )

static struct
{
    uint16_t called;
    psa_key_location_t location;
    psa_status_t return_value;
} mock_init_data;

static struct
{
    uint16_t called;
    psa_key_slot_number_t key_slot;
    psa_key_attributes_t attributes;
    size_t pubkey_size;
    psa_status_t return_value;
} mock_generate_data;

static struct
{
    uint16_t called;
    psa_key_slot_number_t key_slot;
    psa_key_attributes_t attributes;
    size_t bits;
    size_t data_length;
    psa_status_t return_value;
} mock_import_data;

static struct
{
    uint16_t called;
    psa_key_slot_number_t slot_number;
    size_t data_size;
    psa_status_t return_value;
} mock_export_data;

static struct
{
    uint16_t called;
    psa_key_slot_number_t slot_number;
    size_t data_size;
    psa_status_t return_value;
} mock_export_public_data;

static struct
{
    uint16_t called;
    psa_key_slot_number_t key_slot;
    psa_algorithm_t alg;
    size_t hash_length;
    size_t signature_size;
    psa_status_t return_value;
} mock_sign_data;

static struct
{
    uint16_t called;
    psa_key_slot_number_t key_slot;
    psa_algorithm_t alg;
    size_t hash_length;
    size_t signature_length;
    psa_status_t return_value;
} mock_verify_data;

static struct
{
    uint16_t called;
    psa_status_t return_value;
} mock_allocate_data;

static struct
{
    uint16_t called;
    psa_key_slot_number_t slot_number;
    psa_status_t return_value;
} mock_destroy_data;

#define MAX_KEY_ID_FOR_TEST 10
static void psa_purge_storage( void )
{
    psa_key_id_t id;
    psa_key_location_t location;

    /* The tests may have potentially created key ids from 1 to
     * MAX_KEY_ID_FOR_TEST. In addition, run the destroy function on key id
     * 0, which file-based storage uses as a temporary file. */
    for( id = 0; id <= MAX_KEY_ID_FOR_TEST; id++ )
        psa_destroy_persistent_key( mbedtls_svc_key_id_make( 1, id ) );

    /* Purge the transaction file. */
    psa_crypto_stop_transaction( );
    /* Purge driver persistent data. */
    for( location = 0; location < PSA_MAX_SE_LOCATION; location++ )
        psa_destroy_se_persistent_data( location );
}

static void mock_teardown( void )
{
    memset( &mock_init_data, 0, sizeof( mock_init_data ) );
    memset( &mock_import_data, 0, sizeof( mock_import_data ) );
    memset( &mock_export_data, 0, sizeof( mock_export_data ) );
    memset( &mock_export_public_data, 0, sizeof( mock_export_public_data ) );
    memset( &mock_sign_data, 0, sizeof( mock_sign_data ) );
    memset( &mock_verify_data, 0, sizeof( mock_verify_data ) );
    memset( &mock_allocate_data, 0, sizeof( mock_allocate_data ) );
    memset( &mock_destroy_data, 0, sizeof( mock_destroy_data ) );
    memset( &mock_generate_data, 0, sizeof( mock_generate_data ) );
    psa_purge_storage( );
}

static psa_status_t mock_init( psa_drv_se_context_t *drv_context,
                               void *persistent_data,
                               psa_key_location_t location )
{
    (void) drv_context;
    (void) persistent_data;

    mock_init_data.called++;
    mock_init_data.location = location;
    return( mock_init_data.return_value );
}

static psa_status_t mock_generate( psa_drv_se_context_t *drv_context,
                                   psa_key_slot_number_t key_slot,
                                   const psa_key_attributes_t *attributes,
                                   uint8_t *pubkey,
                                   size_t pubkey_size,
                                   size_t *pubkey_length )
{
    (void) drv_context;
    (void) pubkey;
    (void) pubkey_length;

    mock_generate_data.called++;
    mock_generate_data.key_slot = key_slot;
    mock_generate_data.attributes = *attributes;
    mock_generate_data.pubkey_size = pubkey_size;

    return( mock_generate_data.return_value );
}

static psa_status_t mock_import( psa_drv_se_context_t *drv_context,
                                 psa_key_slot_number_t key_slot,
                                 const psa_key_attributes_t *attributes,
                                 const uint8_t *data,
                                 size_t data_length,
                                 size_t *bits )
{
    (void) drv_context;
    (void) data;

    *bits = mock_import_data.bits;

    mock_import_data.called++;
    mock_import_data.key_slot = key_slot;
    mock_import_data.attributes = *attributes;
    mock_import_data.data_length = data_length;

    return( mock_import_data.return_value );
}

psa_status_t mock_export( psa_drv_se_context_t *context,
                          psa_key_slot_number_t slot_number,
                          uint8_t *p_data,
                          size_t data_size,
                          size_t *p_data_length )
{
    (void) context;
    (void) p_data;
    (void) p_data_length;

    mock_export_data.called++;
    mock_export_data.slot_number = slot_number;
    mock_export_data.data_size = data_size;

    return( mock_export_data.return_value );
}

psa_status_t mock_export_public( psa_drv_se_context_t *context,
                                 psa_key_slot_number_t slot_number,
                                 uint8_t *p_data,
                                 size_t data_size,
                                 size_t *p_data_length )
{
    (void) context;
    (void) p_data;
    (void) p_data_length;

    mock_export_public_data.called++;
    mock_export_public_data.slot_number = slot_number;
    mock_export_public_data.data_size = data_size;

    return( mock_export_public_data.return_value );
}

psa_status_t mock_sign( psa_drv_se_context_t *context,
                        psa_key_slot_number_t key_slot,
                        psa_algorithm_t alg,
                        const uint8_t *p_hash,
                        size_t hash_length,
                        uint8_t *p_signature,
                        size_t signature_size,
                        size_t *p_signature_length )
{
    (void) context;
    (void) p_hash;
    (void) p_signature;
    (void) p_signature_length;

    mock_sign_data.called++;
    mock_sign_data.key_slot = key_slot;
    mock_sign_data.alg = alg;
    mock_sign_data.hash_length = hash_length;
    mock_sign_data.signature_size = signature_size;

    return mock_sign_data.return_value;
}

psa_status_t mock_verify( psa_drv_se_context_t *context,
                          psa_key_slot_number_t key_slot,
                          psa_algorithm_t alg,
                          const uint8_t *p_hash,
                          size_t hash_length,
                          const uint8_t *p_signature,
                          size_t signature_length )
{
    (void) context;
    (void) p_hash;
    (void) p_signature;

    mock_verify_data.called++;
    mock_verify_data.key_slot = key_slot;
    mock_verify_data.alg = alg;
    mock_verify_data.hash_length = hash_length;
    mock_verify_data.signature_length = signature_length;

    return mock_verify_data.return_value;
}

psa_status_t mock_allocate( psa_drv_se_context_t *drv_context,
                            void *persistent_data,
                            const psa_key_attributes_t *attributes,
                            psa_key_creation_method_t method,
                            psa_key_slot_number_t *key_slot )
{
    (void) drv_context;
    (void) persistent_data;
    (void) attributes;
    (void) method;
    (void) key_slot;

    mock_allocate_data.called++;
    *key_slot = 0;

    return( mock_allocate_data.return_value );
}

psa_status_t mock_destroy( psa_drv_se_context_t *context,
                           void *persistent_data,
                           psa_key_slot_number_t slot_number )
{
    (void) context;
    (void) persistent_data;

    mock_destroy_data.called++;
    mock_destroy_data.slot_number = slot_number;

    return( mock_destroy_data.return_value );
}

/* END_HEADER */

/* BEGIN_DEPENDENCIES
 * depends_on:MBEDTLS_PSA_CRYPTO_SE_C
 * END_DEPENDENCIES
 */

/* BEGIN_CASE */
void mock_init( int location_arg,
                int expected_register_status_arg,
                int driver_status_arg,
                int expected_psa_status_arg,
                int expected_called )
{
    psa_key_location_t location = location_arg;
    psa_status_t expected_register_status = expected_register_status_arg;
    psa_status_t driver_status = driver_status_arg;
    psa_status_t expected_psa_status = expected_psa_status_arg;
    psa_drv_se_t driver = {
        .hal_version = PSA_DRV_SE_HAL_VERSION,
        .p_init = mock_init,
    };
    int psa_crypto_init_called = 0;

    mock_init_data.return_value = driver_status;

    TEST_EQUAL( psa_register_se_driver( location, &driver ),
                expected_register_status );

    psa_crypto_init_called = 1;
    TEST_EQUAL( psa_crypto_init( ), expected_psa_status );

    TEST_EQUAL( mock_init_data.called, expected_called );
    if( expected_called )
        TEST_EQUAL( mock_init_data.location, location );

exit:
    if( psa_crypto_init_called )
        PSA_DONE( );
    mock_teardown( );
}
/* END_CASE */

/* BEGIN_CASE */
void mock_import( int mock_alloc_return_value,
                  int mock_import_return_value,
                  int bits,
                  int expected_result )
{
    psa_drv_se_t driver;
    psa_drv_se_key_management_t key_management;
    psa_key_lifetime_t lifetime = TEST_SE_PERSISTENT_LIFETIME;
    psa_key_location_t location = PSA_KEY_LIFETIME_GET_LOCATION( lifetime );
    mbedtls_svc_key_id_t id = mbedtls_svc_key_id_make( 1, 1 );
    psa_key_handle_t handle = 0;
    psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
    const uint8_t key_material[3] = {0xfa, 0xca, 0xde};

    mock_allocate_data.return_value = mock_alloc_return_value;
    mock_import_data.return_value = mock_import_return_value;
    mock_import_data.bits = bits;
    memset( &driver, 0, sizeof( driver ) );
    memset( &key_management, 0, sizeof( key_management ) );
    driver.hal_version = PSA_DRV_SE_HAL_VERSION;
    driver.key_management = &key_management;
    key_management.p_import = mock_import;
    key_management.p_destroy = mock_destroy;
    key_management.p_allocate = mock_allocate;

    PSA_ASSERT( psa_register_se_driver( location, &driver ) );
    PSA_ASSERT( psa_crypto_init( ) );

    psa_set_key_id( &attributes, id );
    psa_set_key_lifetime( &attributes, lifetime );
    psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_EXPORT );
    psa_set_key_type( &attributes, PSA_KEY_TYPE_RAW_DATA );
    TEST_ASSERT( psa_import_key( &attributes,
                                 key_material, sizeof( key_material ),
                                 &handle ) == expected_result );

    TEST_ASSERT( mock_allocate_data.called == 1 );
    TEST_ASSERT( mock_import_data.called ==
        ( mock_alloc_return_value == PSA_SUCCESS? 1 : 0 ) );

    if( mock_alloc_return_value == PSA_SUCCESS )
    {
        TEST_ASSERT( mbedtls_svc_key_id_equal(
                         mock_import_data.attributes.core.id, id ) );
    }
    else
    {
        TEST_ASSERT( MBEDTLS_SVC_KEY_ID_GET_KEY_ID(
                         mock_import_data.attributes.core.id ) == 0 );
        TEST_ASSERT( MBEDTLS_SVC_KEY_ID_GET_OWNER_ID(
                         mock_import_data.attributes.core.id ) == 0 );
    }

    TEST_ASSERT( mock_import_data.attributes.core.lifetime ==
        ( mock_alloc_return_value == PSA_SUCCESS? lifetime : 0 ) );
    TEST_ASSERT( mock_import_data.attributes.core.policy.usage ==
        ( mock_alloc_return_value == PSA_SUCCESS? PSA_KEY_USAGE_EXPORT : 0 ) );
    TEST_ASSERT( mock_import_data.attributes.core.type ==
        ( mock_alloc_return_value == PSA_SUCCESS? PSA_KEY_TYPE_RAW_DATA : 0 ) );

    if( expected_result == PSA_SUCCESS )
    {
        PSA_ASSERT( psa_destroy_key( handle ) );
        TEST_ASSERT( mock_destroy_data.called == 1 );
    }
exit:
    PSA_DONE( );
    mock_teardown( );
}
/* END_CASE */

/* BEGIN_CASE */
void mock_export( int mock_export_return_value, int expected_result )
{
    psa_drv_se_t driver;
    psa_drv_se_key_management_t key_management;
    psa_key_lifetime_t lifetime = TEST_SE_PERSISTENT_LIFETIME;
    psa_key_location_t location = PSA_KEY_LIFETIME_GET_LOCATION( lifetime );
    mbedtls_svc_key_id_t id = mbedtls_svc_key_id_make( 1, 1 );
    psa_key_handle_t handle = 0;
    psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
    const uint8_t key_material[3] = {0xfa, 0xca, 0xde};
    uint8_t exported[sizeof( key_material )];
    size_t exported_length;

    mock_export_data.return_value = mock_export_return_value;
    memset( &driver, 0, sizeof( driver ) );
    memset( &key_management, 0, sizeof( key_management ) );
    driver.hal_version = PSA_DRV_SE_HAL_VERSION;
    driver.key_management = &key_management;
    driver.p_init = mock_init;
    key_management.p_import = mock_import;
    key_management.p_export = mock_export;
    key_management.p_destroy = mock_destroy;
    key_management.p_allocate = mock_allocate;

    PSA_ASSERT( psa_register_se_driver( location, &driver ) );
    PSA_ASSERT( psa_crypto_init( ) );

    psa_set_key_id( &attributes, id );
    psa_set_key_lifetime( &attributes, lifetime );
    psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_EXPORT );
    psa_set_key_type( &attributes, PSA_KEY_TYPE_RAW_DATA );
    PSA_ASSERT( psa_import_key( &attributes,
                                key_material, sizeof( key_material ),
                                &handle ) );

    TEST_ASSERT( psa_export_key( handle,
                                exported, sizeof( exported ),
                                &exported_length ) == expected_result );

    TEST_ASSERT( mock_export_data.called == 1 );

    PSA_ASSERT( psa_destroy_key( handle ) );

    TEST_ASSERT( mock_destroy_data.called == 1 );

exit:
    PSA_DONE( );
    mock_teardown( );
}
/* END_CASE */

/* BEGIN_CASE */
void mock_generate( int mock_alloc_return_value,
                    int mock_generate_return_value,
                    int expected_result )
{
    psa_drv_se_t driver;
    psa_drv_se_key_management_t key_management;
    psa_key_lifetime_t lifetime = TEST_SE_PERSISTENT_LIFETIME;
    psa_key_location_t location = PSA_KEY_LIFETIME_GET_LOCATION( lifetime );
    mbedtls_svc_key_id_t id = mbedtls_svc_key_id_make( 1, 1 );
    psa_key_handle_t handle = 0;
    psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;

    mock_allocate_data.return_value = mock_alloc_return_value;
    mock_generate_data.return_value = mock_generate_return_value;
    memset( &driver, 0, sizeof( driver ) );
    memset( &key_management, 0, sizeof( key_management ) );
    driver.hal_version = PSA_DRV_SE_HAL_VERSION;
    driver.key_management = &key_management;
    key_management.p_generate = mock_generate;
    key_management.p_destroy = mock_destroy;
    key_management.p_allocate = mock_allocate;

    PSA_ASSERT( psa_register_se_driver( location, &driver ) );
    PSA_ASSERT( psa_crypto_init( ) );

    psa_set_key_id( &attributes, id );
    psa_set_key_lifetime( &attributes, lifetime );
    psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_EXPORT );
    psa_set_key_type( &attributes, PSA_KEY_TYPE_RAW_DATA );
    psa_set_key_bits( &attributes, 8 );
    TEST_ASSERT( psa_generate_key( &attributes, &handle ) == expected_result );
    TEST_ASSERT( mock_allocate_data.called == 1 );
    TEST_ASSERT( mock_generate_data.called ==
        ( mock_alloc_return_value == PSA_SUCCESS? 1 : 0 ) );

    if( mock_alloc_return_value == PSA_SUCCESS )
    {
        TEST_ASSERT( mbedtls_svc_key_id_equal(
                         mock_generate_data.attributes.core.id, id ) );
    }
    else
    {
        TEST_ASSERT( MBEDTLS_SVC_KEY_ID_GET_KEY_ID(
                         mock_generate_data.attributes.core.id ) == 0 );
        TEST_ASSERT( MBEDTLS_SVC_KEY_ID_GET_OWNER_ID(
                         mock_generate_data.attributes.core.id ) == 0 );
    }

    TEST_ASSERT( mock_generate_data.attributes.core.lifetime ==
        ( mock_alloc_return_value == PSA_SUCCESS? lifetime : 0 ) );
    TEST_ASSERT( mock_generate_data.attributes.core.policy.usage ==
        ( mock_alloc_return_value == PSA_SUCCESS? PSA_KEY_USAGE_EXPORT : 0 ) );
    TEST_ASSERT( mock_generate_data.attributes.core.type ==
        ( mock_alloc_return_value == PSA_SUCCESS? PSA_KEY_TYPE_RAW_DATA : 0 ) );

    if( expected_result == PSA_SUCCESS )
    {
        PSA_ASSERT( psa_destroy_key( handle ) );
        TEST_ASSERT( mock_destroy_data.called == 1 );
    }

exit:
    PSA_DONE( );
    mock_teardown( );
}
/* END_CASE */

/* BEGIN_CASE */
void mock_export_public( int mock_export_public_return_value,
                         int expected_result )
{
    psa_drv_se_t driver;
    psa_drv_se_key_management_t key_management;
    psa_key_lifetime_t lifetime = TEST_SE_PERSISTENT_LIFETIME;
    psa_key_location_t location = PSA_KEY_LIFETIME_GET_LOCATION( lifetime );
    mbedtls_svc_key_id_t id = mbedtls_svc_key_id_make( 1, 1 );
    psa_key_handle_t handle = 0;
    psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
    const uint8_t key_material[3] = {0xfa, 0xca, 0xde};
    uint8_t exported[sizeof( key_material )];
    size_t exported_length;

    mock_export_public_data.return_value = mock_export_public_return_value;
    memset( &driver, 0, sizeof( driver ) );
    memset( &key_management, 0, sizeof( key_management ) );
    driver.hal_version = PSA_DRV_SE_HAL_VERSION;
    driver.key_management = &key_management;
    key_management.p_import = mock_import;
    key_management.p_export_public = mock_export_public;
    key_management.p_destroy = mock_destroy;
    key_management.p_allocate = mock_allocate;

    PSA_ASSERT( psa_register_se_driver( location, &driver ) );
    PSA_ASSERT( psa_crypto_init( ) );

    psa_set_key_id( &attributes, id );
    psa_set_key_lifetime( &attributes, lifetime );
    psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_EXPORT );
    psa_set_key_type( &attributes, PSA_KEY_TYPE_RSA_PUBLIC_KEY );

    PSA_ASSERT( psa_import_key( &attributes,
                                key_material, sizeof( key_material ),
                                &handle ) );

    TEST_ASSERT( psa_export_public_key( handle, exported, sizeof(exported),
                                        &exported_length ) == expected_result );
    TEST_ASSERT( mock_export_public_data.called == 1 );

    PSA_ASSERT( psa_destroy_key( handle ) );
    TEST_ASSERT( mock_destroy_data.called == 1 );

exit:
    PSA_DONE( );
    mock_teardown( );
}
/* END_CASE */

/* BEGIN_CASE */
void mock_sign( int mock_sign_return_value, int expected_result )
{
    psa_drv_se_t driver;
    psa_drv_se_key_management_t key_management;
    psa_drv_se_asymmetric_t asymmetric;
    psa_key_lifetime_t lifetime = TEST_SE_PERSISTENT_LIFETIME;
    psa_key_location_t location = PSA_KEY_LIFETIME_GET_LOCATION( lifetime );
    mbedtls_svc_key_id_t id = mbedtls_svc_key_id_make( 1, 1 );
    psa_key_handle_t handle = 0;
    psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
    const uint8_t key_material[3] = {0xfa, 0xca, 0xde};
    psa_algorithm_t algorithm = PSA_ALG_ECDSA(PSA_ALG_SHA_256);
    const uint8_t hash[1] = {'H'};
    uint8_t signature[1] = {'S'};
    size_t signature_length;

    mock_sign_data.return_value = mock_sign_return_value;
    memset( &driver, 0, sizeof( driver ) );
    memset( &key_management, 0, sizeof( key_management ) );
    memset( &asymmetric, 0, sizeof( asymmetric ) );

    driver.hal_version = PSA_DRV_SE_HAL_VERSION;

    driver.key_management = &key_management;
    key_management.p_import = mock_import;
    key_management.p_destroy = mock_destroy;
    key_management.p_allocate = mock_allocate;

    driver.asymmetric = &asymmetric;
    asymmetric.p_sign = mock_sign;

    PSA_ASSERT( psa_register_se_driver( location, &driver ) );
    PSA_ASSERT( psa_crypto_init( ) );

    psa_set_key_id( &attributes, id );
    psa_set_key_lifetime( &attributes, lifetime );
    psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_SIGN_HASH );
    psa_set_key_algorithm( &attributes, algorithm );
    psa_set_key_type( &attributes, PSA_KEY_TYPE_RSA_KEY_PAIR );

    PSA_ASSERT( psa_import_key( &attributes,
                                key_material, sizeof( key_material ),
                                &handle ) );

    TEST_ASSERT( psa_sign_hash( handle, algorithm,
                                hash, sizeof( hash ),
                                signature, sizeof( signature ),
                                &signature_length)
                 == expected_result );
    TEST_ASSERT( mock_sign_data.called == 1 );

    PSA_ASSERT( psa_destroy_key( handle ) );
    TEST_ASSERT( mock_destroy_data.called == 1 );

exit:
    PSA_DONE( );
    mock_teardown( );
}
/* END_CASE */

/* BEGIN_CASE */
void mock_verify( int mock_verify_return_value, int expected_result )
{
    psa_drv_se_t driver;
    psa_drv_se_key_management_t key_management;
    psa_drv_se_asymmetric_t asymmetric;
    psa_key_lifetime_t lifetime = TEST_SE_PERSISTENT_LIFETIME;
    psa_key_location_t location = PSA_KEY_LIFETIME_GET_LOCATION( lifetime );
    mbedtls_svc_key_id_t id = mbedtls_svc_key_id_make( 1, 1 );
    psa_key_handle_t handle = 0;
    psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
    const uint8_t key_material[3] = {0xfa, 0xca, 0xde};
    psa_algorithm_t algorithm = PSA_ALG_ECDSA(PSA_ALG_SHA_256);
    const uint8_t hash[1] = {'H'};
    const uint8_t signature[1] = {'S'};

    mock_verify_data.return_value = mock_verify_return_value;
    memset( &driver, 0, sizeof( driver ) );
    memset( &key_management, 0, sizeof( key_management ) );
    memset( &asymmetric, 0, sizeof( asymmetric ) );

    driver.hal_version = PSA_DRV_SE_HAL_VERSION;

    driver.key_management = &key_management;
    key_management.p_import = mock_import;
    key_management.p_destroy = mock_destroy;
    key_management.p_allocate = mock_allocate;

    driver.asymmetric = &asymmetric;
    asymmetric.p_verify = mock_verify;

    PSA_ASSERT( psa_register_se_driver( location, &driver ) );
    PSA_ASSERT( psa_crypto_init( ) );

    psa_set_key_id( &attributes, id );
    psa_set_key_lifetime( &attributes, lifetime );
    psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_VERIFY_HASH );
    psa_set_key_algorithm( &attributes, algorithm );
    psa_set_key_type( &attributes, PSA_KEY_TYPE_RAW_DATA );

    PSA_ASSERT( psa_import_key( &attributes,
                                key_material, sizeof( key_material ),
                                &handle ) );

    TEST_ASSERT( psa_verify_hash( handle, algorithm,
                                  hash, sizeof( hash ),
                                  signature, sizeof( signature ) )
                 == expected_result );
    TEST_ASSERT( mock_verify_data.called == 1 );

    PSA_ASSERT( psa_destroy_key( handle ) );
    TEST_ASSERT( mock_destroy_data.called == 1 );

exit:
    PSA_DONE( );
    mock_teardown( );
}
/* END_CASE */
