summaryrefslogtreecommitdiff
path: root/src/lib/exchange_api_management_get_keys.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/exchange_api_management_get_keys.c')
-rw-r--r--src/lib/exchange_api_management_get_keys.c240
1 files changed, 134 insertions, 106 deletions
diff --git a/src/lib/exchange_api_management_get_keys.c b/src/lib/exchange_api_management_get_keys.c
index e9cab5810..b88ddc205 100644
--- a/src/lib/exchange_api_management_get_keys.c
+++ b/src/lib/exchange_api_management_get_keys.c
@@ -1,6 +1,6 @@
/*
This file is part of TALER
- Copyright (C) 2015-2020 Taler Systems SA
+ Copyright (C) 2015-2023 Taler Systems SA
TALER is free software; you can redistribute it and/or modify it under the
terms of the GNU General Public License as published by the Free Software
@@ -23,9 +23,10 @@
#include "taler_json_lib.h"
#include <gnunet/gnunet_curl_lib.h>
#include "taler_exchange_service.h"
+#include "exchange_api_curl_defaults.h"
#include "taler_signatures.h"
#include "taler_curl_lib.h"
-#include "taler_crypto_lib.h"
+#include "taler_util.h"
#include "taler_json_lib.h"
/**
@@ -74,25 +75,32 @@ struct TALER_EXCHANGE_ManagementGetKeysHandle
* @param response the response
* @return #GNUNET_OK if the response was well-formed
*/
-static int
+static enum GNUNET_GenericReturnValue
handle_ok (struct TALER_EXCHANGE_ManagementGetKeysHandle *gh,
const json_t *response)
{
- struct TALER_EXCHANGE_FutureKeys fk;
- json_t *sk;
- json_t *dk;
+ struct TALER_EXCHANGE_ManagementGetKeysResponse gkr = {
+ .hr.http_status = MHD_HTTP_OK,
+ .hr.reply = response,
+ };
+ struct TALER_EXCHANGE_FutureKeys *fk
+ = &gkr.details.ok.keys;
+ const json_t *sk;
+ const json_t *dk;
bool ok;
struct GNUNET_JSON_Specification spec[] = {
- GNUNET_JSON_spec_json ("future_denoms",
- &dk),
- GNUNET_JSON_spec_json ("future_signkeys",
- &sk),
+ GNUNET_JSON_spec_array_const ("future_denoms",
+ &dk),
+ GNUNET_JSON_spec_array_const ("future_signkeys",
+ &sk),
GNUNET_JSON_spec_fixed_auto ("master_pub",
- &fk.master_pub),
+ &fk->master_pub),
GNUNET_JSON_spec_fixed_auto ("denom_secmod_public_key",
- &fk.denom_secmod_public_key),
+ &fk->denom_secmod_public_key),
+ GNUNET_JSON_spec_fixed_auto ("denom_secmod_cs_public_key",
+ &fk->denom_secmod_cs_public_key),
GNUNET_JSON_spec_fixed_auto ("signkey_secmod_public_key",
- &fk.signkey_secmod_public_key),
+ &fk->signkey_secmod_public_key),
GNUNET_JSON_spec_end ()
};
@@ -104,38 +112,38 @@ handle_ok (struct TALER_EXCHANGE_ManagementGetKeysHandle *gh,
GNUNET_break_op (0);
return GNUNET_SYSERR;
}
- fk.num_sign_keys = json_array_size (sk);
- fk.num_denom_keys = json_array_size (dk);
- fk.sign_keys = GNUNET_new_array (
- fk.num_sign_keys,
+ fk->num_sign_keys = json_array_size (sk);
+ fk->num_denom_keys = json_array_size (dk);
+ fk->sign_keys = GNUNET_new_array (
+ fk->num_sign_keys,
struct TALER_EXCHANGE_FutureSigningPublicKey);
- fk.denom_keys = GNUNET_new_array (
- fk.num_denom_keys,
+ fk->denom_keys = GNUNET_new_array (
+ fk->num_denom_keys,
struct TALER_EXCHANGE_FutureDenomPublicKey);
ok = true;
- for (unsigned int i = 0; i<fk.num_sign_keys; i++)
+ for (unsigned int i = 0; i<fk->num_sign_keys; i++)
{
json_t *j = json_array_get (sk,
i);
struct TALER_EXCHANGE_FutureSigningPublicKey *sign_key
- = &fk.sign_keys[i];
- struct GNUNET_JSON_Specification spec[] = {
+ = &fk->sign_keys[i];
+ struct GNUNET_JSON_Specification ispec[] = {
GNUNET_JSON_spec_fixed_auto ("key",
&sign_key->key),
GNUNET_JSON_spec_fixed_auto ("signkey_secmod_sig",
&sign_key->signkey_secmod_sig),
- TALER_JSON_spec_absolute_time ("stamp_start",
- &sign_key->valid_from),
- TALER_JSON_spec_absolute_time ("stamp_expire",
- &sign_key->valid_until),
- TALER_JSON_spec_absolute_time ("stamp_end",
- &sign_key->valid_legal),
+ GNUNET_JSON_spec_timestamp ("stamp_start",
+ &sign_key->valid_from),
+ GNUNET_JSON_spec_timestamp ("stamp_expire",
+ &sign_key->valid_until),
+ GNUNET_JSON_spec_timestamp ("stamp_end",
+ &sign_key->valid_legal),
GNUNET_JSON_spec_end ()
};
if (GNUNET_OK !=
GNUNET_JSON_parse (j,
- spec,
+ ispec,
NULL, NULL))
{
GNUNET_break_op (0);
@@ -144,15 +152,15 @@ handle_ok (struct TALER_EXCHANGE_ManagementGetKeysHandle *gh,
}
{
struct GNUNET_TIME_Relative duration
- = GNUNET_TIME_absolute_get_difference (sign_key->valid_from,
- sign_key->valid_until);
+ = GNUNET_TIME_absolute_get_difference (sign_key->valid_from.abs_time,
+ sign_key->valid_until.abs_time);
if (GNUNET_OK !=
TALER_exchange_secmod_eddsa_verify (
&sign_key->key,
sign_key->valid_from,
duration,
- &fk.signkey_secmod_public_key,
+ &fk->signkey_secmod_public_key,
&sign_key->signkey_secmod_sig))
{
GNUNET_break_op (0);
@@ -161,26 +169,26 @@ handle_ok (struct TALER_EXCHANGE_ManagementGetKeysHandle *gh,
}
}
}
- for (unsigned int i = 0; i<fk.num_denom_keys; i++)
+ for (unsigned int i = 0; i<fk->num_denom_keys; i++)
{
json_t *j = json_array_get (dk,
i);
struct TALER_EXCHANGE_FutureDenomPublicKey *denom_key
- = &fk.denom_keys[i];
+ = &fk->denom_keys[i];
const char *section_name;
struct GNUNET_JSON_Specification spec[] = {
TALER_JSON_spec_amount_any ("value",
&denom_key->value),
- TALER_JSON_spec_absolute_time ("stamp_start",
- &denom_key->valid_from),
- TALER_JSON_spec_absolute_time ("stamp_expire_withdraw",
- &denom_key->withdraw_valid_until),
- TALER_JSON_spec_absolute_time ("stamp_expire_deposit",
- &denom_key->expire_deposit),
- TALER_JSON_spec_absolute_time ("stamp_expire_legal",
- &denom_key->expire_legal),
- GNUNET_JSON_spec_rsa_public_key ("denom_pub",
- &denom_key->key.rsa_public_key),
+ GNUNET_JSON_spec_timestamp ("stamp_start",
+ &denom_key->valid_from),
+ GNUNET_JSON_spec_timestamp ("stamp_expire_withdraw",
+ &denom_key->withdraw_valid_until),
+ GNUNET_JSON_spec_timestamp ("stamp_expire_deposit",
+ &denom_key->expire_deposit),
+ GNUNET_JSON_spec_timestamp ("stamp_expire_legal",
+ &denom_key->expire_legal),
+ TALER_JSON_spec_denom_pub ("denom_pub",
+ &denom_key->key),
TALER_JSON_spec_amount_any ("fee_withdraw",
&denom_key->fee_withdraw),
TALER_JSON_spec_amount_any ("fee_deposit",
@@ -212,51 +220,76 @@ handle_ok (struct TALER_EXCHANGE_ManagementGetKeysHandle *gh,
}
{
+ struct TALER_DenominationHashP h_denom_pub;
struct GNUNET_TIME_Relative duration
- = GNUNET_TIME_absolute_get_difference (denom_key->valid_from,
- denom_key->withdraw_valid_until);
- struct GNUNET_HashCode h_denom_pub;
+ = GNUNET_TIME_absolute_get_difference (
+ denom_key->valid_from.abs_time,
+ denom_key->withdraw_valid_until.abs_time);
- GNUNET_CRYPTO_rsa_public_key_hash (denom_key->key.rsa_public_key,
- &h_denom_pub);
- if (GNUNET_OK !=
- TALER_exchange_secmod_rsa_verify (&h_denom_pub,
- section_name,
- denom_key->valid_from,
- duration,
- &fk.denom_secmod_public_key,
- &denom_key->denom_secmod_sig))
+ TALER_denom_pub_hash (&denom_key->key,
+ &h_denom_pub);
+ switch (denom_key->key.bsign_pub_key->cipher)
{
+ case GNUNET_CRYPTO_BSA_RSA:
+ {
+ struct TALER_RsaPubHashP h_rsa;
+
+ TALER_rsa_pub_hash (
+ denom_key->key.bsign_pub_key->details.rsa_public_key,
+ &h_rsa);
+ if (GNUNET_OK !=
+ TALER_exchange_secmod_rsa_verify (&h_rsa,
+ section_name,
+ denom_key->valid_from,
+ duration,
+ &fk->denom_secmod_public_key,
+ &denom_key->denom_secmod_sig))
+ {
+ GNUNET_break_op (0);
+ ok = false;
+ break;
+ }
+ }
+ break;
+ case GNUNET_CRYPTO_BSA_CS:
+ {
+ struct TALER_CsPubHashP h_cs;
+
+ TALER_cs_pub_hash (
+ &denom_key->key.bsign_pub_key->details.cs_public_key,
+ &h_cs);
+ if (GNUNET_OK !=
+ TALER_exchange_secmod_cs_verify (&h_cs,
+ section_name,
+ denom_key->valid_from,
+ duration,
+ &fk->denom_secmod_cs_public_key,
+ &denom_key->denom_secmod_sig))
+ {
+ GNUNET_break_op (0);
+ ok = false;
+ break;
+ }
+ }
+ break;
+ default:
GNUNET_break_op (0);
ok = false;
break;
}
}
- GNUNET_JSON_parse_free (spec);
+ if (! ok)
+ break;
}
if (ok)
{
- struct TALER_EXCHANGE_HttpResponse hr = {
- .http_status = MHD_HTTP_OK,
- .reply = response
- };
-
gh->cb (gh->cb_cls,
- &hr,
- &fk);
- }
- for (unsigned int i = 0; i<fk.num_denom_keys; i++)
- {
- if (NULL != fk.denom_keys[i].key.rsa_public_key)
- {
- GNUNET_CRYPTO_rsa_public_key_free (
- fk.denom_keys[i].key.rsa_public_key);
- fk.denom_keys[i].key.rsa_public_key = NULL;
- }
+ &gkr);
}
- GNUNET_free (fk.sign_keys);
- GNUNET_free (fk.denom_keys);
- GNUNET_JSON_parse_free (spec);
+ for (unsigned int i = 0; i<fk->num_denom_keys; i++)
+ TALER_denom_pub_free (&fk->denom_keys[i].key);
+ GNUNET_free (fk->sign_keys);
+ GNUNET_free (fk->denom_keys);
return (ok) ? GNUNET_OK : GNUNET_SYSERR;
}
@@ -276,9 +309,9 @@ handle_get_keys_finished (void *cls,
{
struct TALER_EXCHANGE_ManagementGetKeysHandle *gh = cls;
const json_t *json = response;
- struct TALER_EXCHANGE_HttpResponse hr = {
- .http_status = (unsigned int) response_code,
- .reply = json
+ struct TALER_EXCHANGE_ManagementGetKeysResponse gkr = {
+ .hr.http_status = (unsigned int) response_code,
+ .hr.reply = json
};
gh->job = NULL;
@@ -296,45 +329,49 @@ handle_get_keys_finished (void *cls,
response_code = 0;
}
break;
+ case MHD_HTTP_NOT_FOUND:
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "Server did not find handler at `%s'. Did you configure the correct exchange base URL?\n",
+ gh->url);
+ if (NULL != json)
+ {
+ gkr.hr.ec = TALER_JSON_get_error_code (json);
+ gkr.hr.hint = TALER_JSON_get_error_hint (json);
+ }
+ else
+ {
+ gkr.hr.ec = TALER_EC_GENERIC_INVALID_RESPONSE;
+ gkr.hr.hint = TALER_ErrorCode_get_hint (gkr.hr.ec);
+ }
+ break;
default:
/* unexpected response code */
if (NULL != json)
{
- hr.ec = TALER_JSON_get_error_code (json);
- hr.hint = TALER_JSON_get_error_hint (json);
+ gkr.hr.ec = TALER_JSON_get_error_code (json);
+ gkr.hr.hint = TALER_JSON_get_error_hint (json);
}
else
{
- hr.ec = TALER_EC_GENERIC_INVALID_RESPONSE;
- hr.hint = TALER_ErrorCode_get_hint (hr.ec);
+ gkr.hr.ec = TALER_EC_GENERIC_INVALID_RESPONSE;
+ gkr.hr.hint = TALER_ErrorCode_get_hint (gkr.hr.ec);
}
GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
"Unexpected response code %u/%d for exchange management get keys\n",
(unsigned int) response_code,
- (int) hr.ec);
+ (int) gkr.hr.ec);
break;
}
if (NULL != gh->cb)
{
gh->cb (gh->cb_cls,
- &hr,
- NULL);
+ &gkr);
gh->cb = NULL;
}
TALER_EXCHANGE_get_management_keys_cancel (gh);
};
-/**
- * Request future keys from the exchange. The obtained information will be
- * passed to the @a cb.
- *
- * @param ctx the context
- * @param url HTTP base URL for the exchange
- * @param cb function to call with the exchange's future keys result
- * @param cb_cls closure for @a cb
- * @return the request handle; NULL upon error
- */
struct TALER_EXCHANGE_ManagementGetKeysHandle *
TALER_EXCHANGE_get_management_keys (struct GNUNET_CURL_Context *ctx,
const char *url,
@@ -358,14 +395,10 @@ TALER_EXCHANGE_get_management_keys (struct GNUNET_CURL_Context *ctx,
GNUNET_free (gh);
return NULL;
}
- eh = curl_easy_init ();
+ eh = TALER_EXCHANGE_curl_easy_get_ (gh->url);
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
"Requesting URL '%s'\n",
gh->url);
- GNUNET_assert (CURLE_OK ==
- curl_easy_setopt (eh,
- CURLOPT_URL,
- gh->url));
gh->job = GNUNET_CURL_job_add (ctx,
eh,
&handle_get_keys_finished,
@@ -379,11 +412,6 @@ TALER_EXCHANGE_get_management_keys (struct GNUNET_CURL_Context *ctx,
}
-/**
- * Cancel #TALER_EXCHANGE_get_management_keys() operation.
- *
- * @param gh handle of the operation to cancel
- */
void
TALER_EXCHANGE_get_management_keys_cancel (
struct TALER_EXCHANGE_ManagementGetKeysHandle *gh)