From 647ae694cc9f1aef44e792b96676b115231e8898 Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Mon, 1 May 2023 19:37:29 +0200 Subject: -fix uninitialized variable and memory leak --- src/kyclogic/plugin_kyclogic_oauth2.c | 120 ++++++++++++++++++---------------- 1 file changed, 65 insertions(+), 55 deletions(-) (limited to 'src/kyclogic') diff --git a/src/kyclogic/plugin_kyclogic_oauth2.c b/src/kyclogic/plugin_kyclogic_oauth2.c index 228525e2..c72b04b7 100644 --- a/src/kyclogic/plugin_kyclogic_oauth2.c +++ b/src/kyclogic/plugin_kyclogic_oauth2.c @@ -490,8 +490,6 @@ initiate_task (void *cls) struct PluginState *ps = pd->ps; char *hps; char *url; - char *redirect_uri; - char *redirect_uri_encoded; char legi_s[42]; ih->task = NULL; @@ -501,19 +499,27 @@ initiate_task (void *cls) (unsigned long long) ih->legitimization_uuid); hps = GNUNET_STRINGS_data_to_string_alloc (&ih->h_payto, sizeof (ih->h_payto)); - GNUNET_asprintf (&redirect_uri, - "%skyc-proof/%s?state=%s", - ps->exchange_base_url, - pd->section, - hps); - redirect_uri_encoded = TALER_urlencode (redirect_uri); - GNUNET_free (redirect_uri); - GNUNET_asprintf (&url, - "%s?response_type=code&client_id=%s&redirect_uri=%s", - pd->login_url, - pd->client_id, - redirect_uri_encoded); - GNUNET_free (redirect_uri_encoded); + { + char *redirect_uri_encoded; + + { + char *redirect_uri; + + GNUNET_asprintf (&redirect_uri, + "%skyc-proof/%s?state=%s", + ps->exchange_base_url, + pd->section, + hps); + redirect_uri_encoded = TALER_urlencode (redirect_uri); + GNUNET_free (redirect_uri); + } + GNUNET_asprintf (&url, + "%s?response_type=code&client_id=%s&redirect_uri=%s", + pd->login_url, + pd->client_id, + redirect_uri_encoded); + GNUNET_free (redirect_uri_encoded); + } /* FIXME-API: why do we *redirect* the client here, instead of making the HTTP request *ourselves* and forwarding the response? This prevents us @@ -582,6 +588,37 @@ oauth2_initiate_cancel (struct TALER_KYCLOGIC_InitiateHandle *ih) } +/** + * Cancel KYC proof. + * + * @param[in] ph handle of operation to cancel + */ +static void +oauth2_proof_cancel (struct TALER_KYCLOGIC_ProofHandle *ph) +{ + if (NULL != ph->task) + { + GNUNET_SCHEDULER_cancel (ph->task); + ph->task = NULL; + } + if (NULL != ph->job) + { + GNUNET_CURL_job_cancel (ph->job); + ph->job = NULL; + } + if (NULL != ph->response) + { + MHD_destroy_response (ph->response); + ph->response = NULL; + } + GNUNET_free (ph->provider_user_id); + if (NULL != ph->attributes) + json_decref (ph->attributes); + GNUNET_free (ph->post_body); + GNUNET_free (ph); +} + + /** * Function called to asynchronously return the final * result to the callback. @@ -602,10 +639,8 @@ return_proof_response (void *cls) ph->attributes, ph->http_status, ph->response); - GNUNET_free (ph->provider_user_id); - if (NULL != ph->attributes) - json_decref (ph->attributes); - GNUNET_free (ph); + ph->response = NULL; /*Ownership passed to 'ph->cb'!*/ + oauth2_proof_cancel (ph); } @@ -1101,7 +1136,6 @@ oauth2_proof (void *cls, 1)); { char *client_id; - char *redirect_uri; char *client_secret; char *authorization_code; char *redirect_uri_encoded; @@ -1109,13 +1143,17 @@ oauth2_proof (void *cls, hps = GNUNET_STRINGS_data_to_string_alloc (&ph->h_payto, sizeof (ph->h_payto)); - GNUNET_asprintf (&redirect_uri, - "%skyc-proof/%s?state=%s", - ps->exchange_base_url, - pd->section, - hps); - redirect_uri_encoded = TALER_urlencode (redirect_uri); - GNUNET_free (redirect_uri); + { + char *redirect_uri; + + GNUNET_asprintf (&redirect_uri, + "%skyc-proof/%s?state=%s", + ps->exchange_base_url, + pd->section, + hps); + redirect_uri_encoded = TALER_urlencode (redirect_uri); + GNUNET_free (redirect_uri); + } GNUNET_assert (NULL != redirect_uri_encoded); client_id = curl_easy_escape (ph->eh, pd->client_id, @@ -1164,34 +1202,6 @@ oauth2_proof (void *cls, } -/** - * Cancel KYC proof. - * - * @param[in] ph handle of operation to cancel - */ -static void -oauth2_proof_cancel (struct TALER_KYCLOGIC_ProofHandle *ph) -{ - if (NULL != ph->task) - { - GNUNET_SCHEDULER_cancel (ph->task); - ph->task = NULL; - } - if (NULL != ph->job) - { - GNUNET_CURL_job_cancel (ph->job); - ph->job = NULL; - } - if (NULL != ph->response) - { - MHD_destroy_response (ph->response); - ph->response = NULL; - } - GNUNET_free (ph->post_body); - GNUNET_free (ph); -} - - /** * Function to asynchronously return the 404 not found * page for the webhook. -- cgit v1.2.3 From 3ebd0a70b2bba2e64615c0973477a610e117c97a Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Wed, 10 May 2023 00:57:04 +0200 Subject: fix 0-length VLAs --- src/kyclogic/kyclogic_api.c | 9 +++++---- src/lib/exchange_api_handle.c | 16 ++++++++-------- 2 files changed, 13 insertions(+), 12 deletions(-) (limited to 'src/kyclogic') diff --git a/src/kyclogic/kyclogic_api.c b/src/kyclogic/kyclogic_api.c index 0ef1295e..65f3f3ba 100644 --- a/src/kyclogic/kyclogic_api.c +++ b/src/kyclogic/kyclogic_api.c @@ -780,10 +780,11 @@ TALER_KYCLOGIC_kyc_init (const struct GNUNET_CONFIGURATION_Handle *cfg) TALER_KYCLOGIC_kyc_done (); return GNUNET_SYSERR; } - qsort (kyc_triggers, - num_kyc_triggers, - sizeof (struct TALER_KYCLOGIC_KycTrigger *), - &sort_by_timeframe); + if (0 != num_kyc_triggers) + qsort (kyc_triggers, + num_kyc_triggers, + sizeof (struct TALER_KYCLOGIC_KycTrigger *), + &sort_by_timeframe); return GNUNET_OK; } diff --git a/src/lib/exchange_api_handle.c b/src/lib/exchange_api_handle.c index f6a5e979..0e804630 100644 --- a/src/lib/exchange_api_handle.c +++ b/src/lib/exchange_api_handle.c @@ -1366,10 +1366,10 @@ keys_completed_cb (void *cls, kd.num_denom_keys); /* First make a shallow copy, we then need another pass for the RSA key... */ - memcpy (kd.denom_keys, - kd_old.denom_keys, - kd_old.num_denom_keys * sizeof (struct - TALER_EXCHANGE_DenomPublicKey)); + GNUNET_memcpy (kd.denom_keys, + kd_old.denom_keys, + kd_old.num_denom_keys * sizeof (struct + TALER_EXCHANGE_DenomPublicKey)); for (unsigned int i = 0; idenom_keys, anew->num_denom_keys, aold->num_denom_keys); - memcpy (anew->denom_keys, - aold->denom_keys, - aold->num_denom_keys - * sizeof (struct TALER_EXCHANGE_AuditorDenominationInfo)); + GNUNET_memcpy (anew->denom_keys, + aold->denom_keys, + aold->num_denom_keys + * sizeof (struct TALER_EXCHANGE_AuditorDenominationInfo)); } /* Old auditors got just copied into new ones. */ -- cgit v1.2.3 From c014acf3c4ccf03109b0141d6b68d4f464464e19 Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Wed, 10 May 2023 01:01:37 +0200 Subject: always use GNUNET_memcpy --- src/auditor/taler-helper-auditor-coins.c | 6 +-- src/auditor/taler-helper-auditor-wire.c | 24 ++++----- src/bank-lib/bank_api_transfer.c | 12 ++--- src/bank-lib/fakebank.c | 6 +-- src/exchange/taler-exchange-closer.c | 8 +-- src/exchange/taler-exchange-httpd.c | 6 +-- src/exchange/taler-exchange-transfer.c | 6 +-- src/exchangedb/bench_db.c | 12 ++--- src/exchangedb/pg_lookup_records_by_table.c | 6 +-- src/kyclogic/taler-exchange-kyc-tester.c | 6 +-- src/pq/pq_query_helper.c | 84 ++++++++++++++--------------- src/pq/pq_result_helper.c | 66 +++++++++++------------ src/templating/mustach.c | 6 +-- src/testing/test_bank_api_twisted.c | 6 +-- src/testing/testing_api_cmd_batch.c | 6 +-- src/testing/testing_api_loop.c | 6 +-- src/util/amount.c | 30 +++++------ src/util/crypto_confirmation.c | 6 +-- src/util/crypto_contract.c | 42 +++++++-------- src/util/crypto_helper_esign.c | 6 +-- src/util/crypto_helper_rsa.c | 12 ++--- src/util/exchange_signatures.c | 16 +++--- src/util/iban.c | 6 +-- src/util/payto.c | 6 +-- src/util/taler-exchange-secmod-cs.c | 24 ++++----- src/util/taler-exchange-secmod-eddsa.c | 6 +-- src/util/taler-exchange-secmod-rsa.c | 36 ++++++------- src/util/util.c | 6 +-- 28 files changed, 231 insertions(+), 231 deletions(-) (limited to 'src/kyclogic') diff --git a/src/auditor/taler-helper-auditor-coins.c b/src/auditor/taler-helper-auditor-coins.c index 7637e463..8edbcf29 100644 --- a/src/auditor/taler-helper-auditor-coins.c +++ b/src/auditor/taler-helper-auditor-coins.c @@ -172,9 +172,9 @@ coin_history_index (const struct TALER_CoinSpendPublicKeyP *coin_pub) { uint32_t i; - memcpy (&i, - coin_pub, - sizeof (i)); + GNUNET_memcpy (&i, + coin_pub, + sizeof (i)); return i % MAX_COIN_HISTORIES; } diff --git a/src/auditor/taler-helper-auditor-wire.c b/src/auditor/taler-helper-auditor-wire.c index 8615c439..bfc465b0 100644 --- a/src/auditor/taler-helper-auditor-wire.c +++ b/src/auditor/taler-helper-auditor-wire.c @@ -674,12 +674,12 @@ hash_rc (const char *receiver_account, size_t slen = strlen (receiver_account); char buf[sizeof (struct TALER_WireTransferIdentifierRawP) + slen]; - memcpy (buf, - wtid, - sizeof (*wtid)); - memcpy (&buf[sizeof (*wtid)], - receiver_account, - slen); + GNUNET_memcpy (buf, + wtid, + sizeof (*wtid)); + GNUNET_memcpy (&buf[sizeof (*wtid)], + receiver_account, + slen); GNUNET_CRYPTO_hash (buf, sizeof (buf), key); @@ -1504,9 +1504,9 @@ history_debit_cb (void *cls, roi->details.execution_date = dd->execution_date; roi->details.wtid = dd->wtid; roi->details.credit_account_uri = (const char *) &roi[1]; - memcpy (&roi[1], - dd->credit_account_uri, - slen); + GNUNET_memcpy (&roi[1], + dd->credit_account_uri, + slen); if (GNUNET_OK != GNUNET_CONTAINER_multihashmap_put (out_map, &roi->subject_hash, @@ -1678,9 +1678,9 @@ reserve_in_cb (void *cls, rii->details.execution_date = execution_date; rii->details.reserve_pub = *reserve_pub; rii->details.debit_account_uri = (const char *) &rii[1]; - memcpy (&rii[1], - sender_account_details, - slen); + GNUNET_memcpy (&rii[1], + sender_account_details, + slen); GNUNET_CRYPTO_hash (&wire_reference, sizeof (uint64_t), &rii->row_off_hash); diff --git a/src/bank-lib/bank_api_transfer.c b/src/bank-lib/bank_api_transfer.c index 3b50018d..94d8c6b6 100644 --- a/src/bank-lib/bank_api_transfer.c +++ b/src/bank-lib/bank_api_transfer.c @@ -99,12 +99,12 @@ TALER_BANK_prepare_transfer ( wp->account_len = htonl ((uint32_t) d_len); wp->exchange_url_len = htonl ((uint32_t) u_len); end = (char *) &wp[1]; - memcpy (end, - destination_account_payto_uri, - d_len); - memcpy (end + d_len, - exchange_base_url, - u_len); + GNUNET_memcpy (end, + destination_account_payto_uri, + d_len); + GNUNET_memcpy (end + d_len, + exchange_base_url, + u_len); *buf = (char *) wp; } diff --git a/src/bank-lib/fakebank.c b/src/bank-lib/fakebank.c index 60492e50..c916ad70 100644 --- a/src/bank-lib/fakebank.c +++ b/src/bank-lib/fakebank.c @@ -1389,9 +1389,9 @@ make_transfer ( if (NULL != timestamp) *timestamp = t->date; t->type = T_DEBIT; - memcpy (t->subject.debit.exchange_base_url, - exchange_base_url, - url_len); + GNUNET_memcpy (t->subject.debit.exchange_base_url, + exchange_base_url, + url_len); t->subject.debit.wtid = *subject; if (NULL == request_uid) GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_NONCE, diff --git a/src/exchange/taler-exchange-closer.c b/src/exchange/taler-exchange-closer.c index 41c6436a..63a98bd0 100644 --- a/src/exchange/taler-exchange-closer.c +++ b/src/exchange/taler-exchange-closer.c @@ -312,10 +312,10 @@ expired_reserve_cb (void *cls, memset (&wtid, 0, sizeof (wtid)); - memcpy (&wtid, - reserve_pub, - GNUNET_MIN (sizeof (wtid), - sizeof (*reserve_pub))); + GNUNET_memcpy (&wtid, + reserve_pub, + GNUNET_MIN (sizeof (wtid), + sizeof (*reserve_pub))); qs = db_plugin->insert_reserve_closed (db_plugin->cls, reserve_pub, now, diff --git a/src/exchange/taler-exchange-httpd.c b/src/exchange/taler-exchange-httpd.c index 97cf54c8..6c6398bc 100644 --- a/src/exchange/taler-exchange-httpd.c +++ b/src/exchange/taler-exchange-httpd.c @@ -932,9 +932,9 @@ proceed_with_handler (struct TEH_RequestContext *rc, /* Parse command-line arguments */ /* make a copy of 'url' because 'strtok_r()' will modify */ - memcpy (d, - url, - ulen); + GNUNET_memcpy (d, + url, + ulen); i = 0; args[i++] = strtok_r (d, "/", &sp); while ( (NULL != args[i - 1]) && diff --git a/src/exchange/taler-exchange-transfer.c b/src/exchange/taler-exchange-transfer.c index 5a4aace9..255fe76a 100644 --- a/src/exchange/taler-exchange-transfer.c +++ b/src/exchange/taler-exchange-transfer.c @@ -563,9 +563,9 @@ wire_prepare_cb (void *cls, } wpd = GNUNET_malloc (sizeof (struct WirePrepareData) + buf_size); - memcpy (&wpd[1], - buf, - buf_size); + GNUNET_memcpy (&wpd[1], + buf, + buf_size); wpd->buf_size = buf_size; wpd->row_id = rowid; GNUNET_CONTAINER_DLL_insert (wpd_head, diff --git a/src/exchangedb/bench_db.c b/src/exchangedb/bench_db.c index a85834d1..302d2306 100644 --- a/src/exchangedb/bench_db.c +++ b/src/exchangedb/bench_db.c @@ -169,9 +169,9 @@ bem_insert (struct GNUNET_PQ_Context *conn, GNUNET_CRYPTO_hash (&b, sizeof (b), &hc); - memcpy (&ihc, - &hc, - sizeof (ihc)); + GNUNET_memcpy (&ihc, + &hc, + sizeof (ihc)); { struct GNUNET_PQ_QueryParam params[] = { GNUNET_PQ_query_param_auto_from_type (&hc), @@ -265,9 +265,9 @@ bem_select (struct GNUNET_PQ_Context *conn, GNUNET_CRYPTO_hash (&b, sizeof (b), &hc); - memcpy (&ihc, - &hc, - sizeof (ihc)); + GNUNET_memcpy (&ihc, + &hc, + sizeof (ihc)); { struct GNUNET_PQ_QueryParam params[] = { GNUNET_PQ_query_param_uint32 (&ihc), diff --git a/src/exchangedb/pg_lookup_records_by_table.c b/src/exchangedb/pg_lookup_records_by_table.c index efa0fec5..534e9a1d 100644 --- a/src/exchangedb/pg_lookup_records_by_table.c +++ b/src/exchangedb/pg_lookup_records_by_table.c @@ -1118,9 +1118,9 @@ lrbt_cb_table_refresh_transfer_keys (void *cls, ctx->error = true; return; } - memcpy (&td.details.refresh_transfer_keys.tprivs[0], - tpriv, - tpriv_size); + GNUNET_memcpy (&td.details.refresh_transfer_keys.tprivs[0], + tpriv, + tpriv_size); ctx->cb (ctx->cb_cls, &td); GNUNET_PQ_cleanup_result (rs); diff --git a/src/kyclogic/taler-exchange-kyc-tester.c b/src/kyclogic/taler-exchange-kyc-tester.c index 652d498c..c2efafd7 100644 --- a/src/kyclogic/taler-exchange-kyc-tester.c +++ b/src/kyclogic/taler-exchange-kyc-tester.c @@ -990,9 +990,9 @@ proceed_with_handler (struct TEKT_RequestContext *rc, /* Parse command-line arguments */ /* make a copy of 'url' because 'strtok_r()' will modify */ - memcpy (d, - url, - ulen); + GNUNET_memcpy (d, + url, + ulen); i = 0; args[i++] = strtok_r (d, "/", &sp); while ( (NULL != args[i - 1]) && diff --git a/src/pq/pq_query_helper.c b/src/pq/pq_query_helper.c index 1db608ed..2904b63f 100644 --- a/src/pq/pq_query_helper.c +++ b/src/pq/pq_query_helper.c @@ -202,21 +202,21 @@ qconv_denom_pub (void *cls, } len = tlen + sizeof (be); buf = GNUNET_malloc (len); - memcpy (buf, - be, - sizeof (be)); + GNUNET_memcpy (buf, + be, + sizeof (be)); switch (denom_pub->cipher) { case TALER_DENOMINATION_RSA: - memcpy (&buf[sizeof (be)], - tbuf, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + tbuf, + tlen); GNUNET_free (tbuf); break; case TALER_DENOMINATION_CS: - memcpy (&buf[sizeof (be)], - &denom_pub->details.cs_public_key, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + &denom_pub->details.cs_public_key, + tlen); break; default: GNUNET_assert (0); @@ -298,21 +298,21 @@ qconv_denom_sig (void *cls, } len = tlen + sizeof (be); buf = GNUNET_malloc (len); - memcpy (buf, - &be, - sizeof (be)); + GNUNET_memcpy (buf, + &be, + sizeof (be)); switch (denom_sig->cipher) { case TALER_DENOMINATION_RSA: - memcpy (&buf[sizeof (be)], - tbuf, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + tbuf, + tlen); GNUNET_free (tbuf); break; case TALER_DENOMINATION_CS: - memcpy (&buf[sizeof (be)], - &denom_sig->details.cs_signature, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + &denom_sig->details.cs_signature, + tlen); break; default: GNUNET_assert (0); @@ -394,21 +394,21 @@ qconv_blinded_denom_sig (void *cls, } len = tlen + sizeof (be); buf = GNUNET_malloc (len); - memcpy (buf, - &be, - sizeof (be)); + GNUNET_memcpy (buf, + &be, + sizeof (be)); switch (denom_sig->cipher) { case TALER_DENOMINATION_RSA: - memcpy (&buf[sizeof (be)], - tbuf, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + tbuf, + tlen); GNUNET_free (tbuf); break; case TALER_DENOMINATION_CS: - memcpy (&buf[sizeof (be)], - &denom_sig->details.blinded_cs_answer, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + &denom_sig->details.blinded_cs_answer, + tlen); break; default: GNUNET_assert (0); @@ -487,20 +487,20 @@ qconv_blinded_planchet (void *cls, } len = tlen + sizeof (be); buf = GNUNET_malloc (len); - memcpy (buf, - &be, - sizeof (be)); + GNUNET_memcpy (buf, + &be, + sizeof (be)); switch (bp->cipher) { case TALER_DENOMINATION_RSA: - memcpy (&buf[sizeof (be)], - bp->details.rsa_blinded_planchet.blinded_msg, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + bp->details.rsa_blinded_planchet.blinded_msg, + tlen); break; case TALER_DENOMINATION_CS: - memcpy (&buf[sizeof (be)], - &bp->details.cs_blinded_planchet, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + &bp->details.cs_blinded_planchet, + tlen); break; default: GNUNET_assert (0); @@ -578,17 +578,17 @@ qconv_exchange_withdraw_values (void *cls, } len = tlen + sizeof (be); buf = GNUNET_malloc (len); - memcpy (buf, - &be, - sizeof (be)); + GNUNET_memcpy (buf, + &be, + sizeof (be)); switch (alg_values->cipher) { case TALER_DENOMINATION_RSA: break; case TALER_DENOMINATION_CS: - memcpy (&buf[sizeof (be)], - &alg_values->details.cs_values, - tlen); + GNUNET_memcpy (&buf[sizeof (be)], + &alg_values->details.cs_values, + tlen); break; default: GNUNET_assert (0); diff --git a/src/pq/pq_result_helper.c b/src/pq/pq_result_helper.c index 139cf1cb..9441412d 100644 --- a/src/pq/pq_result_helper.c +++ b/src/pq/pq_result_helper.c @@ -113,9 +113,9 @@ extract_amount_nbo_helper (PGresult *result, } len = GNUNET_MIN (TALER_CURRENCY_LEN - 1, strlen (currency)); - memcpy (r_amount_nbo->currency, - currency, - len); + GNUNET_memcpy (r_amount_nbo->currency, + currency, + len); return GNUNET_OK; } @@ -420,9 +420,9 @@ extract_denom_pub (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (be, - res, - sizeof (be)); + GNUNET_memcpy (be, + res, + sizeof (be)); res += sizeof (be); len -= sizeof (be); pk->cipher = ntohl (be[0]); @@ -445,9 +445,9 @@ extract_denom_pub (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&pk->details.cs_public_key, - res, - len); + GNUNET_memcpy (&pk->details.cs_public_key, + res, + len); return GNUNET_OK; default: GNUNET_break (0); @@ -543,9 +543,9 @@ extract_denom_sig (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&be, - res, - sizeof (be)); + GNUNET_memcpy (&be, + res, + sizeof (be)); if (0x00 != ntohl (be[1])) { GNUNET_break (0); @@ -572,9 +572,9 @@ extract_denom_sig (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&sig->details.cs_signature, - res, - len); + GNUNET_memcpy (&sig->details.cs_signature, + res, + len); return GNUNET_OK; default: GNUNET_break (0); @@ -670,9 +670,9 @@ extract_blinded_denom_sig (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&be, - res, - sizeof (be)); + GNUNET_memcpy (&be, + res, + sizeof (be)); if (0x01 != ntohl (be[1])) /* magic marker: blinded */ { GNUNET_break (0); @@ -699,9 +699,9 @@ extract_blinded_denom_sig (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&sig->details.blinded_cs_answer, - res, - len); + GNUNET_memcpy (&sig->details.blinded_cs_answer, + res, + len); return GNUNET_OK; default: GNUNET_break (0); @@ -798,9 +798,9 @@ extract_blinded_planchet (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&be, - res, - sizeof (be)); + GNUNET_memcpy (&be, + res, + sizeof (be)); if (0x0100 != ntohl (be[1])) /* magic marker: blinded */ { GNUNET_break (0); @@ -824,9 +824,9 @@ extract_blinded_planchet (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&bp->details.cs_blinded_planchet, - res, - len); + GNUNET_memcpy (&bp->details.cs_blinded_planchet, + res, + len); return GNUNET_OK; default: GNUNET_break (0); @@ -923,9 +923,9 @@ extract_exchange_withdraw_values (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&be, - res, - sizeof (be)); + GNUNET_memcpy (&be, + res, + sizeof (be)); if (0x010000 != ntohl (be[1])) /* magic marker: EWV */ { GNUNET_break (0); @@ -949,9 +949,9 @@ extract_exchange_withdraw_values (void *cls, GNUNET_break (0); return GNUNET_SYSERR; } - memcpy (&alg_values->details.cs_values, - res, - len); + GNUNET_memcpy (&alg_values->details.cs_values, + res, + len); return GNUNET_OK; default: GNUNET_break (0); diff --git a/src/templating/mustach.c b/src/templating/mustach.c index caa80dcc..9797c533 100644 --- a/src/templating/mustach.c +++ b/src/templating/mustach.c @@ -297,7 +297,7 @@ static int process(const char *template, struct iwrap *iwrap, FILE *file, const #endif if (len > MUSTACH_MAX_LENGTH) return MUSTACH_ERROR_TAG_TOO_LONG; - memcpy(name, beg, len); + GNUNET_memcpy(name, beg, len); name[len] = 0; break; } @@ -317,7 +317,7 @@ static int process(const char *template, struct iwrap *iwrap, FILE *file, const return MUSTACH_ERROR_BAD_SEPARATORS; oplen = l; tmp = alloca(oplen + 1); - memcpy(tmp, beg, oplen); + GNUNET_memcpy(tmp, beg, oplen); tmp[oplen] = 0; opstr = tmp; while (l < len && isspace(beg[l])) l++; @@ -325,7 +325,7 @@ static int process(const char *template, struct iwrap *iwrap, FILE *file, const return MUSTACH_ERROR_BAD_SEPARATORS; cllen = len - l; tmp = alloca(cllen + 1); - memcpy(tmp, beg + l, cllen); + GNUNET_memcpy(tmp, beg + l, cllen); tmp[cllen] = 0; clstr = tmp; break; diff --git a/src/testing/test_bank_api_twisted.c b/src/testing/test_bank_api_twisted.c index 80629b6f..84379ad1 100644 --- a/src/testing/test_bank_api_twisted.c +++ b/src/testing/test_bank_api_twisted.c @@ -85,9 +85,9 @@ run (void *cls, memset (&wtid, 0x5a, sizeof (wtid)); - memcpy (&exchange_auth_twisted, - &bc.exchange_auth, - sizeof (struct TALER_BANK_AuthenticationData)); + GNUNET_memcpy (&exchange_auth_twisted, + &bc.exchange_auth, + sizeof (struct TALER_BANK_AuthenticationData)); if (with_fakebank) exchange_auth_twisted.wire_gateway_url = "http://localhost:8888/2/"; diff --git a/src/testing/testing_api_cmd_batch.c b/src/testing/testing_api_cmd_batch.c index a5263b03..d81a7767 100644 --- a/src/testing/testing_api_cmd_batch.c +++ b/src/testing/testing_api_cmd_batch.c @@ -150,9 +150,9 @@ TALER_TESTING_cmd_batch (const char *label, bs->batch = GNUNET_new_array (i + 1, struct TALER_TESTING_Command); - memcpy (bs->batch, - batch, - sizeof (struct TALER_TESTING_Command) * i); + GNUNET_memcpy (bs->batch, + batch, + sizeof (struct TALER_TESTING_Command) * i); { struct TALER_TESTING_Command cmd = { .cls = bs, diff --git a/src/testing/testing_api_loop.c b/src/testing/testing_api_loop.c index 3ac9bea2..271b6e76 100644 --- a/src/testing/testing_api_loop.c +++ b/src/testing/testing_api_loop.c @@ -452,9 +452,9 @@ TALER_TESTING_run2 (struct TALER_TESTING_Interpreter *is, is->commands = GNUNET_malloc_large ( (i + 1) * sizeof (struct TALER_TESTING_Command)); GNUNET_assert (NULL != is->commands); - memcpy (is->commands, - commands, - sizeof (struct TALER_TESTING_Command) * i); + GNUNET_memcpy (is->commands, + commands, + sizeof (struct TALER_TESTING_Command) * i); is->timeout_task = GNUNET_SCHEDULER_add_delayed ( timeout, &do_timeout, diff --git a/src/util/amount.c b/src/util/amount.c index d5698e8b..dfe10b07 100644 --- a/src/util/amount.c +++ b/src/util/amount.c @@ -72,9 +72,9 @@ TALER_string_to_amount (const char *str, } GNUNET_assert (TALER_CURRENCY_LEN > (colon - str)); - memcpy (amount->currency, - str, - colon - str); + GNUNET_memcpy (amount->currency, + str, + colon - str); /* 0-terminate *and* normalize buffer by setting everything to '\0' */ memset (&amount->currency [colon - str], 0, @@ -193,9 +193,9 @@ TALER_amount_hton (struct TALER_AmountNBO *res, TALER_amount_is_valid (d)); res->value = GNUNET_htonll (d->value); res->fraction = htonl (d->fraction); - memcpy (res->currency, - d->currency, - TALER_CURRENCY_LEN); + GNUNET_memcpy (res->currency, + d->currency, + TALER_CURRENCY_LEN); } @@ -205,9 +205,9 @@ TALER_amount_ntoh (struct TALER_Amount *res, { res->value = GNUNET_ntohll (dn->value); res->fraction = ntohl (dn->fraction); - memcpy (res->currency, - dn->currency, - TALER_CURRENCY_LEN); + GNUNET_memcpy (res->currency, + dn->currency, + TALER_CURRENCY_LEN); GNUNET_assert (GNUNET_YES == TALER_amount_is_valid (res)); } @@ -225,9 +225,9 @@ TALER_amount_set_zero (const char *cur, memset (amount, 0, sizeof (struct TALER_Amount)); - memcpy (amount->currency, - cur, - slen); + GNUNET_memcpy (amount->currency, + cur, + slen); return GNUNET_OK; } @@ -680,9 +680,9 @@ TALER_amount_multiply (struct TALER_Amount *result, if (GNUNET_SYSERR == TALER_amount_normalize (&in)) return TALER_AAR_INVALID_NORMALIZATION_FAILED; - memcpy (result->currency, - amount->currency, - TALER_CURRENCY_LEN); + GNUNET_memcpy (result->currency, + amount->currency, + TALER_CURRENCY_LEN); if ( (0 == factor) || ( (0 == in.value) && (0 == in.fraction) ) ) diff --git a/src/util/crypto_confirmation.c b/src/util/crypto_confirmation.c index e52562e3..bbdf701e 100644 --- a/src/util/crypto_confirmation.c +++ b/src/util/crypto_confirmation.c @@ -90,9 +90,9 @@ compute_totp (struct GNUNET_TIME_Timestamp ts, mc = gcry_md_read (md, GCRY_MD_SHA1); GNUNET_assert (NULL != mc); - memcpy (hmac, - mc, - sizeof (hmac)); + GNUNET_memcpy (hmac, + mc, + sizeof (hmac)); gcry_md_close (md); } diff --git a/src/util/crypto_contract.c b/src/util/crypto_contract.c index 3bfe9eb8..bec34c98 100644 --- a/src/util/crypto_contract.c +++ b/src/util/crypto_contract.c @@ -131,9 +131,9 @@ blob_encrypt (const struct NonceP *nonce, + data_size; *res_size = ciphertext_size; *res = GNUNET_malloc (ciphertext_size); - memcpy (*res, - nonce, - crypto_secretbox_NONCEBYTES); + GNUNET_memcpy (*res, + nonce, + crypto_secretbox_NONCEBYTES); GNUNET_assert (0 == crypto_secretbox_easy (*res + crypto_secretbox_NONCEBYTES, data, @@ -274,9 +274,9 @@ TALER_CRYPTO_contract_encrypt_for_merge ( hdr->header.ctype = htonl (TALER_EXCHANGE_CONTRACT_PAYMENT_OFFER); hdr->header.clen = htonl ((uint32_t) clen); hdr->merge_priv = *merge_priv; - memcpy (&hdr[1], - xbuf, - cbuf_size); + GNUNET_memcpy (&hdr[1], + xbuf, + cbuf_size); GNUNET_free (xbuf); GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_NONCE, &nonce, @@ -423,9 +423,9 @@ TALER_CRYPTO_contract_encrypt_for_deposit ( hdr = GNUNET_malloc (sizeof (*hdr) + cbuf_size); hdr->ctype = htonl (TALER_EXCHANGE_CONTRACT_PAYMENT_REQUEST); hdr->clen = htonl ((uint32_t) clen); - memcpy (&hdr[1], - xbuf, - cbuf_size); + GNUNET_memcpy (&hdr[1], + xbuf, + cbuf_size); GNUNET_free (xbuf); GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_NONCE, &nonce, @@ -441,12 +441,12 @@ TALER_CRYPTO_contract_encrypt_for_deposit ( GNUNET_free (hdr); /* prepend purse_pub */ *econtract = GNUNET_malloc (xecontract_size + sizeof (*purse_pub)); - memcpy (*econtract, - purse_pub, - sizeof (*purse_pub)); - memcpy (sizeof (*purse_pub) + *econtract, - xecontract, - xecontract_size); + GNUNET_memcpy (*econtract, + purse_pub, + sizeof (*purse_pub)); + GNUNET_memcpy (sizeof (*purse_pub) + *econtract, + xecontract, + xecontract_size); *econtract_size = xecontract_size + sizeof (*purse_pub); GNUNET_free (xecontract); } @@ -573,9 +573,9 @@ TALER_CRYPTO_kyc_attributes_encrypt ( cbuf_size = compressBound (clen); xbuf = GNUNET_malloc (cbuf_size + sizeof (uint32_t)); belen = htonl ((uint32_t) clen); - memcpy (xbuf, - &belen, - sizeof (belen)); + GNUNET_memcpy (xbuf, + &belen, + sizeof (belen)); ret = compress (xbuf + 4, &cbuf_size, (const Bytef *) cstr, @@ -623,9 +623,9 @@ TALER_CRYPTO_kyc_attributes_decrypt ( GNUNET_break_op (0); return NULL; } - memcpy (&belen, - xhdr, - sizeof (belen)); + GNUNET_memcpy (&belen, + xhdr, + sizeof (belen)); clen = ntohl (belen); if (clen >= GNUNET_MAX_MALLOC_CHECKED) { diff --git a/src/util/crypto_helper_esign.c b/src/util/crypto_helper_esign.c index 5a9ad74e..5b04d0ea 100644 --- a/src/util/crypto_helper_esign.c +++ b/src/util/crypto_helper_esign.c @@ -357,9 +357,9 @@ TALER_CRYPTO_helper_esign_sign_ ( sr->header.size = htons (sizeof (buf)); sr->header.type = htons (TALER_HELPER_EDDSA_MT_REQ_SIGN); sr->reserved = htonl (0); - memcpy (&sr->purpose, - purpose, - purpose_size); + GNUNET_memcpy (&sr->purpose, + purpose, + purpose_size); if (GNUNET_OK != TALER_crypto_helper_send_all (esh->sock, buf, diff --git a/src/util/crypto_helper_rsa.c b/src/util/crypto_helper_rsa.c index efded50a..4098a846 100644 --- a/src/util/crypto_helper_rsa.c +++ b/src/util/crypto_helper_rsa.c @@ -417,9 +417,9 @@ TALER_CRYPTO_helper_rsa_sign ( sr->header.type = htons (TALER_HELPER_RSA_MT_REQ_SIGN); sr->reserved = htonl (0); sr->h_rsa = *rsr->h_rsa; - memcpy (&sr[1], - rsr->msg, - rsr->msg_size); + GNUNET_memcpy (&sr[1], + rsr->msg, + rsr->msg_size); if (GNUNET_OK != TALER_crypto_helper_send_all (dh->sock, buf, @@ -655,9 +655,9 @@ TALER_CRYPTO_helper_rsa_batch_sign ( sr->header.size = htons (sizeof (*sr) + rsr->msg_size); sr->reserved = htonl (0); sr->h_rsa = *rsr->h_rsa; - memcpy (&sr[1], - rsr->msg, - rsr->msg_size); + GNUNET_memcpy (&sr[1], + rsr->msg, + rsr->msg_size); wbuf += sizeof (*sr) + rsr->msg_size; } GNUNET_assert (wbuf == &obuf[mlen]); diff --git a/src/util/exchange_signatures.c b/src/util/exchange_signatures.c index d8bf716c..6f8ebdaf 100644 --- a/src/util/exchange_signatures.c +++ b/src/util/exchange_signatures.c @@ -1177,10 +1177,10 @@ TALER_exchange_online_denomination_expired_sign ( }; /* strncpy would create a compiler warning */ - memcpy (dua.operation, - op, - GNUNET_MIN (sizeof (dua.operation), - strlen (op))); + GNUNET_memcpy (dua.operation, + op, + GNUNET_MIN (sizeof (dua.operation), + strlen (op))); return scb (&dua.purpose, pub, sig); @@ -1204,10 +1204,10 @@ TALER_exchange_online_denomination_expired_verify ( }; /* strncpy would create a compiler warning */ - memcpy (dua.operation, - op, - GNUNET_MIN (sizeof (dua.operation), - strlen (op))); + GNUNET_memcpy (dua.operation, + op, + GNUNET_MIN (sizeof (dua.operation), + strlen (op))); return GNUNET_CRYPTO_eddsa_verify (TALER_SIGNATURE_EXCHANGE_AFFIRM_DENOM_EXPIRED, &dua, diff --git a/src/util/iban.c b/src/util/iban.c index efd8c428..c2274d3c 100644 --- a/src/util/iban.c +++ b/src/util/iban.c @@ -233,9 +233,9 @@ TALER_iban_validate (const char *iban) return GNUNET_strdup ("IBAN number too short to be valid"); if (len > 34) return GNUNET_strdup ("IBAN number too long to be valid"); - memcpy (cc, iban, 2); - memcpy (ibancpy, iban + 4, len - 4); - memcpy (ibancpy + len - 4, iban, 4); + GNUNET_memcpy (cc, iban, 2); + GNUNET_memcpy (ibancpy, iban + 4, len - 4); + GNUNET_memcpy (ibancpy + len - 4, iban, 4); ibancpy[len] = '\0'; cc_entry.code = cc; cc_entry.english = NULL; diff --git a/src/util/payto.c b/src/util/payto.c index 81664b1d..9b0e83e8 100644 --- a/src/util/payto.c +++ b/src/util/payto.c @@ -267,9 +267,9 @@ TALER_payto_hash (const char *payto, &sha512); GNUNET_static_assert (sizeof (sha512) > sizeof (*h_payto)); /* truncate */ - memcpy (h_payto, - &sha512, - sizeof (*h_payto)); + GNUNET_memcpy (h_payto, + &sha512, + sizeof (*h_payto)); } diff --git a/src/util/taler-exchange-secmod-cs.c b/src/util/taler-exchange-secmod-cs.c index 2cdf09ad..ed0eba15 100644 --- a/src/util/taler-exchange-secmod-cs.c +++ b/src/util/taler-exchange-secmod-cs.c @@ -423,9 +423,9 @@ generate_response (struct DenominationKey *dk) &an->secm_sig); an->secm_pub = TES_smpub; p = (void *) &an[1]; - memcpy (p, - denom->section, - nlen); + GNUNET_memcpy (p, + denom->section, + nlen); dk->an = an; } @@ -1373,9 +1373,9 @@ cs_client_init (struct TES_Client *client) NULL != dk; dk = dk->next) { - memcpy (&buf[obs], - dk->an, - ntohs (dk->an->header.size)); + GNUNET_memcpy (&buf[obs], + dk->an, + ntohs (dk->an->header.size)); obs += ntohs (dk->an->header.size); } } @@ -1472,18 +1472,18 @@ cs_update_client_keys (struct TES_Client *client) .h_cs = key->h_cs }; - memcpy (&buf[obs], - &pn, - sizeof (pn)); + GNUNET_memcpy (&buf[obs], + &pn, + sizeof (pn)); GNUNET_assert (obs + sizeof (pn) > obs); obs += sizeof (pn); } else { - memcpy (&buf[obs], - key->an, - ntohs (key->an->header.size)); + GNUNET_memcpy (&buf[obs], + key->an, + ntohs (key->an->header.size)); GNUNET_assert (obs + ntohs (key->an->header.size) > obs); obs += ntohs (key->an->header.size); diff --git a/src/util/taler-exchange-secmod-eddsa.c b/src/util/taler-exchange-secmod-eddsa.c index e07e9a71..3b78e71d 100644 --- a/src/util/taler-exchange-secmod-eddsa.c +++ b/src/util/taler-exchange-secmod-eddsa.c @@ -826,9 +826,9 @@ parse_key (const char *filename, filename); return GNUNET_SYSERR; } - memcpy (&priv, - buf, - buf_size); + GNUNET_memcpy (&priv, + buf, + buf_size); { struct GNUNET_CRYPTO_EddsaPublicKey pub; diff --git a/src/util/taler-exchange-secmod-rsa.c b/src/util/taler-exchange-secmod-rsa.c index c651d78a..414cb4ac 100644 --- a/src/util/taler-exchange-secmod-rsa.c +++ b/src/util/taler-exchange-secmod-rsa.c @@ -394,13 +394,13 @@ generate_response (struct DenominationKey *dk) &an->secm_sig); an->secm_pub = TES_smpub; p = (void *) &an[1]; - memcpy (p, - buf, - buf_len); + GNUNET_memcpy (p, + buf, + buf_len); GNUNET_free (buf); - memcpy (p + buf_len, - denom->section, - nlen); + GNUNET_memcpy (p + buf_len, + denom->section, + nlen); dk->an = an; } @@ -524,9 +524,9 @@ send_signature (struct TES_Client *client, sr = GNUNET_malloc (tsize); sr->header.size = htons (tsize); sr->header.type = htons (TALER_HELPER_RSA_MT_RES_SIGNATURE); - memcpy (&sr[1], - buf, - buf_size); + GNUNET_memcpy (&sr[1], + buf, + buf_size); GNUNET_free (buf); ret = TES_transmit (client->csock, &sr->header); @@ -1111,9 +1111,9 @@ rsa_client_init (struct TES_Client *client) NULL != dk; dk = dk->next) { - memcpy (&buf[obs], - dk->an, - ntohs (dk->an->header.size)); + GNUNET_memcpy (&buf[obs], + dk->an, + ntohs (dk->an->header.size)); GNUNET_assert (obs + ntohs (dk->an->header.size) > obs); obs += ntohs (dk->an->header.size); @@ -1212,18 +1212,18 @@ rsa_update_client_keys (struct TES_Client *client) .h_rsa = key->h_rsa }; - memcpy (&buf[obs], - &pn, - sizeof (pn)); + GNUNET_memcpy (&buf[obs], + &pn, + sizeof (pn)); GNUNET_assert (obs + sizeof (pn) > obs); obs += sizeof (pn); } else { - memcpy (&buf[obs], - key->an, - ntohs (key->an->header.size)); + GNUNET_memcpy (&buf[obs], + key->an, + ntohs (key->an->header.size)); GNUNET_assert (obs + ntohs (key->an->header.size) > obs); obs += ntohs (key->an->header.size); diff --git a/src/util/util.c b/src/util/util.c index 82c5f7f3..da572748 100644 --- a/src/util/util.c +++ b/src/util/util.c @@ -41,9 +41,9 @@ TALER_b2s (const void *buf, &hc); tmp = GNUNET_STRINGS_data_to_string_alloc (&hc, sizeof (hc)); - memcpy (ret, - tmp, - 8); + GNUNET_memcpy (ret, + tmp, + 8); GNUNET_free (tmp); ret[8] = '\0'; return ret; -- cgit v1.2.3 From 7899bc5621d7f5040e2938b034705a7e3569f31d Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Thu, 11 May 2023 01:18:24 +0200 Subject: externalize persona JSON conversion logic, expand with file download --- src/kyclogic/Makefile.am | 6 +- src/kyclogic/kyclogic-persona.conf | 4 + src/kyclogic/plugin_kyclogic_persona.c | 374 ++++++++++----------- .../taler-exchange-kyc-persona-converter.sh | 54 +++ src/util/.gitignore | 1 + 5 files changed, 235 insertions(+), 204 deletions(-) create mode 100755 src/kyclogic/taler-exchange-kyc-persona-converter.sh (limited to 'src/kyclogic') diff --git a/src/kyclogic/Makefile.am b/src/kyclogic/Makefile.am index 858331f3..20430a4e 100644 --- a/src/kyclogic/Makefile.am +++ b/src/kyclogic/Makefile.am @@ -16,7 +16,11 @@ pkgcfg_DATA = \ EXTRA_DIST = \ $(pkgcfg_DATA) \ - sample.conf + sample.conf \ + persona-sample-reply.json + +bin_SCRIPTS = \ + taler-exchange-kyc-persona-converter.sh lib_LTLIBRARIES = \ libtalerkyclogic.la diff --git a/src/kyclogic/kyclogic-persona.conf b/src/kyclogic/kyclogic-persona.conf index 7f02bf49..2d52a9ee 100644 --- a/src/kyclogic/kyclogic-persona.conf +++ b/src/kyclogic/kyclogic-persona.conf @@ -29,6 +29,10 @@ KYC_PERSONA_SUBDOMAIN = taler # Authentication token to use. KYC_PERSONA_AUTH_TOKEN = persona_sandbox_42 +# Program that converts Persona KYC data into the +# GNU Taler format. +KYC_PERSONA_CONVERTER_HELPER = taler-exchange-kyc-persona-converter.sh + # Form to use. KYC_PERSONA_TEMPLATE_ID = itempl_Uj6Xxxxx diff --git a/src/kyclogic/plugin_kyclogic_persona.c b/src/kyclogic/plugin_kyclogic_persona.c index 4f01ae40..35ab9ded 100644 --- a/src/kyclogic/plugin_kyclogic_persona.c +++ b/src/kyclogic/plugin_kyclogic_persona.c @@ -111,6 +111,12 @@ struct TALER_KYCLOGIC_ProviderDetails */ char *subdomain; + /** + * Name of the program we use to convert outputs + * from Persona into our JSON inputs. + */ + char *conversion_binary; + /** * Where to redirect the client upon completion. */ @@ -230,6 +236,12 @@ struct TALER_KYCLOGIC_ProofHandle */ char *url; + /** + * Handle to an external process that converts the + * Persona response to our internal format. + */ + struct TALER_JSON_ExternalConversion *ec; + /** * Hash of the payto:// URI we are checking the KYC for. */ @@ -246,6 +258,11 @@ struct TALER_KYCLOGIC_ProofHandle */ char *provider_user_id; + /** + * Account ID from the service. + */ + char *account_id; + /** * Inquiry ID at the provider. */ @@ -294,6 +311,11 @@ struct TALER_KYCLOGIC_WebhookHandle */ char *inquiry_id; + /** + * Account ID from the service. + */ + char *account_id; + /** * URL of the cURL request. */ @@ -315,6 +337,12 @@ struct TALER_KYCLOGIC_WebhookHandle */ const char *template_id; + /** + * Handle to an external process that converts the + * Persona response to our internal format. + */ + struct TALER_JSON_ExternalConversion *ec; + /** * Our account ID. */ @@ -344,6 +372,7 @@ persona_unload_configuration (struct TALER_KYCLOGIC_ProviderDetails *pd) GNUNET_free (pd->auth_token); GNUNET_free (pd->template_id); GNUNET_free (pd->subdomain); + GNUNET_free (pd->conversion_binary); GNUNET_free (pd->salt); GNUNET_free (pd->section); GNUNET_free (pd->post_kyc_redirect_url); @@ -418,6 +447,18 @@ persona_load_configuration (void *cls, persona_unload_configuration (pd); return NULL; } + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (ps->cfg, + provider_section_name, + "KYC_PERSONA_CONVERTER_HELPER", + &pd->conversion_binary)) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + provider_section_name, + "KYC_PERSONA_CONVERTER_HELPER"); + persona_unload_configuration (pd); + return NULL; + } if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string (ps->cfg, provider_section_name, @@ -838,8 +879,14 @@ persona_proof_cancel (struct TALER_KYCLOGIC_ProofHandle *ph) GNUNET_CURL_job_cancel (ph->job); ph->job = NULL; } + if (NULL != ph->ec) + { + TALER_JSON_external_conversion_stop (ph->ec); + ph->ec = NULL; + } GNUNET_free (ph->url); GNUNET_free (ph->provider_user_id); + GNUNET_free (ph->account_id); GNUNET_free (ph->inquiry_id); GNUNET_free (ph); } @@ -922,161 +969,6 @@ proof_reply_error (struct TALER_KYCLOGIC_ProofHandle *ph, } -/** - * Convert KYC attribute data from Persona response. - * - * @param attr json array with Persona attribute data - * @return KYC attribute data - */ -static json_t * -convert_attributes (const json_t *attr) -{ - const char *country_code = NULL; - const char *name_first = NULL; - const char *name_middle = NULL; - const char *name_last = NULL; - const char *address_street_1 = NULL; - const char *address_street_2 = NULL; - const char *address_city = NULL; - const char *address_postal_code = NULL; - const char *birthdate = NULL; - struct GNUNET_JSON_Specification spec[] = { - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("country-code", - &country_code), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("name-first", - &name_first), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("name-middle", - &name_middle), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("name-last", - &name_last), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("address-street-1", - &address_street_1), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("address-street-2", - &address_street_2), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("address-city", - &address_city), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("address-postal-code", - &address_postal_code), - NULL), - GNUNET_JSON_spec_mark_optional ( - GNUNET_JSON_spec_string ("birthdate", - &birthdate), - NULL), - GNUNET_JSON_spec_end () - }; - json_t *ret; - - if (GNUNET_OK != - GNUNET_JSON_parse (attr, - spec, - NULL, NULL)) - { - GNUNET_break (0); - json_dumpf (attr, - stderr, - JSON_INDENT (2)); - return NULL; - } - { - char *name = NULL; - char *street = NULL; - char *city = NULL; - - if ( (NULL != name_last) || - (NULL != name_first) || - (NULL != name_middle) ) - { - GNUNET_asprintf (&name, - "%s, %s %s", - (NULL != name_last) - ? name_last - : "", - (NULL != name_first) - ? name_first - : "", - (NULL != name_middle) - ? name_middle - : ""); - } - if ( (NULL != address_city) || - (NULL != address_postal_code) ) - { - GNUNET_asprintf (&city, - "%s%s%s %s", - (NULL != country_code) - ? country_code - : "", - (NULL != country_code) - ? "-" - : "", - (NULL != address_postal_code) - ? address_postal_code - : "", - (NULL != address_city) - ? address_city - : ""); - } - if ( (NULL != address_street_1) || - (NULL != address_street_2) ) - { - GNUNET_asprintf (&street, - "%s%s%s", - (NULL != address_street_1) - ? address_street_1 - : "", - ( (NULL != address_street_1) && - (NULL != address_street_2) ) - ? "\n" - : "", - (NULL != address_street_2) - ? address_street_2 - : ""); - } - ret = GNUNET_JSON_PACK ( - GNUNET_JSON_pack_allow_null ( - GNUNET_JSON_pack_string ( - TALER_ATTRIBUTE_BIRTHDATE, - birthdate)), - GNUNET_JSON_pack_allow_null ( - GNUNET_JSON_pack_string ( - TALER_ATTRIBUTE_FULL_NAME, - name)), - GNUNET_JSON_pack_allow_null ( - GNUNET_JSON_pack_string ( - TALER_ATTRIBUTE_ADDRESS_STREET, - street)), - GNUNET_JSON_pack_allow_null ( - GNUNET_JSON_pack_string ( - TALER_ATTRIBUTE_ADDRESS_CITY, - city)), - GNUNET_JSON_pack_allow_null ( - GNUNET_JSON_pack_string ( - TALER_ATTRIBUTE_RESIDENCES, - country_code)) - ); - GNUNET_free (street); - GNUNET_free (city); - GNUNET_free (name); - } - return ret; -} - - /** * Return a response for the @a ph request indicating a * protocol violation by the Persona server. @@ -1115,6 +1007,86 @@ return_invalid_response (struct TALER_KYCLOGIC_ProofHandle *ph, } +/** + * Start the external conversion helper. + * + * @param pd configuration details + * @param attr attributes to give to the helper + * @param cb function to call with the result + * @param cb_cls closure for @a cb + * @return handle for the helper + */ +static struct TALER_JSON_ExternalConversion * +start_conversion (const struct TALER_KYCLOGIC_ProviderDetails *pd, + const json_t *attr, + TALER_JSON_JsonCallback cb, + void *cb_cls) +{ + return TALER_JSON_external_conversion_start ( + attr, + cb, + cb_cls, + pd->conversion_binary, + pd->conversion_binary, + "-a", + pd->auth_token, + NULL + ); +} + + +/** + * Type of a callback that receives a JSON @a result. + * + * @param cls closure with a `struct TALER_KYCLOGIC_ProofHandle *` + * @param status_type how did the process die + * @param code termination status code from the process + * @param result some JSON result, NULL if we failed to get an JSON output + */ +static void +proof_post_conversion_cb (void *cls, + enum GNUNET_OS_ProcessStatusType status_type, + unsigned long code, + const json_t *attr) +{ + struct TALER_KYCLOGIC_ProofHandle *ph = cls; + struct MHD_Response *resp; + struct GNUNET_TIME_Absolute expiration; + + ph->ec = NULL; + if ( (NULL == attr) || + (0 != code) ) + { + GNUNET_break_op (0); + return_invalid_response (ph, + MHD_HTTP_OK, + ph->inquiry_id, + "converter", + NULL); + persona_proof_cancel (ph); + return; + } + expiration = GNUNET_TIME_relative_to_absolute (ph->pd->validity); + resp = MHD_create_response_from_buffer (0, + "", + MHD_RESPMEM_PERSISTENT); + GNUNET_break (MHD_YES == + MHD_add_response_header (resp, + MHD_HTTP_HEADER_LOCATION, + ph->pd->post_kyc_redirect_url)); + TALER_MHD_add_global_headers (resp); + ph->cb (ph->cb_cls, + TALER_KYCLOGIC_STATUS_SUCCESS, + ph->account_id, + ph->inquiry_id, + expiration, + attr, + MHD_HTTP_SEE_OTHER, + resp); + persona_proof_cancel (ph); +} + + /** * Function called when we're done processing the * HTTP "/api/v1/inquiries/{inquiry-id}" request. @@ -1283,46 +1255,15 @@ handle_proof_finished (void *cls, data); break; } - - { - struct MHD_Response *resp; - struct GNUNET_TIME_Absolute expiration; - json_t *attr; - - attr = convert_attributes (attributes); - if (NULL == attr) - { - GNUNET_break_op (0); - return_invalid_response (ph, - response_code, - inquiry_id, - "data-relationships-account-data-id", - data); - break; - } - expiration = GNUNET_TIME_relative_to_absolute (ph->pd->validity); - resp = MHD_create_response_from_buffer (0, - "", - MHD_RESPMEM_PERSISTENT); - GNUNET_break (MHD_YES == - MHD_add_response_header (resp, - MHD_HTTP_HEADER_LOCATION, - ph->pd->post_kyc_redirect_url)); - TALER_MHD_add_global_headers (resp); - ph->cb (ph->cb_cls, - TALER_KYCLOGIC_STATUS_SUCCESS, - account_id, - inquiry_id, - expiration, - attr, - MHD_HTTP_SEE_OTHER, - resp); - json_decref (attr); - } + ph->account_id = GNUNET_strdup (account_id); + ph->ec = start_conversion (ph->pd, + j, + &proof_post_conversion_cb, + ph); GNUNET_JSON_parse_free (ispec); } GNUNET_JSON_parse_free (spec); - break; + return; /* continued in proof_post_conversion_cb */ } case MHD_HTTP_BAD_REQUEST: case MHD_HTTP_NOT_FOUND: @@ -1580,6 +1521,12 @@ persona_webhook_cancel (struct TALER_KYCLOGIC_WebhookHandle *wh) GNUNET_CURL_job_cancel (wh->job); wh->job = NULL; } + if (NULL != wh->ec) + { + TALER_JSON_external_conversion_stop (wh->ec); + wh->ec = NULL; + } + GNUNET_free (wh->account_id); GNUNET_free (wh->inquiry_id); GNUNET_free (wh->url); GNUNET_free (wh); @@ -1650,6 +1597,32 @@ webhook_reply_error (struct TALER_KYCLOGIC_WebhookHandle *wh, } +/** + * Type of a callback that receives a JSON @a result. + * + * @param cls closure with a `struct TALER_KYCLOGIC_WebhookHandle *` + * @param status_type how did the process die + * @param code termination status code from the process + * @param result some JSON result, NULL if we failed to get an JSON output + */ +static void +webhook_post_conversion_cb (void *cls, + enum GNUNET_OS_ProcessStatusType status_type, + unsigned long code, + const json_t *attr) +{ + struct TALER_KYCLOGIC_WebhookHandle *wh = cls; + + wh->ec = NULL; + webhook_generic_reply (wh, + TALER_KYCLOGIC_STATUS_SUCCESS, + wh->account_id, + wh->inquiry_id, + attr, + MHD_HTTP_OK); +} + + /** * Function called when we're done processing the * HTTP "/api/v1/inquiries/{inquiry_id}" request. @@ -1723,7 +1696,6 @@ handle_webhook_finished (void *cls, NULL), GNUNET_JSON_spec_end () }; - json_t *attr; if (GNUNET_OK != GNUNET_JSON_parse (attributes, @@ -1807,19 +1779,15 @@ handle_webhook_finished (void *cls, MHD_HTTP_BAD_GATEWAY); break; } - - attr = convert_attributes (attributes); - webhook_generic_reply (wh, - TALER_KYCLOGIC_STATUS_SUCCESS, - account_id, - inquiry_id, - attr, - MHD_HTTP_OK); - json_decref (attr); + wh->account_id = GNUNET_strdup (account_id); + wh->ec = start_conversion (wh->pd, + j, + &webhook_post_conversion_cb, + wh); GNUNET_JSON_parse_free (ispec); } GNUNET_JSON_parse_free (spec); - break; + return; /* continued in webhook_post_conversion_cb */ } case MHD_HTTP_BAD_REQUEST: case MHD_HTTP_NOT_FOUND: diff --git a/src/kyclogic/taler-exchange-kyc-persona-converter.sh b/src/kyclogic/taler-exchange-kyc-persona-converter.sh new file mode 100755 index 00000000..a5d4d03a --- /dev/null +++ b/src/kyclogic/taler-exchange-kyc-persona-converter.sh @@ -0,0 +1,54 @@ +#!/bin/bash +# This file is in the public domain. +# +# This code converts (some of) the JSON output from Persona into the GNU Taler +# specific KYC attribute data (again in JSON format). We may need to download +# and inline file data in the process, for authorization pass "-a" with the +# respective bearer token. +# + +# Die if anything goes wrong. +set -eu + +# Parse command-line options +while getopts ':a:' OPTION; do + case "$OPTION" in + a) + TOKEN="$OPTARG" + ;; + ?) + echo "Unrecognized command line option" + exit 1 + ;; + esac +done + + +# First, extract everything from stdin. +J=$(jq '{"first":.data.attributes."name-first","middle":.data.attributes."name-middle","last":.data.attributes."name-last","cc":.data.attributes.fields."address-country-code".value,"birthdate":.data.attributes.birthdate,"city":.data.attributes."address-city","postcode":.data.attributes."address-postal-code","street-1":.data.attributes."address-street-1","street-2":.data.attributes."address-street-2","address-subdivision":.data.attributes."address-subdivision","identification-number":.data.attributes."identification-number","photo":.included[]|select(.type=="verification/government-id")|.attributes|select(.status=="passed")|."front-photo-url"}') + + +# Next, combine some fields into larger values. +FULLNAME=$(echo "$J" | jq -r '[.first,.middle,.last]|join(" ")') +STREET=$(echo $J | jq -r '[."street-1",."street-2"]|join(" ")') +CITY=$(echo $J | jq -r '[.postcode,.city,."address-subdivision,.cc"]|join(" ")') + +# Download and base32-encode the photo +PHOTO_URL=$(echo "$J" | jq -r '.photo') +PHOTO_FILE=$(mktemp -t tmp.XXXXXXXXXX) +if [ -z "${TOKEN:-}" ] +then + wget -q --output-document=- "$PHOTO_URL" | gnunet-base32 > ${PHOTO_FILE} +else + wget -q --output-document=- --header "Authorization: Bearer $TOKEN" "$PHOTO_URL" | gnunet-base32 > ${PHOTO_FILE} +fi + +# Combine into final result. +echo "$J" | jq \ + --arg full_name "${FULLNAME}" \ + --arg street "${STREET}" \ + --arg city "${CITY}" \ + --rawfile photo "${PHOTO_FILE}" \ + '{$full_name,$street,$city,"birthdate":.birthdate,"residences":.cc,"identification_number":."identification-number",$photo}' + +exit 0 diff --git a/src/util/.gitignore b/src/util/.gitignore index c5f8c76d..d79786ec 100644 --- a/src/util/.gitignore +++ b/src/util/.gitignore @@ -9,3 +9,4 @@ test_helper_cs test_helper_cs_home/ test_helper_eddsa test_helper_eddsa_home/ +test_conversion -- cgit v1.2.3 From bc03a27cba050e06ee449fc29d6024be39bd7a84 Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Thu, 11 May 2023 11:47:35 +0200 Subject: -fix doxygen --- contrib/gana | 2 +- src/kyclogic/plugin_kyclogic_persona.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) (limited to 'src/kyclogic') diff --git a/contrib/gana b/contrib/gana index e50e3767..85736484 160000 --- a/contrib/gana +++ b/contrib/gana @@ -1 +1 @@ -Subproject commit e50e37672fae7983fb5e934cd1d381b92648f7b6 +Subproject commit 85736484cb0da26aded705ebb1e944e8bb1b8504 diff --git a/src/kyclogic/plugin_kyclogic_persona.c b/src/kyclogic/plugin_kyclogic_persona.c index 35ab9ded..e14a5039 100644 --- a/src/kyclogic/plugin_kyclogic_persona.c +++ b/src/kyclogic/plugin_kyclogic_persona.c @@ -1041,7 +1041,7 @@ start_conversion (const struct TALER_KYCLOGIC_ProviderDetails *pd, * @param cls closure with a `struct TALER_KYCLOGIC_ProofHandle *` * @param status_type how did the process die * @param code termination status code from the process - * @param result some JSON result, NULL if we failed to get an JSON output + * @param attr result some JSON result, NULL if we failed to get an JSON output */ static void proof_post_conversion_cb (void *cls, @@ -1603,7 +1603,7 @@ webhook_reply_error (struct TALER_KYCLOGIC_WebhookHandle *wh, * @param cls closure with a `struct TALER_KYCLOGIC_WebhookHandle *` * @param status_type how did the process die * @param code termination status code from the process - * @param result some JSON result, NULL if we failed to get an JSON output + * @param attr some JSON result, NULL if we failed to get an JSON output */ static void webhook_post_conversion_cb (void *cls, -- cgit v1.2.3