From 759837da70a819ce1c32efd5e2db6537367e098b Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Fri, 17 Apr 2015 19:45:30 +0200 Subject: adding /test/ecdsa and /test/eddsa to test client signing and verification over Curve25519 --- src/include/taler_signatures.h | 47 +++++++--- src/mint/taler-mint-httpd.c | 14 +++ src/mint/taler-mint-httpd_test.c | 179 +++++++++++++++++++++++++++++++++++++++ src/mint/taler-mint-httpd_test.h | 46 ++++++++++ 4 files changed, 275 insertions(+), 11 deletions(-) (limited to 'src') diff --git a/src/include/taler_signatures.h b/src/include/taler_signatures.h index 1c57ba058..9ef50d1d3 100644 --- a/src/include/taler_signatures.h +++ b/src/include/taler_signatures.h @@ -47,12 +47,12 @@ /** * Purpose for signing public keys signed by the mint master key. */ -#define TALER_SIGNATURE_MASTER_SIGNING_KEY_VALIDITY 1 +#define TALER_SIGNATURE_MASTER_SIGNING_KEY_VALIDITY 1024 /** * Purpose for denomination keys signed by the mint master key. */ -#define TALER_SIGNATURE_MASTER_DENOMINATION_KEY_VALIDITY 2 +#define TALER_SIGNATURE_MASTER_DENOMINATION_KEY_VALIDITY 1025 /*********************************************/ @@ -63,24 +63,24 @@ * Purpose for the state of a reserve, signed by the mint's signing * key. */ -#define TALER_SIGNATURE_MINT_RESERVE_STATUS 32 +#define TALER_SIGNATURE_MINT_RESERVE_STATUS 1032 /** * Signature where the Mint confirms a deposit request. */ -#define TALER_SIGNATURE_MINT_CONFIRM_DEPOSIT 33 +#define TALER_SIGNATURE_MINT_CONFIRM_DEPOSIT 1033 /** * Signature where the mint (current signing key) confirms the * no-reveal index for cut-and-choose and the validity of the melted * coins. */ -#define TALER_SIGNATURE_MINT_CONFIRM_MELT 34 +#define TALER_SIGNATURE_MINT_CONFIRM_MELT 1034 /** * Signature where the Mint confirms the full /keys response set. */ -#define TALER_SIGNATURE_MINT_KEY_SET 35 +#define TALER_SIGNATURE_MINT_KEY_SET 1035 /***********************/ @@ -90,12 +90,12 @@ /** * Signature where the merchant confirms a contract (to the customer). */ -#define TALER_SIGNATURE_MERCHANT_CONTRACT 101 +#define TALER_SIGNATURE_MERCHANT_CONTRACT 1101 /** * Signature where the merchant confirms a refund (of a coin). */ -#define TALER_SIGNATURE_MERCHANT_REFUND 102 +#define TALER_SIGNATURE_MERCHANT_REFUND 1102 /*********************/ @@ -105,17 +105,42 @@ /** * Signature where the reserve key confirms a withdraw request. */ -#define TALER_SIGNATURE_WALLET_RESERVE_WITHDRAW 200 +#define TALER_SIGNATURE_WALLET_RESERVE_WITHDRAW 1200 /** * Signature made by the wallet of a user to confirm a deposit of a coin. */ -#define TALER_SIGNATURE_WALLET_COIN_DEPOSIT 201 +#define TALER_SIGNATURE_WALLET_COIN_DEPOSIT 1201 /** * Signature using a coin key confirming the melting of a coin. */ -#define TALER_SIGNATURE_WALLET_COIN_MELT 202 +#define TALER_SIGNATURE_WALLET_COIN_MELT 1202 + +/*******************/ +/* Test signatures */ +/*******************/ + + +/** + * ECDSA test signature. + */ +#define TALER_SIGNATURE_CLIENT_TEST_ECDSA 1300 + +/** + * ECDSA test signature. + */ +#define TALER_SIGNATURE_MINT_TEST_ECDSA 1301 + +/** + * EdDSA test signature. + */ +#define TALER_SIGNATURE_CLIENT_TEST_EDDSA 1302 + +/** + * EdDSA test signature. + */ +#define TALER_SIGNATURE_MINT_TEST_EDDSA 1303 diff --git a/src/mint/taler-mint-httpd.c b/src/mint/taler-mint-httpd.c index b72db4768..32bad4048 100644 --- a/src/mint/taler-mint-httpd.c +++ b/src/mint/taler-mint-httpd.c @@ -210,6 +210,20 @@ handle_mhd_request (void *cls, { "/test/base32", NULL, "text/plain", "Only POST is allowed", 0, &TMH_MHD_handler_send_json_pack_error, MHD_HTTP_METHOD_NOT_ALLOWED }, + + { "/test/ecdsa", MHD_HTTP_METHOD_POST, "application/json", + NULL, 0, + &TMH_TEST_handler_test_ecdsa, MHD_HTTP_OK }, + { "/test/ecdsa", NULL, "text/plain", + "Only POST is allowed", 0, + &TMH_MHD_handler_send_json_pack_error, MHD_HTTP_METHOD_NOT_ALLOWED }, + + { "/test/eddsa", MHD_HTTP_METHOD_POST, "application/json", + NULL, 0, + &TMH_TEST_handler_test_eddsa, MHD_HTTP_OK }, + { "/test/eddsa", NULL, "text/plain", + "Only POST is allowed", 0, + &TMH_MHD_handler_send_json_pack_error, MHD_HTTP_METHOD_NOT_ALLOWED }, #endif { NULL, NULL, NULL, NULL, 0, 0 } diff --git a/src/mint/taler-mint-httpd_test.c b/src/mint/taler-mint-httpd_test.c index 7d1c1dd57..c7e0af05d 100644 --- a/src/mint/taler-mint-httpd_test.c +++ b/src/mint/taler-mint-httpd_test.c @@ -88,6 +88,185 @@ TMH_TEST_handler_test_base32 (struct TMH_RequestHandler *rh, } +/** + * Handle a "/test/ecdsa" request. Parses the JSON in the post, + * which must contain a "ecdsa_pub" with a public key and an + *"ecdsa_sig" with the corresponding signature for a purpose + * of #TALER_SIGNATURE_CLIENT_TEST_ECDSA. If the signature is + * valid, a reply with a #TALER_SIGNATURE_MINT_TEST_ECDSA is + * returned using the same JSON format. + * + * @param rh context of the handler + * @param connection the MHD connection to handle + * @param[in,out] connection_cls the connection's closure (can be updated) + * @param upload_data upload data + * @param[in,out] upload_data_size number of bytes (left) in @a upload_data + * @return MHD result code + */ +int +TMH_TEST_handler_test_ecdsa (struct TMH_RequestHandler *rh, + struct MHD_Connection *connection, + void **connection_cls, + const char *upload_data, + size_t *upload_data_size) +{ + json_t *json; + int res; + struct GNUNET_CRYPTO_EcdsaPublicKey pub; + struct GNUNET_CRYPTO_EcdsaSignature sig; + struct GNUNET_CRYPTO_EccSignaturePurpose purpose; + struct TMH_PARSE_FieldSpecification spec[] = { + TMH_PARSE_MEMBER_FIXED ("ecdsa_pub", &pub), + TMH_PARSE_MEMBER_FIXED ("ecdsa_sig", &sig), + TMH_PARSE_MEMBER_END + }; + struct GNUNET_CRYPTO_EcdsaPrivateKey *pk; + + res = TMH_PARSE_post_json (connection, + connection_cls, + upload_data, + upload_data_size, + &json); + if (GNUNET_SYSERR == res) + return MHD_NO; + if ( (GNUNET_NO == res) || (NULL == json) ) + return MHD_YES; + res = TMH_PARSE_json_data (connection, + json, + spec); + if (GNUNET_YES != res) + return (GNUNET_NO == res) ? MHD_YES : MHD_NO; + purpose.size = htonl (sizeof (struct GNUNET_CRYPTO_EccSignaturePurpose)); + purpose.purpose = htonl (TALER_SIGNATURE_CLIENT_TEST_ECDSA); + if (GNUNET_OK != + GNUNET_CRYPTO_ecdsa_verify (TALER_SIGNATURE_CLIENT_TEST_ECDSA, + &purpose, + &sig, + &pub)) + { + TMH_PARSE_release_data (spec); + json_decref (json); + return TMH_RESPONSE_reply_signature_invalid (connection, + "ecdsa_sig"); + } + TMH_PARSE_release_data (spec); + json_decref (json); + pk = GNUNET_CRYPTO_ecdsa_key_create (); + purpose.purpose = htonl (TALER_SIGNATURE_MINT_TEST_ECDSA); + if (GNUNET_OK != + GNUNET_CRYPTO_ecdsa_sign (pk, + &purpose, + &sig)) + { + GNUNET_free (pk); + return TMH_RESPONSE_reply_internal_error (connection, + "Failed to ECDSA-sign"); + } + GNUNET_CRYPTO_ecdsa_key_get_public (pk, + &pub); + GNUNET_free (pk); + return TMH_RESPONSE_reply_json_pack (connection, + MHD_HTTP_OK, + "{s:o, s:o}", + "ecdsa_pub", + TALER_json_from_data (&pub, + sizeof (pub)), + "ecdsa_sig", + TALER_json_from_data (&sig, + sizeof (sig))); +} + + +/** + * Handle a "/test/eddsa" request. Parses the JSON in the post, + * which must contain a "eddsa_pub" with a public key and an + *"ecdsa_sig" with the corresponding signature for a purpose + * of #TALER_SIGNATURE_CLIENT_TEST_EDDSA. If the signature is + * valid, a reply with a #TALER_SIGNATURE_MINT_TEST_EDDSA is + * returned using the same JSON format. + * + * @param rh context of the handler + * @param connection the MHD connection to handle + * @param[in,out] connection_cls the connection's closure (can be updated) + * @param upload_data upload data + * @param[in,out] upload_data_size number of bytes (left) in @a upload_data + * @return MHD result code + */ +int +TMH_TEST_handler_test_eddsa (struct TMH_RequestHandler *rh, + struct MHD_Connection *connection, + void **connection_cls, + const char *upload_data, + size_t *upload_data_size) +{ + json_t *json; + int res; + struct GNUNET_CRYPTO_EddsaPublicKey pub; + struct GNUNET_CRYPTO_EddsaSignature sig; + struct GNUNET_CRYPTO_EccSignaturePurpose purpose; + struct TMH_PARSE_FieldSpecification spec[] = { + TMH_PARSE_MEMBER_FIXED ("eddsa_pub", &pub), + TMH_PARSE_MEMBER_FIXED ("eddsa_sig", &sig), + TMH_PARSE_MEMBER_END + }; + struct GNUNET_CRYPTO_EddsaPrivateKey *pk; + + res = TMH_PARSE_post_json (connection, + connection_cls, + upload_data, + upload_data_size, + &json); + if (GNUNET_SYSERR == res) + return MHD_NO; + if ( (GNUNET_NO == res) || (NULL == json) ) + return MHD_YES; + res = TMH_PARSE_json_data (connection, + json, + spec); + if (GNUNET_YES != res) + return (GNUNET_NO == res) ? MHD_YES : MHD_NO; + purpose.size = htonl (sizeof (struct GNUNET_CRYPTO_EccSignaturePurpose)); + purpose.purpose = htonl (TALER_SIGNATURE_CLIENT_TEST_EDDSA); + if (GNUNET_OK != + GNUNET_CRYPTO_eddsa_verify (TALER_SIGNATURE_CLIENT_TEST_EDDSA, + &purpose, + &sig, + &pub)) + { + TMH_PARSE_release_data (spec); + json_decref (json); + return TMH_RESPONSE_reply_signature_invalid (connection, + "eddsa_sig"); + } + TMH_PARSE_release_data (spec); + json_decref (json); + pk = GNUNET_CRYPTO_eddsa_key_create (); + purpose.purpose = htonl (TALER_SIGNATURE_MINT_TEST_EDDSA); + if (GNUNET_OK != + GNUNET_CRYPTO_eddsa_sign (pk, + &purpose, + &sig)) + { + GNUNET_free (pk); + return TMH_RESPONSE_reply_internal_error (connection, + "Failed to EdDSA-sign"); + } + GNUNET_CRYPTO_eddsa_key_get_public (pk, + &pub); + GNUNET_free (pk); + return TMH_RESPONSE_reply_json_pack (connection, + MHD_HTTP_OK, + "{s:o, s:o}", + "eddsa_pub", + TALER_json_from_data (&pub, + sizeof (pub)), + "eddsa_sig", + TALER_json_from_data (&sig, + sizeof (sig))); +} + + + /** * Handle a "/test" request. Parses the JSON in the post. * diff --git a/src/mint/taler-mint-httpd_test.h b/src/mint/taler-mint-httpd_test.h index 6584af581..609473ec1 100644 --- a/src/mint/taler-mint-httpd_test.h +++ b/src/mint/taler-mint-httpd_test.h @@ -49,6 +49,52 @@ TMH_TEST_handler_test_base32 (struct TMH_RequestHandler *rh, size_t *upload_data_size); +/** + * Handle a "/test/ecdsa" request. Parses the JSON in the post, + * which must contain a "ecdsa_pub" with a public key and an + *"ecdsa_sig" with the corresponding signature for a purpose + * of #TALER_SIGNATURE_CLIENT_TEST_ECDSA. If the signature is + * valid, a reply with a #TALER_SIGNATURE_MINT_TEST_ECDSA is + * returned using the same JSON format. + * + * @param rh context of the handler + * @param connection the MHD connection to handle + * @param[in,out] connection_cls the connection's closure (can be updated) + * @param upload_data upload data + * @param[in,out] upload_data_size number of bytes (left) in @a upload_data + * @return MHD result code + */ +int +TMH_TEST_handler_test_ecdsa (struct TMH_RequestHandler *rh, + struct MHD_Connection *connection, + void **connection_cls, + const char *upload_data, + size_t *upload_data_size); + + +/** + * Handle a "/test/eddsa" request. Parses the JSON in the post, + * which must contain a "eddsa_pub" with a public key and an + *"ecdsa_sig" with the corresponding signature for a purpose + * of #TALER_SIGNATURE_CLIENT_TEST_EDDSA. If the signature is + * valid, a reply with a #TALER_SIGNATURE_MINT_TEST_EDDSA is + * returned using the same JSON format. + * + * @param rh context of the handler + * @param connection the MHD connection to handle + * @param[in,out] connection_cls the connection's closure (can be updated) + * @param upload_data upload data + * @param[in,out] upload_data_size number of bytes (left) in @a upload_data + * @return MHD result code + */ +int +TMH_TEST_handler_test_eddsa (struct TMH_RequestHandler *rh, + struct MHD_Connection *connection, + void **connection_cls, + const char *upload_data, + size_t *upload_data_size); + + /** * Handle a "/test" request. Parses the JSON in the post. * -- cgit v1.2.3