diff options
author | Martin Schanzenbach <schanzen@gnunet.org> | 2024-04-29 15:59:23 +0200 |
---|---|---|
committer | Martin Schanzenbach <schanzen@gnunet.org> | 2024-04-29 15:59:23 +0200 |
commit | 7e43187c78bdae919861c44b03454db61f46370a (patch) | |
tree | 0b5b319eb74ffdaeb439549c00d870785a4a8d6c | |
parent | 44c3fa30b9250ad4875587018bab5362cc254f22 (diff) | |
download | gnunet-7e43187c78bdae919861c44b03454db61f46370a.tar.gz gnunet-7e43187c78bdae919861c44b03454db61f46370a.zip |
RECLAIM: Fix OIDC implementation for new API (WIP)
m--------- | contrib/gana | 0 | ||||
m--------- | contrib/handbook | 0 | ||||
-rw-r--r-- | src/service/rest/oidc_helper.c | 13 | ||||
-rw-r--r-- | src/service/rest/oidc_helper.h | 3 | ||||
-rw-r--r-- | src/service/rest/openid_plugin.c | 55 |
5 files changed, 49 insertions, 22 deletions
diff --git a/contrib/gana b/contrib/gana | |||
Subproject d505fecdf8f1339f4115f10f1ae236da7cfea0e | Subproject 53d0992890e1ebb8f8c6bd747533abe157baec6 | ||
diff --git a/contrib/handbook b/contrib/handbook | |||
Subproject 7d66dc1695829f2511f8e8ecc227a64d73d1562 | Subproject c309e416984fc76e4b39adcbd4e8a602d94b198 | ||
diff --git a/src/service/rest/oidc_helper.c b/src/service/rest/oidc_helper.c index 15133b270..0c5a5a0d6 100644 --- a/src/service/rest/oidc_helper.c +++ b/src/service/rest/oidc_helper.c | |||
@@ -24,7 +24,6 @@ | |||
24 | * @author Martin Schanzenbach | 24 | * @author Martin Schanzenbach |
25 | * @author Tristan Schwieren | 25 | * @author Tristan Schwieren |
26 | */ | 26 | */ |
27 | #include "platform.h" | ||
28 | #include <inttypes.h> | 27 | #include <inttypes.h> |
29 | #include <jansson.h> | 28 | #include <jansson.h> |
30 | #include <jose/jose.h> | 29 | #include <jose/jose.h> |
@@ -750,6 +749,7 @@ check_code_challenge (const char *code_challenge, | |||
750 | */ | 749 | */ |
751 | int | 750 | int |
752 | OIDC_parse_authz_code (const char *rp_uri, | 751 | OIDC_parse_authz_code (const char *rp_uri, |
752 | const struct GNUNET_CRYPTO_PublicKey *cid, | ||
753 | const char *code, | 753 | const char *code, |
754 | const char *code_verifier, | 754 | const char *code_verifier, |
755 | struct GNUNET_RECLAIM_Ticket *ticket, | 755 | struct GNUNET_RECLAIM_Ticket *ticket, |
@@ -823,21 +823,12 @@ OIDC_parse_authz_code (const char *rp_uri, | |||
823 | memcpy (ticket, ¶ms->ticket, sizeof(params->ticket)); | 823 | memcpy (ticket, ¶ms->ticket, sizeof(params->ticket)); |
824 | // Signature | 824 | // Signature |
825 | // GNUNET_CRYPTO_ecdsa_key_get_public (ecdsa_priv, &ecdsa_pub); | 825 | // GNUNET_CRYPTO_ecdsa_key_get_public (ecdsa_priv, &ecdsa_pub); |
826 | if (0 != strcmp (rp_uri, ticket->rp_uri)) | ||
827 | { | ||
828 | GNUNET_free (code_payload); | ||
829 | if (NULL != *nonce_str) | ||
830 | GNUNET_free (*nonce_str); | ||
831 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
832 | "Audience in ticket does not match client!\n"); | ||
833 | return GNUNET_SYSERR; | ||
834 | } | ||
835 | if (GNUNET_OK != | 826 | if (GNUNET_OK != |
836 | GNUNET_CRYPTO_signature_verify_ ( | 827 | GNUNET_CRYPTO_signature_verify_ ( |
837 | GNUNET_SIGNATURE_PURPOSE_RECLAIM_CODE_SIGN, | 828 | GNUNET_SIGNATURE_PURPOSE_RECLAIM_CODE_SIGN, |
838 | purpose, | 829 | purpose, |
839 | signature, | 830 | signature, |
840 | &(ticket->identity))) | 831 | cid)) |
841 | { | 832 | { |
842 | GNUNET_free (code_payload); | 833 | GNUNET_free (code_payload); |
843 | if (NULL != *nonce_str) | 834 | if (NULL != *nonce_str) |
diff --git a/src/service/rest/oidc_helper.h b/src/service/rest/oidc_helper.h index 08aedc2ed..3e180f673 100644 --- a/src/service/rest/oidc_helper.h +++ b/src/service/rest/oidc_helper.h | |||
@@ -27,6 +27,8 @@ | |||
27 | #ifndef JWT_H | 27 | #ifndef JWT_H |
28 | #define JWT_H | 28 | #define JWT_H |
29 | 29 | ||
30 | #include "gnunet_util_lib.h" | ||
31 | #include "gnunet_reclaim_service.h" | ||
30 | #define JWT_ALG "alg" | 32 | #define JWT_ALG "alg" |
31 | #define JWT_TYP "typ" | 33 | #define JWT_TYP "typ" |
32 | #define JWT_TYP_VALUE "jwt" | 34 | #define JWT_TYP_VALUE "jwt" |
@@ -129,6 +131,7 @@ OIDC_build_authz_code (const struct GNUNET_CRYPTO_PrivateKey *issuer, | |||
129 | */ | 131 | */ |
130 | int | 132 | int |
131 | OIDC_parse_authz_code (const char *rp_uri, | 133 | OIDC_parse_authz_code (const char *rp_uri, |
134 | const struct GNUNET_CRYPTO_PublicKey *cid, | ||
132 | const char *code, | 135 | const char *code, |
133 | const char *code_verifier, | 136 | const char *code_verifier, |
134 | struct GNUNET_RECLAIM_Ticket *ticket, | 137 | struct GNUNET_RECLAIM_Ticket *ticket, |
diff --git a/src/service/rest/openid_plugin.c b/src/service/rest/openid_plugin.c index 5fc98465a..cd3f975a4 100644 --- a/src/service/rest/openid_plugin.c +++ b/src/service/rest/openid_plugin.c | |||
@@ -34,12 +34,10 @@ | |||
34 | #include "gnunet_gns_service.h" | 34 | #include "gnunet_gns_service.h" |
35 | #include "gnunet_gnsrecord_lib.h" | 35 | #include "gnunet_gnsrecord_lib.h" |
36 | #include "gnunet_identity_service.h" | 36 | #include "gnunet_identity_service.h" |
37 | #include "gnunet_namestore_service.h" | ||
38 | #include "gnunet_reclaim_lib.h" | 37 | #include "gnunet_reclaim_lib.h" |
39 | #include "gnunet_reclaim_service.h" | 38 | #include "gnunet_reclaim_service.h" |
40 | #include "gnunet_rest_lib.h" | 39 | #include "gnunet_rest_lib.h" |
41 | #include "gnunet_rest_plugin.h" | 40 | #include "gnunet_rest_plugin.h" |
42 | #include "gnunet_signatures.h" | ||
43 | #include "microhttpd.h" | 41 | #include "microhttpd.h" |
44 | #include "oidc_helper.h" | 42 | #include "oidc_helper.h" |
45 | 43 | ||
@@ -2193,6 +2191,7 @@ token_endpoint (struct GNUNET_REST_RequestHandle *con_handle, | |||
2193 | char *oidc_jwk_path = NULL; | 2191 | char *oidc_jwk_path = NULL; |
2194 | char *oidc_directory = NULL; | 2192 | char *oidc_directory = NULL; |
2195 | char *tmp_at = NULL; | 2193 | char *tmp_at = NULL; |
2194 | char *received_cid = NULL; | ||
2196 | 2195 | ||
2197 | /* | 2196 | /* |
2198 | * Check Authorization | 2197 | * Check Authorization |
@@ -2204,6 +2203,7 @@ token_endpoint (struct GNUNET_REST_RequestHandle *con_handle, | |||
2204 | GNUNET_SCHEDULER_add_now (&do_error, handle); | 2203 | GNUNET_SCHEDULER_add_now (&do_error, handle); |
2205 | return; | 2204 | return; |
2206 | } | 2205 | } |
2206 | received_cid = get_url_parameter_copy (handle, OIDC_CLIENT_ID_KEY); | ||
2207 | 2207 | ||
2208 | /* | 2208 | /* |
2209 | * Check parameter | 2209 | * Check parameter |
@@ -2265,7 +2265,9 @@ token_endpoint (struct GNUNET_REST_RequestHandle *con_handle, | |||
2265 | } | 2265 | } |
2266 | 2266 | ||
2267 | // decode code | 2267 | // decode code |
2268 | if (GNUNET_OK != OIDC_parse_authz_code (ticket.rp_uri, code, code_verifier, &ticket, | 2268 | if (GNUNET_OK != OIDC_parse_authz_code (received_cid, &cid, code, |
2269 | code_verifier, | ||
2270 | &ticket, | ||
2269 | &cl, &pl, &nonce, | 2271 | &cl, &pl, &nonce, |
2270 | OIDC_VERIFICATION_DEFAULT)) | 2272 | OIDC_VERIFICATION_DEFAULT)) |
2271 | { | 2273 | { |
@@ -2311,6 +2313,15 @@ token_endpoint (struct GNUNET_REST_RequestHandle *con_handle, | |||
2311 | jwa = JWT_ALG_VALUE_RSA; | 2313 | jwa = JWT_ALG_VALUE_RSA; |
2312 | } | 2314 | } |
2313 | 2315 | ||
2316 | char *tmp = GNUNET_strdup (ticket.gns_name); | ||
2317 | GNUNET_assert (NULL != strtok (tmp, ".")); | ||
2318 | char *key = strtok (NULL, "."); | ||
2319 | struct GNUNET_CRYPTO_PublicKey issuer; | ||
2320 | GNUNET_assert (NULL != key); | ||
2321 | GNUNET_assert (GNUNET_OK == | ||
2322 | GNUNET_CRYPTO_public_key_from_string (key, &issuer)); | ||
2323 | GNUNET_free (tmp); | ||
2324 | |||
2314 | if (! strcmp (jwa, JWT_ALG_VALUE_RSA)) | 2325 | if (! strcmp (jwa, JWT_ALG_VALUE_RSA)) |
2315 | { | 2326 | { |
2316 | // Replace for now | 2327 | // Replace for now |
@@ -2338,8 +2349,8 @@ token_endpoint (struct GNUNET_REST_RequestHandle *con_handle, | |||
2338 | } | 2349 | } |
2339 | 2350 | ||
2340 | // Generate oidc token | 2351 | // Generate oidc token |
2341 | id_token = OIDC_generate_id_token_rsa (ticket.rp_uri, | 2352 | id_token = OIDC_generate_id_token_rsa (received_cid, |
2342 | &ticket.identity, | 2353 | &issuer, |
2343 | cl, | 2354 | cl, |
2344 | pl, | 2355 | pl, |
2345 | &expiration_time, | 2356 | &expiration_time, |
@@ -2366,8 +2377,8 @@ token_endpoint (struct GNUNET_REST_RequestHandle *con_handle, | |||
2366 | return; | 2377 | return; |
2367 | } | 2378 | } |
2368 | 2379 | ||
2369 | id_token = OIDC_generate_id_token_hmac (ticket.rp_uri, | 2380 | id_token = OIDC_generate_id_token_hmac (received_cid, |
2370 | &ticket.identity, | 2381 | &issuer, |
2371 | cl, | 2382 | cl, |
2372 | pl, | 2383 | pl, |
2373 | &expiration_time, | 2384 | &expiration_time, |
@@ -2481,7 +2492,15 @@ consume_ticket (void *cls, | |||
2481 | 2492 | ||
2482 | if (NULL == identity) | 2493 | if (NULL == identity) |
2483 | { | 2494 | { |
2484 | result_str = OIDC_generate_userinfo (&handle->ticket.identity, | 2495 | char *tmp = GNUNET_strdup (handle->ticket.gns_name); |
2496 | GNUNET_assert (NULL != strtok (tmp, ".")); | ||
2497 | char *key = strtok (NULL, "."); | ||
2498 | struct GNUNET_CRYPTO_PublicKey issuer; | ||
2499 | GNUNET_assert (NULL != key); | ||
2500 | GNUNET_assert (GNUNET_OK == | ||
2501 | GNUNET_CRYPTO_public_key_from_string (key, &issuer)); | ||
2502 | GNUNET_free (tmp); | ||
2503 | result_str = OIDC_generate_userinfo (&issuer, | ||
2485 | handle->attr_userinfo_list, | 2504 | handle->attr_userinfo_list, |
2486 | handle->presentations); | 2505 | handle->presentations); |
2487 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Userinfo: %s\n", result_str); | 2506 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Userinfo: %s\n", result_str); |
@@ -2538,11 +2557,12 @@ consume_fail (void *cls) | |||
2538 | struct GNUNET_RECLAIM_AttributeList *cl = NULL; | 2557 | struct GNUNET_RECLAIM_AttributeList *cl = NULL; |
2539 | struct GNUNET_RECLAIM_PresentationList *pl = NULL; | 2558 | struct GNUNET_RECLAIM_PresentationList *pl = NULL; |
2540 | struct GNUNET_RECLAIM_Ticket ticket; | 2559 | struct GNUNET_RECLAIM_Ticket ticket; |
2560 | struct GNUNET_CRYPTO_PublicKey cid; | ||
2541 | struct MHD_Response *resp; | 2561 | struct MHD_Response *resp; |
2542 | char *nonce; | 2562 | char *nonce; |
2543 | char *cached_code; | 2563 | char *cached_code; |
2544 | char *result_str; | 2564 | char *result_str; |
2545 | 2565 | char *received_cid; | |
2546 | 2566 | ||
2547 | handle->consume_timeout_op = NULL; | 2567 | handle->consume_timeout_op = NULL; |
2548 | if (NULL != handle->idp_op) | 2568 | if (NULL != handle->idp_op) |
@@ -2571,9 +2591,14 @@ consume_fail (void *cls) | |||
2571 | GNUNET_CONTAINER_multihashmap_remove (oidc_code_cache, | 2591 | GNUNET_CONTAINER_multihashmap_remove (oidc_code_cache, |
2572 | &cache_key, | 2592 | &cache_key, |
2573 | cached_code)); | 2593 | cached_code)); |
2594 | received_cid = get_url_parameter_copy (handle, OIDC_CLIENT_ID_KEY); | ||
2595 | GNUNET_STRINGS_string_to_data (received_cid, | ||
2596 | strlen (received_cid), | ||
2597 | &cid, | ||
2598 | sizeof(struct GNUNET_CRYPTO_PublicKey)); | ||
2574 | 2599 | ||
2575 | // decode code | 2600 | // decode code |
2576 | if (GNUNET_OK != OIDC_parse_authz_code (handle->ticket.rp_uri, | 2601 | if (GNUNET_OK != OIDC_parse_authz_code (received_cid, &cid, |
2577 | cached_code, NULL, &ticket, | 2602 | cached_code, NULL, &ticket, |
2578 | &cl, &pl, &nonce, | 2603 | &cl, &pl, &nonce, |
2579 | OIDC_VERIFICATION_NO_CODE_VERIFIER)) | 2604 | OIDC_VERIFICATION_NO_CODE_VERIFIER)) |
@@ -2590,7 +2615,15 @@ consume_fail (void *cls) | |||
2590 | 2615 | ||
2591 | GNUNET_free (cached_code); | 2616 | GNUNET_free (cached_code); |
2592 | 2617 | ||
2593 | result_str = OIDC_generate_userinfo (&handle->ticket.identity, | 2618 | char *tmp = GNUNET_strdup (handle->ticket.gns_name); |
2619 | GNUNET_assert (NULL != strtok (tmp, ".")); | ||
2620 | char *key = strtok (NULL, "."); | ||
2621 | struct GNUNET_CRYPTO_PublicKey issuer; | ||
2622 | GNUNET_assert (NULL != key); | ||
2623 | GNUNET_assert (GNUNET_OK == | ||
2624 | GNUNET_CRYPTO_public_key_from_string (key, &issuer)); | ||
2625 | GNUNET_free (tmp); | ||
2626 | result_str = OIDC_generate_userinfo (&issuer, | ||
2594 | cl, | 2627 | cl, |
2595 | pl); | 2628 | pl); |
2596 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Userinfo: %s\n", result_str); | 2629 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Userinfo: %s\n", result_str); |