2 * @file ed448goldilocks/eddsa.c
6 * Copyright (c) 2015-2016 Cryptography Research, Inc. \n
7 * Released under the MIT License. See LICENSE.txt for license information.
10 * @brief EdDSA routines.
12 * @warning This file was automatically generated in Python.
13 * Please do not edit it.
15 #include <openssl/crypto.h>
17 #include "curve448_lcl.h"
23 #define API_NAME "decaf_448"
25 #define hash_ctx_t decaf_shake256_ctx_t
26 #define hash_init decaf_shake256_init
27 #define hash_update decaf_shake256_update
28 #define hash_final decaf_shake256_final
29 #define hash_destroy decaf_shake256_destroy
30 #define hash_hash decaf_shake256_hash
32 #define NO_CONTEXT DECAF_EDDSA_448_SUPPORTS_CONTEXTLESS_SIGS
33 #define EDDSA_USE_SIGMA_ISOGENY 0
35 #define EDDSA_PREHASH_BYTES 64
38 const uint8_t NO_CONTEXT_POINTS_HERE
= 0;
39 const uint8_t * const DECAF_ED448_NO_CONTEXT
= &NO_CONTEXT_POINTS_HERE
;
42 /* EDDSA_BASE_POINT_RATIO = 1 or 2
43 * Because EdDSA25519 is not on E_d but on the isogenous E_sigma_d,
44 * its base point is twice ours.
46 #define EDDSA_BASE_POINT_RATIO (1+EDDSA_USE_SIGMA_ISOGENY) /* TODO: remove */
49 uint8_t secret_scalar_ser
[DECAF_EDDSA_448_PRIVATE_BYTES
]
52 secret_scalar_ser
[0] &= -COFACTOR
;
53 uint8_t hibit
= (1<<0)>>1;
55 secret_scalar_ser
[DECAF_EDDSA_448_PRIVATE_BYTES
- 1] = 0;
56 secret_scalar_ser
[DECAF_EDDSA_448_PRIVATE_BYTES
- 2] |= 0x80;
58 secret_scalar_ser
[DECAF_EDDSA_448_PRIVATE_BYTES
- 1] &= hibit
-1;
59 secret_scalar_ser
[DECAF_EDDSA_448_PRIVATE_BYTES
- 1] |= hibit
;
63 static void hash_init_with_dom(
67 const uint8_t *context
,
73 if (context_len
== 0 && context
== DECAF_ED448_NO_CONTEXT
) {
81 const char *dom_s
= "SigEd448";
82 const uint8_t dom
[2] = {2+word_is_zero(prehashed
)+word_is_zero(for_prehash
), context_len
};
83 hash_update(hash
,(const unsigned char *)dom_s
, strlen(dom_s
));
84 hash_update(hash
,dom
,2);
85 hash_update(hash
,context
,context_len
);
88 void decaf_ed448_prehash_init (
94 /* In this file because it uses the hash */
95 void decaf_ed448_convert_private_key_to_x448 (
96 uint8_t x
[DECAF_X448_PRIVATE_BYTES
],
97 const uint8_t ed
[DECAF_EDDSA_448_PRIVATE_BYTES
]
99 /* pass the private key through hash_hash function */
100 /* and keep the first DECAF_X448_PRIVATE_BYTES bytes */
103 DECAF_X448_PRIVATE_BYTES
,
105 DECAF_EDDSA_448_PRIVATE_BYTES
109 void decaf_ed448_derive_public_key (
110 uint8_t pubkey
[DECAF_EDDSA_448_PUBLIC_BYTES
],
111 const uint8_t privkey
[DECAF_EDDSA_448_PRIVATE_BYTES
]
113 /* only this much used for keygen */
114 uint8_t secret_scalar_ser
[DECAF_EDDSA_448_PRIVATE_BYTES
];
118 sizeof(secret_scalar_ser
),
120 DECAF_EDDSA_448_PRIVATE_BYTES
122 clamp(secret_scalar_ser
);
124 curve448_scalar_t secret_scalar
;
125 curve448_scalar_decode_long(secret_scalar
, secret_scalar_ser
, sizeof(secret_scalar_ser
));
127 /* Since we are going to mul_by_cofactor during encoding, divide by it here.
128 * However, the EdDSA base point is not the same as the decaf base point if
129 * the sigma isogeny is in use: the EdDSA base point is on Etwist_d/(1-d) and
130 * the decaf base point is on Etwist_d, and when converted it effectively
131 * picks up a factor of 2 from the isogenies. So we might start at 2 instead of 1.
133 for (unsigned int c
=1; c
<DECAF_448_EDDSA_ENCODE_RATIO
; c
<<= 1) {
134 curve448_scalar_halve(secret_scalar
,secret_scalar
);
138 curve448_precomputed_scalarmul(p
,curve448_precomputed_base
,secret_scalar
);
140 curve448_point_mul_by_ratio_and_encode_like_eddsa(pubkey
, p
);
143 curve448_scalar_destroy(secret_scalar
);
144 curve448_point_destroy(p
);
145 OPENSSL_cleanse(secret_scalar_ser
, sizeof(secret_scalar_ser
));
148 void decaf_ed448_sign (
149 uint8_t signature
[DECAF_EDDSA_448_SIGNATURE_BYTES
],
150 const uint8_t privkey
[DECAF_EDDSA_448_PRIVATE_BYTES
],
151 const uint8_t pubkey
[DECAF_EDDSA_448_PUBLIC_BYTES
],
152 const uint8_t *message
,
155 const uint8_t *context
,
158 curve448_scalar_t secret_scalar
;
161 /* Schedule the secret key */
163 uint8_t secret_scalar_ser
[DECAF_EDDSA_448_PRIVATE_BYTES
];
164 uint8_t seed
[DECAF_EDDSA_448_PRIVATE_BYTES
];
165 } __attribute__((packed
)) expanded
;
167 (uint8_t *)&expanded
,
170 DECAF_EDDSA_448_PRIVATE_BYTES
172 clamp(expanded
.secret_scalar_ser
);
173 curve448_scalar_decode_long(secret_scalar
, expanded
.secret_scalar_ser
, sizeof(expanded
.secret_scalar_ser
));
175 /* Hash to create the nonce */
176 hash_init_with_dom(hash
,prehashed
,0,context
,context_len
);
177 hash_update(hash
,expanded
.seed
,sizeof(expanded
.seed
));
178 hash_update(hash
,message
,message_len
);
179 OPENSSL_cleanse(&expanded
, sizeof(expanded
));
182 /* Decode the nonce */
183 curve448_scalar_t nonce_scalar
;
185 uint8_t nonce
[2*DECAF_EDDSA_448_PRIVATE_BYTES
];
186 hash_final(hash
,nonce
,sizeof(nonce
));
187 curve448_scalar_decode_long(nonce_scalar
, nonce
, sizeof(nonce
));
188 OPENSSL_cleanse(nonce
, sizeof(nonce
));
191 uint8_t nonce_point
[DECAF_EDDSA_448_PUBLIC_BYTES
] = {0};
193 /* Scalarmul to create the nonce-point */
194 curve448_scalar_t nonce_scalar_2
;
195 curve448_scalar_halve(nonce_scalar_2
,nonce_scalar
);
196 for (unsigned int c
= 2; c
< DECAF_448_EDDSA_ENCODE_RATIO
; c
<<= 1) {
197 curve448_scalar_halve(nonce_scalar_2
,nonce_scalar_2
);
201 curve448_precomputed_scalarmul(p
,curve448_precomputed_base
,nonce_scalar_2
);
202 curve448_point_mul_by_ratio_and_encode_like_eddsa(nonce_point
, p
);
203 curve448_point_destroy(p
);
204 curve448_scalar_destroy(nonce_scalar_2
);
207 curve448_scalar_t challenge_scalar
;
209 /* Compute the challenge */
210 hash_init_with_dom(hash
,prehashed
,0,context
,context_len
);
211 hash_update(hash
,nonce_point
,sizeof(nonce_point
));
212 hash_update(hash
,pubkey
,DECAF_EDDSA_448_PUBLIC_BYTES
);
213 hash_update(hash
,message
,message_len
);
214 uint8_t challenge
[2*DECAF_EDDSA_448_PRIVATE_BYTES
];
215 hash_final(hash
,challenge
,sizeof(challenge
));
217 curve448_scalar_decode_long(challenge_scalar
,challenge
,sizeof(challenge
));
218 OPENSSL_cleanse(challenge
,sizeof(challenge
));
221 curve448_scalar_mul(challenge_scalar
,challenge_scalar
,secret_scalar
);
222 curve448_scalar_add(challenge_scalar
,challenge_scalar
,nonce_scalar
);
224 OPENSSL_cleanse(signature
,DECAF_EDDSA_448_SIGNATURE_BYTES
);
225 memcpy(signature
,nonce_point
,sizeof(nonce_point
));
226 curve448_scalar_encode(&signature
[DECAF_EDDSA_448_PUBLIC_BYTES
],challenge_scalar
);
228 curve448_scalar_destroy(secret_scalar
);
229 curve448_scalar_destroy(nonce_scalar
);
230 curve448_scalar_destroy(challenge_scalar
);
234 void decaf_ed448_sign_prehash (
235 uint8_t signature
[DECAF_EDDSA_448_SIGNATURE_BYTES
],
236 const uint8_t privkey
[DECAF_EDDSA_448_PRIVATE_BYTES
],
237 const uint8_t pubkey
[DECAF_EDDSA_448_PUBLIC_BYTES
],
238 const uint8_t hash
[64],
239 const uint8_t *context
,
242 decaf_ed448_sign(signature
,privkey
,pubkey
,hash
,64,1,context
,context_len
);
243 /*OPENSSL_cleanse(hash,sizeof(hash));*/
246 decaf_error_t
decaf_ed448_verify (
247 const uint8_t signature
[DECAF_EDDSA_448_SIGNATURE_BYTES
],
248 const uint8_t pubkey
[DECAF_EDDSA_448_PUBLIC_BYTES
],
249 const uint8_t *message
,
252 const uint8_t *context
,
255 curve448_point_t pk_point
, r_point
;
256 decaf_error_t error
= curve448_point_decode_like_eddsa_and_mul_by_ratio(pk_point
,pubkey
);
257 if (DECAF_SUCCESS
!= error
) { return error
; }
259 error
= curve448_point_decode_like_eddsa_and_mul_by_ratio(r_point
,signature
);
260 if (DECAF_SUCCESS
!= error
) { return error
; }
262 curve448_scalar_t challenge_scalar
;
264 /* Compute the challenge */
266 hash_init_with_dom(hash
,prehashed
,0,context
,context_len
);
267 hash_update(hash
,signature
,DECAF_EDDSA_448_PUBLIC_BYTES
);
268 hash_update(hash
,pubkey
,DECAF_EDDSA_448_PUBLIC_BYTES
);
269 hash_update(hash
,message
,message_len
);
270 uint8_t challenge
[2*DECAF_EDDSA_448_PRIVATE_BYTES
];
271 hash_final(hash
,challenge
,sizeof(challenge
));
273 curve448_scalar_decode_long(challenge_scalar
,challenge
,sizeof(challenge
));
274 OPENSSL_cleanse(challenge
,sizeof(challenge
));
276 curve448_scalar_sub(challenge_scalar
, curve448_scalar_zero
, challenge_scalar
);
278 curve448_scalar_t response_scalar
;
279 curve448_scalar_decode_long(
281 &signature
[DECAF_EDDSA_448_PUBLIC_BYTES
],
282 DECAF_EDDSA_448_PRIVATE_BYTES
285 for (unsigned c
=1; c
<DECAF_448_EDDSA_DECODE_RATIO
; c
<<=1) {
286 curve448_scalar_add(response_scalar
,response_scalar
,response_scalar
);
290 /* pk_point = -c(x(P)) + (cx + k)G = kG */
291 curve448_base_double_scalarmul_non_secret(
297 return decaf_succeed_if(curve448_point_eq(pk_point
,r_point
));
301 decaf_error_t
decaf_ed448_verify_prehash (
302 const uint8_t signature
[DECAF_EDDSA_448_SIGNATURE_BYTES
],
303 const uint8_t pubkey
[DECAF_EDDSA_448_PUBLIC_BYTES
],
304 const uint8_t hash
[64],
305 const uint8_t *context
,
310 ret
= decaf_ed448_verify(signature
,pubkey
,hash
,64,1,context
,context_len
);
315 int ED448_sign(uint8_t *out_sig
, const uint8_t *message
, size_t message_len
,
316 const uint8_t public_key
[56], const uint8_t private_key
[56],
317 const uint8_t *context
, size_t context_len
)
320 decaf_ed448_sign(out_sig
, private_key
, public_key
, message
, message_len
, 0,
321 context
, context_len
);
327 int ED448_verify(const uint8_t *message
, size_t message_len
,
328 const uint8_t signature
[112], const uint8_t public_key
[56],
329 const uint8_t *context
, size_t context_len
)
331 return decaf_ed448_verify(signature
, public_key
, message
, message_len
, 0,
332 context
, context_len
) == DECAF_SUCCESS
;
335 int ED448ph_sign(uint8_t *out_sig
, const uint8_t hash
[64],
336 const uint8_t public_key
[56], const uint8_t private_key
[56],
337 const uint8_t *context
, size_t context_len
)
339 decaf_ed448_sign_prehash(out_sig
, private_key
, public_key
, hash
, context
,
345 int ED448ph_verify(const uint8_t hash
[64], const uint8_t signature
[112],
346 const uint8_t public_key
[56], const uint8_t *context
,
349 return decaf_ed448_verify_prehash(signature
, public_key
, hash
, context
,
350 context_len
) == DECAF_SUCCESS
;
353 void ED448_public_from_private(uint8_t out_public_key
[56],
354 const uint8_t private_key
[56])
356 decaf_ed448_derive_public_key(out_public_key
, private_key
);