diff options
author | Christian Grothoff <christian@grothoff.org> | 2015-06-12 10:46:42 +0200 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2015-06-12 10:46:42 +0200 |
commit | fe6d7a5ae1b883f818538e1c0392624de5e88275 (patch) | |
tree | ab4f7a49c5755f1c3597e6d1a52f89ed4e8373b4 /src | |
parent | 3724e3d1660b4a9a31c2a7e30d51c3f1734cba89 (diff) | |
download | exchange-fe6d7a5ae1b883f818538e1c0392624de5e88275.tar.gz exchange-fe6d7a5ae1b883f818538e1c0392624de5e88275.tar.bz2 exchange-fe6d7a5ae1b883f818538e1c0392624de5e88275.zip |
ensure DKI information is in database before we start to use it (#3808)
Diffstat (limited to 'src')
-rw-r--r-- | src/include/taler_mintdb_plugin.h | 2 | ||||
-rw-r--r-- | src/mint/taler-mint-httpd.c | 23 | ||||
-rw-r--r-- | src/mint/taler-mint-httpd_keystate.c | 64 | ||||
-rw-r--r-- | src/mintdb/plugin_mintdb_postgres.c | 9 |
4 files changed, 84 insertions, 14 deletions
diff --git a/src/include/taler_mintdb_plugin.h b/src/include/taler_mintdb_plugin.h index 25d747a2..7cbc3505 100644 --- a/src/include/taler_mintdb_plugin.h +++ b/src/include/taler_mintdb_plugin.h @@ -690,7 +690,7 @@ struct TALER_MINTDB_Plugin * @param cls the @e cls of this struct with the plugin-specific state * @param sesssion connection to use * @param denom_pub the public key used for signing coins of this denomination - * @param[out] issue set to issue information with value, fees and other info about the coin + * @param[out] issue set to issue information with value, fees and other info about the coin, can be NULL * @return #GNUNET_OK on success; #GNUNET_NO if no record was found, #GNUNET_SYSERR on failure */ int diff --git a/src/mint/taler-mint-httpd.c b/src/mint/taler-mint-httpd.c index b9146c5d..0d221444 100644 --- a/src/mint/taler-mint-httpd.c +++ b/src/mint/taler-mint-httpd.c @@ -251,7 +251,7 @@ handle_mhd_request (void *cls, "Only POST is allowed", 0, &TMH_MHD_handler_send_json_pack_error, MHD_HTTP_METHOD_NOT_ALLOWED }, #endif - + { NULL, NULL, NULL, NULL, 0, 0 } }; static struct TMH_RequestHandler h404 = @@ -314,8 +314,9 @@ mint_serve_process_config (const char *mint_directory) "currency", &TMH_mint_currency_string)) { - fprintf (stderr, - "No currency given in mint configuration."); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "mint", + "currency"); return GNUNET_SYSERR; } if (strlen (TMH_mint_currency_string) >= TALER_CURRENCY_LEN) @@ -332,8 +333,9 @@ mint_serve_process_config (const char *mint_directory) "wireformat", &TMH_expected_wire_format)) { - fprintf (stderr, - "No wireformat given in mint configuration."); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "mint", + "wireformat"); return GNUNET_SYSERR; } if (GNUNET_OK != @@ -342,8 +344,9 @@ mint_serve_process_config (const char *mint_directory) "master_public_key", &TMH_master_public_key_str)) { - fprintf (stderr, - "No master public key given in mint configuration."); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "mint", + "master_public_key"); return GNUNET_SYSERR; } if (GNUNET_OK != @@ -372,8 +375,10 @@ mint_serve_process_config (const char *mint_directory) "port", &port)) { - fprintf (stderr, - "Missing or invalid configuration for the port of the mint\n"); + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_ERROR, + "mint", + "port", + "port number required"); return GNUNET_SYSERR; } diff --git a/src/mint/taler-mint-httpd_keystate.c b/src/mint/taler-mint-httpd_keystate.c index 07b83ac8..1d40b310 100644 --- a/src/mint/taler-mint-httpd_keystate.c +++ b/src/mint/taler-mint-httpd_keystate.c @@ -23,6 +23,7 @@ #include "platform.h" #include <pthread.h> #include "taler-mint-httpd_keystate.h" +#include "taler_mintdb_plugin.h" /** @@ -176,8 +177,10 @@ TALER_MINT_conf_duration_provide () "lookahead_provide", &rel)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "mint_keys.lookahead_provide not valid or not given\n"); + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_ERROR, + "mint_keys", + "lookahead_provide", + "time value required"); GNUNET_assert (0); } return rel; @@ -204,6 +207,7 @@ reload_keys_denom_iter (void *cls, struct GNUNET_TIME_Absolute horizon; struct GNUNET_HashCode denom_key_hash; struct TALER_MINTDB_DenominationKeyIssueInformation *d2; + struct TALER_MINTDB_Session *session; int res; horizon = GNUNET_TIME_relative_to_absolute (TALER_MINT_conf_duration_provide ()); @@ -230,6 +234,62 @@ reload_keys_denom_iter (void *cls, GNUNET_CRYPTO_hash_context_read (ctx->hash_context, &denom_key_hash, sizeof (struct GNUNET_HashCode)); + session = TMH_plugin->get_session (TMH_plugin->cls, + GNUNET_NO); + /* Try to insert DKI into DB until we succeed; note that if the DB + failure is persistent, this code may loop forever (as there is no + sane alternative, we cannot continue without the DKI being in the + DB). */ + res = GNUNET_SYSERR; + while (GNUNET_OK != res) + { + res = TMH_plugin->start (TMH_plugin->cls, + session); + if (GNUNET_OK != res) + { + /* Transaction start failed!? Very bad error, log and retry */ + GNUNET_break (0); + continue; + } + res = TMH_plugin->get_denomination_info (TMH_plugin->cls, + session, + &dki->denom_pub, + NULL); + if (GNUNET_SYSERR == res) + { + /* Fetch failed!? Very bad error, log and retry */ + GNUNET_break (0); + TMH_plugin->rollback (TMH_plugin->cls, + session); + continue; + } + if (GNUNET_OK == res) + { + /* Record exists, we're good, just exit */ + TMH_plugin->rollback (TMH_plugin->cls, + session); + break; + } + res = TMH_plugin->insert_denomination_info (TMH_plugin->cls, + session, + &dki->denom_pub, + &dki->issue); + if (GNUNET_OK != res) + { + /* Insert failed!? Very bad error, log and retry */ + GNUNET_break (0); + TMH_plugin->rollback (TMH_plugin->cls, + session); + continue; + } + res = TMH_plugin->commit (TMH_plugin->cls, + session); + /* If commit succeeded, we're done, otherwise we retry; this + time without logging, as theroetically commits can fail + in a transactional DB due to concurrent activities that + cannot be reconciled. This should be rare for DKIs, but + as it is possible we just retry until we succeed. */ + } d2 = GNUNET_memdup (dki, sizeof (struct TALER_MINTDB_DenominationKeyIssueInformation)); diff --git a/src/mintdb/plugin_mintdb_postgres.c b/src/mintdb/plugin_mintdb_postgres.c index 14473208..b1dffc68 100644 --- a/src/mintdb/plugin_mintdb_postgres.c +++ b/src/mintdb/plugin_mintdb_postgres.c @@ -1105,7 +1105,7 @@ postgres_insert_denomination_info (void *cls, * @param cls the @e cls of this struct with the plugin-specific state * @param sesssion connection to use * @param denom_pub the public key used for signing coins of this denomination - * @param[out] issue set to issue information with value, fees and other info about the coin + * @param[out] issue set to issue information with value, fees and other info about the coin, can be NULL * @return #GNUNET_OK on success; #GNUNET_NO if no record was found, #GNUNET_SYSERR on failure */ static int @@ -1121,7 +1121,7 @@ postgres_get_denomination_info (void *cls, }; result = TALER_PQ_exec_prepared (session->conn, - "reserve_get", + "denomination_get", params); if (PGRES_TUPLES_OK != PQresultStatus (result)) { @@ -1140,6 +1140,11 @@ postgres_get_denomination_info (void *cls, PQclear (result); return GNUNET_SYSERR; } + if (NULL == issue) + { + PQclear (result); + return GNUNET_OK; + } { struct TALER_PQ_ResultSpec rs[] = { TALER_PQ_result_spec_auto_from_type ("master_pub", |