blob: 22465b5a642c278cd4e86b7d8a80d7263c6d2ab8 [file] [edit]
/* Public domain, no copyright. Use at your own risk. */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "jwt_tests.h"
/* @rfc{7516,11.4} Key-usage gating is exercised through the public
* jwe_builder_setkey / jwe_checker_setkey, which call the internal
* jwe_key_usage_check. The builder is the producer (wrap/encrypt), the
* checker the consumer (unwrap/decrypt). */
START_TEST(oct_no_restrictions)
{
jwe_builder_auto_t *builder = NULL;
int ret;
SET_OPS();
/* oct_key_256.json has no "use"/"key_ops" -> usable for A*KW/dir. */
read_json("oct_key_256.json");
builder = jwe_builder_new();
ck_assert_ptr_nonnull(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_A256KW, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 0);
ret = jwe_builder_setkey(builder, JWE_ALG_DIR, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 0);
free_key();
}
END_TEST
START_TEST(oct_use_enc)
{
jwe_builder_auto_t *builder = NULL;
jwe_checker_auto_t *checker = NULL;
int ret;
SET_OPS();
/* use:enc, key_ops:[wrapKey,unwrapKey] */
read_json("oct_key_256_enc.json");
builder = jwe_builder_new();
ck_assert_ptr_nonnull(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_A256KW, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 0);
checker = jwe_checker_new();
ck_assert_ptr_nonnull(checker);
ret = jwe_checker_setkey(checker, JWE_ALG_A256KW, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 0);
free_key();
}
END_TEST
START_TEST(oct_use_sig_rejected)
{
jwe_builder_auto_t *builder = NULL;
int ret;
SET_OPS();
/* use:sig must never be usable for JWE. */
read_json("oct_key_256_sig.json");
builder = jwe_builder_new();
ck_assert_ptr_nonnull(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_A256KW, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 1);
ck_assert_int_eq(jwe_builder_error(builder), 1);
ck_assert_str_eq(jwe_builder_error_msg(builder),
"Key marked for signing cannot be used for JWE");
free_key();
}
END_TEST
START_TEST(oct_key_ops_direction)
{
jwe_builder_auto_t *builder = NULL;
jwe_checker_auto_t *checker = NULL;
int ret;
SET_OPS();
/* key_ops:[wrapKey] only: builder (wrap) OK, checker (unwrap) rejected. */
read_json("oct_key_256_wrap_only.json");
builder = jwe_builder_new();
ck_assert_ptr_nonnull(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_A256KW, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 0);
checker = jwe_checker_new();
ck_assert_ptr_nonnull(checker);
ret = jwe_checker_setkey(checker, JWE_ALG_A256KW, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 1);
ck_assert_str_eq(jwe_checker_error_msg(checker),
"Key does not permit the required JWE operation");
free_key();
}
END_TEST
START_TEST(wrong_kty_rejected)
{
jwe_builder_auto_t *builder = NULL;
int ret;
SET_OPS();
/* An RSA key cannot be used for AES Key Wrap (needs oct). */
read_json("rsa_key_2048.json");
builder = jwe_builder_new();
ck_assert_ptr_nonnull(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_A256KW, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 1);
ck_assert_str_eq(jwe_builder_error_msg(builder),
"Key type does not match JWE algorithm");
free_key();
}
END_TEST
START_TEST(rsa_oaep_kty)
{
jwe_builder_auto_t *builder = NULL;
int ret;
SET_OPS();
/* use:enc RSA key is valid for RSA-OAEP. */
read_json("rsa_key_2048_enc.json");
builder = jwe_builder_new();
ck_assert_ptr_nonnull(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_RSA_OAEP, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 0);
ret = jwe_builder_setkey(builder, JWE_ALG_RSA_OAEP_256, JWE_ENC_A128GCM,
g_item);
ck_assert_int_eq(ret, 0);
free_key();
}
END_TEST
START_TEST(rsa_sig_rejected)
{
jwe_builder_auto_t *builder = NULL;
int ret;
SET_OPS();
/* The stock RSA test key is use:sig and must be rejected for JWE. */
read_json("rsa_key_2048.json");
builder = jwe_builder_new();
ck_assert_ptr_nonnull(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_RSA_OAEP, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 1);
ck_assert_str_eq(jwe_builder_error_msg(builder),
"Key marked for signing cannot be used for JWE");
free_key();
/* An oct key cannot be used for RSA-OAEP regardless of usage. */
read_json("oct_key_256.json");
jwe_builder_error_clear(builder);
ret = jwe_builder_setkey(builder, JWE_ALG_RSA_OAEP, JWE_ENC_A256GCM,
g_item);
ck_assert_int_eq(ret, 1);
ck_assert_str_eq(jwe_builder_error_msg(builder),
"Key type does not match JWE algorithm");
free_key();
}
END_TEST
static Suite *libjwt_suite(const char *title)
{
Suite *s;
TCase *tc_core;
int i = ARRAY_SIZE(jwt_test_ops);
s = suite_create(title);
tc_core = tcase_create("JWE Key Usage");
tcase_add_loop_test(tc_core, oct_no_restrictions, 0, i);
tcase_add_loop_test(tc_core, oct_use_enc, 0, i);
tcase_add_loop_test(tc_core, oct_use_sig_rejected, 0, i);
tcase_add_loop_test(tc_core, oct_key_ops_direction, 0, i);
tcase_add_loop_test(tc_core, wrong_kty_rejected, 0, i);
tcase_add_loop_test(tc_core, rsa_oaep_kty, 0, i);
tcase_add_loop_test(tc_core, rsa_sig_rejected, 0, i);
tcase_set_timeout(tc_core, 30);
suite_add_tcase(s, tc_core);
return s;
}
int main(void)
{
JWT_TEST_MAIN("LibJWT JWE Key Usage");
}