diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/exchangedb/exchange_do_get_link_data.sql | 59 | ||||
| -rw-r--r-- | src/exchangedb/pg_get_link_data.c | 70 | ||||
| -rw-r--r-- | src/exchangedb/procedures.sql.in | 1 | ||||
| -rw-r--r-- | src/exchangedb/test_exchangedb_populate_link_data.c | 275 | 
4 files changed, 259 insertions, 146 deletions
| diff --git a/src/exchangedb/exchange_do_get_link_data.sql b/src/exchangedb/exchange_do_get_link_data.sql new file mode 100644 index 00000000..a76f4aaa --- /dev/null +++ b/src/exchangedb/exchange_do_get_link_data.sql @@ -0,0 +1,59 @@ +-- +-- This file is part of TALER +-- Copyright (C) 2014--2022 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 +-- Foundation; either version 3, or (at your option) any later version. +-- +-- TALER is distributed in the hope that it will be useful, but WITHOUT ANY +-- WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +-- A PARTICULAR PURPOSE.  See the GNU General Public License for more details. +-- +-- You should have received a copy of the GNU General Public License along with +-- TALER; see the file COPYING.  If not, see <http://www.gnu.org/licenses/> +-- +/*DROP FUNCTION exchange_do_refund_by_coin( +  IN in_coin_pub BYTEA, +  IN in_merchant_pub BYTEA, +  IN in_h_contract BYTEA +);*/ +CREATE OR REPLACE FUNCTION exchange_do_get_link_data( +  IN in_coin_pub BYTEA +) +RETURNS SETOF record +LANGUAGE plpgsql +AS $$ +DECLARE +  curs CURSOR +  FOR +  SELECT +   melt_serial_id +  FROM refresh_commitments +  WHERE old_coin_pub=in_coin_pub; + +DECLARE +  i RECORD; +BEGIN +OPEN curs; +LOOP +    FETCH NEXT FROM curs INTO i; +    EXIT WHEN NOT FOUND; +    RETURN QUERY +      SELECT +       tp.transfer_pub +      ,denoms.denom_pub +      ,rrc.ev_sig +      ,rrc.ewv +      ,rrc.link_sig +      ,rrc.freshcoin_index +      ,rrc.coin_ev +      FROM refresh_revealed_coins rrc +       JOIN refresh_transfer_keys tp +         ON (tp.melt_serial_id=rrc.melt_serial_id) +       JOIN denominations denoms +         ON (rrc.denominations_serial=denoms.denominations_serial) +       WHERE rrc.melt_serial_id =i.melt_serial_id; +END LOOP; +CLOSE curs; +END $$; diff --git a/src/exchangedb/pg_get_link_data.c b/src/exchangedb/pg_get_link_data.c index 9bc4c9b0..26225a13 100644 --- a/src/exchangedb/pg_get_link_data.c +++ b/src/exchangedb/pg_get_link_data.c @@ -177,11 +177,35 @@ TEH_PG_get_link_data (void *cls,    };    enum GNUNET_DB_QueryStatus qs;    struct LinkDataContext ldctx; +  static int percent_refund = -2; +  const char *query; -  if (NULL == getenv ("NEW_LOGIC")) +  if (-2 == percent_refund)    { +    const char *mode = getenv ("NEW_LOGIC"); +    char dummy; + +    if ( (NULL==mode) || +         (1 != sscanf (mode, +                       "%d%c", +                       &percent_refund, +                       &dummy)) ) +      { +        if (NULL != mode) +          GNUNET_log (GNUNET_ERROR_TYPE_ERROR, +                      "Bad mode `%s' specified\n", +                      mode); +      } +      if (NULL==mode) +        percent_refund=0; +  } + +  switch (percent_refund) +  { +  case 0: +    query="get_link";      PREPARE (pg, -             "get_link", +             query,               "SELECT "               " tp.transfer_pub"               ",denoms.denom_pub" @@ -199,15 +223,15 @@ TEH_PG_get_link_data (void *cls,               "       ON (rrc.denominations_serial = denoms.denominations_serial)"               " WHERE old_coin_pub=$1"               " ORDER BY tp.transfer_pub, rrc.freshcoin_index ASC"); -  } - -  else -  { +    break; +  case 1: +    query="get_link_v1";      PREPARE (pg, -             "get_link", +             query,               "WITH rc AS MATERIALIZED ("               "SELECT" -             "* FROM refresh_commitments" +             " melt_serial_id" +             " FROM refresh_commitments"               " WHERE old_coin_pub=$1"               ")"               "SELECT " @@ -217,13 +241,37 @@ TEH_PG_get_link_data (void *cls,               ",rrc.ewv"               ",rrc.link_sig"               ",rrc.freshcoin_index" -             ",rrc.coin_ev" -             " FROM refresh_revealed_coins rrc" +             ",rrc.coin_ev " +             "FROM " +             "refresh_revealed_coins rrc"               "  JOIN refresh_transfer_keys tp"               "   USING (melt_serial_id)"               "  JOIN denominations denoms"               "   USING (denominations_serial)" +             " WHERE rrc.melt_serial_id = (SELECT melt_serial_id FROM rc)"               " ORDER BY tp.transfer_pub, rrc.freshcoin_index ASC"); +    break; +  case 2: +    query="get_link_v2"; +    PREPARE (pg, +             query, +             "SELECT" +             " *" +             " FROM" +             " exchange_do_get_link_data" +             " ($1) " +             " AS " +             " (transfer_pub BYTEA" +             " ,denom_pub BYTEA" +             " ,ev_sig BYTEA" +             " ,ewv BYTEA" +             " ,link_sig BYTEA" +             " ,freshcoin_index INT4" +             " ,coin_ev BYTEA);"); +    break; +  default: +    GNUNET_break (0); +    return GNUNET_DB_STATUS_HARD_ERROR;    }    ldctx.ldc = ldc; @@ -231,7 +279,7 @@ TEH_PG_get_link_data (void *cls,    ldctx.last = NULL;    ldctx.status = GNUNET_OK;    qs = GNUNET_PQ_eval_prepared_multi_select (pg->conn, -                                             "get_link", +                                             query,                                               params,                                               &add_ldl,                                               &ldctx); diff --git a/src/exchangedb/procedures.sql.in b/src/exchangedb/procedures.sql.in index ef6341a1..a53396c3 100644 --- a/src/exchangedb/procedures.sql.in +++ b/src/exchangedb/procedures.sql.in @@ -46,5 +46,6 @@ SET search_path TO exchange;  #include "exchange_do_batch8_reserves_in_insert.sql"  #include "exchange_do_refund_by_coin.sql"  #include "exchange_do_get_ready_deposit.sql" +#include "exchange_do_get_link_data.sql"  COMMIT; diff --git a/src/exchangedb/test_exchangedb_populate_link_data.c b/src/exchangedb/test_exchangedb_populate_link_data.c index 1323f3b3..a4ddce1a 100644 --- a/src/exchangedb/test_exchangedb_populate_link_data.c +++ b/src/exchangedb/test_exchangedb_populate_link_data.c @@ -49,9 +49,10 @@  #define CURRENCY "EUR"  #define RSA_KEY_SIZE 1024 -#define ROUNDS 10 -#define NUM_ROWS 1000 +#define ROUNDS 2 +#define NUM_ROWS 10  #define MELT_NEW_COINS 5 +#define DENOMINATIONS 5  #define MELT_NOREVEAL_INDEX 1  /**   * Database plugin under test. @@ -63,7 +64,7 @@ static struct TALER_DenomFeeSet fees;   */  static struct DenomKeyPair **new_dkp;  static int result; -static struct TALER_EXCHANGEDB_RefreshRevealedCoin *revealed_coins; +  static struct TALER_TransferPrivateKeyP tprivs[TALER_CNC_KAPPA];  static struct TALER_TransferPublicKeyP tpub;  struct DenomKeyPair @@ -165,7 +166,6 @@ create_denom_key_pair (unsigned int size,    }    return dkp;  } -  /**   * Function called with the session hashes and transfer secret   * information for a given coin. @@ -181,30 +181,10 @@ handle_link_data_cb (void *cls,  {    (void) cls;    (void) transfer_pub; -  for (const struct TALER_EXCHANGEDB_LinkList *ldlp = ldl; -       NULL != ldlp; -       ldlp = ldlp->next) -  { -    bool found; - -    found = false; -    for (unsigned int cnt = 0; cnt < MELT_NEW_COINS; cnt++) -    { -      if ( (0 == -            TALER_denom_pub_cmp (&ldlp->denom_pub, -                                 &new_dkp[cnt]->pub)) && -           (0 == -            TALER_blinded_denom_sig_cmp (&ldlp->ev_sig, -                                         &revealed_coins[cnt].coin_sig)) ) -      { -        found = true; -        break; -      } -    } -    GNUNET_assert (GNUNET_NO != found); -  } +  (void) ldl;  } +  /**   * Main function that will be run by the scheduler.   * @@ -221,13 +201,11 @@ run (void *cls)    struct DenomKeyPair *dkp = NULL;    struct TALER_EXCHANGEDB_Deposit *depos=NULL;    struct TALER_Amount value; -  struct TALER_DenominationPublicKey *new_denom_pubs = NULL;    struct GNUNET_TIME_Relative times = GNUNET_TIME_UNIT_ZERO;    unsigned long long sqrs=0;    struct TALER_EXCHANGEDB_Refund *ref=NULL;    unsigned int *perm;    unsigned long long duration_sq; -  struct TALER_EXCHANGEDB_RefreshRevealedCoin *ccoin;    struct TALER_ExchangeWithdrawValues alg_values = {      .cipher = TALER_DENOMINATION_RSA      }; @@ -237,7 +215,7 @@ run (void *cls)    depos = GNUNET_new_array (ROUNDS +1,                              struct TALER_EXCHANGEDB_Deposit);    refresh = GNUNET_new_array (ROUNDS +1, -                            struct TALER_EXCHANGEDB_Refresh); +                              struct TALER_EXCHANGEDB_Refresh);    if (NULL ==        (plugin = TALER_EXCHANGEDB_plugin_load (cfg))) @@ -282,51 +260,18 @@ run (void *cls)    {      //PAIR KEY LIST      new_dkp = GNUNET_new_array (MELT_NEW_COINS, -                              struct DenomKeyPair *); -    //PUBLIC KEY LIST -    new_denom_pubs = GNUNET_new_array (MELT_NEW_COINS, -                                       struct TALER_DenominationPublicKey); -    //REFRESH REVEAL COIN LIST -    revealed_coins -      = GNUNET_new_array (MELT_NEW_COINS, -                          struct TALER_EXCHANGEDB_RefreshRevealedCoin); +                                struct DenomKeyPair *); +      for (unsigned int cnt = 0; cnt < MELT_NEW_COINS; cnt++) -      { -        struct GNUNET_TIME_Timestamp now; -        struct TALER_BlindedRsaPlanchet *rp; -        struct TALER_BlindedPlanchet *bp; - -        now = GNUNET_TIME_timestamp_get (); -        //5 KEY PAIR -        new_dkp[cnt] = create_denom_key_pair (RSA_KEY_SIZE, -                                              now, -                                              &value, -                                              &fees); -        GNUNET_assert (NULL != new_dkp[cnt]); -        new_denom_pubs[cnt] = new_dkp[cnt]->pub; -        ccoin = &revealed_coins[cnt]; -        bp = &ccoin->blinded_planchet; -        bp->cipher = TALER_DENOMINATION_RSA; -        rp = &bp->details.rsa_blinded_planchet; -        rp->blinded_msg_size = 1 + (size_t) GNUNET_CRYPTO_random_u64 ( -                                                                      GNUNET_CRYPTO_QUALITY_WEAK, -                                                                      (RSA_KEY_SIZE / 8) - 1); -        rp->blinded_msg = GNUNET_malloc (rp->blinded_msg_size); -        GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_WEAK, -                                    rp->blinded_msg, -                                    rp->blinded_msg_size); -        TALER_denom_pub_hash (&new_dkp[cnt]->pub, -                              &ccoin->h_denom_pub); -        ccoin->exchange_vals = alg_values; -        TALER_coin_ev_hash (bp, -                            &ccoin->h_denom_pub, -                            &ccoin->coin_envelope_hash); -        GNUNET_assert (GNUNET_OK == -                     TALER_denom_sign_blinded (&ccoin->coin_sig, -                                               &new_dkp[cnt]->priv, -                                               true, -                                               bp)); -      } +    { +      struct GNUNET_TIME_Timestamp now = GNUNET_TIME_timestamp_get (); +       +      new_dkp[cnt] = create_denom_key_pair (RSA_KEY_SIZE, +                                            now, +                                            &value, +                                            &fees); +      GNUNET_assert (NULL != new_dkp[cnt]); +    }    }    perm = GNUNET_CRYPTO_random_permute (GNUNET_CRYPTO_QUALITY_NONCE,                                         NUM_ROWS); @@ -335,60 +280,111 @@ run (void *cls)            plugin->start (plugin->cls,                           "Transaction"));    for (unsigned int j = 0; j < NUM_ROWS; j++) +  { +    union TALER_DenominationBlindingKeyP bks; +    struct TALER_CoinPubHashP c_hash; +    unsigned int i = perm[j]; +    uint64_t known_coin_id; +    struct TALER_EXCHANGEDB_CollectableBlindcoin cbc; +    if (i >= ROUNDS) +      i = ROUNDS; /* throw-away slot, do not keep around */ +    RND_BLK (&depos[i].coin.coin_pub); +    ZR_BLK (&cbc); +    TALER_denom_pub_hash (&new_dkp[(unsigned int)rand()%MELT_NEW_COINS]->pub, +                          &depos[i].coin.denom_pub_hash); + + +          { -      union TALER_DenominationBlindingKeyP bks; -      struct TALER_CoinSpendPublicKeyP coin_pub; -      struct TALER_CoinPubHashP c_hash; -      unsigned int k = (unsigned int)rand()%5; -      unsigned int i = perm[j]; -      if (i >= ROUNDS) -        i = ROUNDS; /* throw-away slot, do not keep around */ -      RND_BLK (&coin_pub); -      RND_BLK (&c_hash); - -      RND_BLK (&depos[i].coin.coin_pub); -      TALER_denom_pub_hash (&new_dkp[k]->pub, -                            &depos[i].coin.denom_pub_hash); -      GNUNET_assert (GNUNET_OK == -                     TALER_denom_sig_unblind (&depos[i].coin.denom_sig, -                                              &ccoin->coin_sig, -                                              &bks, -                                              &c_hash, -                                              &alg_values, -                                              &new_dkp[k]->pub)); +      struct TALER_EXCHANGEDB_RefreshRevealedCoin revealed_coins[MELT_NEW_COINS]; +       +      for (unsigned int p=0;p<MELT_NEW_COINS;p++) +        { +          struct TALER_EXCHANGEDB_RefreshRevealedCoin *revealed_coin = &revealed_coins[p]; +          struct TALER_BlindedPlanchet *bp = &revealed_coin->blinded_planchet; +          struct TALER_BlindedRsaPlanchet *rp = &bp->details.rsa_blinded_planchet; +           +          /* h_coin_ev must be unique, but we only have MELT_NEW_COINS created +             above for NUM_ROWS iterations; instead of making "all new" coins, +             we simply randomize the hash here as nobody is checking for consistency +             anyway ;-) */ +          bp->cipher = TALER_DENOMINATION_RSA; +          rp->blinded_msg_size = 1 + (size_t) GNUNET_CRYPTO_random_u64 ( +                                                                        GNUNET_CRYPTO_QUALITY_WEAK, +                                                                        (RSA_KEY_SIZE / 8) - 1); +          rp->blinded_msg = GNUNET_malloc (rp->blinded_msg_size); +          GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_WEAK, +                                      rp->blinded_msg, +                                      rp->blinded_msg_size); +          TALER_denom_pub_hash (&new_dkp[(unsigned int)rand()%MELT_NEW_COINS]->pub, +                                &revealed_coin->h_denom_pub); +          revealed_coin->exchange_vals = alg_values; +          TALER_coin_ev_hash (bp, +                              &revealed_coin->h_denom_pub, +                              &revealed_coin->coin_envelope_hash);  +          GNUNET_assert (GNUNET_OK == +                         TALER_denom_sign_blinded (&revealed_coin->coin_sig, +                                                   &new_dkp[(unsigned int)rand()%MELT_NEW_COINS]->priv, +                                                   true, +                                                   bp)); +          GNUNET_assert ( +                         GNUNET_OK == +                         TALER_denom_sign_blinded ( +                                                   &cbc.sig, +                                                   &new_dkp[(unsigned int)rand()%MELT_NEW_COINS]->priv, +                                                   false, +                                                   bp)); +        } +    GNUNET_assert (GNUNET_OK == +                   TALER_denom_sig_unblind (&depos[i].coin.denom_sig, +                                            &cbc.sig, +                                            &bks, +                                            &c_hash, +                                            &alg_values, +                                            &new_dkp[(unsigned int)rand()%MELT_NEW_COINS]->pub)); +    { +      /* ENSURE_COIN_KNOWN */ +      struct TALER_DenominationHashP dph; +      struct TALER_AgeCommitmentHash agh; +      bool zombie_required = false; +      bool balance_ok; + +      FAILIF (TALER_EXCHANGEDB_CKS_ADDED != +              plugin->ensure_coin_known (plugin->cls, +                                         &depos[i].coin, +                                         &known_coin_id, +                                         &dph, +                                         &agh)); +      /**** INSERT REFRESH COMMITMENTS ****/ +      refresh[i].coin = depos[i].coin; +      RND_BLK (&refresh[i].coin_sig); +      RND_BLK (&refresh[i].rc); +      refresh[i].amount_with_fee = value; +      refresh[i].noreveal_index = MELT_NOREVEAL_INDEX; +      FAILIF (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT != +              plugin->do_melt (plugin->cls, +                               NULL, +                               &refresh[i], +                               known_coin_id, +                               &zombie_required, +                               &balance_ok)); +    } +      /****GET melt_serial_id generated by default****/        { -        /* ENSURE_COIN_KNOWN */ -        uint64_t known_coin_id; -        struct TALER_DenominationHashP dph; -        struct TALER_AgeCommitmentHash agh; -        bool zombie_required = false; -        bool balance_ok; -        FAILIF (TALER_EXCHANGEDB_CKS_ADDED != -                plugin->ensure_coin_known (plugin->cls, -                                           &depos[i].coin, -                                           &known_coin_id, -                                           &dph, -                                           &agh)); -        /**** INSERT REFRESH COMMITMENTS ****/ -        refresh[i].coin = depos[i].coin; -        RND_BLK (&refresh[i].coin_sig); -        RND_BLK (&refresh[i].rc); -        refresh[i].amount_with_fee = value; -        refresh[i].noreveal_index = MELT_NOREVEAL_INDEX; +        struct TALER_EXCHANGEDB_Melt ret_refresh_session; +                  FAILIF (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT != -                plugin->do_melt (plugin->cls, -                                 NULL, -                                 &refresh[i], -                                 known_coin_id, -                                 &zombie_required, -                                 &balance_ok)); -        FAILIF (! balance_ok); -        FAILIF (zombie_required); +                plugin->get_melt (plugin->cls, +                                  &refresh[i].rc, +                                  &ret_refresh_session, +                                  &melt_serial_id));        }        /**** INSERT REFRESH_REVEAL + TRANSFER_KEYS *****/ +      { +        static unsigned int cnt; +                  RND_BLK (&tprivs);          RND_BLK (&tpub); -        RND_BLK(&melt_serial_id);          FAILIF (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT !=                  plugin->insert_refresh_reveal (plugin->cls,                                                 melt_serial_id, @@ -397,9 +393,29 @@ run (void *cls)                                                 TALER_CNC_KAPPA - 1,                                                 tprivs,                                                 &tpub)); -        if (ROUNDS == i) -          TALER_denom_sig_free (&depos[i].coin.denom_sig); +        cnt++; +        //        fprintf (stderr, "CNT: %u - %llu\n", cnt, (unsigned long long) melt_serial_id); +      } +      for (unsigned int cnt = 0; cnt < MELT_NEW_COINS; cnt++) +      { +          TALER_blinded_denom_sig_free (&revealed_coins[cnt].coin_sig); +          TALER_blinded_planchet_free (&revealed_coins[cnt].blinded_planchet); +      } +     +      { +        struct TALER_CoinSpendPublicKeyP ocp; +        uint64_t rrc_serial; +         +        FAILIF (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT != +                plugin->get_old_coin_by_h_blind (plugin->cls, +                                                 &revealed_coins[0].coin_envelope_hash, +                                                 &ocp, +                                                 &rrc_serial)); +      }      } +    if (ROUNDS == i) +      TALER_denom_sig_free (&depos[i].coin.denom_sig); +  }    /* End of benchmark setup */    GNUNET_free(perm);    // commit @@ -412,6 +428,7 @@ run (void *cls)      struct GNUNET_TIME_Relative duration;      enum GNUNET_DB_QueryStatus qs;      time = GNUNET_TIME_absolute_get(); +      qs = plugin->get_link_data (plugin->cls,                                  &refresh[r].coin.coin_pub,                                  &handle_link_data_cb, @@ -444,22 +461,10 @@ run (void *cls)    }    result = 0;  drop: -  GNUNET_break (GNUNET_OK == -  plugin->drop_tables (plugin->cls)); +  // GNUNET_break (GNUNET_OK == plugin->drop_tables (plugin->cls));  cleanup:    if (NULL != dkp)      destroy_denom_key_pair (dkp); -  if (NULL != revealed_coins) -  { -    for (unsigned int cnt = 0; cnt < MELT_NEW_COINS; cnt++) -    { -      TALER_blinded_denom_sig_free (&revealed_coins[cnt].coin_sig); -      TALER_blinded_planchet_free (&revealed_coins[cnt].blinded_planchet); -    } -    GNUNET_free (revealed_coins); -    revealed_coins = NULL; -  } -  GNUNET_free (new_denom_pubs);    for (unsigned int cnt = 0;         (NULL != new_dkp) && (cnt < MELT_NEW_COINS) && (NULL != new_dkp[cnt]);         cnt++) | 
