ed25519.c revision 261287
190792Sgshapiro/* $OpenBSD: ed25519.c,v 1.3 2013/12/09 11:03:45 markus Exp $ */ 294334Sgshapiro 390792Sgshapiro/* 490792Sgshapiro * Public Domain, Authors: Daniel J. Bernstein, Niels Duif, Tanja Lange, 590792Sgshapiro * Peter Schwabe, Bo-Yin Yang. 690792Sgshapiro * Copied from supercop-20130419/crypto_sign/ed25519/ref/ed25519.c 790792Sgshapiro */ 890792Sgshapiro 990792Sgshapiro#include "includes.h" 1090792Sgshapiro#include "crypto_api.h" 1190792Sgshapiro 1290792Sgshapiro#include "ge25519.h" 1390792Sgshapiro 1490792Sgshapirostatic void get_hram(unsigned char *hram, const unsigned char *sm, const unsigned char *pk, unsigned char *playground, unsigned long long smlen) 1590792Sgshapiro{ 1690792Sgshapiro unsigned long long i; 1790792Sgshapiro 1890792Sgshapiro for (i = 0;i < 32;++i) playground[i] = sm[i]; 1990792Sgshapiro for (i = 32;i < 64;++i) playground[i] = pk[i-32]; 2090792Sgshapiro for (i = 64;i < smlen;++i) playground[i] = sm[i]; 2198841Sgshapiro 2290792Sgshapiro crypto_hash_sha512(hram,playground,smlen); 2390792Sgshapiro} 2490792Sgshapiro 2590792Sgshapiro 2690792Sgshapiroint crypto_sign_ed25519_keypair( 2790792Sgshapiro unsigned char *pk, 2890792Sgshapiro unsigned char *sk 2990792Sgshapiro ) 3090792Sgshapiro{ 3190792Sgshapiro sc25519 scsk; 3290792Sgshapiro ge25519 gepk; 3390792Sgshapiro unsigned char extsk[64]; 3490792Sgshapiro int i; 3590792Sgshapiro 3690792Sgshapiro randombytes(sk, 32); 3790792Sgshapiro crypto_hash_sha512(extsk, sk, 32); 3890792Sgshapiro extsk[0] &= 248; 3990792Sgshapiro extsk[31] &= 127; 4090792Sgshapiro extsk[31] |= 64; 4190792Sgshapiro 4290792Sgshapiro sc25519_from32bytes(&scsk,extsk); 4390792Sgshapiro 4490792Sgshapiro ge25519_scalarmult_base(&gepk, &scsk); 4590792Sgshapiro ge25519_pack(pk, &gepk); 4690792Sgshapiro for(i=0;i<32;i++) 4790792Sgshapiro sk[32 + i] = pk[i]; 4890792Sgshapiro return 0; 4990792Sgshapiro} 5090792Sgshapiro 5190792Sgshapiroint crypto_sign_ed25519( 5290792Sgshapiro unsigned char *sm,unsigned long long *smlen, 5390792Sgshapiro const unsigned char *m,unsigned long long mlen, 5490792Sgshapiro const unsigned char *sk 5590792Sgshapiro ) 5690792Sgshapiro{ 5790792Sgshapiro sc25519 sck, scs, scsk; 5890792Sgshapiro ge25519 ger; 5990792Sgshapiro unsigned char r[32]; 6090792Sgshapiro unsigned char s[32]; 6190792Sgshapiro unsigned char extsk[64]; 6290792Sgshapiro unsigned long long i; 6390792Sgshapiro unsigned char hmg[crypto_hash_sha512_BYTES]; 6490792Sgshapiro unsigned char hram[crypto_hash_sha512_BYTES]; 6590792Sgshapiro 6690792Sgshapiro crypto_hash_sha512(extsk, sk, 32); 6790792Sgshapiro extsk[0] &= 248; 6890792Sgshapiro extsk[31] &= 127; 6990792Sgshapiro extsk[31] |= 64; 7090792Sgshapiro 7190792Sgshapiro *smlen = mlen+64; 7290792Sgshapiro for(i=0;i<mlen;i++) 7390792Sgshapiro sm[64 + i] = m[i]; 7490792Sgshapiro for(i=0;i<32;i++) 7590792Sgshapiro sm[32 + i] = extsk[32+i]; 7690792Sgshapiro 7790792Sgshapiro crypto_hash_sha512(hmg, sm+32, mlen+32); /* Generate k as h(extsk[32],...,extsk[63],m) */ 7890792Sgshapiro 7990792Sgshapiro /* Computation of R */ 8090792Sgshapiro sc25519_from64bytes(&sck, hmg); 8190792Sgshapiro ge25519_scalarmult_base(&ger, &sck); 8290792Sgshapiro ge25519_pack(r, &ger); 8390792Sgshapiro 8490792Sgshapiro /* Computation of s */ 8590792Sgshapiro for(i=0;i<32;i++) 8694334Sgshapiro sm[i] = r[i]; 8790792Sgshapiro 8890792Sgshapiro get_hram(hram, sm, sk+32, sm, mlen+64); 8990792Sgshapiro 9090792Sgshapiro sc25519_from64bytes(&scs, hram); 9190792Sgshapiro sc25519_from32bytes(&scsk, extsk); 9290792Sgshapiro sc25519_mul(&scs, &scs, &scsk); 9390792Sgshapiro 9490792Sgshapiro sc25519_add(&scs, &scs, &sck); 9590792Sgshapiro 9690792Sgshapiro sc25519_to32bytes(s,&scs); /* cat s */ 9790792Sgshapiro for(i=0;i<32;i++) 9890792Sgshapiro sm[32 + i] = s[i]; 9990792Sgshapiro 10090792Sgshapiro return 0; 10190792Sgshapiro} 10290792Sgshapiro 10390792Sgshapiroint crypto_sign_ed25519_open( 10490792Sgshapiro unsigned char *m,unsigned long long *mlen, 10590792Sgshapiro const unsigned char *sm,unsigned long long smlen, 10690792Sgshapiro const unsigned char *pk 10790792Sgshapiro ) 10890792Sgshapiro{ 10990792Sgshapiro unsigned int i; 11090792Sgshapiro int ret; 11190792Sgshapiro unsigned char t2[32]; 11290792Sgshapiro ge25519 get1, get2; 11390792Sgshapiro sc25519 schram, scs; 11490792Sgshapiro unsigned char hram[crypto_hash_sha512_BYTES]; 11590792Sgshapiro 11690792Sgshapiro *mlen = (unsigned long long) -1; 11790792Sgshapiro if (smlen < 64) return -1; 11890792Sgshapiro 11990792Sgshapiro if (ge25519_unpackneg_vartime(&get1, pk)) return -1; 12090792Sgshapiro 12190792Sgshapiro get_hram(hram,sm,pk,m,smlen); 12290792Sgshapiro 12390792Sgshapiro sc25519_from64bytes(&schram, hram); 12490792Sgshapiro 12590792Sgshapiro sc25519_from32bytes(&scs, sm+32); 12690792Sgshapiro 12790792Sgshapiro ge25519_double_scalarmult_vartime(&get2, &get1, &schram, &ge25519_base, &scs); 12890792Sgshapiro ge25519_pack(t2, &get2); 12990792Sgshapiro 13090792Sgshapiro ret = crypto_verify_32(sm, t2); 13190792Sgshapiro 13290792Sgshapiro if (!ret) 13390792Sgshapiro { 13490792Sgshapiro for(i=0;i<smlen-64;i++) 13590792Sgshapiro m[i] = sm[i + 64]; 13690792Sgshapiro *mlen = smlen-64; 13790792Sgshapiro } 13890792Sgshapiro else 13990792Sgshapiro { 14090792Sgshapiro for(i=0;i<smlen-64;i++) 14190792Sgshapiro m[i] = 0; 14290792Sgshapiro } 14390792Sgshapiro return ret; 14490792Sgshapiro} 14590792Sgshapiro