aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/backend/taler-merchant-httpd.c40
-rw-r--r--src/backend/taler-merchant-httpd.h2
-rw-r--r--src/backend/taler-merchant-httpd_exchanges.c973
-rw-r--r--src/backend/taler-merchant-httpd_exchanges.h91
-rw-r--r--src/backend/taler-merchant-httpd_helper.c206
-rw-r--r--src/backend/taler-merchant-httpd_post-orders-ID-abort.c4
-rw-r--r--src/backend/taler-merchant-httpd_post-orders-ID-pay.c127
-rw-r--r--src/backend/taler-merchant-httpd_post-orders-ID-refund.c4
-rw-r--r--src/backend/taler-merchant-httpd_post-tips-ID-pickup.c6
-rw-r--r--src/backend/taler-merchant-httpd_private-get-instances-ID-kyc.c4
-rw-r--r--src/backend/taler-merchant-httpd_private-get-orders-ID.c4
-rw-r--r--src/backend/taler-merchant-httpd_private-get-reserves-ID.c25
-rw-r--r--src/backend/taler-merchant-httpd_private-post-reserves.c4
-rw-r--r--src/backend/taler-merchant-httpd_reserves.c2
14 files changed, 751 insertions, 741 deletions
diff --git a/src/backend/taler-merchant-httpd.c b/src/backend/taler-merchant-httpd.c
index 00e4689c..1c8b80d0 100644
--- a/src/backend/taler-merchant-httpd.c
+++ b/src/backend/taler-merchant-httpd.c
@@ -145,6 +145,17 @@ static uint16_t port;
* Should a "Connection: close" header be added to each HTTP response?
*/
static int merchant_connection_close;
+/**
+ * Context for all exchange operations (useful to the event loop).
+ * FIXME: rename, move to taler-merchant-httpd.c
+ */
+struct GNUNET_CURL_Context *TMH_curl_ctx;
+
+/**
+ * Context for integrating #TMH_curl_ctx with the
+ * GNUnet event loop.
+ */
+static struct GNUNET_CURL_RescheduleContext *merchant_curl_rc;
/**
* Global return code
@@ -329,6 +340,16 @@ do_shutdown (void *cls)
TMH_by_id_map = NULL;
}
TALER_TEMPLATING_done ();
+ if (NULL != TMH_curl_ctx)
+ {
+ GNUNET_CURL_fini (TMH_curl_ctx);
+ TMH_curl_ctx = NULL;
+ }
+ if (NULL != merchant_curl_rc)
+ {
+ GNUNET_CURL_gnunet_rc_destroy (merchant_curl_rc);
+ merchant_curl_rc = NULL;
+ }
}
@@ -1915,6 +1936,25 @@ run (void *cls,
result = GNUNET_SYSERR;
GNUNET_SCHEDULER_add_shutdown (&do_shutdown,
NULL);
+
+ TMH_curl_ctx
+ = GNUNET_CURL_init (&GNUNET_CURL_gnunet_scheduler_reschedule,
+ &merchant_curl_rc);
+ if (NULL == TMH_curl_ctx)
+ {
+ GNUNET_break (0);
+ result = GNUNET_SYSERR;
+ GNUNET_SCHEDULER_shutdown ();
+ return;
+ }
+ merchant_curl_rc = GNUNET_CURL_gnunet_rc_create (TMH_curl_ctx);
+ /* Disable 100 continue processing */
+ GNUNET_break (GNUNET_OK ==
+ GNUNET_CURL_append_header (TMH_curl_ctx,
+ MHD_HTTP_HEADER_EXPECT ":"));
+ GNUNET_CURL_enable_async_scope_header (TMH_curl_ctx,
+ "Taler-Correlation-Id");
+
if (GNUNET_OK !=
TALER_config_get_currency (cfg,
&TMH_currency))
diff --git a/src/backend/taler-merchant-httpd.h b/src/backend/taler-merchant-httpd.h
index 732c1bf3..e262b314 100644
--- a/src/backend/taler-merchant-httpd.h
+++ b/src/backend/taler-merchant-httpd.h
@@ -639,7 +639,7 @@ extern int TMH_force_audit;
/**
* Context for all CURL operations (useful to the event loop)
*/
-extern struct GNUNET_CURL_Context *merchant_curl_ctx;
+extern struct GNUNET_CURL_Context *TMH_curl_ctx;
/**
* Handle to the database backend.
diff --git a/src/backend/taler-merchant-httpd_exchanges.c b/src/backend/taler-merchant-httpd_exchanges.c
index 665607c1..ff4360b0 100644
--- a/src/backend/taler-merchant-httpd_exchanges.c
+++ b/src/backend/taler-merchant-httpd_exchanges.c
@@ -66,18 +66,18 @@
/**
* Information we keep for a pending #MMH_EXCHANGES_keys4exchange() operation.
*/
-struct TMH_EXCHANGES_Find2Operation
+struct TMH_EXCHANGES_KeysOperation
{
/**
* Kept in a DLL.
*/
- struct TMH_EXCHANGES_Find2Operation *next;
+ struct TMH_EXCHANGES_KeysOperation *next;
/**
* Kept in a DLL.
*/
- struct TMH_EXCHANGES_Find2Operation *prev;
+ struct TMH_EXCHANGES_KeysOperation *prev;
/**
* Function to call with the result.
@@ -254,7 +254,7 @@ struct ExchangeAccount
/**
- * Exchange
+ * Internal representation for an exchange
*/
struct TMH_Exchange
{
@@ -272,12 +272,12 @@ struct TMH_Exchange
/**
* Head of FOs pending for this exchange.
*/
- struct TMH_EXCHANGES_Find2Operation *fo2_head;
+ struct TMH_EXCHANGES_KeysOperation *keys_head;
/**
* Tail of FOs pending for this exchange.
*/
- struct TMH_EXCHANGES_Find2Operation *fo2_tail;
+ struct TMH_EXCHANGES_KeysOperation *keys_tail;
/**
* Head of /wire pending for this exchange.
@@ -290,6 +290,11 @@ struct TMH_Exchange
struct TMH_EXCHANGES_WireOperation *w_tail;
/**
+ * Request to /keys needed for our /wire operation.
+ */
+ struct TMH_EXCHANGES_KeysOperation *ko;
+
+ /**
* Head of accounts of this exchange.
*/
struct ExchangeAccount *acc_head;
@@ -335,8 +340,7 @@ struct TMH_Exchange
struct FeesByWireMethod *wire_fees_tail;
/**
- * Master public key, guaranteed to be set ONLY for
- * trusted exchanges.
+ * Master public key of the exchange.
*/
struct TALER_MasterPublicKeyP master_pub;
@@ -377,16 +381,17 @@ struct TMH_Exchange
/**
- * Context for all exchange operations (useful to the event loop).
- * FIXME: rename, move to taler-merchant-httpd.c
+ * Opaque wire details abstraction returned to a client after successfully
+ * obtaining /wire.
*/
-struct GNUNET_CURL_Context *merchant_curl_ctx;
+struct TMH_ExchangeWireDetails
+{
+ /**
+ * Internal representation of the exchange
+ */
+ struct TMH_Exchange *exchange;
+};
-/**
- * Context for integrating #merchant_curl_ctx with the
- * GNUnet event loop.
- */
-static struct GNUNET_CURL_RescheduleContext *merchant_curl_rc;
/**
* Head of exchanges we know about.
@@ -405,19 +410,6 @@ static struct TMH_Exchange *exchange_tail;
*/
static int trusted_exchange_count;
-/**
- * Function called with information about who is auditing
- * a particular exchange and what key the exchange is using.
- *
- * @param cls closure, will be `struct TMH_Exchange`
- * @param kr response details
- * @param[in] keys keys object returned
- */
-static void
-keys_mgmt_cb (void *cls,
- const struct TALER_EXCHANGE_KeysResponse *kr,
- struct TALER_EXCHANGE_Keys *keys);
-
/**
* Free data structures within @a ea, but not @a ea
@@ -475,6 +467,36 @@ purge_exchange_accounts (struct TMH_Exchange *exchange)
/**
+ * Lookup exchange by @a exchange_url. Create one
+ * if it does not exist.
+ *
+ * @param exchange_url base URL to match against
+ * @return fresh entry if exchange was not yet known
+ */
+static struct TMH_Exchange *
+lookup_exchange (const char *exchange_url)
+{
+ struct TMH_Exchange *exchange;
+
+ for (exchange = exchange_head;
+ NULL != exchange;
+ exchange = exchange->next)
+ if (0 == strcmp (exchange->url,
+ exchange_url))
+ return exchange;
+ exchange = GNUNET_new (struct TMH_Exchange);
+ exchange->url = GNUNET_strdup (exchange_url);
+ GNUNET_CONTAINER_DLL_insert (exchange_head,
+ exchange_tail,
+ exchange);
+ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+ "The exchange `%s' is new\n",
+ exchange_url);
+ return exchange;
+}
+
+
+/**
* Set the list of accounts of @a exchange.
*
* @param[in,out] exchange exchange to initialize or update
@@ -536,10 +558,24 @@ set_exchange_accounts (
/**
- * Retry getting information from the given exchange in
- * the closure.
+ * Function called with information about who is auditing
+ * a particular exchange and what key the exchange is using.
*
- * @param cls the exchange
+ * @param cls closure, will be `struct TMH_Exchange`
+ * @param kr response details
+ * @param[in] keys keys object returned
+ */
+static void
+keys_mgmt_cb (
+ void *cls,
+ const struct TALER_EXCHANGE_KeysResponse *kr,
+ struct TALER_EXCHANGE_Keys *keys);
+
+
+/**
+ * Retry getting keys from the given exchange in the closure.
+ *
+ * @param cls the `struct TMH_Exchange *`
*/
static void
retry_exchange (void *cls)
@@ -549,18 +585,31 @@ retry_exchange (void *cls)
/* might be a scheduled reload and not our first attempt */
exchange->retry_task = NULL;
if (NULL != exchange->conn)
- return;
+ return; /* already trying */
+ if ( (NULL != exchange->keys) &&
+ (GNUNET_TIME_absolute_is_future (
+ exchange->keys->key_data_expiration.abs_time)) )
+ return; /* still have a valid reply */
+ /* increment exponential-backoff */
+ exchange->retry_delay
+ = RETRY_BACKOFF (exchange->retry_delay);
+ /* No download until both backoff and #FORCED_RELOAD_DELAY
+ are satisfied again */
+ exchange->first_retry
+ = GNUNET_TIME_relative_to_absolute (
+ GNUNET_TIME_relative_max (
+ exchange->retry_delay,
+ FORCED_RELOAD_DELAY));
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "Connecting to exchange %s in retry_exchange()\n",
+ "Fetching /keys from exchange %s in retry_exchange()\n",
exchange->url);
- if ( (NULL == exchange->keys) ||
- (GNUNET_TIME_absolute_is_past (
- exchange->keys->key_data_expiration.abs_time)) )
- exchange->conn = TALER_EXCHANGE_get_keys (merchant_curl_ctx,
- exchange->url,
- exchange->keys,
- &keys_mgmt_cb,
- exchange);
+ exchange->conn
+ = TALER_EXCHANGE_get_keys (
+ TMH_curl_ctx,
+ exchange->url,
+ exchange->keys,
+ &keys_mgmt_cb,
+ exchange);
/* Note: while the API spec says 'returns NULL on error', the implementation
actually never returns NULL. */
GNUNET_break (NULL != exchange->conn);
@@ -568,9 +617,200 @@ retry_exchange (void *cls)
/**
- * Function called with information about the wire fees
- * for each wire method. Stores the wire fees with the
- * exchange for later use.
+ * Check if we have any remaining pending requests for the
+ * given @a exchange, and if we have the required data, call
+ * the callback.
+ *
+ * @param exchange the exchange to check for pending find operations
+ * @return true if we need /wire data from @a exchange
+ */
+static bool
+process_find_operations (struct TMH_Exchange *exchange)
+{
+ struct TMH_EXCHANGES_KeysOperation *fn2;
+ struct TMH_EXCHANGES_WireOperation *wn;
+ struct GNUNET_TIME_Timestamp now;
+
+ fn2 = NULL;
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "Processing find operations for `%s'\n",
+ exchange->url);
+ for (struct TMH_EXCHANGES_KeysOperation *fo = exchange->keys_head;
+ NULL != fo;
+ fo = fn2)
+ {
+ fn2 = fo->next;
+ fo->fc (fo->fc_cls,
+ exchange->keys);
+ TMH_EXCHANGES_keys4exchange_cancel (fo);
+ }
+ if (! exchange->have_wire)
+ return true;
+ now = GNUNET_TIME_timestamp_get ();
+ for (struct FeesByWireMethod *fbw = exchange->wire_fees_head;
+ NULL != fbw;
+ fbw = fbw->next)
+ {
+ bool removed = false;
+
+ while ( (NULL != fbw->af) &&
+ (GNUNET_TIME_timestamp_cmp (fbw->af->end_date,
+ <,
+ now)) )
+ {
+ struct TALER_EXCHANGE_WireAggregateFees *af = fbw->af;
+
+ fbw->af = af->next;
+ GNUNET_free (af);
+ removed = true;
+ }
+ if (NULL == fbw->af)
+ {
+ /* Disagreement on the current time */
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "Exchange has no wire fees configured for `%s' wire method\n",
+ fbw->wire_method);
+ if (removed)
+ {
+ exchange->have_wire = false;
+ return true; /* We just removed previous fees, try fetching update */
+ }
+ }
+ if (GNUNET_TIME_timestamp_cmp (fbw->af->start_date,
+ >,
+ now))
+ {
+ /* Disagreement on the current time */
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "Exchange's earliest fee is %s ahead of our time. Clock skew issue?\n",
+ GNUNET_TIME_relative2s (
+ GNUNET_TIME_absolute_get_remaining (
+ fbw->af->start_date.abs_time),
+ true));
+ }
+ }
+
+ if (! exchange->have_wire)
+ return true; /* need /wire response to continue */
+ {
+ struct TMH_ExchangeWireDetails wd = {
+ .exchange = exchange
+ };
+
+ wn = NULL;
+ for (struct TMH_EXCHANGES_WireOperation *w = exchange->w_head;
+ NULL != w;
+ w = wn)
+ {
+ wn = w->next;
+ w->fc (w->fc_cls,
+ &wd);
+ TMH_EXCHANGES_wire4exchange_cancel (w);
+ }
+ }
+ return false;
+}
+
+
+/**
+ * Task to asynchronously return keys operation result to caller.
+ *
+ * @param cls a `struct TMH_EXCHANGES_KeysOperation`
+ */
+static void
+return_keys (void *cls)
+{
+ struct TMH_EXCHANGES_KeysOperation *fo = cls;
+ struct TMH_Exchange *exchange = fo->my_exchange;
+
+ fo->at = NULL;
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "Returning key data for %s instantly\n",
+ exchange->url);
+ process_find_operations (exchange);
+}
+
+
+struct TMH_EXCHANGES_KeysOperation *
+TMH_EXCHANGES_keys4exchange (
+ const char *chosen_exchange,
+ TMH_EXCHANGES_Find2Continuation fc,
+ void *fc_cls)
+{
+ struct TMH_Exchange *exchange;
+ struct TMH_EXCHANGES_KeysOperation *fo;
+
+ if (NULL == TMH_curl_ctx)
+ {
+ GNUNET_break (0);
+ return NULL;
+ }
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "Trying to find chosen exchange `%s'\n",
+ chosen_exchange);
+ exchange = lookup_exchange (chosen_exchange);
+ fo = GNUNET_new (struct TMH_EXCHANGES_KeysOperation);
+ fo->fc = fc;
+ fo->fc_cls = fc_cls;
+ fo->my_exchange = exchange;
+ GNUNET_CONTAINER_DLL_insert (exchange->keys_head,
+ exchange->keys_tail,
+ fo);
+ if ( (NULL != exchange->keys) &&
+ (GNUNET_TIME_absolute_is_future (
+ exchange->keys->key_data_expiration.abs_time)) )
+ {
+ /* We have a valid reply, immediately return result */
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "The exchange `%s' is ready\n",
+ exchange->url);
+ GNUNET_assert (NULL == fo->at);
+ fo->at = GNUNET_SCHEDULER_add_now (&return_keys,
+ fo);
+ return fo;
+ }
+ if ( (NULL == exchange->retry_task) &&
+ (NULL == exchange->conn) )
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "No valid keys, fetching /keys at %s\n",
+ GNUNET_TIME_absolute2s (exchange->first_retry));
+ exchange->retry_task
+ = GNUNET_SCHEDULER_add_at (exchange->first_retry,
+ &retry_exchange,
+ exchange);
+ return fo;
+ }
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "Next /keys request scheduled for %s\n",
+ GNUNET_TIME_absolute2s (
+ exchange->first_retry));
+ /* No activity to launch, we are already doing so. */
+ return fo;
+}
+
+
+void
+TMH_EXCHANGES_keys4exchange_cancel (
+ struct TMH_EXCHANGES_KeysOperation *fo)
+{
+ struct TMH_Exchange *exchange = fo->my_exchange;
+
+ if (NULL != fo->at)
+ {
+ GNUNET_SCHEDULER_cancel (fo->at);
+ fo->at = NULL;
+ }
+ GNUNET_CONTAINER_DLL_remove (exchange->keys_head,
+ exchange->keys_tail,
+ fo);
+ GNUNET_free (fo);
+}
+
+
+/**
+ * Function called with information about the wire fees for each wire method.
+ * Stores the wire fees with the exchange for later use.
*
* @param exchange connection to the exchange
* @param master_pub public key of the exchange
@@ -910,90 +1150,13 @@ get_wire_fees (struct TMH_Exchange *exchange,
/**
* Check if we have any remaining pending requests for the
* given @a exchange, and if we have the required data, call
- * the callback.
+ * the callback. If requests without /wire data remain,
+ * retry the /wire request after some delay.
*
- * @param exchange the exchange to check for pending find operations
- * @return true if we need /wire data from @a exchange
+ * Must only be called if 'exchange->keys' is non-NULL.
+ *
+ * @param cls a `struct TMH_Exchange` to check
*/
-static bool
-process_find_operations (struct TMH_Exchange *exchange)
-{
- struct TMH_EXCHANGES_Find2Operation *fn2;
- struct TMH_EXCHANGES_WireOperation *wn;
- struct GNUNET_TIME_Timestamp now;
-
- fn2 = NULL;
- for (struct TMH_EXCHANGES_Find2Operation *fo = exchange->fo2_head;
- NULL != fo;
- fo = fn2)
- {
- fo->fc (fo->fc_cls,
- exchange->keys);
- fn2 = fo->next;
- TMH_EXCHANGES_keys4exchange_cancel (fo);
- }
- if (! exchange->have_wire)
- return true;
- now = GNUNET_TIME_timestamp_get ();
- for (struct FeesByWireMethod *fbw = exchange->wire_fees_head;
- NULL != fbw;
- fbw = fbw->next)
- {
- bool removed = false;
-
- while ( (NULL != fbw->af) &&
- (GNUNET_TIME_timestamp_cmp (fbw->af->end_date,
- <,
- now)) )
- {
- struct TALER_EXCHANGE_WireAggregateFees *af = fbw->af;
-
- fbw->af = af->next;
- GNUNET_free (af);
- removed = true;
- }
- if (NULL == fbw->af)
- {
- /* Disagreement on the current time */
- GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
- "Exchange has no wire fees configured for `%s' wire method\n",
- fbw->wire_method);
- if (removed)
- {
- exchange->have_wire = false;
- return true; /* We just removed previous fees, try fetching update */
- }
- }
- if (GNUNET_TIME_timestamp_cmp (fbw->af->start_date,
- >,
- now))
- {
- /* Disagreement on the current time */
- GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
- "Exchange's earliest fee is %s ahead of our time. Clock skew issue?\n",
- GNUNET_TIME_relative2s (
- GNUNET_TIME_absolute_get_remaining (
- fbw->af->start_date.abs_time),
- true));
- }
- }
-
- if (! exchange->have_wire)
- return true; /* need /wire response to continue */
- wn = NULL;
- for (struct TMH_EXCHANGES_WireOperation *w = exchange->w_head;
- NULL != w;
- w = wn)
- {
- w->fc (w->fc_cls,
- exchange);
- wn = w->next;
- TMH_EXCHANGES_wire4exchange_cancel (w);
- }
- return false;
-}
-
-
static void
wire_task_cb (void *cls);
@@ -1053,15 +1216,15 @@ handle_wire_data (void *cls,
if (TALER_EC_NONE != ecx)
{
/* Report hard failure to all callbacks! */
- struct TMH_EXCHANGES_Find2Operation *fo2;
+ struct TMH_EXCHANGES_KeysOperation *keys;
GNUNET_break_op (0);
exchange->have_wire = false;
- while (NULL != (fo2 = exchange->fo2_head))
+ while (NULL != (keys = exchange->keys_head))
{
- fo2->fc (fo2->fc_cls,
- NULL);
- TMH_EXCHANGES_keys4exchange_cancel (fo2);
+ keys->fc (keys->fc_cls,
+ NULL);
+ TMH_EXCHANGES_keys4exchange_cancel (keys);
}
return;
}
@@ -1091,16 +1254,6 @@ handle_wire_data (void *cls,
}
-/**
- * Check if we have any remaining pending requests for the
- * given @a exchange, and if we have the required data, call
- * the callback. If requests without /wire data remain,
- * retry the /wire request after some delay.
- *
- * Must only be called if 'exchange->keys' is non-NULL.
- *
- * @param cls a `struct TMH_Exchange` to check
- */
static void
wire_task_cb (void *cls)
{
@@ -1113,7 +1266,7 @@ wire_task_cb (void *cls)
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
"Initiating /wire download\n");
exchange->wire_request
- = TALER_EXCHANGE_wire (merchant_curl_ctx,
+ = TALER_EXCHANGE_wire (TMH_curl_ctx,
exchange->url,
exchange->keys,
&handle_wire_data,
@@ -1172,8 +1325,8 @@ free_exchange_entry (struct TMH_Exchange *exchange)
GNUNET_SCHEDULER_cancel (exchange->retry_task);
exchange->retry_task = NULL;
}
- GNUNET_assert (NULL == exchange->fo2_head);
- GNUNET_assert (NULL == exchange->fo2_tail);
+ GNUNET_assert (NULL == exchange->keys_head);
+ GNUNET_assert (NULL == exchange->keys_tail);
GNUNET_assert (NULL == exchange->w_head);
GNUNET_assert (NULL == exchange->w_tail);
GNUNET_free (exchange->url);
@@ -1192,7 +1345,7 @@ static void
fail_and_retry (struct TMH_Exchange *exchange,
const struct TALER_EXCHANGE_HttpResponse *hr)
{
- struct TMH_EXCHANGES_Find2Operation *fo2;
+ struct TMH_EXCHANGES_KeysOperation *keys;
struct TMH_EXCHANGES_WireOperation *w;
if (NULL != exchange->wire_request)
@@ -1205,11 +1358,11 @@ fail_and_retry (struct TMH_Exchange *exchange,
GNUNET_SCHEDULER_cancel (exchange->wire_task);
exchange->wire_task = NULL;
}
- while (NULL != (fo2 = exchange->fo2_head))
+ while (NULL != (keys = exchange->keys_head))
{
- fo2->fc (fo2->fc_cls,
- NULL);
- TMH_EXCHANGES_keys4exchange_cancel (fo2);
+ keys->fc (keys->fc_cls,
+ NULL);
+ TMH_EXCHANGES_keys4exchange_cancel (keys);
}
while (NULL != (w = exchange->w_head))
{
@@ -1233,14 +1386,24 @@ fail_and_retry (struct TMH_Exchange *exchange,
true));
if (NULL != exchange->retry_task)
GNUNET_SCHEDULER_cancel (exchange->retry_task);
- exchange->first_retry = GNUNET_TIME_relative_to_absolute (
- exchange->retry_delay);
- exchange->retry_task = GNUNET_SCHEDULER_add_delayed (exchange->retry_delay,
- &retry_exchange,
- exchange);
+ exchange->first_retry
+ = GNUNET_TIME_relative_to_absolute (
+ exchange->retry_delay);
+ exchange->retry_task
+ = GNUNET_SCHEDULER_add_delayed (exchange->retry_delay,
+ &retry_exchange,
+ exchange);
}
+/**
+ * Function called with the result of a
+ * /keys request to the exchange.
+ *
+ * @param cls a `struct TMH_Exchange *`
+ * @param kr response details
+ * @param[in] keys key data now owned by this function
+ */
static void
keys_mgmt_cb (void *cls,
const struct TALER_EXCHANGE_KeysResponse *kr,
@@ -1293,13 +1456,14 @@ keys_mgmt_cb (void *cls,
enum GNUNET_DB_QueryStatus qs;
TMH_db->preflight (TMH_db->cls);
- qs = TMH_db->insert_exchange_signkey (TMH_db->cls,
- &keys->master_pub,
- &sign_key->key,
- sign_key->valid_from,
- sign_key->valid_until,
- sign_key->valid_legal,
- &sign_key->master_sig);
+ qs = TMH_db->insert_exchange_signkey (
+ TMH_db->cls,
+ &keys->master_pub,
+ &sign_key->key,
+ sign_key->valid_from,
+ sign_key->valid_until,
+ sign_key->valid_legal,
+ &sign_key->master_sig);
/* 0 is OK, we may already have the key in the DB! */
if (0 > qs)
{
@@ -1315,7 +1479,7 @@ keys_mgmt_cb (void *cls,
delay = GNUNET_TIME_absolute_get_remaining (
keys->key_data_expiration.abs_time);
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "/keys response from expires at %s! Retrying at that time!\n",
+ "/keys response expires at %s! Retrying at that time!\n",
GNUNET_TIME_absolute2s (
keys->key_data_expiration.abs_time));
delay = GNUNET_TIME_relative_max (delay,
@@ -1327,6 +1491,7 @@ keys_mgmt_cb (void *cls,
= GNUNET_SCHEDULER_add_delayed (delay,
&retry_exchange,
exchange);
+
if ( (process_find_operations (exchange)) &&
(NULL == exchange->wire_request) &&
(NULL == exchange->wire_task) )
@@ -1335,7 +1500,7 @@ keys_mgmt_cb (void *cls,
"Got key data, but also need wire data. Will request /wire now\n");
exchange->wire_request
= TALER_EXCHANGE_wire (
- merchant_curl_ctx,
+ TMH_curl_ctx,
exchange->url,
exchange->keys,
&handle_wire_data,
@@ -1347,22 +1512,6 @@ keys_mgmt_cb (void *cls,
/**
* Task to return find operation result asynchronously to caller.
*
- * @param cls a `struct TMH_EXCHANGES_Find2Operation`
- */
-static void
-return_result2 (void *cls)
-{
- struct TMH_EXCHANGES_Find2Operation *fo = cls;
- struct TMH_Exchange *exchange = fo->my_exchange;
-
- fo->at = NULL;
- process_find_operations (exchange);
-}
-
-
-/**
- * Task to return find operation result asynchronously to caller.
- *
* @param cls a `struct TMH_EXCHANGES_WireOperation`
*/
static void
@@ -1376,115 +1525,6 @@ return_wire_result (void *cls)
}
-/**
- * Lookup exchange by @a exchange_url.
- *
- * @param exchange_url base URL to match against
- * @return NULL if exchange is not yet known
- */
-static struct TMH_Exchange *
-lookup_exchange (const char *exchange_url)
-{
- for (struct TMH_Exchange *exchange = exchange_head;
- NULL != exchange;
- exchange = exchange->next)
- if (0 == strcmp (exchange->url,
- exchange_url))
- return exchange;
- return NULL;
-}
-
-
-struct TMH_EXCHANGES_Find2Operation *
-TMH_EXCHANGES_keys4exchange (
- const char *chosen_exchange,
- TMH_EXCHANGES_Find2Continuation fc,
- void *fc_cls)
-{
- struct TMH_Exchange *exchange;
- struct TMH_EXCHANGES_Find2Operation *fo;
-
- if (NULL == merchant_curl_ctx)
- {
- GNUNET_break (0);
- return NULL;
- }
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "Trying to find chosen exchange `%s'\n",
- chosen_exchange);
- /* Check if the exchange is known */
- exchange = lookup_exchange (chosen_exchange);
- if (NULL == exchange)
- {
- /* This is a new exchange */
- exchange = GNUNET_new (struct TMH_Exchange);
- exchange->url = GNUNET_strdup (chosen_exchange);
- GNUNET_CONTAINER_DLL_insert (exchange_head,
- exchange_tail,
- exchange);
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "The exchange `%s' is new\n",
- chosen_exchange);
- }
-
- fo = GNUNET_new (struct TMH_EXCHANGES_Find2Operation);
- fo->fc = fc;
- fo->fc_cls = fc_cls;
- fo->my_exchange = exchange;
- GNUNET_CONTAINER_DLL_insert (exchange->fo2_head,
- exchange->fo2_tail,
- fo);
-
- if (GNUNET_TIME_absolute_is_past (exchange->first_retry))
- {
- /* increment exponential-backoff */
- exchange->retry_delay = RETRY_BACKOFF (exchange->retry_delay);
- /* do not allow forced check until both backoff and #FORCED_RELOAD_DELAY
- are satisfied again */
- exchange->first_retry
- = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_relative_max (
- exchange->retry_delay,
- FORCED_RELOAD_DELAY));
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "/keys retry forced, waiting until %s\n",
- GNUNET_TIME_absolute2s (exchange->first_retry));
-
- if (NULL == exchange->retry_task)
- exchange->retry_task
- = GNUNET_SCHEDULER_add_now (&retry_exchange,
- exchange);
- return fo;
- }
-
- if (NULL != exchange->keys)
- {
- /* We are not currently waiting for a reply, immediately
- return result */
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "The exchange `%s' is ready\n",
- exchange->url);
- GNUNET_assert (NULL == fo->at);
- fo->at = GNUNET_SCHEDULER_add_now (&return_result2,
- fo);
- return fo;
- }
-
- /* If new or resumed, (re)try fetching /keys */
- if ( (NULL == exchange->keys) &&
- (NULL == exchange->retry_task) )
- {
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "Do not have current /keys data for `%s'. Will request /keys now\n",
- exchange->url);
- exchange->retry_task = GNUNET_SCHEDULER_add_now (&retry_exchange,
- exchange);
- return fo;
- }
- /* No activity to launch, we are already doing so */
- return fo;
-}
-
-
struct TMH_EXCHANGES_WireOperation *
TMH_EXCHANGES_wire4exchange (
const char *chosen_exchange,
@@ -1494,7 +1534,7 @@ TMH_EXCHANGES_wire4exchange (
struct TMH_Exchange *exchange;
struct TMH_EXCHANGES_WireOperation *w;
- if (NULL == merchant_curl_ctx)
+ if (NULL == TMH_curl_ctx)
{
GNUNET_break (0);
return NULL;
@@ -1502,21 +1542,7 @@ TMH_EXCHANGES_wire4exchange (
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
"Trying to find chosen exchange `%s'\n",
chosen_exchange);
- /* Check if the exchange is known */
exchange = lookup_exchange (chosen_exchange);
- if (NULL == exchange)
- {
- /* This is a new exchange */
- exchange = GNUNET_new (struct TMH_Exchange);
- exchange->url = GNUNET_strdup (chosen_exchange);
- GNUNET_CONTAINER_DLL_insert (exchange_head,
- exchange_tail,
- exchange);
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "The exchange `%s' is new\n",
- chosen_exchange);
- }
-
w = GNUNET_new (struct TMH_EXCHANGES_WireOperation);
w->fc = fc;
w->fc_cls = fc_cls;
@@ -1536,56 +1562,42 @@ TMH_EXCHANGES_wire4exchange (
w);
return w;
}
-
- if (NULL == exchange->wire_request)
+ if (NULL != exchange->wire_request)
+ return w; /* /wire request is active, do nothing */
+ if ( (NULL != exchange->keys) &&
+ (GNUNET_TIME_absolute_is_future (
+ exchange->keys->key_data_expiration.abs_time)) )
{
- if (NULL == exchange->conn)
- {
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "Requesting /keys from `%s' to connect\n",
- exchange->url);
- exchange->conn = TALER_EXCHANGE_get_keys (merchant_curl_ctx,
- exchange->url,
- exchange->keys,
- &keys_mgmt_cb,
- exchange);
- }
- else
- {
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "Requesting /wire from `%s'\n",
- exchange->url);
- exchange->wire_request
- = TALER_EXCHANGE_wire (merchant_curl_ctx,
- exchange->url,
- exchange->keys,
- &handle_wire_data,
- exchange);
- }
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "Requesting /wire from `%s'\n",
+ exchange->url);
+ exchange->wire_request
+ = TALER_EXCHANGE_wire (TMH_curl_ctx,
+ exchange->url,
+ exchange->keys,
+ &handle_wire_data,
+ exchange);
+ return w;
}
- return w;
-}
-
-
-void
-TMH_EXCHANGES_keys4exchange_cancel (struct TMH_EXCHANGES_Find2Operation *fo)
-{
- struct TMH_Exchange *exchange = fo->my_exchange;
+ if ( (NULL == exchange->keys) &&
+ ( (NULL != exchange->conn) ||
+ (NULL != exchange->retry_task) ) )
+ return w; /* /keys request active, do nothing */
- if (NULL != fo->at)
- {
- GNUNET_SCHEDULER_cancel (fo->at);
- fo->at = NULL;
- }
- GNUNET_CONTAINER_DLL_remove (exchange->fo2_head,
- exchange->fo2_tail,
- fo);
- GNUNET_free (fo);
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ "No valid keys, fetching /keys at %s\n",
+ GNUNET_TIME_absolute2s (exchange->first_retry));
+ exchange->retry_task
+ = GNUNET_SCHEDULER_add_at (exchange->first_retry,
+ &retry_exchange,
+ exchange);
+ return w;
}
void
-TMH_EXCHANGES_wire4exchange_cancel (struct TMH_EXCHANGES_WireOperation *w)
+TMH_EXCHANGES_wire4exchange_cancel (
+ struct TMH_EXCHANGES_WireOperation *w)
{
struct TMH_Exchange *exchange = w->my_exchange;
@@ -1601,10 +1613,128 @@ TMH_EXCHANGES_wire4exchange_cancel (struct TMH_EXCHANGES_WireOperation *w)
}
+enum GNUNET_GenericReturnValue
+TMH_EXCHANGES_lookup_wire_fee (
+ const struct TMH_ExchangeWireDetails *wd,
+ const char *wire_method,
+ struct TALER_Amount *wire_fee)
+{
+ struct TMH_Exchange *exchange = wd->exchange;
+ const struct FeesByWireMethod *fbm;
+ const struct TALER_EXCHANGE_WireAggregateFees *af;
+
+ if (! exchange->have_wire)
+ {
+ GNUNET_break (0);
+ return GNUNET_SYSERR;
+ }
+ fbm = get_wire_fees (exchange,
+ GNUNET_TIME_timestamp_get (),
+ wire_method);
+ if (NULL == fbm)
+ return GNUNET_NO;
+ af = fbm->af;
+ *wire_fee = af->fees.wire;
+ return GNUNET_OK;
+}
+
+
+enum GNUNET_GenericReturnValue
+TMH_exchange_check_debit (
+ const struct TMH_ExchangeWireDetails *wd,
+ const struct TMH_WireMethod *wm)
+{
+ struct TMH_Exchange *ex = wd->exchange;
+ for (struct ExchangeAccount *acc = ex->acc_head;
+ NULL != acc;
+ acc = acc->next)
+ {
+ bool ok = true;
+
+ if (0 != strcmp (acc->wire_method,
+ wm->wire_method))
+ continue;
+ if (NULL != acc->conversion_url)
+ continue; /* never use accounts with conversion */
+ for (struct Restriction *r = acc->d_head;
+ NULL != r;
+ r = r->next)
+ {
+ switch (r->type)
+ {
+ case TALER_EXCHANGE_AR_INVALID:
+ GNUNET_break (0);
+ ok = false;
+ break;
+ case TALER_EXCHANGE_AR_DENY:
+ ok = false;
+ break;
+ case TALER_EXCHANGE_AR_REGEX:
+ if (0 != regexec (&r->details.regex.ex,
+ wm->payto_uri,
+ 0, NULL, 0))
+ ok = false;
+ break;
+ }
+ if (! ok)
+ break;
+ }
+
+ if (ok)
+ return GNUNET_OK;
+ }
+ return GNUNET_NO;
+}
+
+
+json_t *
+TMH_exchange_get_acceptable (const struct TMH_WireMethod *wm)
+{
+ json_t *te = json_array ();
+
+ GNUNET_assert (NULL != te);
+ for (struct TMH_Exchange *exchange = exchange_head;
+ NULL != exchange;
+ exchange = exchange->next)
+ {
+ json_t *j_exchange;
+ unsigned int priority;
+
+ if (! exchange->trusted)
+ continue;
+ priority = 512; /* medium */
+ if (exchange->have_wire)
+ {
+ struct TMH_ExchangeWireDetails wd = {
+ .exchange = exchange
+ };
+
+ if (GNUNET_OK ==
+ TMH_exchange_check_debit (&wd,
+ wm))
+ priority = 1024; /* high */
+ else
+ priority = 0; /* negative response */
+ }
+ j_exchange = GNUNET_JSON_PACK (
+ GNUNET_JSON_pack_string ("url",
+ exchange->url),
+ GNUNET_JSON_pack_uint64 ("priority",
+ priority),
+ GNUNET_JSON_pack_data_auto ("master_pub",
+ &exchange->master_pub));
+ GNUNET_assert (NULL != j_exchange);
+ GNUNET_assert (0 ==
+ json_array_append_new (te,
+ j_exchange));
+ }
+ return te;
+}
+
+
/**
* Function called on each configuration section. Finds sections
- * about exchanges, parses the entries and tries to connect to
- * it in order to fetch /keys.
+ * about exchanges, parses the entries.
*
* @param cls closure, with a `const struct GNUNET_CONFIGURATION_Handle *`
* @param section name of the section
@@ -1677,7 +1807,7 @@ accept_exchanges (void *cls,
GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_ERROR,
section,
"MASTER_KEY",
- _ ("ill-formed EdDSA key"));
+ "malformed EdDSA key");
}
GNUNET_free (mks);
}
@@ -1686,7 +1816,6 @@ accept_exchanges (void *cls,
GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
"MASTER_KEY missing in section '%s', not trusting exchange\n",
section);
-
}
GNUNET_CONTAINER_DLL_insert (exchange_head,
exchange_tail,
@@ -1698,53 +1827,8 @@ accept_exchanges (void *cls,
enum GNUNET_GenericReturnValue
-TMH_EXCHANGES_lookup_wire_fee (const char *exchange_url,
- const char *wire_method,
- struct TALER_Amount *wire_fee)
-{
- struct TMH_Exchange *exchange;
- const struct FeesByWireMethod *fbm;
- const struct TALER_EXCHANGE_WireAggregateFees *af;
-
- exchange = lookup_exchange (exchange_url);
- if (NULL == exchange)
- {
- return GNUNET_SYSERR;
- }
- if (! exchange->have_wire)
- {
- return GNUNET_SYSERR;
- }
- fbm = get_wire_fees (exchange,
- GNUNET_TIME_timestamp_get (),
- wire_method);
- if (NULL == fbm)
- return GNUNET_NO;
- af = fbm->af;
- *wire_fee = af->fees.wire;
- return GNUNET_OK;
-}
-
-
-enum GNUNET_GenericReturnValue
TMH_EXCHANGES_init (const struct GNUNET_CONFIGURATION_Handle *cfg)
{
- merchant_curl_ctx
- = GNUNET_CURL_init (&GNUNET_CURL_gnunet_scheduler_reschedule,
- &merchant_curl_rc);
- if (NULL == merchant_curl_ctx)
- {
- GNUNET_break (0);
- return GNUNET_SYSERR;
- }
- merchant_curl_rc = GNUNET_CURL_gnunet_rc_create (merchant_curl_ctx);
- /* Disable 100 continue processing */
- GNUNET_break (GNUNET_OK ==
- GNUNET_CURL_append_header (merchant_curl_ctx,
- MHD_HTTP_HEADER_EXPECT ":"));
-
- GNUNET_CURL_enable_async_scope_header (merchant_curl_ctx,
- "Taler-Correlation-Id");
/* get exchanges from the merchant configuration and try to connect to them */
GNUNET_CONFIGURATION_iterate_sections (cfg,
&accept_exchanges,
@@ -1759,103 +1843,6 @@ TMH_EXCHANGES_done ()
{
while (NULL != exchange_head)
free_exchange_entry (exchange_head);
- if (NULL != merchant_curl_ctx)
- {
- GNUNET_CURL_fini (merchant_curl_ctx);
- merchant_curl_ctx = NULL;
- }
- if (NULL != merchant_curl_rc)
- {
- GNUNET_CURL_gnunet_rc_destroy (merchant_curl_rc);
- merchant_curl_rc = NULL;
- }
-}
-
-
-enum GNUNET_GenericReturnValue
-TMH_exchange_check_debit (struct TMH_Exchange *ex,
- const struct TMH_WireMethod *wm)
-{
- for (struct ExchangeAccount *acc = ex->acc_head;
- NULL != acc;
- acc = acc->next)
- {
- bool ok = true;
-
- if (0 != strcmp (acc->wire_method,
- wm->wire_method))
- continue;
- if (NULL != acc->conversion_url)
- continue; /* never use accounts with conversion */
- for (struct Restriction *r = acc->d_head;
- NULL != r;
- r = r->next)
- {
- switch (r->type)
- {
- case TALER_EXCHANGE_AR_INVALID:
- GNUNET_break (0);
- ok = false;
- break;
- case TALER_EXCHANGE_AR_DENY:
- ok = false;
- break;
- case TALER_EXCHANGE_AR_REGEX:
- if (0 != regexec (&r->details.regex.ex,
- wm->payto_uri,
- 0, NULL, 0))
- ok = false;
- break;
- }
- if (! ok)
- break;
- }
-
- if (ok)
- return GNUNET_OK;
- }
- return GNUNET_NO;
-}
-
-
-json_t *
-TMH_exchange_get_acceptable (const struct TMH_WireMethod *wm)
-{
- json_t *te = json_array ();
-
- GNUNET_assert (NULL != te);
- for (struct TMH_Exchange *exchange = exchange_head;
- NULL != exchange;
- exchange = exchange->next)
- {
- json_t *j_exchange;
- unsigned int priority;
-
- if (! exchange->trusted)
- continue;
- priority = 512; /* medium */
- if (exchange->have_wire)
- {
- if (GNUNET_OK ==
- TMH_exchange_check_debit (exchange,
- wm))
- priority = 1024; /* high */
- else
- priority = 0; /* negative response */
- }
- j_exchange = GNUNET_JSON_PACK (
- GNUNET_JSON_pack_string ("url",
- exchange->url),
- GNUNET_JSON_pack_uint64 ("priority",
- priority),
- GNUNET_JSON_pack_data_auto ("master_pub",
- &exchange->master_pub));
- GNUNET_assert (NULL != j_exchange);
- GNUNET_assert (0 ==
- json_array_append_new (te,
- j_exchange));
- }
- return te;
}
diff --git a/src/backend/taler-merchant-httpd_exchanges.h b/src/backend/taler-merchant-httpd_exchanges.h
index 5fc57a3e..2a2e9b13 100644
--- a/src/backend/taler-merchant-httpd_exchanges.h
+++ b/src/backend/taler-merchant-httpd_exchanges.h
@@ -37,21 +37,6 @@ struct TMH_Exchange;
/**
- * Check if we would trust @a ex to deposit funds
- * into our account @a wm. Checks that both @a ex
- * is trusted and that @a ex allows wire transfers
- * into the account given in @a wm.
- *
- * @param ex the exchange to check
- * @param wm the wire method to check with
- * @return #GNUNET_OK if such a debit can happen
- */
-enum GNUNET_GenericReturnValue
-TMH_exchange_check_debit (struct TMH_Exchange *ex,
- const struct TMH_WireMethod *wm);
-
-
-/**
* Return the list of exchanges we would find
* acceptable for a payment given the @a wire_method.
*
@@ -96,6 +81,12 @@ typedef void
/**
+ * Abstraction of wire knowledge returned internally.
+ */
+struct TMH_ExchangeWireDetails;
+
+
+/**
* Function called with the result of a #TMH_EXCHANGES_wire4exchange()
* operation.
*
@@ -105,13 +96,13 @@ typedef void
typedef void
(*TMH_EXCHANGES_WireContinuation)(
void *cls,
- struct TMH_Exchange *wire);
+ const struct TMH_ExchangeWireDetails *wire);
/**
* Information we keep for a pending #MMH_EXCHANGES_keys4exchange() operation.
*/
-struct TMH_EXCHANGES_Find2Operation;
+struct TMH_EXCHANGES_KeysOperation;
/**
* Information we keep for a pending #MMH_EXCHANGES_wire4exchange() operation.
@@ -126,10 +117,20 @@ struct TMH_EXCHANGES_WireOperation;
* @param fc function to call with the handles for the exchange
* @param fc_cls closure for @a fc
*/
-struct TMH_EXCHANGES_Find2Operation *
-TMH_EXCHANGES_keys4exchange (const char *exchange,
- TMH_EXCHANGES_Find2Continuation fc,
- void *fc_cls);
+struct TMH_EXCHANGES_KeysOperation *
+TMH_EXCHANGES_keys4exchange (
+ const char *exchange,
+ TMH_EXCHANGES_Find2Continuation fc,
+ void *fc_cls);
+
+
+/**
+ * Abort pending keys details lookup operation.
+ *
+ * @param fo handle to operation to abort
+ */
+void
+TMH_EXCHANGES_keys4exchange_cancel (struct TMH_EXCHANGES_KeysOperation *fo);
/**
@@ -140,9 +141,20 @@ TMH_EXCHANGES_keys4exchange (const char *exchange,
* @param fc_cls closure for @a fc
*/
struct TMH_EXCHANGES_WireOperation *
-TMH_EXCHANGES_wire4exchange (const char *exchange,
- TMH_EXCHANGES_WireContinuation fc,
- void *fc_cls);
+TMH_EXCHANGES_wire4exchange (
+ const char *exchange,
+ TMH_EXCHANGES_WireContinuation fc,
+ void *fc_cls);
+
+
+/**
+ * Abort pending wire details lookup operation.
+ *
+ * @param fo handle to operation to abort
+ */
+void
+TMH_EXCHANGES_wire4exchange_cancel (
+ struct TMH_EXCHANGES_WireOperation *fo);
/**
@@ -157,27 +169,26 @@ TMH_EXCHANGES_wire4exchange (const char *exchange,
* #GNUNET_SYSERR if @a exchange_url did not yet respond properly to our /wire request
*/
enum GNUNET_GenericReturnValue
-TMH_EXCHANGES_lookup_wire_fee (const char *exchange_url,
- const char *wire_method,
- struct TALER_Amount *wire_fee);
+TMH_EXCHANGES_lookup_wire_fee (
+ const struct TMH_ExchangeWireDetails *wd,
+ const char *wire_method,
+ struct TALER_Amount *wire_fee);
/**
- * Abort pending keys details lookup operation.
- *
- * @param fo handle to operation to abort
- */
-void
-TMH_EXCHANGES_keys4exchange_cancel (struct TMH_EXCHANGES_Find2Operation *fo);
-
-
-/**
- * Abort pending wire details lookup operation.
+ * Check if we would trust @a ex to deposit funds
+ * into our account @a wm. Checks that both @a ex
+ * is trusted and that @a ex allows wire transfers
+ * into the account given in @a wm.
*
- * @param fo handle to operation to abort
+ * @param wd the wire details of the exchange to check
+ * @param wm the wire method to check with
+ * @return #GNUNET_OK if such a debit can happen
*/
-void
-TMH_EXCHANGES_wire4exchange_cancel (struct TMH_EXCHANGES_WireOperation *fo);
+enum GNUNET_GenericReturnValue
+TMH_exchange_check_debit (
+ const struct TMH_ExchangeWireDetails *wd,
+ const struct TMH_WireMethod *wm);
#endif
diff --git a/src/backend/taler-merchant-httpd_helper.c b/src/backend/taler-merchant-httpd_helper.c
index 407323e2..172cb0a1 100644
--- a/src/backend/taler-merchant-httpd_helper.c
+++ b/src/backend/taler-merchant-httpd_helper.c
@@ -732,111 +732,6 @@ TMH_trigger_webhook (const char *instance,
}
-/**
- * Closure for #add_matching_account().
- */
-struct ExchangeMatchContext
-{
- /**
- * Wire method to match, NULL for all.
- */
- const char *wire_method;
-
- /**
- * Array of accounts to return.
- */
- json_t *accounts;
-};
-
-
-/**
- * If the given account is feasible, add it to the array
- * of accounts we return.
- *
- * @param cls a `struct PostReserveContext`
- * @param payto_uri URI of the account
- * @param conversion_url URL of a conversion service
- * @param debit_restrictions restrictions for debits from account
- * @param credit_restrictions restrictions for credits to account
- * @param master_sig signature affirming the account
- */
-static void
-add_matching_account (void *cls,
- const char *payto_uri,
- const char *conversion_url,
- const json_t *debit_restrictions,
- const json_t *credit_restrictions,
- const struct TALER_MasterSignatureP *master_sig)
-{
- struct ExchangeMatchContext *rc = cls;
- char *method;
-
- method = TALER_payto_get_method (payto_uri);
- if ( (NULL == rc->wire_method) ||
- (0 == strcmp (method,
- rc->wire_method)) )
- {
- json_t *acc;
-
- acc = GNUNET_JSON_PACK (
- GNUNET_JSON_pack_string ("payto_uri",
- payto_uri),
- GNUNET_JSON_pack_data_auto ("master_sig",
- master_sig),
- GNUNET_JSON_pack_allow_null (
- GNUNET_JSON_pack_string ("conversion_url",
- conversion_url)),
- GNUNET_JSON_pack_array_incref ("credit_restrictions",
- (json_t *) credit_restrictions),
- GNUNET_JSON_pack_array_incref ("debit_restrictions",
- (json_t *) debit_restrictions)
- );
- GNUNET_assert (0 ==
- json_array_append_new (rc->accounts,
- acc));
- }
- GNUNET_free (method);
-}
-
-
-/**
- * Return JSON array with all of the exchange accounts
- * that support the given @a wire_method.
- *
- * FIXME: bad API, doesn't inherently ensure that we
- * actually did request /wire before!
- * => move into t-m-h_exchanges.c and integrate with /wire
- * logic there!
- *
- * @param master_pub master public key to match exchange by
- * @param wire_method NULL for any
- * @return JSON array with information about all matching accounts
- */
-json_t *
-TMH_exchange_accounts_by_method (
- const struct TALER_MasterPublicKeyP *master_pub,
- const char *wire_method)
-{
- struct ExchangeMatchContext emc = {
- .wire_method = wire_method,
- .accounts = json_array ()
- };
- enum GNUNET_DB_QueryStatus qs;
-
- GNUNET_assert (NULL != emc.accounts);
- qs = TMH_db->select_accounts_by_exchange (TMH_db->cls,
- master_pub,
- &add_matching_account,
- &emc);
- if (qs < 0)
- {
- json_decref (emc.accounts);
- return NULL;
- }
- return emc.accounts;
-}
-
-
enum GNUNET_GenericReturnValue
TMH_base_url_by_connection (struct MHD_Connection *connection,
const char *instance,
@@ -948,3 +843,104 @@ TMH_taler_uri_by_connection (struct MHD_Connection *connection,
}
return GNUNET_OK;
}
+
+
+/**
+ * Closure for #add_matching_account().
+ */
+struct ExchangeMatchContext
+{
+ /**
+ * Wire method to match, NULL for all.
+ */
+ const char *wire_method;
+
+ /**
+ * Array of accounts to return.
+ */
+ json_t *accounts;
+};
+
+
+/**
+ * If the given account is feasible, add it to the array
+ * of accounts we return.
+ *
+ * @param cls a `struct PostReserveContext`
+ * @param payto_uri URI of the account
+ * @param conversion_url URL of a conversion service
+ * @param debit_restrictions restrictions for debits from account
+ * @param credit_restrictions restrictions for credits to account
+ * @param master_sig signature affirming the account
+ */
+static void
+add_matching_account (
+ void *cls,
+ const char *payto_uri,
+ const char *conversion_url,
+ const json_t *debit_restrictions,
+ const json_t *credit_restrictions,
+ const struct TALER_MasterSignatureP *master_sig)
+{
+ struct ExchangeMatchContext *rc = cls;
+ char *method;
+
+ method = TALER_payto_get_method (payto_uri);
+ if ( (NULL == rc->wire_method) ||
+ (0 == strcmp (method,
+ rc->wire_method)) )
+ {
+ json_t *acc;
+
+ acc = GNUNET_JSON_PACK (
+ GNUNET_JSON_pack_string ("payto_uri",
+ payto_uri),
+ GNUNET_JSON_pack_data_auto ("master_sig",
+ master_sig),
+ GNUNET_JSON_pack_allow_null (
+ GNUNET_JSON_pack_string ("conversion_url",
+ conversion_url)),
+ GNUNET_JSON_pack_array_incref ("credit_restrictions",
+ (json_t *) credit_restrictions),
+ GNUNET_JSON_pack_array_incref ("debit_restrictions",
+ (json_t *) debit_restrictions)
+ );
+ GNUNET_assert (0 ==
+ json_array_append_new (rc->accounts,
+ acc));
+ }
+ GNUNET_free (method);
+}
+
+
+/**
+ * Return JSON array with all of the exchange accounts
+ * that support the given @a wire_method.
+ *
+ * @param master_pub master public key to match exchange by
+ * @param wire_method NULL for any
+ * @return JSON array with information about all matching accounts
+ */
+json_t *
+TMH_exchange_accounts_by_method (
+ const struct TALER_MasterPublicKeyP *master_pub,
+ const char *wire_method)
+{
+ struct ExchangeMatchContext emc = {
+ .wire_method = wire_method,
+ .accounts = json_array ()
+ };
+ enum GNUNET_DB_QueryStatus qs;
+
+ GNUNET_assert (NULL != emc.accounts);
+ qs = TMH_db->select_accounts_by_exchange (TMH_db->cls,
+ master_pub,
+ &add_matching_account,
+ &emc);
+ if (qs < 0)
+ {
+ json_decref (emc.accounts);
+ return NULL;
+ }
+ return emc.accounts;
+}
diff --git a/src/backend/taler-merchant-httpd_post-orders-ID-abort.c b/src/backend/taler-merchant-httpd_post-orders-ID-abort.c
index f5d76436..f63404b4 100644
--- a/src/backend/taler-merchant-httpd_post-orders-ID-abort.c
+++ b/src/backend/taler-merchant-httpd_post-orders-ID-abort.c
@@ -176,7 +176,7 @@ struct AbortContext
* the exchange used for this transaction; NULL if no operation is
* pending.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* URL of the exchange used for the last @e fo.
@@ -532,7 +532,7 @@ process_abort_with_exchange (void *cls,
rdi->processed = true;
ac->pending--;
rdi->rh = TALER_EXCHANGE_refund (
- merchant_curl_ctx,
+ TMH_curl_ctx,
ac->current_exchange,
keys,
&rdi->amount_with_fee,
diff --git a/src/backend/taler-merchant-httpd_post-orders-ID-pay.c b/src/backend/taler-merchant-httpd_post-orders-ID-pay.c
index 3a051a3c..75bc4345 100644
--- a/src/backend/taler-merchant-httpd_post-orders-ID-pay.c
+++ b/src/backend/taler-merchant-httpd_post-orders-ID-pay.c
@@ -173,7 +173,7 @@ struct ExchangeGroup
* the exchange used for this transaction; NULL if no operation is
* pending.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* Handle for operation to lookup /wire from
@@ -189,6 +189,12 @@ struct ExchangeGroup
const char *exchange_url;
/**
+ * Wire fee that applies to this exchange for the
+ * given payment context's wire method.
+ */
+ struct TALER_Amount wire_fee;
+
+ /**
* true if we already tried a forced /keys download.
*/
bool tried_force_keys;
@@ -454,7 +460,7 @@ struct KycContext
/**
* Looking for the exchange.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* Exchange this is about.
@@ -636,20 +642,19 @@ resume_pay_with_response (struct PayContext *pc,
* Resume payment processing with an error.
*
* @param pc operation to resume
- * @param http_status http status code to return
* @param ec taler error code to return
* @param msg human readable error message
*/
static void
resume_pay_with_error (struct PayContext *pc,
- unsigned int http_status,
enum TALER_ErrorCode ec,
const char *msg)
{
- resume_pay_with_response (pc,
- http_status,
- TALER_MHD_make_error (ec,
- msg));
+ resume_pay_with_response (
+ pc,
+ TALER_ErrorCode_get_http_status_safe (ec),
+ TALER_MHD_make_error (ec,
+ msg));
}
@@ -795,7 +800,7 @@ process_kyc_with_exchange (
return;
}
kc->dg = TALER_EXCHANGE_deposits_get (
- merchant_curl_ctx,
+ TMH_curl_ctx,
kc->exchange_url,
keys,
&kc->mi->merchant_priv,
@@ -1007,7 +1012,6 @@ handle_batch_deposit_ok (struct ExchangeGroup *eg,
GNUNET_break (GNUNET_DB_STATUS_HARD_ERROR == qs);
/* Forward error including 'proof' for the body */
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_STORE_FAILED,
"insert_deposit");
return;
@@ -1023,7 +1027,6 @@ handle_batch_deposit_ok (struct ExchangeGroup *eg,
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_COMMIT_FAILED,
"insert_deposit");
}
@@ -1032,7 +1035,6 @@ handle_batch_deposit_ok (struct ExchangeGroup *eg,
if (GNUNET_DB_STATUS_SOFT_ERROR == qs)
{
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_SOFT_FAILURE,
"insert_deposit");
return;
@@ -1160,6 +1162,7 @@ process_pay_with_keys (
unsigned int group_size;
eg->fo = NULL;
+ GNUNET_SCHEDULER_begin_async_scope (&hc->async_scope_id);
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
"Processing payment with exchange %s\n",
eg->exchange_url);
@@ -1168,11 +1171,10 @@ process_pay_with_keys (
{
GNUNET_break_op (0);
pc->pending_at_eg--;
- resume_pay_with_response (
+ resume_pay_with_error (
pc,
- MHD_HTTP_GATEWAY_TIMEOUT,
- TALER_MHD_MAKE_JSON_PACK (
- TALER_JSON_pack_ec (TALER_EC_MERCHANT_GENERIC_EXCHANGE_TIMEOUT)));
+ TALER_EC_MERCHANT_GENERIC_EXCHANGE_TIMEOUT,
+ NULL);
return;
}
@@ -1286,7 +1288,8 @@ AGE_FAIL:
&dc->cdd.h_age_commitment);
GNUNET_free (dc->age_commitment.keys);
}
- else if (is_age_restricted_denom && dc->no_h_age_commitment)
+ else if (is_age_restricted_denom &&
+ dc->no_h_age_commitment)
{
/* The contract did not ask for a minimum_age but the client paid
* with a coin that has age restriction enabled. We lack the hash
@@ -1336,7 +1339,6 @@ AGE_FAIL:
for (unsigned int i = 0; i<pc->coins_cnt; i++)
{
struct DepositConfirmation *dc = &pc->dc[i];
- enum GNUNET_GenericReturnValue ret;
if (dc->found_in_db)
continue;
@@ -1344,36 +1346,13 @@ AGE_FAIL:
eg->exchange_url))
continue;
cdds[i] = dc->cdd;
- ret = TMH_EXCHANGES_lookup_wire_fee (dc->exchange_url,
- pc->wm->wire_method,
- &dc->wire_fee);
- if (GNUNET_OK != ret)
- {
- enum TALER_ErrorCode ec;
-
- fprintf (stderr,
- "%d\n",
- ret);
- ec = (GNUNET_NO == ret)
- ? TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_WIRE_METHOD_UNSUPPORTED
- : TALER_EC_MERCHANT_GENERIC_EXCHANGE_WIRE_REQUEST_FAILED;
- pc->pending_at_eg--;
- GNUNET_break_op (0);
- resume_pay_with_response (
- pc,
- TALER_ErrorCode_get_http_status_safe (ec),
- TALER_MHD_MAKE_JSON_PACK (
- TALER_JSON_pack_ec (ec),
- GNUNET_JSON_pack_string ("wire_method",
- pc->wm->wire_method)));
- return;
- }
+ dc->wire_fee = eg->wire_fee;
}
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
"Initiating batch deposit with %u coins\n",
group_size);
eg->bdh = TALER_EXCHANGE_batch_deposit (
- merchant_curl_ctx,
+ TMH_curl_ctx,
eg->exchange_url,
keys,
&dcd,
@@ -1413,23 +1392,24 @@ AGE_FAIL:
static void
process_pay_with_wire (
void *cls,
- struct TMH_Exchange *wire)
+ const struct TMH_ExchangeWireDetails *wire)
{
struct ExchangeGroup *eg = cls;
struct PayContext *pc = eg->pc;
+ struct TMH_HandlerContext *hc = pc->hc;
+ enum GNUNET_GenericReturnValue ret;
eg->gwo = NULL;
+ GNUNET_SCHEDULER_begin_async_scope (&hc->async_scope_id);
if (NULL == wire)
{
GNUNET_break_op (0);
pc->pending_at_eg--;
/* FIXME: define more specific error code... */
- resume_pay_with_response (
+ resume_pay_with_error (
pc,
- MHD_HTTP_BAD_GATEWAY,
- TALER_MHD_MAKE_JSON_PACK (
- TALER_JSON_pack_ec (
- TALER_EC_MERCHANT_GENERIC_EXCHANGE_CONNECT_FAILURE)));
+ TALER_EC_MERCHANT_GENERIC_EXCHANGE_CONNECT_FAILURE,
+ NULL);
return;
}
if (GNUNET_OK !=
@@ -1438,16 +1418,32 @@ process_pay_with_wire (
{
GNUNET_break_op (0);
pc->pending_at_eg--;
- resume_pay_with_response (
+ resume_pay_with_error (
pc,
- MHD_HTTP_CONFLICT,
- TALER_MHD_MAKE_JSON_PACK (
- TALER_JSON_pack_ec (
- TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_WIRE_METHOD_UNSUPPORTED)));
+ TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_WIRE_METHOD_UNSUPPORTED,
+ NULL);
+ return;
+ }
+ ret = TMH_EXCHANGES_lookup_wire_fee (wire,
+ pc->wm->wire_method,
+ &eg->wire_fee);
+ if (GNUNET_OK != ret)
+ {
+ enum TALER_ErrorCode ec;
+
+ ec = (GNUNET_NO == ret)
+ ? TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_WIRE_METHOD_UNSUPPORTED
+ : TALER_EC_MERCHANT_GENERIC_EXCHANGE_WIRE_REQUEST_FAILED;
+ pc->pending_at_eg--;
+ GNUNET_break_op (0);
+ resume_pay_with_error (
+ pc,
+ ec,
+ pc->wm->wire_method);
return;
}
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "Fetching /keys for %s\n",
+ "Got /wire for %s, now going for /keys\n",
eg->exchange_url);
eg->fo = TMH_EXCHANGES_keys4exchange (eg->exchange_url,
&process_pay_with_keys,
@@ -1457,7 +1453,6 @@ process_pay_with_wire (
GNUNET_break (0);
pc->pending_at_eg--;
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_EXCHANGE_LOOKUP_FAILED,
"Failed to lookup exchange by URL");
return;
@@ -1503,7 +1498,6 @@ start_batch_deposits (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_EXCHANGE_LOOKUP_FAILED,
"Failed to lookup exchange by URL");
return;
@@ -1665,7 +1659,6 @@ check_payment_sufficient (struct PayContext *pc)
GNUNET_break (0);
/* Overflow in these amounts? Very strange. */
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_AMOUNT_OVERFLOW,
"Overflow adding up amounts");
return false;
@@ -1676,7 +1669,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break_op (0);
resume_pay_with_error (pc,
- MHD_HTTP_BAD_REQUEST,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_FEES_EXCEED_PAYMENT,
"Deposit fees exceed coin's contribution");
return false;
@@ -1703,7 +1695,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break_op (0);
resume_pay_with_error (pc,
- MHD_HTTP_CONFLICT,
TALER_EC_GENERIC_CURRENCY_MISMATCH,
total_wire_fee.currency);
return false;
@@ -1715,7 +1706,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_EXCHANGE_WIRE_FEE_ADDITION_FAILED,
"could not add exchange wire fee to total");
return false;
@@ -1750,7 +1740,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_CONFLICT,
TALER_EC_GENERIC_CURRENCY_MISMATCH,
total_wire_fee.currency);
return false;
@@ -1787,7 +1776,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_AMOUNT_OVERFLOW,
"Overflow adding up amounts");
return false;
@@ -1815,7 +1803,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_AMOUNT_OVERFLOW,
"Overflow adding up amounts");
return false;
@@ -1839,7 +1826,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_REFUNDS_EXCEED_PAYMENTS,
"refunded amount exceeds total payments");
return false;
@@ -1854,7 +1840,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break_op (0);
resume_pay_with_error (pc,
- MHD_HTTP_PAYMENT_REQUIRED,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_REFUNDED,
"contract not paid up due to refunds");
}
@@ -1863,7 +1848,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break_op (0);
resume_pay_with_error (pc,
- MHD_HTTP_NOT_ACCEPTABLE,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_INSUFFICIENT_DUE_TO_FEES,
"contract not paid up due to fees (client may have calculated them badly)");
}
@@ -1871,7 +1855,6 @@ check_payment_sufficient (struct PayContext *pc)
{
GNUNET_break_op (0);
resume_pay_with_error (pc,
- MHD_HTTP_NOT_ACCEPTABLE,
TALER_EC_MERCHANT_POST_ORDERS_ID_PAY_PAYMENT_INSUFFICIENT,
"payment insufficient");
}
@@ -1982,7 +1965,6 @@ execute_pay_transaction (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_SOFT_FAILURE,
NULL);
return;
@@ -2013,7 +1995,6 @@ execute_pay_transaction (struct PayContext *pc)
{
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_START_FAILED,
NULL);
return;
@@ -2039,7 +2020,6 @@ execute_pay_transaction (struct PayContext *pc)
/* Always report on hard error as well to enable diagnostics */
GNUNET_break (GNUNET_DB_STATUS_HARD_ERROR == qs);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_FETCH_FAILED,
"lookup deposits");
return;
@@ -2067,7 +2047,6 @@ execute_pay_transaction (struct PayContext *pc)
/* Always report on hard error as well to enable diagnostics */
GNUNET_break (GNUNET_DB_STATUS_HARD_ERROR == qs);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_FETCH_FAILED,
"lookup refunds");
return;
@@ -2117,7 +2096,6 @@ execute_pay_transaction (struct PayContext *pc)
}
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_STORE_FAILED,
"mark contract paid");
return;
@@ -2153,7 +2131,6 @@ execute_pay_transaction (struct PayContext *pc)
}
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_STORE_FAILED,
"failed to trigger webhooks");
return;
@@ -2175,7 +2152,6 @@ execute_pay_transaction (struct PayContext *pc)
}
GNUNET_break (0);
resume_pay_with_error (pc,
- MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_COMMIT_FAILED,
NULL);
return;
@@ -2740,7 +2716,6 @@ handle_pay_timeout (void *cls)
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
"Resuming pay with error after timeout\n");
resume_pay_with_error (pc,
- MHD_HTTP_GATEWAY_TIMEOUT,
TALER_EC_MERCHANT_GENERIC_EXCHANGE_TIMEOUT,
NULL);
}
diff --git a/src/backend/taler-merchant-httpd_post-orders-ID-refund.c b/src/backend/taler-merchant-httpd_post-orders-ID-refund.c
index a20f6b12..ded6ff9d 100644
--- a/src/backend/taler-merchant-httpd_post-orders-ID-refund.c
+++ b/src/backend/taler-merchant-httpd_post-orders-ID-refund.c
@@ -51,7 +51,7 @@ struct CoinRefund
/**
* Request to connect to the target exchange.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* Handle for the refund operation with the exchange.
@@ -456,7 +456,7 @@ exchange_found_cb (void *cls,
return;
}
cr->rh = TALER_EXCHANGE_refund (
- merchant_curl_ctx,
+ TMH_curl_ctx,
cr->exchange_url,
keys,
&cr->refund_amount,
diff --git a/src/backend/taler-merchant-httpd_post-tips-ID-pickup.c b/src/backend/taler-merchant-httpd_post-tips-ID-pickup.c
index a87ea710..e8f9ba45 100644
--- a/src/backend/taler-merchant-httpd_post-tips-ID-pickup.c
+++ b/src/backend/taler-merchant-httpd_post-tips-ID-pickup.c
@@ -73,7 +73,7 @@ struct PlanchetOperation
/**
* Find operation (while active), later NULL.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* Withdraw handle (NULL while @e fo is active).
@@ -145,7 +145,7 @@ struct PickupContext
/**
* Find operation (while active), later NULL.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* Which reserve are we draining?
@@ -409,7 +409,7 @@ do_withdraw (void *cls,
TALER_MHD_daemon_trigger (); /* we resumed, kick MHD */
return;
}
- po->w2h = TALER_EXCHANGE_withdraw2 (merchant_curl_ctx,
+ po->w2h = TALER_EXCHANGE_withdraw2 (TMH_curl_ctx,
pc->exchange_url,
keys,
&po->pd,
diff --git a/src/backend/taler-merchant-httpd_private-get-instances-ID-kyc.c b/src/backend/taler-merchant-httpd_private-get-instances-ID-kyc.c
index 7c2f7a2c..f5b9d36e 100644
--- a/src/backend/taler-merchant-httpd_private-get-instances-ID-kyc.c
+++ b/src/backend/taler-merchant-httpd_private-get-instances-ID-kyc.c
@@ -73,7 +73,7 @@ struct ExchangeKycRequest
/**
* Find operation where we connect to the respective exchange.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* KYC request this exchange request is made for.
@@ -676,7 +676,7 @@ kyc_with_exchange (void *cls,
TALER_payto_hash (ekr->payto_uri,
&h_payto);
ekr->kyc = TALER_EXCHANGE_kyc_check (
- merchant_curl_ctx,
+ TMH_curl_ctx,
ekr->exchange_url,
keys,
ekr->exchange_kyc_serial,
diff --git a/src/backend/taler-merchant-httpd_private-get-orders-ID.c b/src/backend/taler-merchant-httpd_private-get-orders-ID.c
index 788c7bf1..6d2140d0 100644
--- a/src/backend/taler-merchant-httpd_private-get-orders-ID.c
+++ b/src/backend/taler-merchant-httpd_private-get-orders-ID.c
@@ -73,7 +73,7 @@ struct TransferQuery
/**
* Handle for ongoing exchange operation.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* Overall request this TQ belongs with.
@@ -614,7 +614,7 @@ exchange_found_cb (void *cls,
return;
}
tq->dgh = TALER_EXCHANGE_deposits_get (
- merchant_curl_ctx,
+ TMH_curl_ctx,
tq->exchange_url,
keys,
&gorc->hc->instance->merchant_priv,
diff --git a/src/backend/taler-merchant-httpd_private-get-reserves-ID.c b/src/backend/taler-merchant-httpd_private-get-reserves-ID.c
index 27ea2be1..4eaa6538 100644
--- a/src/backend/taler-merchant-httpd_private-get-reserves-ID.c
+++ b/src/backend/taler-merchant-httpd_private-get-reserves-ID.c
@@ -70,18 +70,19 @@ struct GetReserveContext
* @param tips information about the tips created by this reserve
*/
static void
-handle_reserve_details (void *cls,
- struct GNUNET_TIME_Timestamp creation_time,
- struct GNUNET_TIME_Timestamp expiration_time,
- const struct TALER_Amount *merchant_initial_amount,
- const struct TALER_Amount *exchange_initial_amount,
- const struct TALER_Amount *picked_up_amount,
- const struct TALER_Amount *committed_amount,
- bool active,
- const struct TALER_MasterPublicKeyP *master_pub,
- const char *exchange_url,
- unsigned int tips_length,
- const struct TALER_MERCHANTDB_TipDetails *tips)
+handle_reserve_details (
+ void *cls,
+ struct GNUNET_TIME_Timestamp creation_time,
+ struct GNUNET_TIME_Timestamp expiration_time,
+ const struct TALER_Amount *merchant_initial_amount,
+ const struct TALER_Amount *exchange_initial_amount,
+ const struct TALER_Amount *picked_up_amount,
+ const struct TALER_Amount *committed_amount,
+ bool active,
+ const struct TALER_MasterPublicKeyP *master_pub,
+ const char *exchange_url,
+ unsigned int tips_length,
+ const struct TALER_MERCHANTDB_TipDetails *tips)
{
struct GetReserveContext *ctx = cls;
json_t *tips_json;
diff --git a/src/backend/taler-merchant-httpd_private-post-reserves.c b/src/backend/taler-merchant-httpd_private-post-reserves.c
index 00e4a4ee..5ca8e768 100644
--- a/src/backend/taler-merchant-httpd_private-post-reserves.c
+++ b/src/backend/taler-merchant-httpd_private-post-reserves.c
@@ -86,7 +86,7 @@ struct PostReserveContext
/**
* Handle for contacting the exchange for /keys.
*/
- struct TMH_EXCHANGES_Find2Operation *fo;
+ struct TMH_EXCHANGES_KeysOperation *fo;
/**
* Handle for contacting the exchange for /wire.
@@ -223,7 +223,7 @@ resume_request (struct PostReserveContext *rc)
*/
static void
wire_cb (void *cls,
- struct TMH_Exchange *wire)
+ const struct TMH_ExchangeWireDetails *wire)
{
struct PostReserveContext *rc = cls;
diff --git a/src/backend/taler-merchant-httpd_reserves.c b/src/backend/taler-merchant-httpd_reserves.c
index 83b70010..31dec87f 100644
--- a/src/backend/taler-merchant-httpd_reserves.c
+++ b/src/backend/taler-merchant-httpd_reserves.c
@@ -226,7 +226,7 @@ try_now (void *cls)
struct Reserve *r = cls;
r->tt = NULL;
- r->gh = TALER_EXCHANGE_reserves_get (merchant_curl_ctx,
+ r->gh = TALER_EXCHANGE_reserves_get (TMH_curl_ctx,
r->exchange_url,
&r->reserve_pub,
LONGPOLL_DELAY,