From a659c209e489adf22ec8cad02e016d3dd3c75731 Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Thu, 21 Feb 2019 22:38:40 +0800 Subject: [PATCH 001/132] it builds --- src/cc/rogue/main.c | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index ca05226d3..93391d153 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -30,7 +30,7 @@ extern char Gametxidstr[67]; #define SATOSHIDEN ((uint64_t)100000000L) #define dstr(x) ((double)(x) / SATOSHIDEN) #define KOMODO_ASSETCHAIN_MAXLEN 65 -char ASSETCHAINS_SYMBOL[KOMODO_ASSETCHAIN_MAXLEN]; +char ASSETCHAINS_SYMBOL[KOMODO_ASSETCHAIN_MAXLEN],IPADDRESS[100]; #ifndef _BITS256 #define _BITS256 @@ -583,7 +583,7 @@ char *curl_post(CURL **cHandlep,char *url,char *userpass,char *postfields,char * return(chunk.memory); } -uint16_t _komodo_userpass(char *username,char *password,FILE *fp) +uint16_t _komodo_userpass(char *username, char *password, char *ipaddress, FILE *fp) { char *rpcuser,*rpcpassword,*str,line[8192]; uint16_t port = 0; rpcuser = rpcpassword = 0; @@ -602,6 +602,10 @@ uint16_t _komodo_userpass(char *username,char *password,FILE *fp) port = atoi(parse_conf_line(str,(char *)"rpcport")); //fprintf(stderr,"rpcport.%u in file\n",port); } + else if ( (str= strstr(line,(char *)"ipaddress")) != 0 ) + { + ipaddress = parse_conf_line(str,(char *)"ipaddress"); + } } if ( rpcuser != 0 && rpcpassword != 0 ) { @@ -653,7 +657,7 @@ uint16_t _komodo_userpass(char *username,char *password,FILE *fp) //printf("test.(%s) -> [%s] statename.(%s) %s\n",test,ASSETCHAINS_SYMBOL,symbol,fname); }*/ -uint16_t komodo_userpass(char *userpass,char *symbol) +uint16_t komodo_userpass(char *userpass,char *symbol,char *ipaddress) { FILE *fp; uint16_t port = 0; char fname[512],username[512],password[512],confname[KOMODO_ASSETCHAIN_MAXLEN]; userpass[0] = 0; @@ -669,7 +673,7 @@ uint16_t komodo_userpass(char *userpass,char *symbol) //komodo_statefname(fname,symbol,confname); if ( (fp= fopen(confname,"rb")) != 0 ) { - port = _komodo_userpass(username,password,fp); + port = _komodo_userpass(username,password,ipaddress,fp); sprintf(userpass,"%s:%s",username,password); if ( strcmp(symbol,ASSETCHAINS_SYMBOL) == 0 ) strcpy(USERPASS,userpass); @@ -688,7 +692,7 @@ char *komodo_issuemethod(char *userpass,char *method,char *params,uint16_t port) params = (char *)"[]"; if ( strlen(params) < sizeof(postdata)-128 ) { - sprintf(url,(char *)"http://127.0.0.1:%u",port); + sprintf(url,(char *)"http://%s:%u",IPADDRESS,port); sprintf(postdata,"{\"method\":\"%s\",\"params\":%s}",method,params); //printf("[%s] (%s) postdata.(%s) params.(%s) USERPASS.(%s)\n",ASSETCHAINS_SYMBOL,url,postdata,params,USERPASS); retstr2 = bitcoind_RPC(&retstr,(char *)"debug",url,userpass,method,params); @@ -793,7 +797,7 @@ int main(int argc, char **argv, char **envp) ASSETCHAINS_SYMBOL[j++] = toupper(c); } ASSETCHAINS_SYMBOL[j++] = 0; - ROGUE_PORT = komodo_userpass(userpass,ASSETCHAINS_SYMBOL); + ROGUE_PORT = komodo_userpass(userpass,ASSETCHAINS_SYMBOL,IPADDRESS); printf("ASSETCHAINS_SYMBOL.(%s) port.%u (%s)\n",ASSETCHAINS_SYMBOL,ROGUE_PORT,USERPASS); sleep(1); if ( argc == 2 && (fp=fopen(argv[1],"rb")) == 0 ) { @@ -813,5 +817,3 @@ int main(int argc, char **argv, char **envp) return(rogue(argc,argv,envp)); } } - - From 7453b21b6da2b0f7ecc5bac28832cfb3ccda88c7 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 06:01:19 -1100 Subject: [PATCH 002/132] Comments --- src/cc/musig.cpp | 151 ++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 149 insertions(+), 2 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 17c4d1368..ec7f5e788 100755 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -217,6 +217,37 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); result.push_back(Pair("result","success")); + /** Initializes a signing session for a signer + * + * Returns: 1: session is successfully initialized + * 0: session could not be initialized: secret key or secret nonce overflow + * Args: ctx: pointer to a context object, initialized for signing (cannot + * be NULL) + * Out: session: the session structure to initialize (cannot be NULL) + * signers: an array of signers' data to be initialized. Array length must + * equal to `n_signers` (cannot be NULL) + * nonce_commitment32: filled with a 32-byte commitment to the generated nonce + * (cannot be NULL) + * In: session_id32: a *unique* 32-byte ID to assign to this session (cannot be + * NULL). If a non-unique session_id32 was given then a partial + * signature will LEAK THE SECRET KEY. + * msg32: the 32-byte message to be signed. Shouldn't be NULL unless you + * require sharing public nonces before the message is known + * because it reduces nonce misuse resistance. If NULL, must be + * set with `musig_session_set_msg` before signing and verifying. + * combined_pk: the combined public key of all signers (cannot be NULL) + * pk_hash32: the 32-byte hash of the signers' individual keys (cannot be + * NULL) + * n_signers: length of signers array. Number of signers participating in + * the MuSig. Must be greater than 0 and at most 2^32 - 1. + * my_index: index of this signer in the signers array + * seckey: the signer's 32-byte secret key (cannot be NULL) + */ + //if (!secp256k1_musig_session_initialize(ctx, &musig_session[i], signer_data[i], nonce_commitment[i], session_id32, msg32, &combined_pk, pk_hash, N_SIGNERS, i, seckeys[i])) + //return 0; + // randombytes_buf(buf, num); + + //nonce_commitment_ptr[i] = &nonce_commitment[i][0]; return(result); } @@ -224,6 +255,25 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); result.push_back(Pair("result","success")); + /** Gets the signer's public nonce given a list of all signers' data with commitments + * + * Returns: 1: public nonce is written in nonce + * 0: signer data is missing commitments or session isn't initialized + * for signing + * Args: ctx: pointer to a context object (cannot be NULL) + * session: the signing session to get the nonce from (cannot be NULL) + * signers: an array of signers' data initialized with + * `musig_session_initialize`. Array length must equal to + * `n_commitments` (cannot be NULL) + * Out: nonce: the nonce (cannot be NULL) + * In: commitments: array of 32-byte nonce commitments (cannot be NULL) + * n_commitments: the length of commitments and signers array. Must be the total + * number of signers participating in the MuSig. + */ + // Set nonce commitments in the signer data and get the own public nonce + //if (!secp256k1_musig_session_get_public_nonce(ctx, &musig_session[i], signer_data[i], &nonce[i], nonce_commitment_ptr, N_SIGNERS)) + // return 0; + return(result); } @@ -231,13 +281,69 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); result.push_back(Pair("result","success")); - return(result); + /** Checks a signer's public nonce against a commitment to said nonce, and update + * data structure if they match + * + * Returns: 1: commitment was valid, data structure updated + * 0: commitment was invalid, nothing happened + * Args: ctx: pointer to a context object (cannot be NULL) + * signer: pointer to the signer data to update (cannot be NULL). Must have + * been used with `musig_session_get_public_nonce` or initialized + * with `musig_session_initialize_verifier`. + * In: nonce: signer's alleged public nonce (cannot be NULL) + */ + //if (!secp256k1_musig_set_nonce(ctx, &signer_data[i][j], &nonce[j])) { + + + /** Updates a session with the combined public nonce of all signers. The combined + * public nonce is the sum of every signer's public nonce. + * + * Returns: 1: nonces are successfully combined + * 0: a signer's nonce is missing + * Args: ctx: pointer to a context object (cannot be NULL) + * session: session to update with the combined public nonce (cannot be + * NULL) + * signers: an array of signers' data, which must have had public nonces + * set with `musig_set_nonce`. Array length must equal to `n_signers` + * (cannot be NULL) + * n_signers: the length of the signers array. Must be the total number of + * signers participating in the MuSig. + * Out: nonce_is_negated: a pointer to an integer that indicates if the combined + * public nonce had to be negated. + * adaptor: point to add to the combined public nonce. If NULL, nothing is + * added to the combined nonce. + */ + // after all nonces: if (!secp256k1_musig_session_combine_nonces(ctx, &musig_session[i], signer_data[i], N_SIGNERS, NULL, NULL)) { + return(result); } UniValue musig_partialsign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); result.push_back(Pair("result","success")); + /** Produces a partial signature + * + * Returns: 1: partial signature constructed + * 0: session in incorrect or inconsistent state + * Args: ctx: pointer to a context object (cannot be NULL) + * session: active signing session for which the combined nonce has been + * computed (cannot be NULL) + * Out: partial_sig: partial signature (cannot be NULL) + */ + //if (!secp256k1_musig_partial_sign(ctx, &musig_session[i], &partial_sig[i])) { + /** Parse and verify a MuSig partial signature. + * + * Returns: 1 when the signature could be parsed, 0 otherwise. + * Args: ctx: a secp256k1 context object + * Out: sig: pointer to a signature object + * In: in32: pointer to the 32-byte signature to be parsed + * + * After the call, sig will always be initialized. If parsing failed or the + * encoded numbers are out of range, signature verification with it is + * guaranteed to fail for every message and public key. + */ + //SECP256K1_API int secp256k1_musig_partial_signature_parse( + return(result); } @@ -245,13 +351,54 @@ UniValue musig_sigcombine(uint64_t txfee,struct CCcontract_info *cp,cJSON *param { UniValue result(UniValue::VOBJ); result.push_back(Pair("result","success")); - return(result); + /** Checks that an individual partial signature verifies + * + * This function is essential when using protocols with adaptor signatures. + * However, it is not essential for regular MuSig's, in the sense that if any + * partial signatures does not verify, the full signature will also not verify, so the + * problem will be caught. But this function allows determining the specific party + * who produced an invalid signature, so that signing can be restarted without them. + * + * Returns: 1: partial signature verifies + * 0: invalid signature or bad data + * Args: ctx: pointer to a context object (cannot be NULL) + * session: active session for which the combined nonce has been computed + * (cannot be NULL) + * signer: data for the signer who produced this signature (cannot be NULL) + * In: partial_sig: signature to verify (cannot be NULL) + * pubkey: public key of the signer who produced the signature (cannot be NULL) + */ + //if (!secp256k1_musig_partial_sig_verify(ctx, &musig_session[i], &signer_data[i][j], &partial_sig[j], &pubkeys[j])) { + return 0; + /** Combines partial signatures + * + * Returns: 1: all partial signatures have values in range. Does NOT mean the + * resulting signature verifies. + * 0: some partial signature had s/r out of range + * Args: ctx: pointer to a context object (cannot be NULL) + * session: initialized session for which the combined nonce has been + * computed (cannot be NULL) + * Out: sig: complete signature (cannot be NULL) + * In: partial_sigs: array of partial signatures to combine (cannot be NULL) + * n_sigs: number of signatures in the partial_sigs array + */ + // after all partials: return secp256k1_musig_partial_sig_combine(ctx, &musig_session[0], sig, partial_sig, N_SIGNERS return(result); } UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); result.push_back(Pair("result","success")); + /** Verify a Schnorr signature. + * + * Returns: 1: correct signature + * 0: incorrect or unparseable signature + * Args: ctx: a secp256k1 context object, initialized for verification. + * In: sig: the signature being verified (cannot be NULL) + * msg32: the 32-byte message hash being verified (cannot be NULL) + * pubkey: pointer to a public key to verify with (cannot be NULL) + */ + // if (!secp256k1_schnorrsig_verify(ctx, &sig, msg, &combined_pk)) { return(result); } From a709fe0fef57f03a74e6506b56ff450f31c6f5db Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 06:44:01 -1100 Subject: [PATCH 003/132] Remove exe permission on source files --- src/cc/dapps/cJSON.c | 0 src/cc/musig.cpp | 0 src/komodo_cJSON.c | 0 src/komodo_cJSON.h | 0 src/komodo_jumblr.h | 0 src/uthash.h | 0 src/utlist.h | 0 7 files changed, 0 insertions(+), 0 deletions(-) mode change 100755 => 100644 src/cc/dapps/cJSON.c mode change 100755 => 100644 src/cc/musig.cpp mode change 100755 => 100644 src/komodo_cJSON.c mode change 100755 => 100644 src/komodo_cJSON.h mode change 100755 => 100644 src/komodo_jumblr.h mode change 100755 => 100644 src/uthash.h mode change 100755 => 100644 src/utlist.h diff --git a/src/cc/dapps/cJSON.c b/src/cc/dapps/cJSON.c old mode 100755 new mode 100644 diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp old mode 100755 new mode 100644 diff --git a/src/komodo_cJSON.c b/src/komodo_cJSON.c old mode 100755 new mode 100644 diff --git a/src/komodo_cJSON.h b/src/komodo_cJSON.h old mode 100755 new mode 100644 diff --git a/src/komodo_jumblr.h b/src/komodo_jumblr.h old mode 100755 new mode 100644 diff --git a/src/uthash.h b/src/uthash.h old mode 100755 new mode 100644 diff --git a/src/utlist.h b/src/utlist.h old mode 100755 new mode 100644 From 7cef15077601820d30f2b14788daa3f1aad75b9d Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 18:48:22 +0100 Subject: [PATCH 004/132] add win deps --- src/cc/rogue/Makefile_win | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue/Makefile_win b/src/cc/rogue/Makefile_win index dbc900e48..96b6e61be 100644 --- a/src/cc/rogue/Makefile_win +++ b/src/cc/rogue/Makefile_win @@ -26,7 +26,7 @@ O=o CC = x86_64-w64-mingw32-gcc #CFLAGS=-O2 -CFLAGS= -g -O2 -I./ncurses/include +CFLAGS= -g -O2 -I./ncurses/include --I../../../depends/x86_64-w64-mingw32/include #LIBS=-lcurses LIBS = -L./ncurses/lib -lncursesw From 118461e55427865e34bdbb8a873b489ca9809aab Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 18:51:12 +0100 Subject: [PATCH 005/132] fix typo --- src/cc/makerogue | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/makerogue b/src/cc/makerogue index ff175c586..c67892b90 100755 --- a/src/cc/makerogue +++ b/src/cc/makerogue @@ -5,7 +5,7 @@ if [ "$HOST" = "x86_64-w64-mingw32" ]; then echo building rogue.exe... mkdir ncurses && cd ncurses wget https://invisible-island.net/datafiles/release/mingw32.zip - unzip mingw32.zip && delete mingw32.zip + unzip mingw32.zip && rm mingw32.zip cd .. if make -f Makefile_win "$@"; then echo rogue.exe build SUCCESSFUL From bf44755dadc8ba400c86018d3aed161b778cb8cf Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 18:56:25 +0100 Subject: [PATCH 006/132] pwd --- src/cc/makerogue | 1 - 1 file changed, 1 deletion(-) diff --git a/src/cc/makerogue b/src/cc/makerogue index c67892b90..9135753c1 100755 --- a/src/cc/makerogue +++ b/src/cc/makerogue @@ -6,7 +6,6 @@ if [ "$HOST" = "x86_64-w64-mingw32" ]; then mkdir ncurses && cd ncurses wget https://invisible-island.net/datafiles/release/mingw32.zip unzip mingw32.zip && rm mingw32.zip - cd .. if make -f Makefile_win "$@"; then echo rogue.exe build SUCCESSFUL cd .. From 8998c66874885248c2ac53aa044fdee3c413bcfb Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 18:58:09 +0100 Subject: [PATCH 007/132] revert --- src/cc/makerogue | 1 + 1 file changed, 1 insertion(+) diff --git a/src/cc/makerogue b/src/cc/makerogue index 9135753c1..c67892b90 100755 --- a/src/cc/makerogue +++ b/src/cc/makerogue @@ -6,6 +6,7 @@ if [ "$HOST" = "x86_64-w64-mingw32" ]; then mkdir ncurses && cd ncurses wget https://invisible-island.net/datafiles/release/mingw32.zip unzip mingw32.zip && rm mingw32.zip + cd .. if make -f Makefile_win "$@"; then echo rogue.exe build SUCCESSFUL cd .. From 55b7035f9b0736f06607768e13e2cd5b94a8da06 Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 19:04:45 +0100 Subject: [PATCH 008/132] add include --- src/cc/rogue/Makefile_win | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue/Makefile_win b/src/cc/rogue/Makefile_win index 96b6e61be..17941732c 100644 --- a/src/cc/rogue/Makefile_win +++ b/src/cc/rogue/Makefile_win @@ -26,7 +26,7 @@ O=o CC = x86_64-w64-mingw32-gcc #CFLAGS=-O2 -CFLAGS= -g -O2 -I./ncurses/include --I../../../depends/x86_64-w64-mingw32/include +CFLAGS= -g -O2 -I./ncurses/include -I../../../depends/x86_64-w64-mingw32/include #LIBS=-lcurses LIBS = -L./ncurses/lib -lncursesw From 762e3582d1d1109e97c3cb81ac8fb9501236033e Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 19:09:07 +0100 Subject: [PATCH 009/132] pwd --- src/cc/makerogue | 1 - 1 file changed, 1 deletion(-) diff --git a/src/cc/makerogue b/src/cc/makerogue index c67892b90..9135753c1 100755 --- a/src/cc/makerogue +++ b/src/cc/makerogue @@ -6,7 +6,6 @@ if [ "$HOST" = "x86_64-w64-mingw32" ]; then mkdir ncurses && cd ncurses wget https://invisible-island.net/datafiles/release/mingw32.zip unzip mingw32.zip && rm mingw32.zip - cd .. if make -f Makefile_win "$@"; then echo rogue.exe build SUCCESSFUL cd .. From b635717ec1219c8d3542962cfc01dc43432815b1 Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 19:40:52 +0100 Subject: [PATCH 010/132] add ncursesw --- src/cc/rogue/Makefile_win | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue/Makefile_win b/src/cc/rogue/Makefile_win index 17941732c..9c440349e 100644 --- a/src/cc/rogue/Makefile_win +++ b/src/cc/rogue/Makefile_win @@ -26,7 +26,7 @@ O=o CC = x86_64-w64-mingw32-gcc #CFLAGS=-O2 -CFLAGS= -g -O2 -I./ncurses/include -I../../../depends/x86_64-w64-mingw32/include +CFLAGS= -g -O2 -I./ncurses/include -I./ncurses/include/ncursesw -I../../../depends/x86_64-w64-mingw32/include #LIBS=-lcurses LIBS = -L./ncurses/lib -lncursesw From 47b99da2a3d4a7dfa6bd9ccce67446a6183dcabb Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 20:41:57 +0100 Subject: [PATCH 011/132] add debug --- src/cc/makerogue | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/cc/makerogue b/src/cc/makerogue index 9135753c1..b690e60e7 100755 --- a/src/cc/makerogue +++ b/src/cc/makerogue @@ -4,8 +4,11 @@ cd rogue; if [ "$HOST" = "x86_64-w64-mingw32" ]; then echo building rogue.exe... mkdir ncurses && cd ncurses + echo $PWD wget https://invisible-island.net/datafiles/release/mingw32.zip unzip mingw32.zip && rm mingw32.zip + echo lib archive cleaned + echo $PWD if make -f Makefile_win "$@"; then echo rogue.exe build SUCCESSFUL cd .. From fddc7d4369b242cb3b481f0a09d6247513a7913a Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 21:28:57 +0100 Subject: [PATCH 012/132] change dir --- src/cc/makerogue | 1 + 1 file changed, 1 insertion(+) diff --git a/src/cc/makerogue b/src/cc/makerogue index b690e60e7..063de081e 100755 --- a/src/cc/makerogue +++ b/src/cc/makerogue @@ -8,6 +8,7 @@ if [ "$HOST" = "x86_64-w64-mingw32" ]; then wget https://invisible-island.net/datafiles/release/mingw32.zip unzip mingw32.zip && rm mingw32.zip echo lib archive cleaned + cd .. echo $PWD if make -f Makefile_win "$@"; then echo rogue.exe build SUCCESSFUL From adb32b5a5138baa53adb30e7d324cb3d28405fdd Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 22:36:25 +0100 Subject: [PATCH 013/132] add WIN ifdef --- src/cc/rogue/main.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index ca05226d3..bcd35da73 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -41,7 +41,11 @@ typedef union _bits256 bits256; double OS_milliseconds() { struct timeval tv; double millis; + #ifdef __MINGW32__ + mingw_gettimeofday(&tv,NULL); + #else gettimeofday(&tv,NULL); + #endif millis = ((double)tv.tv_sec * 1000. + (double)tv.tv_usec / 1000.); //printf("tv_sec.%ld usec.%d %f\n",tv.tv_sec,tv.tv_usec,millis); return(millis); From 064179cf1894a31b018cf1461074e6895e3b0677 Mon Sep 17 00:00:00 2001 From: ca333 Date: Thu, 21 Feb 2019 23:09:25 +0100 Subject: [PATCH 014/132] config WIN --- src/cc/makerogue | 1 + 1 file changed, 1 insertion(+) diff --git a/src/cc/makerogue b/src/cc/makerogue index 063de081e..51caef6e2 100755 --- a/src/cc/makerogue +++ b/src/cc/makerogue @@ -3,6 +3,7 @@ cd rogue; if [ "$HOST" = "x86_64-w64-mingw32" ]; then echo building rogue.exe... + ./configure --host=x86_64-w64-mingw32 mkdir ncurses && cd ncurses echo $PWD wget https://invisible-island.net/datafiles/release/mingw32.zip From 6ca1613add51ece97efb7c9bb33ab878bd76cc2a Mon Sep 17 00:00:00 2001 From: ca333 Date: Fri, 22 Feb 2019 00:31:49 +0100 Subject: [PATCH 015/132] add ifdef WIN mdport --- src/cc/rogue/mdport.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/cc/rogue/mdport.c b/src/cc/rogue/mdport.c index 988e1c7b7..fd53be72c 100644 --- a/src/cc/rogue/mdport.c +++ b/src/cc/rogue/mdport.c @@ -705,7 +705,9 @@ md_erasechar() #elif defined(VERASE) return(_tty.c_cc[VERASE]); /* process erase character */ #else + #ifndef __MINGW32__ return(_tty.sg_erase); /* process erase character */ + #endif #endif } @@ -717,7 +719,9 @@ md_killchar() #elif defined(VKILL) return(_tty.c_cc[VKILL]); #else + #ifndef __MINGW32__ return(_tty.sg_kill); + #endif #endif } From ff9f59279bc6bf3a4e178b99eebda54050208014 Mon Sep 17 00:00:00 2001 From: ca333 Date: Fri, 22 Feb 2019 01:21:04 +0100 Subject: [PATCH 016/132] cache deps --- .gitlab-ci.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 3ace05cb9..a9fb7a01b 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -32,9 +32,9 @@ build:ubuntu: variables: DOCKER_DRIVER: overlay2 cache: - key: "${CI_JOB_NAME}${CI_COMMIT_REF_NAME}" + key: ${CI_COMMIT_REF_SLUG} paths: - - depends/built + - depends/ script: - zcutil/build.sh -j$(nproc) - mkdir ${PACKAGE_DIR_LINUX} From c7b070e91ca79f220e25cfae3d65e057fae519b4 Mon Sep 17 00:00:00 2001 From: ca333 Date: Fri, 22 Feb 2019 01:48:44 +0100 Subject: [PATCH 017/132] add curl --- src/cc/rogue/Makefile_win | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue/Makefile_win b/src/cc/rogue/Makefile_win index 9c440349e..6e558960c 100644 --- a/src/cc/rogue/Makefile_win +++ b/src/cc/rogue/Makefile_win @@ -29,7 +29,7 @@ CC = x86_64-w64-mingw32-gcc CFLAGS= -g -O2 -I./ncurses/include -I./ncurses/include/ncursesw -I../../../depends/x86_64-w64-mingw32/include #LIBS=-lcurses -LIBS = -L./ncurses/lib -lncursesw +LIBS = -L./ncurses/lib -lncursesw -lcurl #RM=rm -f RM = rm -f From ba34a8050009e4d1bef4df01b9ec685d7db5cca1 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 19:58:07 -1100 Subject: [PATCH 018/132] +print --- src/cc/faucet.cpp | 2 +- src/cc/musig.cpp | 297 +++++++++++++++++++++++++++++++--------------- 2 files changed, 204 insertions(+), 95 deletions(-) diff --git a/src/cc/faucet.cpp b/src/cc/faucet.cpp index b44337461..3f1ac4982 100644 --- a/src/cc/faucet.cpp +++ b/src/cc/faucet.cpp @@ -124,9 +124,9 @@ bool FaucetValidate(struct CCcontract_info *cp,Eval* eval,const CTransaction &tx //int height = it->first.blockHeight; if ( CCduration(numblocks,it->first.txhash) > 0 && numblocks > 3 ) { - //fprintf(stderr,"would return error %s numblocks.%d ago\n",uint256_str(str,it->first.txhash),numblocks); return eval->Invalid("faucet is only for brand new addresses"); } + fprintf(stderr,"txid %s numblocks.%d ago\n",uint256_str(str,it->first.txhash),numblocks); } retval = PreventCC(eval,tx,preventCCvins,numvins,preventCCvouts,numvouts); if ( retval != 0 ) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index ec7f5e788..263ed2fff 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -88,6 +88,54 @@ extern "C" int secp256k1_musig_pubkey_combine(const secp256k1_context* ctx, secp #define MUSIG_PREVN 0 // for now, just use vout0 for the musig output #define MUSIG_TXFEE 10000 +struct musig_info +{ + secp256k1_musig_session musig_session; + secp256k1_pubkey combined_pk; + uint8_t *nonce_commitments; // 32*N_SIGNERS + secp256k1_musig_session_signer_data *signer_data; //[N_SIGNERS]; + secp256k1_pubkey *nonce; //[N_SIGNERS]; + secp256k1_musig_partial_signature *partial_sig; //[N_SIGNERS]; + int32_t myind,num; + uint8_t msg[32],pkhash[32],combpk[33]; +} *MUSIG; + +struct musig_info *musig_infocreate(int32_t myind,int32_t num) +{ + struct musig_info *mp = (struct musig_info *)calloc(1,sizeof(*mp)); + mp->myind = myind, mp->num = num; + mp->nonce_commitments = (uint8_t *)calloc(num,32); + mp->signer_data = (uint8_t *)calloc(num,sizeof(*np->signer_data)); + mp->nonce = (uint8_t *)calloc(num,sizeof(*np->nonce)); + mp->partial_sig = (uint8_t *)calloc(num,sizeof(*np->partial_sig)); + return(mp); +} + +void musig_infofree(struct musig_info *mp) +{ + if ( mp->partial_sig != 0 ) + { + random_buf(mp->partial_sig,num*sizeof(*np->partial_sig)) + free(mp->partial_sig); + } + if ( mp->nonce != 0 ) + { + random_buf(mp->nonce,num*sizeof(*np->nonce)) + free(mp->nonce); + } + if ( mp->signer_data != 0 ) + { + random_buf(mp->signer_data,num*sizeof(*np->signer_data)) + free(mp->signer_data); + } + if ( mp->nonce_commitments != 0 ) + { + random_buf(mp->nonce_commitments,num*32) + free(mp->nonce_commitments); + } + free(mp); +} + CScript musig_sendopret(uint8_t funcid,CPubKey pk) { CScript opret; uint8_t evalcode = EVAL_MUSIG; @@ -215,111 +263,158 @@ UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); - result.push_back(Pair("result","success")); - /** Initializes a signing session for a signer - * - * Returns: 1: session is successfully initialized - * 0: session could not be initialized: secret key or secret nonce overflow - * Args: ctx: pointer to a context object, initialized for signing (cannot - * be NULL) - * Out: session: the session structure to initialize (cannot be NULL) - * signers: an array of signers' data to be initialized. Array length must - * equal to `n_signers` (cannot be NULL) - * nonce_commitment32: filled with a 32-byte commitment to the generated nonce - * (cannot be NULL) - * In: session_id32: a *unique* 32-byte ID to assign to this session (cannot be - * NULL). If a non-unique session_id32 was given then a partial - * signature will LEAK THE SECRET KEY. - * msg32: the 32-byte message to be signed. Shouldn't be NULL unless you - * require sharing public nonces before the message is known - * because it reduces nonce misuse resistance. If NULL, must be - * set with `musig_session_set_msg` before signing and verifying. - * combined_pk: the combined public key of all signers (cannot be NULL) - * pk_hash32: the 32-byte hash of the signers' individual keys (cannot be - * NULL) - * n_signers: length of signers array. Number of signers participating in - * the MuSig. Must be greater than 0 and at most 2^32 - 1. - * my_index: index of this signer in the signers array - * seckey: the signer's 32-byte secret key (cannot be NULL) - */ - //if (!secp256k1_musig_session_initialize(ctx, &musig_session[i], signer_data[i], nonce_commitment[i], session_id32, msg32, &combined_pk, pk_hash, N_SIGNERS, i, seckeys[i])) - //return 0; - // randombytes_buf(buf, num); - - //nonce_commitment_ptr[i] = &nonce_commitment[i][0]; - return(result); + static secp256k1_context *ctx; + UniValue result(UniValue::VOBJ); int32_t i,n,myind,num; char *pkstr,*pkhashstr,*msgstr; uint8_t session[32],msg[32],pkhash[32],privkey[32],pub33[33]; CPubKey pk; char str[67]; + if ( ctx == 0 ) + ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 5 ) + { + // set the 5 args: myind, num, pub33, pkhash32, msg32 + if ( MUSIG != 0 ) + musig_infofree(MUSIG), MUSIG = 0; + MUSIG = musig_infocreate(myind,num); + pk = buf2pk(pub33); + if ( secp256k1_ec_pubkey_parse(ctx,&MUSIG->combined_pk,pk.begin(),33) > 0 ) + { + memcpy(MUSIG->pkhash,pkhash,sizeof(pkhash)); + memcpy(MUSIG->msg,msg,sizeof(msg)); + random_buf(session,32); + Myprivkey(privkey); + /** Initializes a signing session for a signer + * + * Returns: 1: session is successfully initialized + * 0: session could not be initialized: secret key or secret nonce overflow + * Args: ctx: pointer to a context object, initialized for signing (cannot + * be NULL) + * Out: session: the session structure to initialize (cannot be NULL) + * signers: an array of signers' data to be initialized. Array length must + * equal to `n_signers` (cannot be NULL) + * nonce_commitment32: filled with a 32-byte commitment to the generated nonce + * (cannot be NULL) + * In: session_id32: a *unique* 32-byte ID to assign to this session (cannot be + * NULL). If a non-unique session_id32 was given then a partial + * signature will LEAK THE SECRET KEY. + * msg32: the 32-byte message to be signed. Shouldn't be NULL unless you + * require sharing public nonces before the message is known + * because it reduces nonce misuse resistance. If NULL, must be + * set with `musig_session_set_msg` before signing and verifying. + * combined_pk: the combined public key of all signers (cannot be NULL) + * pk_hash32: the 32-byte hash of the signers' individual keys (cannot be + * NULL) + * n_signers: length of signers array. Number of signers participating in + * the MuSig. Must be greater than 0 and at most 2^32 - 1. + * my_index: index of this signer in the signers array + * seckey: the signer's 32-byte secret key (cannot be NULL) + */ + if ( secp256k1_musig_session_initialize(ctx,&MUSIG->musig_session,MUSIG->signer_data, &MUSIG->nonce_commitment[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) + { + result.push_back(Pair("myind",(int64_t)myind)); + result.push_back(Pair("numsigners",(int64_t)num)); + for (i=0; i<32; i++) + sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitment[MUSIG->myind*32 + i]); + str[64] = 0; + result.push_back(Pair("commitment",str)); + result.push_back(Pair("result","success")); + return(result) + } else return(cclib_error(result,"couldnt initialize session")); + } else return(cclib_error(result,"couldnt parse combined pubkey")); + } else return(cclib_error(result,"wrong number of params, need 5: myindex, numsigners, combined_pk, pkhash, msg32")); } UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); - result.push_back(Pair("result","success")); - /** Gets the signer's public nonce given a list of all signers' data with commitments - * - * Returns: 1: public nonce is written in nonce - * 0: signer data is missing commitments or session isn't initialized - * for signing - * Args: ctx: pointer to a context object (cannot be NULL) - * session: the signing session to get the nonce from (cannot be NULL) - * signers: an array of signers' data initialized with - * `musig_session_initialize`. Array length must equal to - * `n_commitments` (cannot be NULL) - * Out: nonce: the nonce (cannot be NULL) - * In: commitments: array of 32-byte nonce commitments (cannot be NULL) - * n_commitments: the length of commitments and signers array. Must be the total - * number of signers participating in the MuSig. - */ - // Set nonce commitments in the signer data and get the own public nonce - //if (!secp256k1_musig_session_get_public_nonce(ctx, &musig_session[i], signer_data[i], &nonce[i], nonce_commitment_ptr, N_SIGNERS)) - // return 0; - - return(result); + static secp256k1_context *ctx; + UniValue result(UniValue::VOBJ); int32_t n; + if ( ctx == 0 ) + ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + { + // pkhash, ind, commitment + // if all commitments, emit nonce, else just update MUSIG-> + + /** Gets the signer's public nonce given a list of all signers' data with commitments + * + * Returns: 1: public nonce is written in nonce + * 0: signer data is missing commitments or session isn't initialized + * for signing + * Args: ctx: pointer to a context object (cannot be NULL) + * session: the signing session to get the nonce from (cannot be NULL) + * signers: an array of signers' data initialized with + * `musig_session_initialize`. Array length must equal to + * `n_commitments` (cannot be NULL) + * Out: nonce: the nonce (cannot be NULL) + * In: commitments: array of 32-byte nonce commitments (cannot be NULL) + * n_commitments: the length of commitments and signers array. Must be the total + * number of signers participating in the MuSig. + */ + // Set nonce commitments in the signer data and get the own public nonce + //if (secp256k1_musig_session_get_public_nonce(ctx, &musig_session[i], signer_data[i], &nonce[i], nonce_commitment_ptr, N_SIGNERS) > 0 ) + { + // publish nonce + result.push_back(Pair("result","success")); + } + // return 0; + } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, commitment")); } UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); - result.push_back(Pair("result","success")); - /** Checks a signer's public nonce against a commitment to said nonce, and update - * data structure if they match - * - * Returns: 1: commitment was valid, data structure updated - * 0: commitment was invalid, nothing happened - * Args: ctx: pointer to a context object (cannot be NULL) - * signer: pointer to the signer data to update (cannot be NULL). Must have - * been used with `musig_session_get_public_nonce` or initialized - * with `musig_session_initialize_verifier`. - * In: nonce: signer's alleged public nonce (cannot be NULL) - */ - //if (!secp256k1_musig_set_nonce(ctx, &signer_data[i][j], &nonce[j])) { - - - /** Updates a session with the combined public nonce of all signers. The combined - * public nonce is the sum of every signer's public nonce. - * - * Returns: 1: nonces are successfully combined - * 0: a signer's nonce is missing - * Args: ctx: pointer to a context object (cannot be NULL) - * session: session to update with the combined public nonce (cannot be - * NULL) - * signers: an array of signers' data, which must have had public nonces - * set with `musig_set_nonce`. Array length must equal to `n_signers` - * (cannot be NULL) - * n_signers: the length of the signers array. Must be the total number of - * signers participating in the MuSig. - * Out: nonce_is_negated: a pointer to an integer that indicates if the combined - * public nonce had to be negated. - * adaptor: point to add to the combined public nonce. If NULL, nothing is - * added to the combined nonce. - */ - // after all nonces: if (!secp256k1_musig_session_combine_nonces(ctx, &musig_session[i], signer_data[i], N_SIGNERS, NULL, NULL)) { + static secp256k1_context *ctx; + UniValue result(UniValue::VOBJ); int32_t n; + if ( ctx == 0 ) + ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); + if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) + { + // pkhash, ind, nonce + // if all nonces, combine nonce, else just update MUSIG-> + result.push_back(Pair("result","success")); + /** Checks a signer's public nonce against a commitment to said nonce, and update + * data structure if they match + * + * Returns: 1: commitment was valid, data structure updated + * 0: commitment was invalid, nothing happened + * Args: ctx: pointer to a context object (cannot be NULL) + * signer: pointer to the signer data to update (cannot be NULL). Must have + * been used with `musig_session_get_public_nonce` or initialized + * with `musig_session_initialize_verifier`. + * In: nonce: signer's alleged public nonce (cannot be NULL) + */ + //if (!secp256k1_musig_set_nonce(ctx, &signer_data[i][j], &nonce[j])) { + + + /** Updates a session with the combined public nonce of all signers. The combined + * public nonce is the sum of every signer's public nonce. + * + * Returns: 1: nonces are successfully combined + * 0: a signer's nonce is missing + * Args: ctx: pointer to a context object (cannot be NULL) + * session: session to update with the combined public nonce (cannot be + * NULL) + * signers: an array of signers' data, which must have had public nonces + * set with `musig_set_nonce`. Array length must equal to `n_signers` + * (cannot be NULL) + * n_signers: the length of the signers array. Must be the total number of + * signers participating in the MuSig. + * Out: nonce_is_negated: a pointer to an integer that indicates if the combined + * public nonce had to be negated. + * adaptor: point to add to the combined public nonce. If NULL, nothing is + * added to the combined nonce. + */ + // after all nonces: if (!secp256k1_musig_session_combine_nonces(ctx, &musig_session[i], signer_data[i], N_SIGNERS, NULL, NULL)) { return(result); + } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, nonce")); } UniValue musig_partialsign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); + static secp256k1_context *ctx; + UniValue result(UniValue::VOBJ); int32_t n; + if ( ctx == 0 ) + ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); + if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) + { + // similar to commit/nonce + } result.push_back(Pair("result","success")); /** Produces a partial signature * @@ -349,7 +444,14 @@ UniValue musig_partialsign(uint64_t txfee,struct CCcontract_info *cp,cJSON *para UniValue musig_sigcombine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); + static secp256k1_context *ctx; + UniValue result(UniValue::VOBJ); int32_t n; + if ( ctx == 0 ) + ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); + if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) + { + // finally! + } result.push_back(Pair("result","success")); /** Checks that an individual partial signature verifies * @@ -387,7 +489,14 @@ UniValue musig_sigcombine(uint64_t txfee,struct CCcontract_info *cp,cJSON *param UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); + static secp256k1_context *ctx; + UniValue result(UniValue::VOBJ); int32_t n; + if ( ctx == 0 ) + ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); + if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) + { + // can code this out of order + } result.push_back(Pair("result","success")); /** Verify a Schnorr signature. * From cb1a6291c6e45addf50146971703be58badeff52 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 19:59:46 -1100 Subject: [PATCH 019/132] Mp --- src/cc/musig.cpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 263ed2fff..b54bf26d1 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -105,9 +105,9 @@ struct musig_info *musig_infocreate(int32_t myind,int32_t num) struct musig_info *mp = (struct musig_info *)calloc(1,sizeof(*mp)); mp->myind = myind, mp->num = num; mp->nonce_commitments = (uint8_t *)calloc(num,32); - mp->signer_data = (uint8_t *)calloc(num,sizeof(*np->signer_data)); - mp->nonce = (uint8_t *)calloc(num,sizeof(*np->nonce)); - mp->partial_sig = (uint8_t *)calloc(num,sizeof(*np->partial_sig)); + mp->signer_data = (uint8_t *)calloc(num,sizeof(*mp->signer_data)); + mp->nonce = (uint8_t *)calloc(num,sizeof(*mp->nonce)); + mp->partial_sig = (uint8_t *)calloc(num,sizeof(*mp->partial_sig)); return(mp); } @@ -115,22 +115,22 @@ void musig_infofree(struct musig_info *mp) { if ( mp->partial_sig != 0 ) { - random_buf(mp->partial_sig,num*sizeof(*np->partial_sig)) + random_buf(mp->partial_sig,mp->num*sizeof(*np->partial_sig)) free(mp->partial_sig); } if ( mp->nonce != 0 ) { - random_buf(mp->nonce,num*sizeof(*np->nonce)) + random_buf(mp->nonce,mp->num*sizeof(*mp->nonce)) free(mp->nonce); } if ( mp->signer_data != 0 ) { - random_buf(mp->signer_data,num*sizeof(*np->signer_data)) + random_buf(mp->signer_data,mp->num*sizeof(*mp->signer_data)) free(mp->signer_data); } if ( mp->nonce_commitments != 0 ) { - random_buf(mp->nonce_commitments,num*32) + random_buf(mp->nonce_commitments,mp->num*32) free(mp->nonce_commitments); } free(mp); From da11af7c0ff54a3071e0e3f50723d2d6610e4364 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:01:06 -1100 Subject: [PATCH 020/132] Test --- src/cc/musig.cpp | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index b54bf26d1..44ddf6ef3 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -87,6 +87,7 @@ extern "C" int secp256k1_musig_pubkey_combine(const secp256k1_context* ctx, secp #define MUSIG_PREVN 0 // for now, just use vout0 for the musig output #define MUSIG_TXFEE 10000 +#define random_buf(a,b) struct musig_info { @@ -105,9 +106,9 @@ struct musig_info *musig_infocreate(int32_t myind,int32_t num) struct musig_info *mp = (struct musig_info *)calloc(1,sizeof(*mp)); mp->myind = myind, mp->num = num; mp->nonce_commitments = (uint8_t *)calloc(num,32); - mp->signer_data = (uint8_t *)calloc(num,sizeof(*mp->signer_data)); - mp->nonce = (uint8_t *)calloc(num,sizeof(*mp->nonce)); - mp->partial_sig = (uint8_t *)calloc(num,sizeof(*mp->partial_sig)); + mp->signer_data = (secp256k1_musig_session_signer_data *)calloc(num,sizeof(*mp->signer_data)); + mp->nonce = (secp256k1_pubkey *)calloc(num,sizeof(*mp->nonce)); + mp->partial_sig = (secp256k1_musig_partial_signature *)calloc(num,sizeof(*mp->partial_sig)); return(mp); } @@ -115,7 +116,7 @@ void musig_infofree(struct musig_info *mp) { if ( mp->partial_sig != 0 ) { - random_buf(mp->partial_sig,mp->num*sizeof(*np->partial_sig)) + random_buf(mp->partial_sig,mp->num*sizeof(*mp->partial_sig)) free(mp->partial_sig); } if ( mp->nonce != 0 ) From e1c434466734a26921d98c6e0db1cb12df3a2f08 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:02:05 -1100 Subject: [PATCH 021/132] syntax --- src/cc/musig.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 44ddf6ef3..aa821f644 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -307,16 +307,16 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * my_index: index of this signer in the signers array * seckey: the signer's 32-byte secret key (cannot be NULL) */ - if ( secp256k1_musig_session_initialize(ctx,&MUSIG->musig_session,MUSIG->signer_data, &MUSIG->nonce_commitment[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) + if ( secp256k1_musig_session_initialize(ctx,&MUSIG->musig_session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) { result.push_back(Pair("myind",(int64_t)myind)); result.push_back(Pair("numsigners",(int64_t)num)); for (i=0; i<32; i++) - sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitment[MUSIG->myind*32 + i]); + sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitments[MUSIG->myind*32 + i]); str[64] = 0; result.push_back(Pair("commitment",str)); result.push_back(Pair("result","success")); - return(result) + return(result); } else return(cclib_error(result,"couldnt initialize session")); } else return(cclib_error(result,"couldnt parse combined pubkey")); } else return(cclib_error(result,"wrong number of params, need 5: myindex, numsigners, combined_pk, pkhash, msg32")); From 40c26873ba97286ed860c8e4c742b68cc28f237c Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:03:14 -1100 Subject: [PATCH 022/132] extern "C" --- src/cc/musig.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index aa821f644..68787e67b 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -78,6 +78,7 @@ extern "C" int secp256k1_ecmult_multi_var(const secp256k1_ecmult_context *ctx, s extern "C" int secp256k1_schnorrsig_verify(const secp256k1_context* ctx, const secp256k1_schnorrsig *sig, const unsigned char *msg32, const secp256k1_pubkey *pk); extern "C" int secp256k1_schnorrsig_parse(const secp256k1_context* ctx, secp256k1_schnorrsig* sig, const unsigned char *in64); extern "C" int secp256k1_musig_pubkey_combine(const secp256k1_context* ctx, secp256k1_scratch_space *scratch, secp256k1_pubkey *combined_pk, unsigned char *pk_hash32, const secp256k1_pubkey *pubkeys, size_t n_pubkeys); +extern "C" int secp256k1_musig_session_initialize(const secp256k1_context* ctx, secp256k1_musig_session *session, secp256k1_musig_session_signer_data *signers, unsigned char *nonce_commitment32, const unsigned char *session_id32, const unsigned char *msg32, const secp256k1_pubkey *combined_pk, const unsigned char *pk_hash32, size_t n_signers, size_t my_index, const unsigned char *seckey); //#include "../secp256k1/include/secp256k1.h" From 146d452410880c1657f479c22f33d51402b667aa Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:03:56 -1100 Subject: [PATCH 023/132] Reorder --- src/cc/musig.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 68787e67b..8fdba80a2 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -74,18 +74,18 @@ struct secp256k1_context_struct { secp256k1_callback error_callback; }; -extern "C" int secp256k1_ecmult_multi_var(const secp256k1_ecmult_context *ctx, secp256k1_scratch *scratch, secp256k1_gej *r, const secp256k1_scalar *inp_g_sc, secp256k1_ecmult_multi_callback cb, void *cbdata, size_t n); -extern "C" int secp256k1_schnorrsig_verify(const secp256k1_context* ctx, const secp256k1_schnorrsig *sig, const unsigned char *msg32, const secp256k1_pubkey *pk); -extern "C" int secp256k1_schnorrsig_parse(const secp256k1_context* ctx, secp256k1_schnorrsig* sig, const unsigned char *in64); -extern "C" int secp256k1_musig_pubkey_combine(const secp256k1_context* ctx, secp256k1_scratch_space *scratch, secp256k1_pubkey *combined_pk, unsigned char *pk_hash32, const secp256k1_pubkey *pubkeys, size_t n_pubkeys); -extern "C" int secp256k1_musig_session_initialize(const secp256k1_context* ctx, secp256k1_musig_session *session, secp256k1_musig_session_signer_data *signers, unsigned char *nonce_commitment32, const unsigned char *session_id32, const unsigned char *msg32, const secp256k1_pubkey *combined_pk, const unsigned char *pk_hash32, size_t n_signers, size_t my_index, const unsigned char *seckey); - //#include "../secp256k1/include/secp256k1.h" //#include "../secp256k1/include/secp256k1_schnorrsig.h" #include "../secp256k1/include/secp256k1_musig.h" +extern "C" int secp256k1_ecmult_multi_var(const secp256k1_ecmult_context *ctx, secp256k1_scratch *scratch, secp256k1_gej *r, const secp256k1_scalar *inp_g_sc, secp256k1_ecmult_multi_callback cb, void *cbdata, size_t n); +extern "C" int secp256k1_schnorrsig_verify(const secp256k1_context* ctx, const secp256k1_schnorrsig *sig, const unsigned char *msg32, const secp256k1_pubkey *pk); +extern "C" int secp256k1_schnorrsig_parse(const secp256k1_context* ctx, secp256k1_schnorrsig* sig, const unsigned char *in64); +extern "C" int secp256k1_musig_pubkey_combine(const secp256k1_context* ctx, secp256k1_scratch_space *scratch, secp256k1_pubkey *combined_pk, unsigned char *pk_hash32, const secp256k1_pubkey *pubkeys, size_t n_pubkeys); +extern "C" int secp256k1_musig_session_initialize(const secp256k1_context* ctx, secp256k1_musig_session *session, secp256k1_musig_session_signer_data *signers, unsigned char *nonce_commitment32, const unsigned char *session_id32, const unsigned char *msg32, const secp256k1_pubkey *combined_pk, const unsigned char *pk_hash32, size_t n_signers, size_t my_index, const unsigned char *seckey); + #define MUSIG_PREVN 0 // for now, just use vout0 for the musig output #define MUSIG_TXFEE 10000 #define random_buf(a,b) From c76bd865230436337d54231fcaa6ca86957cb0b2 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:06:25 -1100 Subject: [PATCH 024/132] #ifdef __cplusplus --- src/secp256k1/include/secp256k1_musig.h | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/secp256k1/include/secp256k1_musig.h b/src/secp256k1/include/secp256k1_musig.h index 7e974e36d..d58550cf8 100644 --- a/src/secp256k1/include/secp256k1_musig.h +++ b/src/secp256k1/include/secp256k1_musig.h @@ -167,7 +167,12 @@ SECP256K1_API int secp256k1_musig_pubkey_combine( * my_index: index of this signer in the signers array * seckey: the signer's 32-byte secret key (cannot be NULL) */ -SECP256K1_API int secp256k1_musig_session_initialize( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_session_initialize( const secp256k1_context* ctx, secp256k1_musig_session *session, secp256k1_musig_session_signer_data *signers, From db9149577974a6cda3a60ae4196c9b2d7a3eeec5 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:07:50 -1100 Subject: [PATCH 025/132] Again --- src/secp256k1/include/secp256k1_musig.h | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/secp256k1/include/secp256k1_musig.h b/src/secp256k1/include/secp256k1_musig.h index d58550cf8..a0106e691 100644 --- a/src/secp256k1/include/secp256k1_musig.h +++ b/src/secp256k1/include/secp256k1_musig.h @@ -132,7 +132,12 @@ typedef struct { * key (cannot be NULL) * n_pubkeys: length of pubkeys array */ -SECP256K1_API int secp256k1_musig_pubkey_combine( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_pubkey_combine( const secp256k1_context* ctx, secp256k1_scratch_space *scratch, secp256k1_pubkey *combined_pk, From f20d2860dec77fcdca16d874787a037058855cf5 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:11:38 -1100 Subject: [PATCH 026/132] -print --- src/cc/faucet.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/faucet.cpp b/src/cc/faucet.cpp index 3f1ac4982..b794d9b1c 100644 --- a/src/cc/faucet.cpp +++ b/src/cc/faucet.cpp @@ -126,7 +126,7 @@ bool FaucetValidate(struct CCcontract_info *cp,Eval* eval,const CTransaction &tx { return eval->Invalid("faucet is only for brand new addresses"); } - fprintf(stderr,"txid %s numblocks.%d ago\n",uint256_str(str,it->first.txhash),numblocks); + //fprintf(stderr,"txid %s numblocks.%d ago\n",uint256_str(str,it->first.txhash),numblocks); } retval = PreventCC(eval,tx,preventCCvins,numvins,preventCCvouts,numvouts); if ( retval != 0 ) From f448c53ac872751e8a2f3d5bd6ed562b61e28443 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:13:18 -1100 Subject: [PATCH 027/132] (uint8_t *) --- src/cc/musig.cpp | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 8fdba80a2..80da59927 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -88,7 +88,6 @@ extern "C" int secp256k1_musig_session_initialize(const secp256k1_context* ctx, #define MUSIG_PREVN 0 // for now, just use vout0 for the musig output #define MUSIG_TXFEE 10000 -#define random_buf(a,b) struct musig_info { @@ -117,22 +116,22 @@ void musig_infofree(struct musig_info *mp) { if ( mp->partial_sig != 0 ) { - random_buf(mp->partial_sig,mp->num*sizeof(*mp->partial_sig)) + GetRandBytes((uint8_t *)mp->partial_sig,mp->num*sizeof(*mp->partial_sig)) free(mp->partial_sig); } if ( mp->nonce != 0 ) { - random_buf(mp->nonce,mp->num*sizeof(*mp->nonce)) + GetRandBytes((uint8_t *)mp->nonce,mp->num*sizeof(*mp->nonce)) free(mp->nonce); } if ( mp->signer_data != 0 ) { - random_buf(mp->signer_data,mp->num*sizeof(*mp->signer_data)) + GetRandBytes((uint8_t *)mp->signer_data,mp->num*sizeof(*mp->signer_data)) free(mp->signer_data); } if ( mp->nonce_commitments != 0 ) { - random_buf(mp->nonce_commitments,mp->num*32) + GetRandBytes((uint8_t *)mp->nonce_commitments,mp->num*32) free(mp->nonce_commitments); } free(mp); @@ -280,7 +279,7 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { memcpy(MUSIG->pkhash,pkhash,sizeof(pkhash)); memcpy(MUSIG->msg,msg,sizeof(msg)); - random_buf(session,32); + GetRandBytes(session,32); Myprivkey(privkey); /** Initializes a signing session for a signer * From 41d1eef0191a48413140f73c5d8abb30602cfceb Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:14:14 -1100 Subject: [PATCH 028/132] ; --- src/cc/musig.cpp | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 80da59927..633c95feb 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -116,24 +116,25 @@ void musig_infofree(struct musig_info *mp) { if ( mp->partial_sig != 0 ) { - GetRandBytes((uint8_t *)mp->partial_sig,mp->num*sizeof(*mp->partial_sig)) + GetRandBytes((uint8_t *)mp->partial_sig,mp->num*sizeof(*mp->partial_sig)); free(mp->partial_sig); } if ( mp->nonce != 0 ) { - GetRandBytes((uint8_t *)mp->nonce,mp->num*sizeof(*mp->nonce)) + GetRandBytes((uint8_t *)mp->nonce,mp->num*sizeof(*mp->nonce)); free(mp->nonce); } if ( mp->signer_data != 0 ) { - GetRandBytes((uint8_t *)mp->signer_data,mp->num*sizeof(*mp->signer_data)) + GetRandBytes((uint8_t *)mp->signer_data,mp->num*sizeof(*mp->signer_data)); free(mp->signer_data); } if ( mp->nonce_commitments != 0 ) { - GetRandBytes((uint8_t *)mp->nonce_commitments,mp->num*32) + GetRandBytes((uint8_t *)mp->nonce_commitments,mp->num*32); free(mp->nonce_commitments); } + GetRandBytes((uint8_t *)mp,sizeof(*mp)); free(mp); } From dc3767b68f5369114164235da1297ebb07525356 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:15:40 -1100 Subject: [PATCH 029/132] Session --- src/cc/musig.cpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 633c95feb..9f529a341 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -281,6 +281,10 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) memcpy(MUSIG->pkhash,pkhash,sizeof(pkhash)); memcpy(MUSIG->msg,msg,sizeof(msg)); GetRandBytes(session,32); + for (i=0; i<32; i++) + sprintf(&str[i<<1],"%02x",session[i]); + str[64] = 0; + fprintf(stderr,"session %s\n",str); Myprivkey(privkey); /** Initializes a signing session for a signer * From 3bc10962e5af83cbca4eaf7f8edf5046ce21b5d0 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 20:17:28 -1100 Subject: [PATCH 030/132] Move --- src/cc/musig.cpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 9f529a341..fc83fe382 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -276,15 +276,15 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) musig_infofree(MUSIG), MUSIG = 0; MUSIG = musig_infocreate(myind,num); pk = buf2pk(pub33); + GetRandBytes(session,32); + for (i=0; i<32; i++) + sprintf(&str[i<<1],"%02x",session[i]); + str[64] = 0; + fprintf(stderr,"session %s\n",str); if ( secp256k1_ec_pubkey_parse(ctx,&MUSIG->combined_pk,pk.begin(),33) > 0 ) { memcpy(MUSIG->pkhash,pkhash,sizeof(pkhash)); memcpy(MUSIG->msg,msg,sizeof(msg)); - GetRandBytes(session,32); - for (i=0; i<32; i++) - sprintf(&str[i<<1],"%02x",session[i]); - str[64] = 0; - fprintf(stderr,"session %s\n",str); Myprivkey(privkey); /** Initializes a signing session for a signer * From d84a9afe6f071c0801f1350c9acbf7a128f96c55 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 22:03:15 -1100 Subject: [PATCH 031/132] Add parsing for session --- src/cc/musig.cpp | 64 ++++++++++++++++++++++++++++++++++-------------- 1 file changed, 46 insertions(+), 18 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index fc83fe382..ccb554e0f 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -223,6 +223,27 @@ UniValue musig_calcmsg(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) } else return(cclib_error(result,"couldnt parse params")); } +int32_t musig_parsepubkey(secp256k1_context *ctx,secp256k1_pubkey &spk,cJSON *item) +{ + char *hexstr; + if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == 66 ) + { + CPubKey pk(ParseHex(hexstr)); + if ( secp256k1_ec_pubkey_parse(ctx,&spk,pk.begin(),33) > 0 ) + return(1); + } else return(-1); +} + +int32_t musig_parsehash32(uint8_t *hash32,cJSON *item) +{ + char *hexstr; + if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == 64 ) + { + decode_hex(hash32,32,hexstr); + return(0); + } else return(-1); +} + UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; @@ -235,13 +256,9 @@ UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) //fprintf(stderr,"n.%d args.(%s)\n",n,jprint(params,0)); for (i=0; i 0 ) - pubkeys.push_back(spk); - else return(cclib_error(result,"error parsing pk")); - } else return(cclib_error(result,"all pubkeys must be 33 bytes hexdata")); + if ( musig_parsepubkey(ctx,spk,jitem(params,i)) < 0 ) + return(cclib_error(result,"error parsing pk")); + pubkeys.push_back(spk); } if ( secp256k1_musig_pubkey_combine(ctx,NULL,&combined_pk,pkhash,&pubkeys[0],n) > 0 ) { @@ -271,21 +288,26 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 5 ) { - // set the 5 args: myind, num, pub33, pkhash32, msg32 + myind = juint(jitem(params,0),0); + num = juint(jitem(params,1),0); + if ( myind < 0 || myind >= num || num <= 0 ) + return(cclib_error(result,"illegal myindex and numsigners")); if ( MUSIG != 0 ) musig_infofree(MUSIG), MUSIG = 0; MUSIG = musig_infocreate(myind,num); - pk = buf2pk(pub33); - GetRandBytes(session,32); - for (i=0; i<32; i++) - sprintf(&str[i<<1],"%02x",session[i]); - str[64] = 0; - fprintf(stderr,"session %s\n",str); - if ( secp256k1_ec_pubkey_parse(ctx,&MUSIG->combined_pk,pk.begin(),33) > 0 ) + if ( musig_parsepubkey(ctx,MUSIG->combined_pk,jitem(params,2)) < 0 ) + return(cclib_error(result,"error parsing combined_pubkey")); { - memcpy(MUSIG->pkhash,pkhash,sizeof(pkhash)); - memcpy(MUSIG->msg,msg,sizeof(msg)); + if ( musig_parsehash32(MUSIG->pkhash,jitem(params,3)) < 0 ) + return(cclib_error(result,"error parsing pkhash")); + if ( musig_parsehash32(MUSIG->msg,jitem(params,4)) < 0 ) + return(cclib_error(result,"error parsing msg")); Myprivkey(privkey); + GetRandBytes(session,32); + for (i=0; i<32; i++) + sprintf(&str[i<<1],"%02x",session[i]); + str[64] = 0; + fprintf(stderr,"session %s\n",str); /** Initializes a signing session for a signer * * Returns: 1: session is successfully initialized @@ -314,6 +336,7 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) */ if ( secp256k1_musig_session_initialize(ctx,&MUSIG->musig_session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) { + memset(session,0,sizeof(session)); result.push_back(Pair("myind",(int64_t)myind)); result.push_back(Pair("numsigners",(int64_t)num)); for (i=0; i<32; i++) @@ -322,7 +345,12 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) result.push_back(Pair("commitment",str)); result.push_back(Pair("result","success")); return(result); - } else return(cclib_error(result,"couldnt initialize session")); + } + else + { + memset(session,0,sizeof(session)); + return(cclib_error(result,"couldnt initialize session")); + } } else return(cclib_error(result,"couldnt parse combined pubkey")); } else return(cclib_error(result,"wrong number of params, need 5: myindex, numsigners, combined_pk, pkhash, msg32")); } From 101a4153799c06ce3efc6705286c36184c3c383b Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 22:05:27 -1100 Subject: [PATCH 032/132] Fix --- src/cc/musig.cpp | 52 +++++++++++++++++++++--------------------------- 1 file changed, 23 insertions(+), 29 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index ccb554e0f..7b9510b2a 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -297,17 +297,12 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) MUSIG = musig_infocreate(myind,num); if ( musig_parsepubkey(ctx,MUSIG->combined_pk,jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing combined_pubkey")); - { - if ( musig_parsehash32(MUSIG->pkhash,jitem(params,3)) < 0 ) - return(cclib_error(result,"error parsing pkhash")); - if ( musig_parsehash32(MUSIG->msg,jitem(params,4)) < 0 ) - return(cclib_error(result,"error parsing msg")); - Myprivkey(privkey); - GetRandBytes(session,32); - for (i=0; i<32; i++) - sprintf(&str[i<<1],"%02x",session[i]); - str[64] = 0; - fprintf(stderr,"session %s\n",str); + else if ( musig_parsehash32(MUSIG->pkhash,jitem(params,3)) < 0 ) + return(cclib_error(result,"error parsing pkhash")); + else if ( musig_parsehash32(MUSIG->msg,jitem(params,4)) < 0 ) + return(cclib_error(result,"error parsing msg")); + Myprivkey(privkey); + GetRandBytes(session,32); /** Initializes a signing session for a signer * * Returns: 1: session is successfully initialized @@ -334,24 +329,23 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * my_index: index of this signer in the signers array * seckey: the signer's 32-byte secret key (cannot be NULL) */ - if ( secp256k1_musig_session_initialize(ctx,&MUSIG->musig_session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) - { - memset(session,0,sizeof(session)); - result.push_back(Pair("myind",(int64_t)myind)); - result.push_back(Pair("numsigners",(int64_t)num)); - for (i=0; i<32; i++) - sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitments[MUSIG->myind*32 + i]); - str[64] = 0; - result.push_back(Pair("commitment",str)); - result.push_back(Pair("result","success")); - return(result); - } - else - { - memset(session,0,sizeof(session)); - return(cclib_error(result,"couldnt initialize session")); - } - } else return(cclib_error(result,"couldnt parse combined pubkey")); + if ( secp256k1_musig_session_initialize(ctx,&MUSIG->musig_session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) + { + memset(session,0,sizeof(session)); + result.push_back(Pair("myind",(int64_t)myind)); + result.push_back(Pair("numsigners",(int64_t)num)); + for (i=0; i<32; i++) + sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitments[MUSIG->myind*32 + i]); + str[64] = 0; + result.push_back(Pair("commitment",str)); + result.push_back(Pair("result","success")); + return(result); + } + else + { + memset(session,0,sizeof(session)); + return(cclib_error(result,"couldnt initialize session")); + } } else return(cclib_error(result,"wrong number of params, need 5: myindex, numsigners, combined_pk, pkhash, msg32")); } From eb09e81eaedefc639bb3ea61729066e3b33224b4 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 23:29:46 -1100 Subject: [PATCH 033/132] Musig commitment, nonce and partial sig roc --- src/cc/cclib.cpp | 20 +- src/cc/musig.cpp | 231 +++++++++++-------- src/secp256k1/include/secp256k1_musig.h | 84 ++++++- src/secp256k1/include/secp256k1_schnorrsig.h | 14 +- 4 files changed, 226 insertions(+), 123 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index bfd57e61d..ec74877b6 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -72,12 +72,11 @@ CClib_methods[] = { (char *)"sudoku", (char *)"pending", (char *)"", 0, 0, 'U', EVAL_SUDOKU }, { (char *)"sudoku", (char *)"solution", (char *)"txid solution timestamps[81]", 83, 83, 'S', EVAL_SUDOKU }, { (char *)"musig", (char *)"calcmsg", (char *)"sendtxid scriptPubKey", 2, 2, 'C', EVAL_MUSIG }, - { (char *)"musig", (char *)"combine", (char *)"pubkeys ...", 2, 256, 'P', EVAL_MUSIG }, - { (char *)"musig", (char *)"session", (char *)"msg pkhash", 2, 2, 'R', EVAL_MUSIG }, - { (char *)"musig", (char *)"commit", (char *)"pubkeys ...", 2, 256, 'H', EVAL_MUSIG }, - { (char *)"musig", (char *)"nonce", (char *)"pubkeys ...", 2, 256, 'N', EVAL_MUSIG }, - { (char *)"musig", (char *)"partialsign", (char *)"pubkeys ...", 2, 256, 'S', EVAL_MUSIG }, - { (char *)"musig", (char *)"sigcombine", (char *)"pubkeys ...", 2, 256, 'M', EVAL_MUSIG }, + { (char *)"musig", (char *)"combine", (char *)"pubkeys ...", 2, 999999999, 'P', EVAL_MUSIG }, + { (char *)"musig", (char *)"session", (char *)"myindex,numsigners,combined_pk,pkhash,msg32", 5, 5, 'R', EVAL_MUSIG }, + { (char *)"musig", (char *)"commit", (char *)"pkhash,ind,commitment", 3, 3, 'H', EVAL_MUSIG }, + { (char *)"musig", (char *)"nonce", (char *)"pkhash,ind,nonce", 3, 3, 'N', EVAL_MUSIG }, + { (char *)"musig", (char *)"partialsig", (char *)"pkhash,ind,partialsig", 3, 3, 'S', EVAL_MUSIG }, { (char *)"musig", (char *)"verify", (char *)"msg sig pubkey", 3, 3, 'V', EVAL_MUSIG }, { (char *)"musig", (char *)"send", (char *)"combined_pk amount", 2, 2, 'x', EVAL_MUSIG }, { (char *)"musig", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_MUSIG }, @@ -116,8 +115,7 @@ UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); -UniValue musig_partialsign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); -UniValue musig_sigcombine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); +UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); @@ -229,10 +227,8 @@ UniValue CClib_method(struct CCcontract_info *cp,char *method,char *jsonstr) return(musig_commit(txfee,cp,params)); else if ( strcmp(method,"nonce") == 0 ) // returns combined nonce if ready return(musig_nonce(txfee,cp,params)); - else if ( strcmp(method,"partialsign") == 0 ) - return(musig_partialsign(txfee,cp,params)); - else if ( strcmp(method,"sigcombine") == 0 ) - return(musig_sigcombine(txfee,cp,params)); + else if ( strcmp(method,"partialsig") == 0 ) + return(musig_partialsig(txfee,cp,params)); else if ( strcmp(method,"verify") == 0 ) return(musig_verify(txfee,cp,params)); else if ( strcmp(method,"send") == 0 ) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 7b9510b2a..f6a7bf7b7 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -20,6 +20,7 @@ "combined_pk": "032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b", "result": "success" } + the combined_pk and pkhash will be needed for various other rpc calls */ /* second, send 0.777 coins to the combined_pk @@ -55,6 +56,33 @@ "result": "success", "msg": "63b799913d4c9487f321b32d6ae8614f653f38e0b50d4df4bc1d36339ea18485" } +the "msg" is what needs to be signed to create a valid spend + + now on each signing node, a session needs to be created: + 5 args: ind, numsigners, combined_pk, pkhash, message to be signed + + on node with pubkey: 02aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848 + ./c cclib session 18 \"[0,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%2263b799913d4c9487f321b32d6ae8614f653f38e0b50d4df4bc1d36339ea18485%22]\" + { + "myind": 0, + "numsigners": 2, + "commitment": "053a97ba56b1b8adf174a0a28dc16b1bb4e91a33ca0b52a579ce9ba4af299973", + "result": "success" + } + + on node with pubkey: 039433dc3749aece1bd568f374a45da3b0bc6856990d7da3cd175399577940a775 + ./c cclib session 18 \"[1,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%2263b799913d4c9487f321b32d6ae8614f653f38e0b50d4df4bc1d36339ea18485%22]\" + { + "myind": 1, + "numsigners": 2, + "commitment": "8c8dc6717aaa1994d4a51d1094c0c5cbfaf033c11642dbeeab32a32de4cfbc86", + "result": "success" + } + + now we need to get the commitment from each node to the other one. the session already put the commitment for each node into the global struct. Keep in mind there is a single global struct with session unique to each cclib session call. that means no restarting any deamon in the middle of the process on any of the nodes and only call cclib session a single time. this is an artificial restriction just to simplify the initial implementation of musig + + ./c cclib commitment 18 \"[1,%228c8dc6717aaa1994d4a51d1094c0c5cbfaf033c11642dbeeab32a32de4cfbc86%22]\" + ./c cclib commitment 18 \"[0,%22053a97ba56b1b8adf174a0a28dc16b1bb4e91a33ca0b52a579ce9ba4af299973%22]\" */ @@ -91,9 +119,9 @@ extern "C" int secp256k1_musig_session_initialize(const secp256k1_context* ctx, struct musig_info { - secp256k1_musig_session musig_session; + secp256k1_musig_session session; secp256k1_pubkey combined_pk; - uint8_t *nonce_commitments; // 32*N_SIGNERS + uint8_t *nonce_commitments,**commitment_ptrs; // 32*N_SIGNERS secp256k1_musig_session_signer_data *signer_data; //[N_SIGNERS]; secp256k1_pubkey *nonce; //[N_SIGNERS]; secp256k1_musig_partial_signature *partial_sig; //[N_SIGNERS]; @@ -103,9 +131,12 @@ struct musig_info struct musig_info *musig_infocreate(int32_t myind,int32_t num) { - struct musig_info *mp = (struct musig_info *)calloc(1,sizeof(*mp)); + int32_t i; struct musig_info *mp = (struct musig_info *)calloc(1,sizeof(*mp)); mp->myind = myind, mp->num = num; mp->nonce_commitments = (uint8_t *)calloc(num,32); + mp->commitment_ptrs = (uint8_t **)calloc(num,sizeof(*mp->commitment_ptrs)); + for (i=0; icommitment_ptrs[i] = &mp->nonce_commitments[i*32]; mp->signer_data = (secp256k1_musig_session_signer_data *)calloc(num,sizeof(*mp->signer_data)); mp->nonce = (secp256k1_pubkey *)calloc(num,sizeof(*mp->nonce)); mp->partial_sig = (secp256k1_musig_partial_signature *)calloc(num,sizeof(*mp->partial_sig)); @@ -134,6 +165,11 @@ void musig_infofree(struct musig_info *mp) GetRandBytes((uint8_t *)mp->nonce_commitments,mp->num*32); free(mp->nonce_commitments); } + if ( mp->commitment_ptrs != 0 ) + { + GetRandBytes((uint8_t *)mp->commitment_ptrs,mp->num*sizeof(*mp->commitment_ptrs)); + free(mp->commitment_ptrs); + } GetRandBytes((uint8_t *)mp,sizeof(*mp)); free(mp); } @@ -329,7 +365,7 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * my_index: index of this signer in the signers array * seckey: the signer's 32-byte secret key (cannot be NULL) */ - if ( secp256k1_musig_session_initialize(ctx,&MUSIG->musig_session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) + if ( secp256k1_musig_session_initialize(ctx,&MUSIG->session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) { memset(session,0,sizeof(session)); result.push_back(Pair("myind",(int64_t)myind)); @@ -352,14 +388,19 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t n; + UniValue result(UniValue::VOBJ); int32_t n,ind; uint8_t pkhash[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - // pkhash, ind, commitment - // if all commitments, emit nonce, else just update MUSIG-> - + if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) + return(cclib_error(result,"error parsing pkhash")); + else if ( memcmp(MUSING->pkhash,pkhash,32) != 0 ) + return(cclib_error(result,"pkhash doesnt match session pkhash")); + else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + return(cclib_error(result,"illegal ind for session")); + else if ( musig_parsehash32(&MUSIG->commitment[ind*32],jitem(params,2)) < 0 ) + return(cclib_error(result,"error parsing commitment")); /** Gets the signer's public nonce given a list of all signers' data with commitments * * Returns: 1: public nonce is written in nonce @@ -375,27 +416,44 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * n_commitments: the length of commitments and signers array. Must be the total * number of signers participating in the MuSig. */ - // Set nonce commitments in the signer data and get the own public nonce - //if (secp256k1_musig_session_get_public_nonce(ctx, &musig_session[i], signer_data[i], &nonce[i], nonce_commitment_ptr, N_SIGNERS) > 0 ) + result.push_back(Pair("added_index",ind)); + if ( secp256k1_musig_session_get_public_nonce(ctx,&MUSIG->session,MUSIG->signer_data,&MUSIG->nonces[MUSIG->myind],MUSIG->nonce_commitments,MUSIG->num) > 0 ) { - // publish nonce + if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG->nonces[MUSIG->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) + { + for (i=0; i<33; i++) + sprintf(&str[i<<1],"%02x",((uint8_t *)pk.begin())[i]); + str[66] = 0; + result.push_back(Pair("nonce",str)); + result.push_back(Pair("result","success")); + } else return(cclib_error(result,"error serializing nonce (pubkey)")); + } + else + { + result.push_back(Pair("status","not enough commitments")); result.push_back(Pair("result","success")); } - // return 0; + return(result); } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, commitment")); } UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t n; + UniValue result(UniValue::VOBJ); int32_t i,n,ind; uint8_t pkhash[32],psig[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - // pkhash, ind, nonce - // if all nonces, combine nonce, else just update MUSIG-> - result.push_back(Pair("result","success")); + if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) + return(cclib_error(result,"error parsing pkhash")); + else if ( memcmp(MUSING->pkhash,pkhash,32) != 0 ) + return(cclib_error(result,"pkhash doesnt match session pkhash")); + else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + return(cclib_error(result,"illegal ind for session")); + else if ( musig_parsepubkey(ctx,&MUSIG->nonces[ind],jitem(params,2)) < 0 ) + return(cclib_error(result,"error parsing nonce")); + result.push_back(Pair("added_index",ind)); /** Checks a signer's public nonce against a commitment to said nonce, and update * data structure if they match * @@ -407,9 +465,11 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * with `musig_session_initialize_verifier`. * In: nonce: signer's alleged public nonce (cannot be NULL) */ - //if (!secp256k1_musig_set_nonce(ctx, &signer_data[i][j], &nonce[j])) { - - + for (i=0; inum; i++) + { + if ( secp256k1_musig_set_nonce(ctx,&MUSIG->signer_data[i],&MUSIG->nonces[i]) == 0 ) + return(cclib_error(result,"error setting nonce")); + } /** Updates a session with the combined public nonce of all signers. The combined * public nonce is the sum of every signer's public nonce. * @@ -428,91 +488,68 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * adaptor: point to add to the combined public nonce. If NULL, nothing is * added to the combined nonce. */ - // after all nonces: if (!secp256k1_musig_session_combine_nonces(ctx, &musig_session[i], signer_data[i], N_SIGNERS, NULL, NULL)) { - return(result); + if ( secp256k1_musig_session_combine_nonces(ctx,&MUSIG->session,MUSIG->signer_data,MUSIG->num,NULL,NULL) > 0 ) + { + if ( secp256k1_musig_partial_sign(ctx,&MUSIG->session,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + { + if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + { + result.push_back(Pair("myind",ind)); + for (i=0; i<32; i++) + sprintf(&str[i<<1],"%02x",psig[i]); + str[64] = 0; + result.push_back(Pair("partialsig",str)); + result.push_back(Pair("result","success")); + return(result); + } else return(cclib_error(result,"error serializing partial sig")); + } else return(cclib_error(result,"error making partial sig")); + } else return(cclib_error(result,"error combining nonces")); } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, nonce")); } -UniValue musig_partialsign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) +UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t n; + UniValue result(UniValue::VOBJ); int32_t ind,n; uint8_t pkhash[32],psig[32],out64[64]; char str[129]; secp256k1_schnorrsig sig; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - // similar to commit/nonce - } - result.push_back(Pair("result","success")); - /** Produces a partial signature - * - * Returns: 1: partial signature constructed - * 0: session in incorrect or inconsistent state - * Args: ctx: pointer to a context object (cannot be NULL) - * session: active signing session for which the combined nonce has been - * computed (cannot be NULL) - * Out: partial_sig: partial signature (cannot be NULL) - */ - //if (!secp256k1_musig_partial_sign(ctx, &musig_session[i], &partial_sig[i])) { - /** Parse and verify a MuSig partial signature. - * - * Returns: 1 when the signature could be parsed, 0 otherwise. - * Args: ctx: a secp256k1 context object - * Out: sig: pointer to a signature object - * In: in32: pointer to the 32-byte signature to be parsed - * - * After the call, sig will always be initialized. If parsing failed or the - * encoded numbers are out of range, signature verification with it is - * guaranteed to fail for every message and public key. - */ - //SECP256K1_API int secp256k1_musig_partial_signature_parse( - - return(result); -} - -UniValue musig_sigcombine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) -{ - static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t n; - if ( ctx == 0 ) - ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) - { - // finally! - } - result.push_back(Pair("result","success")); - /** Checks that an individual partial signature verifies - * - * This function is essential when using protocols with adaptor signatures. - * However, it is not essential for regular MuSig's, in the sense that if any - * partial signatures does not verify, the full signature will also not verify, so the - * problem will be caught. But this function allows determining the specific party - * who produced an invalid signature, so that signing can be restarted without them. - * - * Returns: 1: partial signature verifies - * 0: invalid signature or bad data - * Args: ctx: pointer to a context object (cannot be NULL) - * session: active session for which the combined nonce has been computed - * (cannot be NULL) - * signer: data for the signer who produced this signature (cannot be NULL) - * In: partial_sig: signature to verify (cannot be NULL) - * pubkey: public key of the signer who produced the signature (cannot be NULL) - */ - //if (!secp256k1_musig_partial_sig_verify(ctx, &musig_session[i], &signer_data[i][j], &partial_sig[j], &pubkeys[j])) { - return 0; - /** Combines partial signatures - * - * Returns: 1: all partial signatures have values in range. Does NOT mean the - * resulting signature verifies. - * 0: some partial signature had s/r out of range - * Args: ctx: pointer to a context object (cannot be NULL) - * session: initialized session for which the combined nonce has been - * computed (cannot be NULL) - * Out: sig: complete signature (cannot be NULL) - * In: partial_sigs: array of partial signatures to combine (cannot be NULL) - * n_sigs: number of signatures in the partial_sigs array - */ - // after all partials: return secp256k1_musig_partial_sig_combine(ctx, &musig_session[0], sig, partial_sig, N_SIGNERS return(result); + if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) + return(cclib_error(result,"error parsing pkhash")); + else if ( memcmp(MUSING->pkhash,pkhash,32) != 0 ) + return(cclib_error(result,"pkhash doesnt match session pkhash")); + else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + return(cclib_error(result,"illegal ind for session")); + else if ( musig_parsepartial(ctx,&MUSIG->partial_sig[ind],jitem(params,2)) < 0 ) + return(cclib_error(result,"error parsing partialsig")); + result.push_back(Pair("added_index",ind)); + if (secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) + { + if ( secp256k1_schnorrsig_serialize(ctx,out64,&sig) > 0 ) + { + result.push_back(Pair("result","success")); + for (i=0; i<64; i++) + sprintf(&str[i<<1],"%02x",out64[i]); + str[128] = 0; + result.push_back(Pair("combinedsig",str)); + } else return(cclib_error(result,"error serializing combinedsig")); + } + else + { + if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + { + result.push_back(Pair("myind",ind)); + for (i=0; i<32; i++) + sprintf(&str[i<<1],"%02x",psig[i]); + str[64] = 0; + result.push_back(Pair("partialsig",str)); + result.push_back(Pair("result","success")); + result.push_back(Pair("status","need more partialsigs")); + } else return(cclib_error(result,"error generating my partialsig")); + } + return(result); + } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, partialsig")); } UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) diff --git a/src/secp256k1/include/secp256k1_musig.h b/src/secp256k1/include/secp256k1_musig.h index a0106e691..84106822a 100644 --- a/src/secp256k1/include/secp256k1_musig.h +++ b/src/secp256k1/include/secp256k1_musig.h @@ -206,7 +206,12 @@ SECP256K1_API * n_commitments: the length of commitments and signers array. Must be the total * number of signers participating in the MuSig. */ -SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_session_get_public_nonce( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_session_get_public_nonce( const secp256k1_context* ctx, secp256k1_musig_session *session, secp256k1_musig_session_signer_data *signers, @@ -235,7 +240,12 @@ SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_session_get_publi * participating in the MuSig. Must be greater than 0 and at most * 2^32 - 1. */ -SECP256K1_API int secp256k1_musig_session_initialize_verifier( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_session_initialize_verifier( const secp256k1_context* ctx, secp256k1_musig_session *session, secp256k1_musig_session_signer_data *signers, @@ -257,7 +267,12 @@ SECP256K1_API int secp256k1_musig_session_initialize_verifier( * with `musig_session_initialize_verifier`. * In: nonce: signer's alleged public nonce (cannot be NULL) */ -SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_set_nonce( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_set_nonce( const secp256k1_context* ctx, secp256k1_musig_session_signer_data *signer, const secp256k1_pubkey *nonce @@ -281,7 +296,12 @@ SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_set_nonce( * adaptor: point to add to the combined public nonce. If NULL, nothing is * added to the combined nonce. */ -SECP256K1_API int secp256k1_musig_session_combine_nonces( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_session_combine_nonces( const secp256k1_context* ctx, secp256k1_musig_session *session, const secp256k1_musig_session_signer_data *signers, @@ -298,7 +318,12 @@ SECP256K1_API int secp256k1_musig_session_combine_nonces( * session: the session structure to update with the message (cannot be NULL) * In: msg32: the 32-byte message to be signed (cannot be NULL) */ -SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_session_set_msg( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_session_set_msg( const secp256k1_context* ctx, secp256k1_musig_session *session, const unsigned char *msg32 @@ -311,7 +336,12 @@ SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_session_set_msg( * Out: out32: pointer to a 32-byte array to store the serialized signature * In: sig: pointer to the signature */ -SECP256K1_API int secp256k1_musig_partial_signature_serialize( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_partial_signature_serialize( const secp256k1_context* ctx, unsigned char *out32, const secp256k1_musig_partial_signature* sig @@ -328,7 +358,12 @@ SECP256K1_API int secp256k1_musig_partial_signature_serialize( * encoded numbers are out of range, signature verification with it is * guaranteed to fail for every message and public key. */ -SECP256K1_API int secp256k1_musig_partial_signature_parse( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_partial_signature_parse( const secp256k1_context* ctx, secp256k1_musig_partial_signature* sig, const unsigned char *in32 @@ -343,7 +378,12 @@ SECP256K1_API int secp256k1_musig_partial_signature_parse( * computed (cannot be NULL) * Out: partial_sig: partial signature (cannot be NULL) */ -SECP256K1_API int secp256k1_musig_partial_sign( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_partial_sign( const secp256k1_context* ctx, const secp256k1_musig_session *session, secp256k1_musig_partial_signature *partial_sig @@ -366,7 +406,12 @@ SECP256K1_API int secp256k1_musig_partial_sign( * In: partial_sig: signature to verify (cannot be NULL) * pubkey: public key of the signer who produced the signature (cannot be NULL) */ -SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_partial_sig_verify( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_partial_sig_verify( const secp256k1_context* ctx, const secp256k1_musig_session *session, const secp256k1_musig_session_signer_data *signer, @@ -386,7 +431,12 @@ SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_partial_sig_verif * In: partial_sigs: array of partial signatures to combine (cannot be NULL) * n_sigs: number of signatures in the partial_sigs array */ -SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_partial_sig_combine( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_partial_sig_combine( const secp256k1_context* ctx, const secp256k1_musig_session *session, secp256k1_schnorrsig *sig, @@ -406,7 +456,12 @@ SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_partial_sig_combi * be NULL) * nonce_is_negated: the `nonce_is_negated` output of `musig_session_combine_nonces` */ -SECP256K1_API int secp256k1_musig_partial_sig_adapt( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + int secp256k1_musig_partial_sig_adapt( const secp256k1_context* ctx, secp256k1_musig_partial_signature *adaptor_sig, const secp256k1_musig_partial_signature *partial_sig, @@ -429,7 +484,12 @@ SECP256K1_API int secp256k1_musig_partial_sig_adapt( * n_partial_sigs: number of elements in partial_sigs array * nonce_is_negated: the `nonce_is_negated` output of `musig_session_combine_nonces` */ -SECP256K1_API SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_extract_secret_adaptor( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif + SECP256K1_WARN_UNUSED_RESULT int secp256k1_musig_extract_secret_adaptor( const secp256k1_context* ctx, unsigned char *sec_adaptor32, const secp256k1_schnorrsig *sig, diff --git a/src/secp256k1/include/secp256k1_schnorrsig.h b/src/secp256k1/include/secp256k1_schnorrsig.h index 9dea16653..e4d02f34f 100644 --- a/src/secp256k1/include/secp256k1_schnorrsig.h +++ b/src/secp256k1/include/secp256k1_schnorrsig.h @@ -28,7 +28,12 @@ typedef struct { * * See secp256k1_schnorrsig_parse for details about the encoding. */ -SECP256K1_API int secp256k1_schnorrsig_serialize( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif +int secp256k1_schnorrsig_serialize( const secp256k1_context* ctx, unsigned char *out64, const secp256k1_schnorrsig* sig @@ -50,7 +55,12 @@ SECP256K1_API int secp256k1_schnorrsig_serialize( * encoded numbers are out of range, signature validation with it is * guaranteed to fail for every message and public key. */ -SECP256K1_API int secp256k1_schnorrsig_parse( +#ifdef __cplusplus +extern "C" +#else +SECP256K1_API +#endif +int secp256k1_schnorrsig_parse( const secp256k1_context* ctx, secp256k1_schnorrsig* sig, const unsigned char *in64 From 141790634d27cc0461329d2261859c54ec3bebfa Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 23:33:13 -1100 Subject: [PATCH 034/132] Syntax --- src/cc/musig.cpp | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index f6a7bf7b7..8696809da 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -123,7 +123,7 @@ struct musig_info secp256k1_pubkey combined_pk; uint8_t *nonce_commitments,**commitment_ptrs; // 32*N_SIGNERS secp256k1_musig_session_signer_data *signer_data; //[N_SIGNERS]; - secp256k1_pubkey *nonce; //[N_SIGNERS]; + secp256k1_pubkey *nonces; //[N_SIGNERS]; secp256k1_musig_partial_signature *partial_sig; //[N_SIGNERS]; int32_t myind,num; uint8_t msg[32],pkhash[32],combpk[33]; @@ -138,7 +138,7 @@ struct musig_info *musig_infocreate(int32_t myind,int32_t num) for (i=0; icommitment_ptrs[i] = &mp->nonce_commitments[i*32]; mp->signer_data = (secp256k1_musig_session_signer_data *)calloc(num,sizeof(*mp->signer_data)); - mp->nonce = (secp256k1_pubkey *)calloc(num,sizeof(*mp->nonce)); + mp->nonces = (secp256k1_pubkey *)calloc(num,sizeof(*mp->nonces)); mp->partial_sig = (secp256k1_musig_partial_signature *)calloc(num,sizeof(*mp->partial_sig)); return(mp); } @@ -150,10 +150,10 @@ void musig_infofree(struct musig_info *mp) GetRandBytes((uint8_t *)mp->partial_sig,mp->num*sizeof(*mp->partial_sig)); free(mp->partial_sig); } - if ( mp->nonce != 0 ) + if ( mp->nonces != 0 ) { - GetRandBytes((uint8_t *)mp->nonce,mp->num*sizeof(*mp->nonce)); - free(mp->nonce); + GetRandBytes((uint8_t *)mp->nonces,mp->num*sizeof(*mp->nonces)); + free(mp->nonces); } if ( mp->signer_data != 0 ) { @@ -388,14 +388,14 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t n,ind; uint8_t pkhash[32]; CPubKey pk; char str[67]; + UniValue result(UniValue::VOBJ); int32_t i,n,ind; uint8_t pkhash[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSING->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); @@ -424,6 +424,7 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) for (i=0; i<33; i++) sprintf(&str[i<<1],"%02x",((uint8_t *)pk.begin())[i]); str[66] = 0; + result.push_back(Pair("myind",MUSIG->myind)); result.push_back(Pair("nonce",str)); result.push_back(Pair("result","success")); } else return(cclib_error(result,"error serializing nonce (pubkey)")); @@ -447,7 +448,7 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSING->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); @@ -498,6 +499,7 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) for (i=0; i<32; i++) sprintf(&str[i<<1],"%02x",psig[i]); str[64] = 0; + result.push_back(Pair("myind",MUSIG->myind)); result.push_back(Pair("partialsig",str)); result.push_back(Pair("result","success")); return(result); @@ -510,14 +512,14 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t ind,n; uint8_t pkhash[32],psig[32],out64[64]; char str[129]; secp256k1_schnorrsig sig; + UniValue result(UniValue::VOBJ); int32_t i,ind,n; uint8_t pkhash[32],psig[32],out64[64]; char str[129]; secp256k1_schnorrsig sig; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSING->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); From 3d99ab8a66a0de574abfd066ff6980390734f860 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 23:39:37 -1100 Subject: [PATCH 035/132] Fix --- src/cc/musig.cpp | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 8696809da..2d4002059 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -388,6 +388,7 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; + size_t clen = CPubKey::PUBLIC_KEY_SIZE; UniValue result(UniValue::VOBJ); int32_t i,n,ind; uint8_t pkhash[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); @@ -399,7 +400,7 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash32(&MUSIG->commitment[ind*32],jitem(params,2)) < 0 ) + else if ( musig_parsehash32(&MUSIG->nonce_commitments[ind*32],jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing commitment")); /** Gets the signer's public nonce given a list of all signers' data with commitments * @@ -417,7 +418,7 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * number of signers participating in the MuSig. */ result.push_back(Pair("added_index",ind)); - if ( secp256k1_musig_session_get_public_nonce(ctx,&MUSIG->session,MUSIG->signer_data,&MUSIG->nonces[MUSIG->myind],MUSIG->nonce_commitments,MUSIG->num) > 0 ) + if ( secp256k1_musig_session_get_public_nonce(ctx,&MUSIG->session,MUSIG->signer_data,&MUSIG->nonces[MUSIG->myind],MUSIG->commitment_ptrs,MUSIG->num) > 0 ) { if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG->nonces[MUSIG->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) { @@ -452,7 +453,7 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsepubkey(ctx,&MUSIG->nonces[ind],jitem(params,2)) < 0 ) + else if ( musig_parsepubkey(ctx,MUSIG->nonces[ind],jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing nonce")); result.push_back(Pair("added_index",ind)); /** Checks a signer's public nonce against a commitment to said nonce, and update @@ -523,7 +524,9 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsepartial(ctx,&MUSIG->partial_sig[ind],jitem(params,2)) < 0 ) + else if ( musig_parsehash32(ctx,psig,jitem(params,2)) < 0 ) + return(cclib_error(result,"error parsing psig")); + else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); result.push_back(Pair("added_index",ind)); if (secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) From b17065ce1762782a13ab6205c06bd20df5a644ba Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 23:41:10 -1100 Subject: [PATCH 036/132] extern "C" --- src/cc/musig.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 2d4002059..03eb01e3e 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -113,6 +113,7 @@ extern "C" int secp256k1_schnorrsig_verify(const secp256k1_context* ctx, const s extern "C" int secp256k1_schnorrsig_parse(const secp256k1_context* ctx, secp256k1_schnorrsig* sig, const unsigned char *in64); extern "C" int secp256k1_musig_pubkey_combine(const secp256k1_context* ctx, secp256k1_scratch_space *scratch, secp256k1_pubkey *combined_pk, unsigned char *pk_hash32, const secp256k1_pubkey *pubkeys, size_t n_pubkeys); extern "C" int secp256k1_musig_session_initialize(const secp256k1_context* ctx, secp256k1_musig_session *session, secp256k1_musig_session_signer_data *signers, unsigned char *nonce_commitment32, const unsigned char *session_id32, const unsigned char *msg32, const secp256k1_pubkey *combined_pk, const unsigned char *pk_hash32, size_t n_signers, size_t my_index, const unsigned char *seckey); +extern "C" int secp256k1_schnorrsig_serialize(const secp256k1_context* ctx, unsigned char *out64, const secp256k1_schnorrsig* sig); #define MUSIG_PREVN 0 // for now, just use vout0 for the musig output #define MUSIG_TXFEE 10000 @@ -524,12 +525,12 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash32(ctx,psig,jitem(params,2)) < 0 ) + else if ( musig_parsehash32(psig,jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing psig")); else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); result.push_back(Pair("added_index",ind)); - if (secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) + if ( secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) { if ( secp256k1_schnorrsig_serialize(ctx,out64,&sig) > 0 ) { From c07c6724b2d05dac81104b69a53f8fc23c49b845 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 23:52:20 -1100 Subject: [PATCH 037/132] Rpc examples to make a combined signature "combinedsig": "bc0062cd3233433e098fbf4f3c333946779c3dccfaefc423243e3f90edfdf9a6dbfabf4 2d26f3c668fe6e10f1ed367a46dfddbafaee82b3eb79722ae49f45320" --- src/cc/musig.cpp | 67 ++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 62 insertions(+), 5 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 03eb01e3e..4f08dd4cf 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -66,7 +66,7 @@ the "msg" is what needs to be signed to create a valid spend { "myind": 0, "numsigners": 2, - "commitment": "053a97ba56b1b8adf174a0a28dc16b1bb4e91a33ca0b52a579ce9ba4af299973", + "commitment": "89af8f6db69fc3d4b95480a914dceba9933039e9823151a82677c3ca4e961fcc", "result": "success" } @@ -75,15 +75,73 @@ the "msg" is what needs to be signed to create a valid spend { "myind": 1, "numsigners": 2, - "commitment": "8c8dc6717aaa1994d4a51d1094c0c5cbfaf033c11642dbeeab32a32de4cfbc86", + "commitment": "a43da5ef8322abb43b9fddadef7b6479baf7853e860f915e01521e3060e5342b", "result": "success" } now we need to get the commitment from each node to the other one. the session already put the commitment for each node into the global struct. Keep in mind there is a single global struct with session unique to each cclib session call. that means no restarting any deamon in the middle of the process on any of the nodes and only call cclib session a single time. this is an artificial restriction just to simplify the initial implementation of musig - ./c cclib commitment 18 \"[1,%228c8dc6717aaa1994d4a51d1094c0c5cbfaf033c11642dbeeab32a32de4cfbc86%22]\" - ./c cclib commitment 18 \"[0,%22053a97ba56b1b8adf174a0a28dc16b1bb4e91a33ca0b52a579ce9ba4af299973%22]\" + ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%22a43da5ef8322abb43b9fddadef7b6479baf7853e860f915e01521e3060e5342b%22]\" + { + "added_index": 1, + "myind": 0, + "nonce": "03bf28874f5e5dccf55170406d58ded84ac6ca713011d718c6048400d700cb879a", + "result": "success" + } + + ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%2289af8f6db69fc3d4b95480a914dceba9933039e9823151a82677c3ca4e961fcc%22]\" + { + "added_index": 0, + "myind": 1, + "nonce": "039ae1f542e8f0f6d03d734dc2295651973e1b7fa99508e2f36dad5d21f09889f6", + "result": "success" + } + + Now exchange the revealed nonces to each node: + + ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%22039ae1f542e8f0f6d03d734dc2295651973e1b7fa99508e2f36dad5d21f09889f6%22]\" + { + "added_index": 1, + "myind": 0, + "partialsig": "5da4c1ec828cd1563bc6554aa74c90c29fcd38b2aea26f7fa92e0d007aa9463f", + "result": "success" + } + + ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%2203bf28874f5e5dccf55170406d58ded84ac6ca713011d718c6048400d700cb879a%22]\" + { + "added_index": 0, + "myind": 1, + "partialsig": "7e55fd564fe26b1054208bc47786d6e1ce30a2fd0045bbbf0e6915adcf4b0ce1", + "result": "success" + } + + Almost there! final step is to exchange the partial sigs between signers + ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%227e55fd564fe26b1054208bc47786d6e1ce30a2fd0045bbbf0e6915adcf4b0ce1%22]\" + { + "added_index": 1, + "result": "success", + "combinedsig": "bc0062cd3233433e098fbf4f3c333946779c3dccfaefc423243e3f90edfdf9a6dbfabf42d26f3c668fe6e10f1ed367a46dfddbafaee82b3eb79722ae49f45320" + } + + ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%225da4c1ec828cd1563bc6554aa74c90c29fcd38b2aea26f7fa92e0d007aa9463f%22]\" + + { + "added_index": 0, + "result": "success", + "combinedsig": "bc0062cd3233433e098fbf4f3c333946779c3dccfaefc423243e3f90edfdf9a6dbfabf42d26f3c668fe6e10f1ed367a46dfddbafaee82b3eb79722ae49f45320" + } + + Notice both nodes generated the same combined signature! + + Now for a sanity test, we can use the verify call to make sure this sig will work with the msg needed for the spend: + + xxxx + + + and finally the spend: + + */ @@ -497,7 +555,6 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) { - result.push_back(Pair("myind",ind)); for (i=0; i<32; i++) sprintf(&str[i<<1],"%02x",psig[i]); str[64] = 0; From 925eaa285162afaeed9396aced6413ed38c61a62 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 23:57:30 -1100 Subject: [PATCH 038/132] Test --- src/cc/musig.cpp | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 4f08dd4cf..6b2e7abca 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -139,9 +139,9 @@ the "msg" is what needs to be signed to create a valid spend xxxx - and finally the spend: - + and finally the spend: sendtxid, scriptPubKey, musig +./c cclib spend 18 \"[%22cb5309ed249da95e2b5696eb763a8736e2fff1d14922ada737b931494ca3d2be%22,%222102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac%22,%22bc0062cd3233433e098fbf4f3c333946779c3dccfaefc423243e3f90edfdf9a6dbfabf42d26f3c668fe6e10f1ed367a46dfddbafaee82b3eb79722ae49f45320%22]\" */ @@ -696,6 +696,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) prevhash = juint256(jitem(params,0)); scriptstr = jstr(jitem(params,1),0); musigstr = jstr(jitem(params,2),0); + printf("script.(%s) musig.(%s) %d\n",scriptstr,musigstr,(int32_t)strlen(musigstr)); if ( is_hexstr(scriptstr,0) != 0 && is_hexstr(musigstr,0) != 128 ) { if ( txfee == 0 ) @@ -723,7 +724,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) } else return(cclib_error(result,"couldnt decode send opret")); } else return(cclib_error(result,"couldnt find vin0")); } else return(cclib_error(result,"script or musig is not hex")); - } else return(cclib_error(result,"need to have exactly 3 params prevhash, scriptPubKey, musig")); + } else return(cclib_error(result,"need to have exactly 3 params sendtxid, scriptPubKey, musig")); } else return(cclib_error(result,"params parse error")); } From 748ab667e2d36b71c29d943b855d7dbbc07abd86 Mon Sep 17 00:00:00 2001 From: jl777 Date: Thu, 21 Feb 2019 23:59:42 -1100 Subject: [PATCH 039/132] Test --- src/cc/musig.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 6b2e7abca..172958fba 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -696,7 +696,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) prevhash = juint256(jitem(params,0)); scriptstr = jstr(jitem(params,1),0); musigstr = jstr(jitem(params,2),0); - printf("script.(%s) musig.(%s) %d\n",scriptstr,musigstr,(int32_t)strlen(musigstr)); + printf("script.(%s) %d musig.(%s) %d\n",scriptstr,is_hexstr(scriptstr,0),musigstr,is_hexstr(musigstr,0)); if ( is_hexstr(scriptstr,0) != 0 && is_hexstr(musigstr,0) != 128 ) { if ( txfee == 0 ) From 3bea6f84e4c353df73316e8079e516a903461516 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:00:55 -1100 Subject: [PATCH 040/132] Fix --- src/cc/musig.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 172958fba..a690e4d01 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -696,8 +696,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) prevhash = juint256(jitem(params,0)); scriptstr = jstr(jitem(params,1),0); musigstr = jstr(jitem(params,2),0); - printf("script.(%s) %d musig.(%s) %d\n",scriptstr,is_hexstr(scriptstr,0),musigstr,is_hexstr(musigstr,0)); - if ( is_hexstr(scriptstr,0) != 0 && is_hexstr(musigstr,0) != 128 ) + if ( is_hexstr(scriptstr,0) != 0 && is_hexstr(musigstr,0) == 128 ) { if ( txfee == 0 ) txfee = MUSIG_TXFEE; From 33811cce5f78616998d2b7fe1a75714d028fae23 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:16:26 -1100 Subject: [PATCH 041/132] +print --- src/cc/musig.cpp | 64 ++++++++++++++++++++++++++++++------------------ 1 file changed, 40 insertions(+), 24 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index a690e4d01..be4ff278e 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -26,8 +26,8 @@ /* second, send 0.777 coins to the combined_pk ./c cclib send 18 \"[%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,0.777]\" { - "hex": "0400008085202f8901bf7afcbbab7a5e1ba20c8010325e199305afa7d15b4bc86a589a512201d39924000000004847304402203e0cff8aaa831dd990afd979bbc0a648316f77407cb5e02780d18e0670f5172a0220283d5c52d0406b10c508cc2b19dd6dbe2420e7c5cf431a1d41072d0eec28edb901ffffffff03b0c2a10400000000302ea22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401cca91e223700000000232102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac0000000000000000266a24127821032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b00000000900000000000000000000000000000", - "txid": "cb5309ed249da95e2b5696eb763a8736e2fff1d14922ada737b931494ca3d2be", + "hex": "0400008085202f8908018bbc4a0acf0f896680b84cc1000ec5530042fa3cf7471ab5c11cde56f6d0e60000000048473044022041a900fa57e54f939b797d09f0cee81ab9a79d978cd473ef3fc9f09c7678ad6b02206386bd15ee7ee8224a984fdd1d2a094738d082aec06028a5846d7bc61ddf16ca01ffffffff0b969f0e1ea787f0cc4e81d128353bd1cb670ab89bd1db4b47fbb7e872cd39fb00000000494830450221008c5de4b196e57b0dd94aa415950adf274e3e6859b82cf218729af84c1f15e76c022024aeab7eda63e6a652ef488bf26a8dc4ef8d2d4aa5746726085bfe5f169a5db701ffffffff0b36b70b43457fab377f28fb22da5a3e9d8186a37daae18cf0f710a221ab26250000000048473044022004ec20ae7490e7adabf9a3f78e4a58df84a3245485bfdd40f421cafe61d19c340220456d2b6f3c6e88632027c02606a0af1c21208d05f2de0826fbf4dfe7391ec83901ffffffff0aaff3cfe4ca22b97b6179a6f7cfac91945e5440e9438b89d1ec09500167176a0000000048473044022074dcad30c8ab9ed79a3ac69169611fc9e5f4b76a561b183461d968249316997f022063b25decaa285f494d277b9c8c2bcf6445b7929a304542e89c0645828d30a1a901ffffffff090e1bb92e9bf404a0d6455701b21af3dbf6765e61a1dc28b7c0f608ec4f12da000000004847304402202f9182c532c66138a6bdfcbb85a06cf1bf1532f2bf8f63170ef20843e4a81d0202207612a4353eb9606e84621c444ec7db1b683ff29c56127bda2d5e9c0eb13dbbc001ffffffff08a57005c7a40a923b1a510820b07f7318d760fe2a233b077d918cce357ad3af00000000484730440220643d60c68634fb2e0f6656389fc70c9f84c7086fc6e35b0fa26297e844f6c5fc02201d79669e073efe738d47de0130fdcba875e284e18fd478c0e6834d46632d8b8101ffffffff068cfd0ea6c0f5d401c67ec38f92425a9e59b0d5ade55bb2971ea955675a17bd00000000484730440220747139724248da4bcc1e5e3828e0ea811756e1fad0ebc40aeb006fd8079d46e402200d8f1c229c79494b5617e4373a3e083966dcd74571323f9d334be901d53871fa01ffffffff0200382fb6984b6128bb75115346242809c6555274e0cacef822825a2b4d231700000000484730440220454fcac398f6913fb4d8ed330f110f9cf62eec6c8cdb67d5df1effd2cf8222d5022017f6323630669777573e342e870c88727a917cc06c33611ebbd9d1fccc1dcd3701ffffffff03b0c2a10400000000302ea22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401cc40ca220000000000232102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac0000000000000000266a24127821032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b00000000460100000000000000000000000000", + "txid": "2c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68", "result": "success" } @@ -46,92 +46,94 @@ } change script: 2102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac - sendtxid: cb5309ed249da95e2b5696eb763a8736e2fff1d14922ada737b931494ca3d2be + sendtxid: 2c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68 broadcast sendtxid and wait for it to be confirmed. then get the msg we need to sign: - ./c cclib calcmsg 18 \"[%22cb5309ed249da95e2b5696eb763a8736e2fff1d14922ada737b931494ca3d2be%22,%222102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac%22]\" + ./c cclib calcmsg 18 \"[%222c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68%22,%222102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac%22]\" { "result": "success", - "msg": "63b799913d4c9487f321b32d6ae8614f653f38e0b50d4df4bc1d36339ea18485" + "msg": "caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0" } + the "msg" is what needs to be signed to create a valid spend now on each signing node, a session needs to be created: 5 args: ind, numsigners, combined_pk, pkhash, message to be signed on node with pubkey: 02aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848 - ./c cclib session 18 \"[0,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%2263b799913d4c9487f321b32d6ae8614f653f38e0b50d4df4bc1d36339ea18485%22]\" + ./c cclib session 18 \"[0,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%22caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0%22]\" { "myind": 0, "numsigners": 2, - "commitment": "89af8f6db69fc3d4b95480a914dceba9933039e9823151a82677c3ca4e961fcc", + "commitment": "e82228c10d0e100477630349150dea744d3b2790dcd347511a1a98199840cda4", "result": "success" } on node with pubkey: 039433dc3749aece1bd568f374a45da3b0bc6856990d7da3cd175399577940a775 - ./c cclib session 18 \"[1,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%2263b799913d4c9487f321b32d6ae8614f653f38e0b50d4df4bc1d36339ea18485%22]\" + ./c cclib session 18 \"[1,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%22caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0%22]\" { "myind": 1, "numsigners": 2, - "commitment": "a43da5ef8322abb43b9fddadef7b6479baf7853e860f915e01521e3060e5342b", + "commitment": "6e426e850ddc45e7742cfb6321781c00ee69a995ab12fa1f9ded7fe43658babf", "result": "success" } now we need to get the commitment from each node to the other one. the session already put the commitment for each node into the global struct. Keep in mind there is a single global struct with session unique to each cclib session call. that means no restarting any deamon in the middle of the process on any of the nodes and only call cclib session a single time. this is an artificial restriction just to simplify the initial implementation of musig - ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%22a43da5ef8322abb43b9fddadef7b6479baf7853e860f915e01521e3060e5342b%22]\" + ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%226e426e850ddc45e7742cfb6321781c00ee69a995ab12fa1f9ded7fe43658babf%22]\" { "added_index": 1, "myind": 0, - "nonce": "03bf28874f5e5dccf55170406d58ded84ac6ca713011d718c6048400d700cb879a", + "nonce": "0261671b0a6de416938cf035c98f8af37c6ca88bbbd1bcce693d709d4919b010e1", "result": "success" } - ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%2289af8f6db69fc3d4b95480a914dceba9933039e9823151a82677c3ca4e961fcc%22]\" + ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%22e82228c10d0e100477630349150dea744d3b2790dcd347511a1a98199840cda4%22]\" { "added_index": 0, "myind": 1, - "nonce": "039ae1f542e8f0f6d03d734dc2295651973e1b7fa99508e2f36dad5d21f09889f6", + "nonce": "02570f62a625ceb19a754a053152b162810c3e403df63f3d443e85bdacc74bfdfe", "result": "success" } Now exchange the revealed nonces to each node: - ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%22039ae1f542e8f0f6d03d734dc2295651973e1b7fa99508e2f36dad5d21f09889f6%22]\" + ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%2202570f62a625ceb19a754a053152b162810c3e403df63f3d443e85bdacc74bfdfe%22]\" { "added_index": 1, "myind": 0, - "partialsig": "5da4c1ec828cd1563bc6554aa74c90c29fcd38b2aea26f7fa92e0d007aa9463f", + "partialsig": "3f21885e6d2d020e1473435ccd148a61cdcb1d1105867fed45913185dc0acf59", "result": "success" } - ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%2203bf28874f5e5dccf55170406d58ded84ac6ca713011d718c6048400d700cb879a%22]\" + ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%220261671b0a6de416938cf035c98f8af37c6ca88bbbd1bcce693d709d4919b010e1%22]\" { "added_index": 0, + "myind": 0, "myind": 1, - "partialsig": "7e55fd564fe26b1054208bc47786d6e1ce30a2fd0045bbbf0e6915adcf4b0ce1", + "partialsig": "af7f28455fb2e988d81068cd9d800879cd334036a8300118dc307b777a38c1ed", "result": "success" } Almost there! final step is to exchange the partial sigs between signers - ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%227e55fd564fe26b1054208bc47786d6e1ce30a2fd0045bbbf0e6915adcf4b0ce1%22]\" + ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%22af7f28455fb2e988d81068cd9d800879cd334036a8300118dc307b777a38c1ed%22]\" { "added_index": 1, "result": "success", - "combinedsig": "bc0062cd3233433e098fbf4f3c333946779c3dccfaefc423243e3f90edfdf9a6dbfabf42d26f3c668fe6e10f1ed367a46dfddbafaee82b3eb79722ae49f45320" + "combinedsig": "5e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146" } + - ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%225da4c1ec828cd1563bc6554aa74c90c29fcd38b2aea26f7fa92e0d007aa9463f%22]\" + ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%223f21885e6d2d020e1473435ccd148a61cdcb1d1105867fed45913185dc0acf59%22]\" { "added_index": 0, "result": "success", - "combinedsig": "bc0062cd3233433e098fbf4f3c333946779c3dccfaefc423243e3f90edfdf9a6dbfabf42d26f3c668fe6e10f1ed367a46dfddbafaee82b3eb79722ae49f45320" + "combinedsig": "5e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146" } - Notice both nodes generated the same combined signature! Now for a sanity test, we can use the verify call to make sure this sig will work with the msg needed for the spend: @@ -141,7 +143,7 @@ the "msg" is what needs to be signed to create a valid spend and finally the spend: sendtxid, scriptPubKey, musig -./c cclib spend 18 \"[%22cb5309ed249da95e2b5696eb763a8736e2fff1d14922ada737b931494ca3d2be%22,%222102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac%22,%22bc0062cd3233433e098fbf4f3c333946779c3dccfaefc423243e3f90edfdf9a6dbfabf42d26f3c668fe6e10f1ed367a46dfddbafaee82b3eb79722ae49f45320%22]\" +./c cclib spend 18 \"[%222c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68%22,%222102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac%22,%225e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146%22]\" */ @@ -686,7 +688,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; CMutableTransaction mtx = CreateNewContextualCMutableTransaction(Params().GetConsensus(), komodo_nextheight()); - UniValue result(UniValue::VOBJ); std::string rawtx; CPubKey mypk,pk; secp256k1_pubkey combined_pk; char *scriptstr,*musigstr; uint8_t msg[32]; CTransaction vintx; uint256 prevhash,hashBlock; int32_t n,numvouts; CTxOut vout; secp256k1_schnorrsig musig; + UniValue result(UniValue::VOBJ); std::string rawtx; CPubKey mypk,pk; secp256k1_pubkey combined_pk; char *scriptstr,*musigstr; uint8_t msg[32]; CTransaction vintx; uint256 prevhash,hashBlock; int32_t i,n,numvouts; char str[129]; CTxOut vout; secp256k1_schnorrsig musig; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) @@ -713,6 +715,20 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) secp256k1_ec_pubkey_parse(ctx,&combined_pk,pk.begin(),33) > 0 ) { musig_prevoutmsg(msg,prevhash,vout.scriptPubKey); + { + for (i=0; i<32; i++) + sprintf(&str[i*2],"%02x",msg[i]); + str[64] = 0; + result.push_back(Pair("msg",str)); + for (i=0; i<33; i++) + sprintf(&str[i*2],"%02x",((uint8_t *)pk.begin)[i]); + str[66] = 0; + result.push_back(Pair("combined_pk",str)); + for (i=0; i<64; i++) + sprintf(&str[i*2],"%02x",musig64[i]); + str[128] = 0; + result.push_back(Pair("combinedsig",str)); + } if ( !secp256k1_schnorrsig_verify((const secp256k1_context *)ctx,&musig,(const uint8_t *)msg,(const secp256k1_pubkey *)&combined_pk) ) return(cclib_error(result,"musig didnt validate")); mtx.vin.push_back(CTxIn(prevhash,MUSIG_PREVN)); From 8b8339b5b941963c6ea6331cf57af5c5edc2facc Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:17:05 -1100 Subject: [PATCH 042/132] () --- src/cc/musig.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index be4ff278e..88bf62449 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -721,7 +721,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) str[64] = 0; result.push_back(Pair("msg",str)); for (i=0; i<33; i++) - sprintf(&str[i*2],"%02x",((uint8_t *)pk.begin)[i]); + sprintf(&str[i*2],"%02x",((uint8_t *)pk.begin())[i]); str[66] = 0; result.push_back(Pair("combined_pk",str)); for (i=0; i<64; i++) From 6eaac8547a3ddb506e70896e3251daf07524395c Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:23:02 -1100 Subject: [PATCH 043/132] Skip test --- src/cc/musig.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 88bf62449..63d7e5291 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -730,7 +730,9 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) result.push_back(Pair("combinedsig",str)); } if ( !secp256k1_schnorrsig_verify((const secp256k1_context *)ctx,&musig,(const uint8_t *)msg,(const secp256k1_pubkey *)&combined_pk) ) - return(cclib_error(result,"musig didnt validate")); + { + //return(cclib_error(result,"musig didnt validate")); + } mtx.vin.push_back(CTxIn(prevhash,MUSIG_PREVN)); mtx.vout.push_back(vout); rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,musig_spendopret('y',pk,musig64)); From baef592f94e608d939f4bf627d1ae34e785f1187 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:26:39 -1100 Subject: [PATCH 044/132] Fix script parsing --- src/cc/musig.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 63d7e5291..28795d95c 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -704,7 +704,9 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) txfee = MUSIG_TXFEE; mypk = pubkey2pk(Mypubkey()); std::vector musig64(ParseHex(musigstr)); - CScript scriptPubKey(ParseHex(scriptstr)); + CScript scriptPubKey; + scriptPubKey.resize(strlen(scriptstr)/2); + decode_hex((uint8_t *)scriptPubKey.data(),strlen(scriptstr)/2,scriptstr); if ( myGetTransaction(prevhash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) { vout.nValue = vintx.vout[0].nValue - txfee; From 3de50a250b2d1ad2321d67c2336dfe061fb6d2da Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:29:48 -1100 Subject: [PATCH 045/132] Test --- src/cc/musig.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 28795d95c..fdb24f7a0 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -706,7 +706,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) std::vector musig64(ParseHex(musigstr)); CScript scriptPubKey; scriptPubKey.resize(strlen(scriptstr)/2); - decode_hex((uint8_t *)scriptPubKey.data(),strlen(scriptstr)/2,scriptstr); + decode_hex(&scriptPubKey[0],strlen(scriptstr)/2,scriptstr); if ( myGetTransaction(prevhash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) { vout.nValue = vintx.vout[0].nValue - txfee; From a687d695af02abc60505583027971cfc2373c446 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:41:51 -1100 Subject: [PATCH 046/132] Verify roc --- src/cc/musig.cpp | 44 +++++++++++++++++++++++++++----------------- 1 file changed, 27 insertions(+), 17 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index fdb24f7a0..9eaec4404 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -620,25 +620,35 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t n; + UniValue result(UniValue::VOBJ); int32_t i,n; uint8_t msg[32],musig64[64]; secp256k1_pubkey combined_pk; secp256k1_schnorrsig musig; char str[129]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) != 3 ) { - // can code this out of order - } - result.push_back(Pair("result","success")); - /** Verify a Schnorr signature. - * - * Returns: 1: correct signature - * 0: incorrect or unparseable signature - * Args: ctx: a secp256k1 context object, initialized for verification. - * In: sig: the signature being verified (cannot be NULL) - * msg32: the 32-byte message hash being verified (cannot be NULL) - * pubkey: pointer to a public key to verify with (cannot be NULL) - */ - // if (!secp256k1_schnorrsig_verify(ctx, &sig, msg, &combined_pk)) { - return(result); + if ( musig_parsehash32(msg,jitem(params,0)) < 0 ) + return(cclib_error(result,"error parsing pkhash")); + else if ( musig_parsepubkey(ctx,combined_pk,jitem(params,1)) < 0 ) + return(cclib_error(result,"error parsing combined_pk")); + else if ( musig_parsehash64(musig64,jitem(params,2)) < 0 ) + return(cclib_error(result,"error parsing musig64")); + for (i=0; i<32; i++) + sprintf(&str[i*2],"%02x",msg[i]); + str[64] = 0; + result.push_back(Pair("msg",str)); + result.push_back(Pair("combined_pk",jstr(jitem(params,1),0))); + for (i=0; i<64; i++) + sprintf(&str[i*2],"%02x",musig64[i]); + str[128] = 0; + result.push_back(Pair("combinedsig",str)); + if ( secp256k1_schnorrsig_parse(ctx,&musig,&musig64[0]) > 0 ) + { + if ( secp256k1_schnorrsig_verify(ctx,&musig,msg,&combined_pk) > 0 ) + { + result.push_back(Pair("result","success")); + return(result); + } else return(cclib_error(result,"musig didnt verify")); + } else return(cclib_error(result,"couldnt parse musig64")); + } else return(cclib_error(result,"wrong number of params, need 3: msg, combined_pk, combinedsig")); } // helpers for rpc calls that generate/validate onchain tx @@ -733,7 +743,7 @@ UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) } if ( !secp256k1_schnorrsig_verify((const secp256k1_context *)ctx,&musig,(const uint8_t *)msg,(const secp256k1_pubkey *)&combined_pk) ) { - //return(cclib_error(result,"musig didnt validate")); + return(cclib_error(result,"musig didnt validate")); } mtx.vin.push_back(CTxIn(prevhash,MUSIG_PREVN)); mtx.vout.push_back(vout); From 317fa937b3ca5010daa59cfdb58725c7bc2b7d45 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:43:44 -1100 Subject: [PATCH 047/132] parsehash --- src/cc/musig.cpp | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 9eaec4404..c5cf5fc4e 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -331,12 +331,12 @@ int32_t musig_parsepubkey(secp256k1_context *ctx,secp256k1_pubkey &spk,cJSON *it } else return(-1); } -int32_t musig_parsehash32(uint8_t *hash32,cJSON *item) +int32_t musig_parsehash(uint8_t *hash32,cJSON *item,int32_t len) { char *hexstr; - if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == 64 ) + if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == len*2 ) { - decode_hex(hash32,32,hexstr); + decode_hex(hash32,len,hexstr); return(0); } else return(-1); } @@ -394,9 +394,9 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) MUSIG = musig_infocreate(myind,num); if ( musig_parsepubkey(ctx,MUSIG->combined_pk,jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing combined_pubkey")); - else if ( musig_parsehash32(MUSIG->pkhash,jitem(params,3)) < 0 ) + else if ( musig_parsehash(MUSIG->pkhash,jitem(params,3),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( musig_parsehash32(MUSIG->msg,jitem(params,4)) < 0 ) + else if ( musig_parsehash(MUSIG->msg,jitem(params,4),32) < 0 ) return(cclib_error(result,"error parsing msg")); Myprivkey(privkey); GetRandBytes(session,32); @@ -455,13 +455,13 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) + if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash32(&MUSIG->nonce_commitments[ind*32],jitem(params,2)) < 0 ) + else if ( musig_parsehash(&MUSIG->nonce_commitments[ind*32],jitem(params,2),32) < 0 ) return(cclib_error(result,"error parsing commitment")); /** Gets the signer's public nonce given a list of all signers' data with commitments * @@ -508,7 +508,7 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) + if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); @@ -578,13 +578,13 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - if ( musig_parsehash32(pkhash,jitem(params,0)) < 0 ) + if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash32(psig,jitem(params,2)) < 0 ) + else if ( musig_parsehash(psig,jitem(params,2),32) < 0 ) return(cclib_error(result,"error parsing psig")); else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); @@ -625,11 +625,11 @@ UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) != 3 ) { - if ( musig_parsehash32(msg,jitem(params,0)) < 0 ) + if ( musig_parsehash(msg,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); else if ( musig_parsepubkey(ctx,combined_pk,jitem(params,1)) < 0 ) return(cclib_error(result,"error parsing combined_pk")); - else if ( musig_parsehash64(musig64,jitem(params,2)) < 0 ) + else if ( musig_parsehash(musig64,jitem(params,2),64) < 0 ) return(cclib_error(result,"error parsing musig64")); for (i=0; i<32; i++) sprintf(&str[i*2],"%02x",msg[i]); From 6704dd969965d0b938ad2dceab6714a90daca687 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:52:37 -1100 Subject: [PATCH 048/132] Fix --- src/cc/musig.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index c5cf5fc4e..8e37a2add 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -138,7 +138,7 @@ the "msg" is what needs to be signed to create a valid spend Now for a sanity test, we can use the verify call to make sure this sig will work with the msg needed for the spend: - xxxx + ./c cclib verify 18 \"[%22caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0%22,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146%22]\" and finally the spend: sendtxid, scriptPubKey, musig @@ -623,7 +623,7 @@ UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue result(UniValue::VOBJ); int32_t i,n; uint8_t msg[32],musig64[64]; secp256k1_pubkey combined_pk; secp256k1_schnorrsig musig; char str[129]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) != 3 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { if ( musig_parsehash(msg,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); From 3caa4fb350c74d5af61b02770a523272ddc8324d Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:59:15 -1100 Subject: [PATCH 049/132] Test check.c --- src/cc/cclib.cpp | 32 +---------------------- src/secp256k1/src/modules/musig/example.c | 6 ++--- 2 files changed, 4 insertions(+), 34 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index ec74877b6..b070ded78 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -580,37 +580,7 @@ uint256 juint256(cJSON *obj) #else #include "sudoku.cpp" - -/* -#include "../secp256k1/src/util.h" -#include "../secp256k1/src/num_impl.h" -#include "../secp256k1/src/field_impl.h" -#include "../secp256k1/src/scalar_impl.h" -#include "../secp256k1/src/group_impl.h" -#include "../secp256k1/src/scratch_impl.h" -#include "../secp256k1/src/ecmult_impl.h" -#include "../secp256k1/src/ecmult_const_impl.h" -#include "../secp256k1/src/ecmult_gen_impl.h" -#include "../secp256k1/src/ecdsa_impl.h" -#include "../secp256k1/src/eckey_impl.h" -#include "../secp256k1/src/hash_impl.h" - - - -typedef int (secp256k1_ecmult_multi_callback)(secp256k1_scalar *sc, secp256k1_ge *pt, size_t idx, void *data); -extern "C" void secp256k1_pubkey_save(secp256k1_pubkey* pubkey, secp256k1_ge* ge); -extern "C" int secp256k1_nonce_function_bipschnorr(unsigned char *nonce32, const unsigned char *msg32, const unsigned char *key32, const unsigned char *algo16, void *data, unsigned int counter); -extern "C" int secp256k1_pubkey_load(const secp256k1_context* ctx, secp256k1_ge* ge, const secp256k1_pubkey* pubkey); -extern "C" void secp256k1_scalar_chacha20(secp256k1_scalar *r1, secp256k1_scalar *r2, const unsigned char *seed, uint64_t idx); - -#define ARG_CHECK(cond) do { \ -if (EXPECT(!(cond), 0)) { \ -secp256k1_callback_call(&ctx->illegal_callback, #cond); \ -return 0; \ -} \ -} while(0)*/ - -//#include "../secp256k1/src/secp256k1.c" #include "musig.cpp" +#include "../secp256k1/modules/musig/check.c" #endif diff --git a/src/secp256k1/src/modules/musig/example.c b/src/secp256k1/src/modules/musig/example.c index ceae18686..94c9fdef2 100644 --- a/src/secp256k1/src/modules/musig/example.c +++ b/src/secp256k1/src/modules/musig/example.c @@ -9,11 +9,11 @@ * Additionally, see the documentation in include/secp256k1_musig.h. */ -#include +/*#include #include #include #include -#include +#include */ /* Number of public keys involved in creating the aggregate signature */ #define N_SIGNERS 3 @@ -122,7 +122,7 @@ int sign(const secp256k1_context* ctx, unsigned char seckeys[][32], const secp25 return secp256k1_musig_partial_sig_combine(ctx, &musig_session[0], sig, partial_sig, N_SIGNERS); } - int main(void) { + int testmain(void) { secp256k1_context* ctx; int i; unsigned char seckeys[N_SIGNERS][32]; From fe60cfbf6eb486ac08a5b3906854ab1c82d1d1c3 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 00:59:44 -1100 Subject: [PATCH 050/132] Src --- src/cc/cclib.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index b070ded78..9cd947efc 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -581,6 +581,6 @@ uint256 juint256(cJSON *obj) #else #include "sudoku.cpp" #include "musig.cpp" -#include "../secp256k1/modules/musig/check.c" +#include "../secp256k1/src/modules/musig/check.c" #endif From 1a34721c44c35815f90b739c30eb4d28ef3e6783 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 01:01:00 -1100 Subject: [PATCH 051/132] example.c --- src/cc/cclib.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index 9cd947efc..c770917ea 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -581,6 +581,6 @@ uint256 juint256(cJSON *obj) #else #include "sudoku.cpp" #include "musig.cpp" -#include "../secp256k1/src/modules/musig/check.c" +#include "../secp256k1/src/modules/musig/example.c" #endif From 93acda143f271f0e08b07393f958dc194bb352ba Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 01:03:17 -1100 Subject: [PATCH 052/132] fprintf(stderr, --- src/cc/musig.cpp | 2 ++ src/secp256k1/src/modules/musig/example.c | 26 +++++++++++------------ 2 files changed, 15 insertions(+), 13 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 8e37a2add..446f9333d 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -617,10 +617,12 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, partialsig")); } +int testmain(void); UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; UniValue result(UniValue::VOBJ); int32_t i,n; uint8_t msg[32],musig64[64]; secp256k1_pubkey combined_pk; secp256k1_schnorrsig musig; char str[129]; + testmain(); if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) diff --git a/src/secp256k1/src/modules/musig/example.c b/src/secp256k1/src/modules/musig/example.c index 94c9fdef2..70d183e7d 100644 --- a/src/secp256k1/src/modules/musig/example.c +++ b/src/secp256k1/src/modules/musig/example.c @@ -128,37 +128,37 @@ int sign(const secp256k1_context* ctx, unsigned char seckeys[][32], const secp25 unsigned char seckeys[N_SIGNERS][32]; secp256k1_pubkey pubkeys[N_SIGNERS]; secp256k1_pubkey combined_pk; - unsigned char msg[32] = "this_could_be_the_hash_of_a_msg!"; + unsigned char msg[32] = "this_could_be_the_hash_of_a_msg"; secp256k1_schnorrsig sig; /* Create a context for signing and verification */ ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - printf("Creating key pairs......"); + fprintf(stderr,"Creating key pairs......"); for (i = 0; i < N_SIGNERS; i++) { if (!create_key(ctx, seckeys[i], &pubkeys[i])) { - printf("FAILED\n"); + fprintf(stderr,"FAILED\n"); return 1; } } - printf("ok\n"); - printf("Combining public keys..."); + fprintf(stderr,"ok\n"); + fprintf(stderr,"Combining public keys..."); if (!secp256k1_musig_pubkey_combine(ctx, NULL, &combined_pk, NULL, pubkeys, N_SIGNERS)) { - printf("FAILED\n"); + fprintf(stderr,"FAILED\n"); return 1; } - printf("ok\n"); - printf("Signing message........."); + fprintf(stderr,"ok\n"); + fprintf(stderr,"Signing message........."); if (!sign(ctx, seckeys, pubkeys, msg, &sig)) { - printf("FAILED\n"); + fprintf(stderr,"FAILED\n"); return 1; } - printf("ok\n"); - printf("Verifying signature....."); + fprintf(stderr,"ok\n"); + fprintf(stderr,"Verifying signature....."); if (!secp256k1_schnorrsig_verify(ctx, &sig, msg, &combined_pk)) { - printf("FAILED\n"); + fprintf(stderr,"FAILED\n"); return 1; } - printf("ok\n"); + fprintf(stderr,"ok\n"); secp256k1_context_destroy(ctx); return 0; } From a0b7227e007bcfa96ad6e99c54a85875652eed63 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 09:29:09 -1100 Subject: [PATCH 053/132] Dont create rogue files on validation --- src/cc/rogue_rpc.cpp | 33 ++++++++++++++++++--------------- 1 file changed, 18 insertions(+), 15 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 57ce1e14b..213e382a1 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -833,7 +833,7 @@ UniValue rogue_keystrokes(uint64_t txfee,struct CCcontract_info *cp,cJSON *param } else return(cclib_error(result,"couldnt reparse params")); } -char *rogue_extractgame(char *str,int32_t *numkeysp,std::vector &newdata,uint64_t &seed,uint256 &playertxid,struct CCcontract_info *cp,uint256 gametxid,char *rogueaddr) +char *rogue_extractgame(int32_t makefiles,char *str,int32_t *numkeysp,std::vector &newdata,uint64_t &seed,uint256 &playertxid,struct CCcontract_info *cp,uint256 gametxid,char *rogueaddr) { CPubKey roguepk; int32_t i,num,maxplayers,gameheight,batonht,batonvout,numplayers,regslot,numkeys,err; std::string symbol,pname; CTransaction gametx; int64_t buyin,batonvalue; char fname[64],*keystrokes = 0; std::vector playerdata; uint256 batontxid; FILE *fp; uint8_t newplayer[10000]; struct rogue_player P,endP; roguepk = GetUnspendable(cp,0); @@ -854,19 +854,22 @@ char *rogue_extractgame(char *str,int32_t *numkeysp,std::vector &newdat } if ( keystrokes != 0 ) { - sprintf(fname,"rogue.%llu.0",(long long)seed); - if ( (fp= fopen(fname,"wb")) != 0 ) + if ( makefiles != 0 ) { - if ( fwrite(keystrokes,1,numkeys,fp) != numkeys ) - fprintf(stderr,"error writing %s\n",fname); - fclose(fp); - } - sprintf(fname,"rogue.%llu.player",(long long)seed); - if ( (fp= fopen(fname,"wb")) != 0 ) - { - if ( fwrite(&playerdata[0],1,(int32_t)playerdata.size(),fp) != playerdata.size() ) - fprintf(stderr,"error writing %s\n",fname); - fclose(fp); + sprintf(fname,"rogue.%llu.0",(long long)seed); + if ( (fp= fopen(fname,"wb")) != 0 ) + { + if ( fwrite(keystrokes,1,numkeys,fp) != numkeys ) + fprintf(stderr,"error writing %s\n",fname); + fclose(fp); + } + sprintf(fname,"rogue.%llu.player",(long long)seed); + if ( (fp= fopen(fname,"wb")) != 0 ) + { + if ( fwrite(&playerdata[0],1,(int32_t)playerdata.size(),fp) != playerdata.size() ) + fprintf(stderr,"error writing %s\n",fname); + fclose(fp); + } } num = rogue_replay2(newplayer,seed,keystrokes,numkeys,playerdata.size()==0?0:&P,0); newdata.resize(num); @@ -914,7 +917,7 @@ UniValue rogue_extract(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) GetCCaddress1of2(cp,rogueaddr,roguepk,pk); result.push_back(Pair("rogueaddr",rogueaddr)); str[0] = 0; - if ( (keystrokes= rogue_extractgame(str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) + if ( (keystrokes= rogue_extractgame(1,str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) { result.push_back(Pair("status","success")); flag = 1; @@ -1240,7 +1243,7 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp roguepk = GetUnspendable(cp,0); GetCCaddress1of2(cp,rogueaddr,roguepk,pk); //fprintf(stderr,"call extractgame\n"); - if ( (keystrokes= rogue_extractgame(str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) + if ( (keystrokes= rogue_extractgame(0,str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) { free(keystrokes); //fprintf(stderr,"extracted.(%s)\n",str); From fa3b624d512d7476ea3a3927a810c1f426b98b14 Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sat, 23 Feb 2019 15:12:00 +0800 Subject: [PATCH 054/132] fix musig and working example added --- src/cc/musig.cpp | 236 ++++++++++++++++++++++++++++------------------- 1 file changed, 139 insertions(+), 97 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 446f9333d..bd3d74a95 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -14,47 +14,67 @@ ******************************************************************************/ /* first make a combined pk: -./c cclib combine 18 \"[%2202aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848%22,%22039433dc3749aece1bd568f374a45da3b0bc6856990d7da3cd175399577940a775%22]\" -{ - "pkhash": "5be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba", - "combined_pk": "032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b", - "result": "success" -} - the combined_pk and pkhash will be needed for various other rpc calls -*/ -/* second, send 0.777 coins to the combined_pk - ./c cclib send 18 \"[%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,0.777]\" +./komodo-cli -ac_name=MUSIG cclib combine 18 '["02fb6aa0b96cad24d46b5da93eba3864c45ce07a73bba12da530ae841e140fcf28","0255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4"]' +{ + "pkhash": "5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b", + "combined_pk": "03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b", + "result": "success" +} + + the combined_pk and pkhash will be needed for various other rpc calls + + second, send 1 coin to the combined_pk + ./komodo-cli -ac_name=MUSIG cclib send 18 '["03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b",1]' { - "hex": "0400008085202f8908018bbc4a0acf0f896680b84cc1000ec5530042fa3cf7471ab5c11cde56f6d0e60000000048473044022041a900fa57e54f939b797d09f0cee81ab9a79d978cd473ef3fc9f09c7678ad6b02206386bd15ee7ee8224a984fdd1d2a094738d082aec06028a5846d7bc61ddf16ca01ffffffff0b969f0e1ea787f0cc4e81d128353bd1cb670ab89bd1db4b47fbb7e872cd39fb00000000494830450221008c5de4b196e57b0dd94aa415950adf274e3e6859b82cf218729af84c1f15e76c022024aeab7eda63e6a652ef488bf26a8dc4ef8d2d4aa5746726085bfe5f169a5db701ffffffff0b36b70b43457fab377f28fb22da5a3e9d8186a37daae18cf0f710a221ab26250000000048473044022004ec20ae7490e7adabf9a3f78e4a58df84a3245485bfdd40f421cafe61d19c340220456d2b6f3c6e88632027c02606a0af1c21208d05f2de0826fbf4dfe7391ec83901ffffffff0aaff3cfe4ca22b97b6179a6f7cfac91945e5440e9438b89d1ec09500167176a0000000048473044022074dcad30c8ab9ed79a3ac69169611fc9e5f4b76a561b183461d968249316997f022063b25decaa285f494d277b9c8c2bcf6445b7929a304542e89c0645828d30a1a901ffffffff090e1bb92e9bf404a0d6455701b21af3dbf6765e61a1dc28b7c0f608ec4f12da000000004847304402202f9182c532c66138a6bdfcbb85a06cf1bf1532f2bf8f63170ef20843e4a81d0202207612a4353eb9606e84621c444ec7db1b683ff29c56127bda2d5e9c0eb13dbbc001ffffffff08a57005c7a40a923b1a510820b07f7318d760fe2a233b077d918cce357ad3af00000000484730440220643d60c68634fb2e0f6656389fc70c9f84c7086fc6e35b0fa26297e844f6c5fc02201d79669e073efe738d47de0130fdcba875e284e18fd478c0e6834d46632d8b8101ffffffff068cfd0ea6c0f5d401c67ec38f92425a9e59b0d5ade55bb2971ea955675a17bd00000000484730440220747139724248da4bcc1e5e3828e0ea811756e1fad0ebc40aeb006fd8079d46e402200d8f1c229c79494b5617e4373a3e083966dcd74571323f9d334be901d53871fa01ffffffff0200382fb6984b6128bb75115346242809c6555274e0cacef822825a2b4d231700000000484730440220454fcac398f6913fb4d8ed330f110f9cf62eec6c8cdb67d5df1effd2cf8222d5022017f6323630669777573e342e870c88727a917cc06c33611ebbd9d1fccc1dcd3701ffffffff03b0c2a10400000000302ea22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401cc40ca220000000000232102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac0000000000000000266a24127821032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b00000000460100000000000000000000000000", - "txid": "2c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68", - "result": "success" + "hex": "0400008085202f8901a980664dffc810725a79ffb89ac48be4c7b6bade9b789732fcf871acf8e81a2e010000006a47304402207e52763661ecd2c34a65d6623950be11794825db71576dc11894c606ddc317800220028fef46dc20630d0fdf22647b5d4ff0f1c47cf75f48702d0a91d5589eff99d001210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ffffffff031008f60500000000302ea22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401cce09aa4350000000023210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac0000000000000000266a2412782103f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b00000000920500000000000000000000000000", + "txid": "5ce74037a153ee210413b48d4e88638b99825a2de1a1f1aa0d36ebf93019824c", + "result": "success" } - { - "value": 0.77710000, - "valueZat": 77710000, - "n": 0, - "scriptPubKey": { - "asm": "a22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401 OP_CHECKCRYPTOCONDITION", - "hex": "2ea22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401cc", - "reqSigs": 1, - "type": "cryptocondition", - "addresses": [ - "RKWS7jxyjPX9iaJttk8iMKf1AumanKypez" - ] - } - change script: 2102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac + sendrawtransaction of the above hex. - sendtxid: 2c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68 + ./komodo-cli -ac_name=MUSIG getrawtransaction 5ce74037a153ee210413b48d4e88638b99825a2de1a1f1aa0d36ebf93019824c 1 + "vout": [ + { + "value": 1.00010000, + "valueSat": 100010000, + "n": 0, + "scriptPubKey": { + "asm": "a22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401 OP_CHECKCRYPTOCONDITION", + "hex": "2ea22c8020c71ddb3aac7f9b9e4bdacf032aaa8b8e4433c4ff9f8a43cebb9c1f5da96928a48103120c008203000401cc", + "reqSigs": 1, + "type": "cryptocondition", + "addresses": [ + "RKWS7jxyjPX9iaJttk8iMKf1AumanKypez" + ] + } + }, + { + "value": 8.99980000, + "valueSat": 899980000, + "n": 1, + "scriptPubKey": { + "asm": "0255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4 OP_CHECKSIG", + "hex": "210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac", + "reqSigs": 1, + "type": "pubkey", + "addresses": [ + "RVQjvGdRbYLJ49bfH4SAFseipvwE3UdoDw" + ] + } - broadcast sendtxid and wait for it to be confirmed. then get the msg we need to sign: + script: 210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac - ./c cclib calcmsg 18 \"[%222c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68%22,%222102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac%22]\" + sendtxid: 5ce74037a153ee210413b48d4e88638b99825a2de1a1f1aa0d36ebf93019824c + + get the msg we need to sign: + + ./komodo-cli -ac_name=MUSIG cclib calcmsg 18 '["5ce74037a153ee210413b48d4e88638b99825a2de1a1f1aa0d36ebf93019824c","210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac"]' { - "result": "success", - "msg": "caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0" + "msg": "f7fb85d1412814e3c2f98b990802af6ee33dad368c6ba05c2050e9e5506fcd75", + "result": "success" } the "msg" is what needs to be signed to create a valid spend @@ -62,88 +82,101 @@ the "msg" is what needs to be signed to create a valid spend now on each signing node, a session needs to be created: 5 args: ind, numsigners, combined_pk, pkhash, message to be signed - on node with pubkey: 02aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848 - ./c cclib session 18 \"[0,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%22caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0%22]\" + on node with pubkey: 02fb6aa0b96cad24d46b5da93eba3864c45ce07a73bba12da530ae841e140fcf28 + ./komodo-cli -ac_name=MUSIG cclib session 18 '[0,2,"03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b","c1b34139744f3b54b652dc741ebd0f9d5b53ad28795cc6614dd8ad3aaabf15ae","f5d91999b23b85630a4cbd0baea3736529411b052cf5f1f4345c5d181af12825"]' { - "myind": 0, - "numsigners": 2, - "commitment": "e82228c10d0e100477630349150dea744d3b2790dcd347511a1a98199840cda4", - "result": "success" + "myind": 0, + "numsigners": 2, + "commitment": "bbea1f2562eca01b9a1393c5dc188bdd44551aebf684f4459930f59dde01f7ae", + "result": "success" } - - on node with pubkey: 039433dc3749aece1bd568f374a45da3b0bc6856990d7da3cd175399577940a775 - ./c cclib session 18 \"[1,2,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,%22caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0%22]\" - { - "myind": 1, - "numsigners": 2, - "commitment": "6e426e850ddc45e7742cfb6321781c00ee69a995ab12fa1f9ded7fe43658babf", - "result": "success" - } - - now we need to get the commitment from each node to the other one. the session already put the commitment for each node into the global struct. Keep in mind there is a single global struct with session unique to each cclib session call. that means no restarting any deamon in the middle of the process on any of the nodes and only call cclib session a single time. this is an artificial restriction just to simplify the initial implementation of musig - - ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%226e426e850ddc45e7742cfb6321781c00ee69a995ab12fa1f9ded7fe43658babf%22]\" - { - "added_index": 1, - "myind": 0, - "nonce": "0261671b0a6de416938cf035c98f8af37c6ca88bbbd1bcce693d709d4919b010e1", - "result": "success" - } - - ./c cclib commit 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%22e82228c10d0e100477630349150dea744d3b2790dcd347511a1a98199840cda4%22]\" - { - "added_index": 0, - "myind": 1, - "nonce": "02570f62a625ceb19a754a053152b162810c3e403df63f3d443e85bdacc74bfdfe", - "result": "success" - } - - Now exchange the revealed nonces to each node: - - ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%2202570f62a625ceb19a754a053152b162810c3e403df63f3d443e85bdacc74bfdfe%22]\" + on node with pubkey: 0255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4 + ./komodo-cli -ac_name=MUSIG cclib session 18 '[1,2,"03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b","5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b","f7fb85d1412814e3c2f98b990802af6ee33dad368c6ba05c2050e9e5506fcd75"]' { - "added_index": 1, - "myind": 0, - "partialsig": "3f21885e6d2d020e1473435ccd148a61cdcb1d1105867fed45913185dc0acf59", - "result": "success" + "myind": 1, + "numsigners": 2, + "commitment": "c2291acb747a75b1a40014d8eb0cc90a1360f74d413f65f78e20a7de45eda851", + "result": "success" + } + + now we need to get the commitment from each node to the other one. the session already put the commitment for each node into the global struct. Keep in mind there is a single global struct with session unique to each cclib session call. that means no restarting any deamon in the middle of the process on any of the nodes and only call cclib session a single time. this is an artificial restriction just to simplify the initial implementation of musig + ./komodo-cli -ac_name=MUSIG cclib commit 18 '["5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b","1","c2291acb747a75b1a40014d8eb0cc90a1360f74d413f65f78e20a7de45eda851"]' + { + "added_index": 1, + "myind": 0, + "nonce": "02fec7a9310c959a0a97b86bc3f8c30d392d1fb51793915898c568f73f1f70476b", + "result": "success" } - ./c cclib nonce 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%220261671b0a6de416938cf035c98f8af37c6ca88bbbd1bcce693d709d4919b010e1%22]\" + ./komodo-cli -ac_name=MUSIG cclib commit 18 '["5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b",0,"d242cff13fa8c9b83248e4219fda459ada146b885f2171481f1b0f66c66d94ad"]' { - "added_index": 0, - "myind": 0, - "myind": 1, - "partialsig": "af7f28455fb2e988d81068cd9d800879cd334036a8300118dc307b777a38c1ed", - "result": "success" + "added_index": 0, + "myind": 1, + "nonce": "039365deaaaea089d509ba4c9f846de2baf4aa04cf6b26fa2c1cd818553e47f80c", + "result": "success" } + + Now exchange the revealed nonces to each node: + ./komodo-cli -ac_name=MUSIG cclib nonce 18 '["5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b","1","039365deaaaea089d509ba4c9f846de2baf4aa04cf6b26fa2c1cd818553e47f80c"]' +{ + "added_index": 1, + "myind": 0, + "partialsig": "1d65c09cd9bffe4f0604227e66cd7cd221480bbb08262fe885563a9df7cf8f5b", + "result": "success" +} + +./komodo-cli -ac_name=MUSIG cclib nonce 18 '["5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b",0,"02fec7a9310c959a0a97b86bc3f8c30d392d1fb51793915898c568f73f1f70476b"]' +{ + "added_index": 0, + "myind": 1, + "partialsig": "4a3795e6801b355102c617390cf5a462061e082e35dc2ed8f8b1fab54cc0769e", + "result": "success" +} Almost there! final step is to exchange the partial sigs between signers - ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,1,%22af7f28455fb2e988d81068cd9d800879cd334036a8300118dc307b777a38c1ed%22]\" + ./komodo-cli -ac_name=MUSIG cclib partialsig 18 '["5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b","1","4a3795e6801b355102c617390cf5a462061e082e35dc2ed8f8b1fab54cc0769e"]' { - "added_index": 1, - "result": "success", - "combinedsig": "5e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146" + "added_index": 1, + "result": "success", + "combinedsig": "a76f2790747ed2436a281f2660bdbee21bad9ee130b9cab6e542fa618fba1512679d568359db33a008ca39b773c32134276613e93e025ec17e083553449005f9" } - - ./c cclib partialsig 18 \"[%225be117f3c5ce87e7dc6882c24b8231e0652ee82054bf7b9f94aef1f45e055cba%22,0,%223f21885e6d2d020e1473435ccd148a61cdcb1d1105867fed45913185dc0acf59%22]\" - + ./komodo-cli -ac_name=MUSIG cclib partialsig 18 '["5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b",0,"1d65c09cd9bffe4f0604227e66cd7cd221480bbb08262fe885563a9df7cf8f5b"]' { - "added_index": 0, - "result": "success", - "combinedsig": "5e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146" + "added_index": 0, + "result": "success", + "combinedsig": "a76f2790747ed2436a281f2660bdbee21bad9ee130b9cab6e542fa618fba1512679d568359db33a008ca39b773c32134276613e93e025ec17e083553449005f9" } + Notice both nodes generated the same combined signature! Now for a sanity test, we can use the verify call to make sure this sig will work with the msg needed for the spend: - ./c cclib verify 18 \"[%22caa64ba398ddfe5c33d8c70a61e556caa0e69b19d93110c5a458a1b37ad44cb0%22,%22032ddac56613cd0667b589bd7f32b665e2d2ce0247e337a5a0bca6c72e3d9d057b%22,%225e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146%22]\" - + ./komodo-cli -ac_name=MUSIG cclib verify 18 '["f7fb85d1412814e3c2f98b990802af6ee33dad368c6ba05c2050e9e5506fcd75","03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b","a76f2790747ed2436a281f2660bdbee21bad9ee130b9cab6e542fa618fba1512679d568359db33a008ca39b773c32134276613e93e025ec17e083553449005f9"]' + { + "msg": "f7fb85d1412814e3c2f98b990802af6ee33dad368c6ba05c2050e9e5506fcd75", + "combined_pk": "03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b", + "combinedsig": "a76f2790747ed2436a281f2660bdbee21bad9ee130b9cab6e542fa618fba1512679d568359db33a008ca39b773c32134276613e93e025ec17e083553449005f9", + "result": "success" + } and finally the spend: sendtxid, scriptPubKey, musig -./c cclib spend 18 \"[%222c4159bb19212dcaa412ae37de7d72398f063194053e04a65b0facf767ebcc68%22,%222102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac%22,%225e64dc5dda93b2d3f25fe44b2aaca69b8f15d21f70e2bc1c2c53e17262d941bbeea0b0a3ccdfeb96ec83ac2a6a9492db9afe5d47adb6810621c1acfd56439146%22]\" + ./komodo-cli -ac_name=MUSIG cclib spend 18 '["5ce74037a153ee210413b48d4e88638b99825a2de1a1f1aa0d36ebf93019824c","210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac","a76f2790747ed2436a281f2660bdbee21bad9ee130b9cab6e542fa618fba1512679d568359db33a008ca39b773c32134276613e93e025ec17e083553449005f9"]' +{ + "scriptpubkey": "210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac", + "msg": "f7fb85d1412814e3c2f98b990802af6ee33dad368c6ba05c2050e9e5506fcd75", + "combined_pk": "03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b", + "combinedsig": "a76f2790747ed2436a281f2660bdbee21bad9ee130b9cab6e542fa618fba1512679d568359db33a008ca39b773c32134276613e93e025ec17e083553449005f9", + "hex": "0400008085202f89014c821930f9eb360daaf1a1e12d5a82998b63884e8db4130421ee53a13740e75c000000007b4c79a276a072a26ba067a5658021032d29d6545a2aafad795d9cf50912ecade549137 +163934dfb2895ebc0e211ce8a81409671a60db89b3bc58966f3acc80194479b1a43d868e95a11ebc5609646d18710341a8ff92a7817571980307f5d660cc00a2735ac6333e0a7191243f1263f1959a100af03800112 +a10001ffffffff0200e1f5050000000023210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac0000000000000000686a4c6512792103f016c348437c7422eed92d865aa9789614f +75327cada463eefc566126b54785b40a76f2790747ed2436a281f2660bdbee21bad9ee130b9cab6e542fa618fba1512679d568359db33a008ca39b773c32134276613e93e025ec17e083553449005f900000000a805 +00000000000000000000000000", + "txid": "910635bf69a047fc90567a83ff12e47b753f470658b6d0855ec96e07e7349a8a", + "result": "success" +} */ @@ -298,7 +331,7 @@ int32_t musig_prevoutmsg(uint8_t *msg,uint256 sendtxid,CScript scriptPubKey) UniValue musig_calcmsg(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); uint256 sendtxid; int32_t i; uint8_t msg[32]; char *scriptstr,str[65]; int32_t n; + UniValue result(UniValue::VOBJ); uint256 sendtxid; int32_t i,zeros=0; uint8_t msg[32]; char *scriptstr,str[65]; int32_t n; if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) { if ( n == 2 ) @@ -307,14 +340,23 @@ UniValue musig_calcmsg(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) scriptstr = jstr(jitem(params,1),0); if ( is_hexstr(scriptstr,0) != 0 ) { - CScript scriptPubKey(ParseHex(scriptstr)); + CScript scriptPubKey; + scriptPubKey.resize(strlen(scriptstr)/2); + decode_hex(&scriptPubKey[0],strlen(scriptstr)/2,scriptstr); musig_prevoutmsg(msg,sendtxid,scriptPubKey); - result.push_back(Pair("result","success")); for (i=0; i<32; i++) + { sprintf(&str[i<<1],"%02x",msg[i]); + if ( msg[i] == 0 ) + zeros++; + } str[64] = 0; - result.push_back(Pair("msg",str)); - return(result); + if ( zeros != 32 ) + { + result.push_back(Pair("msg",str)); + result.push_back(Pair("result","success")); + return(result); + } else return(cclib_error(result,"null result, make sure params are sendtxid, scriptPubKey")); } else return(cclib_error(result,"script is not hex")); } else return(cclib_error(result,"need exactly 2 parameters: sendtxid, scriptPubKey")); } else return(cclib_error(result,"couldnt parse params")); From ebc07912fdb319358e162ec5be149f8e03bd5c0f Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sat, 23 Feb 2019 15:18:18 +0800 Subject: [PATCH 055/132] fix rogue ipaddress thing for Alright. Needs to be tested! --- depends/packages/boost.mk | 6 +-- src/cc/rogue/main.c | 2 + src/musigtest.py | 91 +++++++++++++++++++++++++++++++++++++++ 3 files changed, 96 insertions(+), 3 deletions(-) create mode 100755 src/musigtest.py diff --git a/depends/packages/boost.mk b/depends/packages/boost.mk index 7a0439ba7..3c180b0ce 100644 --- a/depends/packages/boost.mk +++ b/depends/packages/boost.mk @@ -1,8 +1,8 @@ package=boost -$(package)_version=1_69_0 -$(package)_download_path=https://dl.bintray.com/boostorg/release/1.69.0/source +$(package)_version=1_66_0 +$(package)_download_path=https://dl.bintray.com/boostorg/release/1.66.0/source $(package)_file_name=$(package)_$($(package)_version).tar.bz2 -$(package)_sha256_hash=8f32d4617390d1c2d16f26a27ab60d97807b35440d45891fa340fc2648b04406 +$(package)_sha256_hash=5721818253e6a0989583192f96782c4a98eb6204965316df9f5ad75819225ca9 define $(package)_set_vars $(package)_config_opts_release=variant=release diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index 3461445ee..6fc3d36c8 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -802,6 +802,8 @@ int main(int argc, char **argv, char **envp) } ASSETCHAINS_SYMBOL[j++] = 0; ROGUE_PORT = komodo_userpass(userpass,ASSETCHAINS_SYMBOL,IPADDRESS); + if ( IPADDRESS[0] == 0 ) + strcopy("127.0.0.1",IPADDRESS); printf("ASSETCHAINS_SYMBOL.(%s) port.%u (%s)\n",ASSETCHAINS_SYMBOL,ROGUE_PORT,USERPASS); sleep(1); if ( argc == 2 && (fp=fopen(argv[1],"rb")) == 0 ) { diff --git a/src/musigtest.py b/src/musigtest.py new file mode 100755 index 000000000..f5f25d250 --- /dev/null +++ b/src/musigtest.py @@ -0,0 +1,91 @@ +#!/usr/bin/env python3 +import platform +import os +import re +import json +import random +import base58 +import binascii +import hashlib +import sys +from slickrpc import Proxy + +# fucntion to define rpc_connection +def def_credentials(chain): + rpcport = ''; + operating_system = platform.system() + if operating_system == 'Darwin': + ac_dir = os.environ['HOME'] + '/Library/Application Support/Komodo' + elif operating_system == 'Linux': + ac_dir = os.environ['HOME'] + '/.komodo' + elif operating_system == 'Windows': + ac_dir = '%s/komodo/' % os.environ['APPDATA'] + if chain == 'KMD': + coin_config_file = str(ac_dir + '/komodo.conf') + else: + coin_config_file = str(ac_dir + '/' + chain + '/' + chain + '.conf') + with open(coin_config_file, 'r') as f: + for line in f: + l = line.rstrip() + if re.search('rpcuser', l): + rpcuser = l.replace('rpcuser=', '') + elif re.search('rpcpassword', l): + rpcpassword = l.replace('rpcpassword=', '') + elif re.search('rpcport', l): + rpcport = l.replace('rpcport=', '') + if len(rpcport) == 0: + if chain == 'KMD': + rpcport = 7771 + else: + print("rpcport not in conf file, exiting") + print("check " + coin_config_file) + exit(1) + return (Proxy("http://%s:%s@127.0.0.1:%d" % (rpcuser, rpcpassword, int(rpcport)))) + + +# generate address, validate address, dump private key +def genvaldump(rpc_connection): + # get new address + address = rpc_connection.getnewaddress() + # validate address + validateaddress_result = rpc_connection.validateaddress(address) + pubkey = validateaddress_result['pubkey'] + address = validateaddress_result['address'] + # dump private key for the address + privkey = rpc_connection.dumpprivkey(address) + # function output + output = [pubkey, privkey, address] + return(output) + +CHAIN = 'MUSIG' #sys.argv[1] + +rpc = def_credentials(CHAIN) + +pubkeys = [] +address_info = [] +ret = input('Do you want to generate new pubkeys? ').lower() + +if ret.startswith('y'): + numpks = int(input('Enter number of pubkeys to combine: ')) + if os.path.isfile("list.json"): + print('Already have list.json, move it if you would like to generate a new set.') + sys.exit(0) + while len(address_info) < numpks: + addressinfo = genvaldump(rpc) + address_info.append(addressinfo) + f = open("list.json", "w+") + f.write(json.dumps(address_info)) +else: + if os.path.isfile("list.json"): + with open('list.json') as list: + address_info = json.load(list) + else: + sys.exit('No list.json you need to create new pubkeys!') + +for addressinfo in address_info: + pubkeys.append(addressinfo[0]) + +ret = rpc.setpubkey(pubkeys[0]) +combinedpk = rpc.cclib("combine", "18", str(pubkeys))['combined_pk'] + +print('Your combined pubkey is: ' + combinedpk) From fb82fc82aaae27fc885a0ad156747bbfbde0b78a Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sat, 23 Feb 2019 15:23:08 +0800 Subject: [PATCH 056/132] fix --- src/cc/rogue/main.c | 2 +- src/musigtest.py | 91 --------------------------------------------- 2 files changed, 1 insertion(+), 92 deletions(-) delete mode 100755 src/musigtest.py diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index 6fc3d36c8..4dfc0a70a 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -803,7 +803,7 @@ int main(int argc, char **argv, char **envp) ASSETCHAINS_SYMBOL[j++] = 0; ROGUE_PORT = komodo_userpass(userpass,ASSETCHAINS_SYMBOL,IPADDRESS); if ( IPADDRESS[0] == 0 ) - strcopy("127.0.0.1",IPADDRESS); + strcpy("127.0.0.1",IPADDRESS); printf("ASSETCHAINS_SYMBOL.(%s) port.%u (%s)\n",ASSETCHAINS_SYMBOL,ROGUE_PORT,USERPASS); sleep(1); if ( argc == 2 && (fp=fopen(argv[1],"rb")) == 0 ) { diff --git a/src/musigtest.py b/src/musigtest.py deleted file mode 100755 index f5f25d250..000000000 --- a/src/musigtest.py +++ /dev/null @@ -1,91 +0,0 @@ -#!/usr/bin/env python3 -import platform -import os -import re -import json -import random -import base58 -import binascii -import hashlib -import sys -from slickrpc import Proxy - -# fucntion to define rpc_connection -def def_credentials(chain): - rpcport = ''; - operating_system = platform.system() - if operating_system == 'Darwin': - ac_dir = os.environ['HOME'] + '/Library/Application Support/Komodo' - elif operating_system == 'Linux': - ac_dir = os.environ['HOME'] + '/.komodo' - elif operating_system == 'Windows': - ac_dir = '%s/komodo/' % os.environ['APPDATA'] - if chain == 'KMD': - coin_config_file = str(ac_dir + '/komodo.conf') - else: - coin_config_file = str(ac_dir + '/' + chain + '/' + chain + '.conf') - with open(coin_config_file, 'r') as f: - for line in f: - l = line.rstrip() - if re.search('rpcuser', l): - rpcuser = l.replace('rpcuser=', '') - elif re.search('rpcpassword', l): - rpcpassword = l.replace('rpcpassword=', '') - elif re.search('rpcport', l): - rpcport = l.replace('rpcport=', '') - if len(rpcport) == 0: - if chain == 'KMD': - rpcport = 7771 - else: - print("rpcport not in conf file, exiting") - print("check " + coin_config_file) - exit(1) - return (Proxy("http://%s:%s@127.0.0.1:%d" % (rpcuser, rpcpassword, int(rpcport)))) - - -# generate address, validate address, dump private key -def genvaldump(rpc_connection): - # get new address - address = rpc_connection.getnewaddress() - # validate address - validateaddress_result = rpc_connection.validateaddress(address) - pubkey = validateaddress_result['pubkey'] - address = validateaddress_result['address'] - # dump private key for the address - privkey = rpc_connection.dumpprivkey(address) - # function output - output = [pubkey, privkey, address] - return(output) - -CHAIN = 'MUSIG' #sys.argv[1] - -rpc = def_credentials(CHAIN) - -pubkeys = [] -address_info = [] -ret = input('Do you want to generate new pubkeys? ').lower() - -if ret.startswith('y'): - numpks = int(input('Enter number of pubkeys to combine: ')) - if os.path.isfile("list.json"): - print('Already have list.json, move it if you would like to generate a new set.') - sys.exit(0) - while len(address_info) < numpks: - addressinfo = genvaldump(rpc) - address_info.append(addressinfo) - f = open("list.json", "w+") - f.write(json.dumps(address_info)) -else: - if os.path.isfile("list.json"): - with open('list.json') as list: - address_info = json.load(list) - else: - sys.exit('No list.json you need to create new pubkeys!') - -for addressinfo in address_info: - pubkeys.append(addressinfo[0]) - -ret = rpc.setpubkey(pubkeys[0]) -combinedpk = rpc.cclib("combine", "18", str(pubkeys))['combined_pk'] - -print('Your combined pubkey is: ' + combinedpk) From 9ed121b9477012c42e16acb4ec4cebf38b39cb6d Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sat, 23 Feb 2019 15:24:23 +0800 Subject: [PATCH 057/132] undo --- depends/packages/boost.mk | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/depends/packages/boost.mk b/depends/packages/boost.mk index 3c180b0ce..7a0439ba7 100644 --- a/depends/packages/boost.mk +++ b/depends/packages/boost.mk @@ -1,8 +1,8 @@ package=boost -$(package)_version=1_66_0 -$(package)_download_path=https://dl.bintray.com/boostorg/release/1.66.0/source +$(package)_version=1_69_0 +$(package)_download_path=https://dl.bintray.com/boostorg/release/1.69.0/source $(package)_file_name=$(package)_$($(package)_version).tar.bz2 -$(package)_sha256_hash=5721818253e6a0989583192f96782c4a98eb6204965316df9f5ad75819225ca9 +$(package)_sha256_hash=8f32d4617390d1c2d16f26a27ab60d97807b35440d45891fa340fc2648b04406 define $(package)_set_vars $(package)_config_opts_release=variant=release From aa6b693feecac75cf90c4dd3657499f13818d220 Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sat, 23 Feb 2019 15:26:18 +0800 Subject: [PATCH 058/132] fix strcpy --- src/cc/rogue/main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index 4dfc0a70a..165f01dfd 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -803,7 +803,7 @@ int main(int argc, char **argv, char **envp) ASSETCHAINS_SYMBOL[j++] = 0; ROGUE_PORT = komodo_userpass(userpass,ASSETCHAINS_SYMBOL,IPADDRESS); if ( IPADDRESS[0] == 0 ) - strcpy("127.0.0.1",IPADDRESS); + strcpy(IPADDRESS,"127.0.0.1"); printf("ASSETCHAINS_SYMBOL.(%s) port.%u (%s)\n",ASSETCHAINS_SYMBOL,ROGUE_PORT,USERPASS); sleep(1); if ( argc == 2 && (fp=fopen(argv[1],"rb")) == 0 ) { From 9df722e1b6a5f82254bcf7281e3a4f365f200023 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 21:04:55 -1100 Subject: [PATCH 059/132] Dilithium lib --- src/cc/cclib.cpp | 3 +- src/cc/dilithium.c | 2837 ++++++++++++++++++++++++++++++++++++++++++++ src/cc/dilithium.h | 474 ++++++++ src/cc/makecclib | 2 +- src/cc/musig.cpp | 4 +- 5 files changed, 3316 insertions(+), 4 deletions(-) create mode 100644 src/cc/dilithium.c create mode 100644 src/cc/dilithium.h diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index c770917ea..84f229069 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -581,6 +581,7 @@ uint256 juint256(cJSON *obj) #else #include "sudoku.cpp" #include "musig.cpp" -#include "../secp256k1/src/modules/musig/example.c" +#inclide "dilithium.c" +//#include "../secp256k1/src/modules/musig/example.c" #endif diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c new file mode 100644 index 000000000..b6624353e --- /dev/null +++ b/src/cc/dilithium.c @@ -0,0 +1,2837 @@ +/* Based on the public domain implementation in + * crypto_hash/keccakc512/simple/ from http://bench.cr.yp.to/supercop.html + * by Ronny Van Keer + * and the public domain "TweetFips202" implementation + * from https://twitter.com/tweetfips202 + * by Gilles Van Assche, Daniel J. Bernstein, and Peter Schwabe */ + +#include +#include "dilithium.h" + + +#define NROUNDS 24 +#define ROL(a, offset) ((a << offset) ^ (a >> (64-offset))) + +/************************************************* +* Name: load64 +* +* Description: Load 8 bytes into uint64_t in little-endian order +* +* Arguments: - const uint8_t *x: pointer to input byte array +* +* Returns the loaded 64-bit unsigned integer +**************************************************/ +static uint64_t load64(const uint8_t *x) { + uint32_t i; + uint64_t r = 0; + + for (i = 0; i < 8; ++i) + r |= (uint64_t)x[i] << 8*i; + + return r; +} + +/************************************************* +* Name: store64 +* +* Description: Store a 64-bit integer to array of 8 bytes in little-endian order +* +* Arguments: - uint8_t *x: pointer to the output byte array (allocated) +* - uint64_t u: input 64-bit unsigned integer +**************************************************/ +static void store64(uint8_t *x, uint64_t u) { + uint32_t i; + + for(i = 0; i < 8; ++i) + x[i] = u >> 8*i; +} + +/* Keccak round constants */ +static const uint64_t KeccakF_RoundConstants[NROUNDS] = { + (uint64_t)0x0000000000000001ULL, + (uint64_t)0x0000000000008082ULL, + (uint64_t)0x800000000000808aULL, + (uint64_t)0x8000000080008000ULL, + (uint64_t)0x000000000000808bULL, + (uint64_t)0x0000000080000001ULL, + (uint64_t)0x8000000080008081ULL, + (uint64_t)0x8000000000008009ULL, + (uint64_t)0x000000000000008aULL, + (uint64_t)0x0000000000000088ULL, + (uint64_t)0x0000000080008009ULL, + (uint64_t)0x000000008000000aULL, + (uint64_t)0x000000008000808bULL, + (uint64_t)0x800000000000008bULL, + (uint64_t)0x8000000000008089ULL, + (uint64_t)0x8000000000008003ULL, + (uint64_t)0x8000000000008002ULL, + (uint64_t)0x8000000000000080ULL, + (uint64_t)0x000000000000800aULL, + (uint64_t)0x800000008000000aULL, + (uint64_t)0x8000000080008081ULL, + (uint64_t)0x8000000000008080ULL, + (uint64_t)0x0000000080000001ULL, + (uint64_t)0x8000000080008008ULL +}; + +/************************************************* +* Name: KeccakF1600_StatePermute +* +* Description: The Keccak F1600 Permutation +* +* Arguments: - uint64_t *state: pointer to input/output Keccak state +**************************************************/ +static void KeccakF1600_StatePermute(uint64_t *state) +{ + int round; + + uint64_t Aba, Abe, Abi, Abo, Abu; + uint64_t Aga, Age, Agi, Ago, Agu; + uint64_t Aka, Ake, Aki, Ako, Aku; + uint64_t Ama, Ame, Ami, Amo, Amu; + uint64_t Asa, Ase, Asi, Aso, Asu; + uint64_t BCa, BCe, BCi, BCo, BCu; + uint64_t Da, De, Di, Do, Du; + uint64_t Eba, Ebe, Ebi, Ebo, Ebu; + uint64_t Ega, Ege, Egi, Ego, Egu; + uint64_t Eka, Eke, Eki, Eko, Eku; + uint64_t Ema, Eme, Emi, Emo, Emu; + uint64_t Esa, Ese, Esi, Eso, Esu; + + //copyFromState(A, state) + Aba = state[ 0]; + Abe = state[ 1]; + Abi = state[ 2]; + Abo = state[ 3]; + Abu = state[ 4]; + Aga = state[ 5]; + Age = state[ 6]; + Agi = state[ 7]; + Ago = state[ 8]; + Agu = state[ 9]; + Aka = state[10]; + Ake = state[11]; + Aki = state[12]; + Ako = state[13]; + Aku = state[14]; + Ama = state[15]; + Ame = state[16]; + Ami = state[17]; + Amo = state[18]; + Amu = state[19]; + Asa = state[20]; + Ase = state[21]; + Asi = state[22]; + Aso = state[23]; + Asu = state[24]; + + for( round = 0; round < NROUNDS; round += 2 ) + { + // prepareTheta + BCa = Aba^Aga^Aka^Ama^Asa; + BCe = Abe^Age^Ake^Ame^Ase; + BCi = Abi^Agi^Aki^Ami^Asi; + BCo = Abo^Ago^Ako^Amo^Aso; + BCu = Abu^Agu^Aku^Amu^Asu; + + //thetaRhoPiChiIotaPrepareTheta(round , A, E) + Da = BCu^ROL(BCe, 1); + De = BCa^ROL(BCi, 1); + Di = BCe^ROL(BCo, 1); + Do = BCi^ROL(BCu, 1); + Du = BCo^ROL(BCa, 1); + + Aba ^= Da; + BCa = Aba; + Age ^= De; + BCe = ROL(Age, 44); + Aki ^= Di; + BCi = ROL(Aki, 43); + Amo ^= Do; + BCo = ROL(Amo, 21); + Asu ^= Du; + BCu = ROL(Asu, 14); + Eba = BCa ^((~BCe)& BCi ); + Eba ^= (uint64_t)KeccakF_RoundConstants[round]; + Ebe = BCe ^((~BCi)& BCo ); + Ebi = BCi ^((~BCo)& BCu ); + Ebo = BCo ^((~BCu)& BCa ); + Ebu = BCu ^((~BCa)& BCe ); + + Abo ^= Do; + BCa = ROL(Abo, 28); + Agu ^= Du; + BCe = ROL(Agu, 20); + Aka ^= Da; + BCi = ROL(Aka, 3); + Ame ^= De; + BCo = ROL(Ame, 45); + Asi ^= Di; + BCu = ROL(Asi, 61); + Ega = BCa ^((~BCe)& BCi ); + Ege = BCe ^((~BCi)& BCo ); + Egi = BCi ^((~BCo)& BCu ); + Ego = BCo ^((~BCu)& BCa ); + Egu = BCu ^((~BCa)& BCe ); + + Abe ^= De; + BCa = ROL(Abe, 1); + Agi ^= Di; + BCe = ROL(Agi, 6); + Ako ^= Do; + BCi = ROL(Ako, 25); + Amu ^= Du; + BCo = ROL(Amu, 8); + Asa ^= Da; + BCu = ROL(Asa, 18); + Eka = BCa ^((~BCe)& BCi ); + Eke = BCe ^((~BCi)& BCo ); + Eki = BCi ^((~BCo)& BCu ); + Eko = BCo ^((~BCu)& BCa ); + Eku = BCu ^((~BCa)& BCe ); + + Abu ^= Du; + BCa = ROL(Abu, 27); + Aga ^= Da; + BCe = ROL(Aga, 36); + Ake ^= De; + BCi = ROL(Ake, 10); + Ami ^= Di; + BCo = ROL(Ami, 15); + Aso ^= Do; + BCu = ROL(Aso, 56); + Ema = BCa ^((~BCe)& BCi ); + Eme = BCe ^((~BCi)& BCo ); + Emi = BCi ^((~BCo)& BCu ); + Emo = BCo ^((~BCu)& BCa ); + Emu = BCu ^((~BCa)& BCe ); + + Abi ^= Di; + BCa = ROL(Abi, 62); + Ago ^= Do; + BCe = ROL(Ago, 55); + Aku ^= Du; + BCi = ROL(Aku, 39); + Ama ^= Da; + BCo = ROL(Ama, 41); + Ase ^= De; + BCu = ROL(Ase, 2); + Esa = BCa ^((~BCe)& BCi ); + Ese = BCe ^((~BCi)& BCo ); + Esi = BCi ^((~BCo)& BCu ); + Eso = BCo ^((~BCu)& BCa ); + Esu = BCu ^((~BCa)& BCe ); + + // prepareTheta + BCa = Eba^Ega^Eka^Ema^Esa; + BCe = Ebe^Ege^Eke^Eme^Ese; + BCi = Ebi^Egi^Eki^Emi^Esi; + BCo = Ebo^Ego^Eko^Emo^Eso; + BCu = Ebu^Egu^Eku^Emu^Esu; + + //thetaRhoPiChiIotaPrepareTheta(round+1, E, A) + Da = BCu^ROL(BCe, 1); + De = BCa^ROL(BCi, 1); + Di = BCe^ROL(BCo, 1); + Do = BCi^ROL(BCu, 1); + Du = BCo^ROL(BCa, 1); + + Eba ^= Da; + BCa = Eba; + Ege ^= De; + BCe = ROL(Ege, 44); + Eki ^= Di; + BCi = ROL(Eki, 43); + Emo ^= Do; + BCo = ROL(Emo, 21); + Esu ^= Du; + BCu = ROL(Esu, 14); + Aba = BCa ^((~BCe)& BCi ); + Aba ^= (uint64_t)KeccakF_RoundConstants[round+1]; + Abe = BCe ^((~BCi)& BCo ); + Abi = BCi ^((~BCo)& BCu ); + Abo = BCo ^((~BCu)& BCa ); + Abu = BCu ^((~BCa)& BCe ); + + Ebo ^= Do; + BCa = ROL(Ebo, 28); + Egu ^= Du; + BCe = ROL(Egu, 20); + Eka ^= Da; + BCi = ROL(Eka, 3); + Eme ^= De; + BCo = ROL(Eme, 45); + Esi ^= Di; + BCu = ROL(Esi, 61); + Aga = BCa ^((~BCe)& BCi ); + Age = BCe ^((~BCi)& BCo ); + Agi = BCi ^((~BCo)& BCu ); + Ago = BCo ^((~BCu)& BCa ); + Agu = BCu ^((~BCa)& BCe ); + + Ebe ^= De; + BCa = ROL(Ebe, 1); + Egi ^= Di; + BCe = ROL(Egi, 6); + Eko ^= Do; + BCi = ROL(Eko, 25); + Emu ^= Du; + BCo = ROL(Emu, 8); + Esa ^= Da; + BCu = ROL(Esa, 18); + Aka = BCa ^((~BCe)& BCi ); + Ake = BCe ^((~BCi)& BCo ); + Aki = BCi ^((~BCo)& BCu ); + Ako = BCo ^((~BCu)& BCa ); + Aku = BCu ^((~BCa)& BCe ); + + Ebu ^= Du; + BCa = ROL(Ebu, 27); + Ega ^= Da; + BCe = ROL(Ega, 36); + Eke ^= De; + BCi = ROL(Eke, 10); + Emi ^= Di; + BCo = ROL(Emi, 15); + Eso ^= Do; + BCu = ROL(Eso, 56); + Ama = BCa ^((~BCe)& BCi ); + Ame = BCe ^((~BCi)& BCo ); + Ami = BCi ^((~BCo)& BCu ); + Amo = BCo ^((~BCu)& BCa ); + Amu = BCu ^((~BCa)& BCe ); + + Ebi ^= Di; + BCa = ROL(Ebi, 62); + Ego ^= Do; + BCe = ROL(Ego, 55); + Eku ^= Du; + BCi = ROL(Eku, 39); + Ema ^= Da; + BCo = ROL(Ema, 41); + Ese ^= De; + BCu = ROL(Ese, 2); + Asa = BCa ^((~BCe)& BCi ); + Ase = BCe ^((~BCi)& BCo ); + Asi = BCi ^((~BCo)& BCu ); + Aso = BCo ^((~BCu)& BCa ); + Asu = BCu ^((~BCa)& BCe ); + } + + //copyToState(state, A) + state[ 0] = Aba; + state[ 1] = Abe; + state[ 2] = Abi; + state[ 3] = Abo; + state[ 4] = Abu; + state[ 5] = Aga; + state[ 6] = Age; + state[ 7] = Agi; + state[ 8] = Ago; + state[ 9] = Agu; + state[10] = Aka; + state[11] = Ake; + state[12] = Aki; + state[13] = Ako; + state[14] = Aku; + state[15] = Ama; + state[16] = Ame; + state[17] = Ami; + state[18] = Amo; + state[19] = Amu; + state[20] = Asa; + state[21] = Ase; + state[22] = Asi; + state[23] = Aso; + state[24] = Asu; +} + +/************************************************* +* Name: keccak_absorb +* +* Description: Absorb step of Keccak; +* non-incremental, starts by zeroeing the state. +* +* Arguments: - uint64_t *s: pointer to (uninitialized) output Keccak state +* - unsigned int r: rate in bytes (e.g., 168 for SHAKE128) +* - const uint8_t *m: pointer to input to be absorbed into s +* - int32_t mlen: length of input in bytes +* - uint8_t p: domain-separation byte for different +* Keccak-derived functions +**************************************************/ +static void keccak_absorb(uint64_t *s, + uint32_t r, + const uint8_t *m, + int32_t mlen, + uint8_t p) +{ + uint32_t i; + uint8_t t[200]; + DBENCH_START(); + + /* Zero state */ + for(i = 0; i < 25; ++i) + s[i] = 0; + + while(mlen >= r) { + for(i = 0; i < r/8; ++i) + s[i] ^= load64(m + 8*i); + + KeccakF1600_StatePermute(s); + mlen -= r; + m += r; + } + + for(i = 0; i < r; ++i) + t[i] = 0; + for(i = 0; i < mlen; ++i) + t[i] = m[i]; + t[i] = p; + t[r-1] |= 128; + for(i = 0; i < r/8; ++i) + s[i] ^= load64(t + 8*i); + + DBENCH_STOP(*tshake); +} + +/************************************************* +* Name: keccak_squeezeblocks +* +* Description: Squeeze step of Keccak. Squeezes full blocks of r bytes each. +* Modifies the state. Can be called multiple times to keep +* squeezing, i.e., is incremental. +* +* Arguments: - uint8_t *h: pointer to output blocks +* - int32_t int nblocks: number of blocks to be +* squeezed (written to h) +* - uint64_t *s: pointer to input/output Keccak state +* - uint32_t r: rate in bytes (e.g., 168 for SHAKE128) +**************************************************/ +static void keccak_squeezeblocks(uint8_t *h, + int32_t nblocks, + uint64_t *s, + uint32_t r) +{ + uint32_t i; + DBENCH_START(); + + while(nblocks > 0) { + KeccakF1600_StatePermute(s); + for(i=0; i < (r >> 3); i++) { + store64(h + 8*i, s[i]); + } + h += r; + --nblocks; + } + + DBENCH_STOP(*tshake); +} + +/************************************************* +* Name: shake128_absorb +* +* Description: Absorb step of the SHAKE128 XOF. +* non-incremental, starts by zeroeing the state. +* +* Arguments: - uint64_t *s: pointer to (uninitialized) output Keccak state +* - const uint8_t *input: pointer to input to be absorbed +* into s +* - int32_t inlen: length of input in bytes +**************************************************/ +void shake128_absorb(uint64_t *s, + const uint8_t *input, + int32_t inlen) +{ + keccak_absorb(s, SHAKE128_RATE, input, inlen, 0x1F); +} + +/************************************************* +* Name: shake128_squeezeblocks +* +* Description: Squeeze step of SHAKE128 XOF. Squeezes full blocks of +* SHAKE128_RATE bytes each. Modifies the state. Can be called +* multiple times to keep squeezing, i.e., is incremental. +* +* Arguments: - uint8_t *output: pointer to output blocks +* - int32_t nblocks: number of blocks to be squeezed +* (written to output) +* - uint64_t *s: pointer to input/output Keccak state +**************************************************/ +void shake128_squeezeblocks(uint8_t *output, + int32_t nblocks, + uint64_t *s) +{ + keccak_squeezeblocks(output, nblocks, s, SHAKE128_RATE); +} + +/************************************************* +* Name: shake256_absorb +* +* Description: Absorb step of the SHAKE256 XOF. +* non-incremental, starts by zeroeing the state. +* +* Arguments: - uint64_t *s: pointer to (uninitialized) output Keccak state +* - const uint8_t *input: pointer to input to be absorbed +* into s +* - int32_t inlen: length of input in bytes +**************************************************/ +void shake256_absorb(uint64_t *s, + const uint8_t *input, + int32_t inlen) +{ + keccak_absorb(s, SHAKE256_RATE, input, inlen, 0x1F); +} + +/************************************************* +* Name: shake256_squeezeblocks +* +* Description: Squeeze step of SHAKE256 XOF. Squeezes full blocks of +* SHAKE256_RATE bytes each. Modifies the state. Can be called +* multiple times to keep squeezing, i.e., is incremental. +* +* Arguments: - uint8_t *output: pointer to output blocks +* - int32_t nblocks: number of blocks to be squeezed +* (written to output) +* - uint64_t *s: pointer to input/output Keccak state +**************************************************/ +void shake256_squeezeblocks(uint8_t *output, + int32_t nblocks, + uint64_t *s) +{ + keccak_squeezeblocks(output, nblocks, s, SHAKE256_RATE); +} + +/************************************************* +* Name: shake128 +* +* Description: SHAKE128 XOF with non-incremental API +* +* Arguments: - uint8_t *output: pointer to output +* - int32_t outlen: requested output length in bytes +* - const uint8_t *input: pointer to input +* - int32_t inlen: length of input in bytes +**************************************************/ +void shake128(uint8_t *output, + int32_t outlen, + const uint8_t *input, + int32_t inlen) +{ + uint32_t i,nblocks = outlen/SHAKE128_RATE; + uint8_t t[SHAKE128_RATE]; + uint64_t s[25]; + + shake128_absorb(s, input, inlen); + shake128_squeezeblocks(output, nblocks, s); + + output += nblocks*SHAKE128_RATE; + outlen -= nblocks*SHAKE128_RATE; + + if(outlen) { + shake128_squeezeblocks(t, 1, s); + for(i = 0; i < outlen; ++i) + output[i] = t[i]; + } +} + +/************************************************* +* Name: shake256 +* +* Description: SHAKE256 XOF with non-incremental API +* +* Arguments: - uint8_t *output: pointer to output +* - int32_t outlen: requested output length in bytes +* - const uint8_t *input: pointer to input +* - int32_t inlen: length of input in bytes +**************************************************/ +void shake256(uint8_t *output, + int32_t outlen, + const uint8_t *input, + int32_t inlen) +{ + uint32_t i,nblocks = outlen/SHAKE256_RATE; + uint8_t t[SHAKE256_RATE]; + uint64_t s[25]; + + shake256_absorb(s, input, inlen); + shake256_squeezeblocks(output, nblocks, s); + + output += nblocks*SHAKE256_RATE; + outlen -= nblocks*SHAKE256_RATE; + + if(outlen) { + shake256_squeezeblocks(t, 1, s); + for(i = 0; i < outlen; ++i) + output[i] = t[i]; + } +} +//#include "params.h" +//#include "reduce.h" +//#include "ntt.h" +//#include "poly.h" + +/* Roots of unity in order needed by forward ntt */ +static const uint32_t zetas[N] = {0, 25847, 5771523, 7861508, 237124, 7602457, 7504169, 466468, 1826347, 2353451, 8021166, 6288512, 3119733, 5495562, 3111497, 2680103, 2725464, 1024112, 7300517, 3585928, 7830929, 7260833, 2619752, 6271868, 6262231, 4520680, 6980856, 5102745, 1757237, 8360995, 4010497, 280005, 2706023, 95776, 3077325, 3530437, 6718724, 4788269, 5842901, 3915439, 4519302, 5336701, 3574422, 5512770, 3539968, 8079950, 2348700, 7841118, 6681150, 6736599, 3505694, 4558682, 3507263, 6239768, 6779997, 3699596, 811944, 531354, 954230, 3881043, 3900724, 5823537, 2071892, 5582638, 4450022, 6851714, 4702672, 5339162, 6927966, 3475950, 2176455, 6795196, 7122806, 1939314, 4296819, 7380215, 5190273, 5223087, 4747489, 126922, 3412210, 7396998, 2147896, 2715295, 5412772, 4686924, 7969390, 5903370, 7709315, 7151892, 8357436, 7072248, 7998430, 1349076, 1852771, 6949987, 5037034, 264944, 508951, 3097992, 44288, 7280319, 904516, 3958618, 4656075, 8371839, 1653064, 5130689, 2389356, 8169440, 759969, 7063561, 189548, 4827145, 3159746, 6529015, 5971092, 8202977, 1315589, 1341330, 1285669, 6795489, 7567685, 6940675, 5361315, 4499357, 4751448, 3839961, 2091667, 3407706, 2316500, 3817976, 5037939, 2244091, 5933984, 4817955, 266997, 2434439, 7144689, 3513181, 4860065, 4621053, 7183191, 5187039, 900702, 1859098, 909542, 819034, 495491, 6767243, 8337157, 7857917, 7725090, 5257975, 2031748, 3207046, 4823422, 7855319, 7611795, 4784579, 342297, 286988, 5942594, 4108315, 3437287, 5038140, 1735879, 203044, 2842341, 2691481, 5790267, 1265009, 4055324, 1247620, 2486353, 1595974, 4613401, 1250494, 2635921, 4832145, 5386378, 1869119, 1903435, 7329447, 7047359, 1237275, 5062207, 6950192, 7929317, 1312455, 3306115, 6417775, 7100756, 1917081, 5834105, 7005614, 1500165, 777191, 2235880, 3406031, 7838005, 5548557, 6709241, 6533464, 5796124, 4656147, 594136, 4603424, 6366809, 2432395, 2454455, 8215696, 1957272, 3369112, 185531, 7173032, 5196991, 162844, 1616392, 3014001, 810149, 1652634, 4686184, 6581310, 5341501, 3523897, 3866901, 269760, 2213111, 7404533, 1717735, 472078, 7953734, 1723600, 6577327, 1910376, 6712985, 7276084, 8119771, 4546524, 5441381, 6144432, 7959518, 6094090, 183443, 7403526, 1612842, 4834730, 7826001, 3919660, 8332111, 7018208, 3937738, 1400424, 7534263, 1976782}; + +/* Roots of unity in order needed by inverse ntt */ +static const uint32_t zetas_inv[N] = {6403635, 846154, 6979993, 4442679, 1362209, 48306, 4460757, 554416, 3545687, 6767575, 976891, 8196974, 2286327, 420899, 2235985, 2939036, 3833893, 260646, 1104333, 1667432, 6470041, 1803090, 6656817, 426683, 7908339, 6662682, 975884, 6167306, 8110657, 4513516, 4856520, 3038916, 1799107, 3694233, 6727783, 7570268, 5366416, 6764025, 8217573, 3183426, 1207385, 8194886, 5011305, 6423145, 164721, 5925962, 5948022, 2013608, 3776993, 7786281, 3724270, 2584293, 1846953, 1671176, 2831860, 542412, 4974386, 6144537, 7603226, 6880252, 1374803, 2546312, 6463336, 1279661, 1962642, 5074302, 7067962, 451100, 1430225, 3318210, 7143142, 1333058, 1050970, 6476982, 6511298, 2994039, 3548272, 5744496, 7129923, 3767016, 6784443, 5894064, 7132797, 4325093, 7115408, 2590150, 5688936, 5538076, 8177373, 6644538, 3342277, 4943130, 4272102, 2437823, 8093429, 8038120, 3595838, 768622, 525098, 3556995, 5173371, 6348669, 3122442, 655327, 522500, 43260, 1613174, 7884926, 7561383, 7470875, 6521319, 7479715, 3193378, 1197226, 3759364, 3520352, 4867236, 1235728, 5945978, 8113420, 3562462, 2446433, 6136326, 3342478, 4562441, 6063917, 4972711, 6288750, 4540456, 3628969, 3881060, 3019102, 1439742, 812732, 1584928, 7094748, 7039087, 7064828, 177440, 2409325, 1851402, 5220671, 3553272, 8190869, 1316856, 7620448, 210977, 5991061, 3249728, 6727353, 8578, 3724342, 4421799, 7475901, 1100098, 8336129, 5282425, 7871466, 8115473, 3343383, 1430430, 6527646, 7031341, 381987, 1308169, 22981, 1228525, 671102, 2477047, 411027, 3693493, 2967645, 5665122, 6232521, 983419, 4968207, 8253495, 3632928, 3157330, 3190144, 1000202, 4083598, 6441103, 1257611, 1585221, 6203962, 4904467, 1452451, 3041255, 3677745, 1528703, 3930395, 2797779, 6308525, 2556880, 4479693, 4499374, 7426187, 7849063, 7568473, 4680821, 1600420, 2140649, 4873154, 3821735, 4874723, 1643818, 1699267, 539299, 6031717, 300467, 4840449, 2867647, 4805995, 3043716, 3861115, 4464978, 2537516, 3592148, 1661693, 4849980, 5303092, 8284641, 5674394, 8100412, 4369920, 19422, 6623180, 3277672, 1399561, 3859737, 2118186, 2108549, 5760665, 1119584, 549488, 4794489, 1079900, 7356305, 5654953, 5700314, 5268920, 2884855, 5260684, 2091905, 359251, 6026966, 6554070, 7913949, 876248, 777960, 8143293, 518909, 2608894, 8354570}; + +/************************************************* +* Name: ntt +* +* Description: Forward NTT, in-place. No modular reduction is performed after +* additions or subtractions. Hence output coefficients can be up +* to 16*Q larger than the coefficients of the input polynomial. +* Output vector is in bitreversed order. +* +* Arguments: - uint32_t p[N]: input/output coefficient array +**************************************************/ +void ntt(uint32_t p[N]) { + uint32_t len, start, j, k; + uint32_t zeta, t; + + k = 1; + for(len = 128; len > 0; len >>= 1) { + for(start = 0; start < N; start = j + len) { + zeta = zetas[k++]; + for(j = start; j < start + len; ++j) { + t = montgomery_reduce((uint64_t)zeta * p[j + len]); + p[j + len] = p[j] + 2*Q - t; + p[j] = p[j] + t; + } + } + } +} + +/************************************************* +* Name: invntt_frominvmont +* +* Description: Inverse NTT and multiplication by Montgomery factor 2^32. +* In-place. No modular reductions after additions or +* subtractions. Input coefficient need to be smaller than 2*Q. +* Output coefficient are smaller than 2*Q. +* +* Arguments: - uint32_t p[N]: input/output coefficient array +**************************************************/ +void invntt_frominvmont(uint32_t p[N]) { + uint32_t start, len, j, k; + uint32_t t, zeta; + const uint32_t f = (((uint64_t)MONT*MONT % Q) * (Q-1) % Q) * ((Q-1) >> 8) % Q; + + k = 0; + for(len = 1; len < N; len <<= 1) { + for(start = 0; start < N; start = j + len) { + zeta = zetas_inv[k++]; + for(j = start; j < start + len; ++j) { + t = p[j]; + p[j] = t + p[j + len]; + p[j + len] = t + 256*Q - p[j + len]; + p[j + len] = montgomery_reduce((uint64_t)zeta * p[j + len]); + } + } + } + + for(j = 0; j < N; ++j) { + p[j] = montgomery_reduce((uint64_t)f * p[j]); + } +} +//#include "params.h" +//#include "poly.h" +//#include "polyvec.h" +//#include "packing.h" + +/************************************************* +* Name: pack_pk +* +* Description: Bit-pack public key pk = (rho, t1). +* +* Arguments: - uint8_t pk[]: output byte array +* - const uint8_t rho[]: byte array containing rho +* - const polyveck *t1: pointer to vector t1 +**************************************************/ +void pack_pk(uint8_t pk[CRYPTO_PUBLICKEYBYTES], + const uint8_t rho[SEEDBYTES], + const polyveck *t1) +{ + uint32_t i; + + for(i = 0; i < SEEDBYTES; ++i) + pk[i] = rho[i]; + pk += SEEDBYTES; + + for(i = 0; i < K; ++i) + polyt1_pack(pk + i*POLT1_SIZE_PACKED, t1->vec+i); +} + +/************************************************* +* Name: unpack_pk +* +* Description: Unpack public key pk = (rho, t1). +* +* Arguments: - const uint8_t rho[]: output byte array for rho +* - const polyveck *t1: pointer to output vector t1 +* - uint8_t pk[]: byte array containing bit-packed pk +**************************************************/ +void unpack_pk(uint8_t rho[SEEDBYTES], + polyveck *t1, + const uint8_t pk[CRYPTO_PUBLICKEYBYTES]) +{ + uint32_t i; + + for(i = 0; i < SEEDBYTES; ++i) + rho[i] = pk[i]; + pk += SEEDBYTES; + + for(i = 0; i < K; ++i) + polyt1_unpack(t1->vec+i, pk + i*POLT1_SIZE_PACKED); +} + +/************************************************* +* Name: pack_sk +* +* Description: Bit-pack secret key sk = (rho, key, tr, s1, s2, t0). +* +* Arguments: - uint8_t sk[]: output byte array +* - const uint8_t rho[]: byte array containing rho +* - const uint8_t key[]: byte array containing key +* - const uint8_t tr[]: byte array containing tr +* - const polyvecl *s1: pointer to vector s1 +* - const polyveck *s2: pointer to vector s2 +* - const polyveck *t0: pointer to vector t0 +**************************************************/ +void pack_sk(uint8_t sk[CRYPTO_SECRETKEYBYTES], + const uint8_t rho[SEEDBYTES], + const uint8_t key[SEEDBYTES], + const uint8_t tr[CRHBYTES], + const polyvecl *s1, + const polyveck *s2, + const polyveck *t0) +{ + uint32_t i; + + for(i = 0; i < SEEDBYTES; ++i) + sk[i] = rho[i]; + sk += SEEDBYTES; + + for(i = 0; i < SEEDBYTES; ++i) + sk[i] = key[i]; + sk += SEEDBYTES; + + for(i = 0; i < CRHBYTES; ++i) + sk[i] = tr[i]; + sk += CRHBYTES; + + for(i = 0; i < L; ++i) + polyeta_pack(sk + i*POLETA_SIZE_PACKED, s1->vec+i); + sk += L*POLETA_SIZE_PACKED; + + for(i = 0; i < K; ++i) + polyeta_pack(sk + i*POLETA_SIZE_PACKED, s2->vec+i); + sk += K*POLETA_SIZE_PACKED; + + for(i = 0; i < K; ++i) + polyt0_pack(sk + i*POLT0_SIZE_PACKED, t0->vec+i); +} + +/************************************************* +* Name: unpack_sk +* +* Description: Unpack secret key sk = (rho, key, tr, s1, s2, t0). +* +* Arguments: - const uint8_t rho[]: output byte array for rho +* - const uint8_t key[]: output byte array for key +* - const uint8_t tr[]: output byte array for tr +* - const polyvecl *s1: pointer to output vector s1 +* - const polyveck *s2: pointer to output vector s2 +* - const polyveck *r0: pointer to output vector t0 +* - uint8_t sk[]: byte array containing bit-packed sk +**************************************************/ +void unpack_sk(uint8_t rho[SEEDBYTES], + uint8_t key[SEEDBYTES], + uint8_t tr[CRHBYTES], + polyvecl *s1, + polyveck *s2, + polyveck *t0, + const uint8_t sk[CRYPTO_SECRETKEYBYTES]) +{ + uint32_t i; + + for(i = 0; i < SEEDBYTES; ++i) + rho[i] = sk[i]; + sk += SEEDBYTES; + + for(i = 0; i < SEEDBYTES; ++i) + key[i] = sk[i]; + sk += SEEDBYTES; + + for(i = 0; i < CRHBYTES; ++i) + tr[i] = sk[i]; + sk += CRHBYTES; + + for(i=0; i < L; ++i) + polyeta_unpack(s1->vec+i, sk + i*POLETA_SIZE_PACKED); + sk += L*POLETA_SIZE_PACKED; + + for(i=0; i < K; ++i) + polyeta_unpack(s2->vec+i, sk + i*POLETA_SIZE_PACKED); + sk += K*POLETA_SIZE_PACKED; + + for(i=0; i < K; ++i) + polyt0_unpack(t0->vec+i, sk + i*POLT0_SIZE_PACKED); +} + +/************************************************* +* Name: pack_sig +* +* Description: Bit-pack signature sig = (z, h, c). +* +* Arguments: - uint8_t sig[]: output byte array +* - const polyvecl *z: pointer to vector z +* - const polyveck *h: pointer to hint vector h +* - const poly *c: pointer to challenge polynomial +**************************************************/ +void pack_sig(uint8_t sig[CRYPTO_BYTES], + const polyvecl *z, + const polyveck *h, + const poly *c) +{ + uint32_t i, j, k; + uint64_t signs, mask; + + for(i = 0; i < L; ++i) + polyz_pack(sig + i*POLZ_SIZE_PACKED, z->vec+i); + sig += L*POLZ_SIZE_PACKED; + + /* Encode h */ + k = 0; + for(i = 0; i < K; ++i) { + for(j = 0; j < N; ++j) + if(h->vec[i].coeffs[j] != 0) + sig[k++] = j; + + sig[OMEGA + i] = k; + } + while(k < OMEGA) sig[k++] = 0; + sig += OMEGA + K; + + /* Encode c */ + signs = 0; + mask = 1; + for(i = 0; i < N/8; ++i) { + sig[i] = 0; + for(j = 0; j < 8; ++j) { + if(c->coeffs[8*i+j] != 0) { + sig[i] |= (1U << j); + if(c->coeffs[8*i+j] == (Q - 1)) signs |= mask; + mask <<= 1; + } + } + } + sig += N/8; + for(i = 0; i < 8; ++i) + sig[i] = signs >> 8*i; +} + +/************************************************* +* Name: unpack_sig +* +* Description: Unpack signature sig = (z, h, c). +* +* Arguments: - polyvecl *z: pointer to output vector z +* - polyveck *h: pointer to output hint vector h +* - poly *c: pointer to output challenge polynomial +* - const uint8_t sig[]: byte array containing +* bit-packed signature +* +* Returns 1 in case of malformed signature; otherwise 0. +**************************************************/ +int unpack_sig(polyvecl *z, + polyveck *h, + poly *c, + const uint8_t sig[CRYPTO_BYTES]) +{ + uint32_t i, j, k; + uint64_t signs, mask; + + for(i = 0; i < L; ++i) + polyz_unpack(z->vec+i, sig + i*POLZ_SIZE_PACKED); + sig += L*POLZ_SIZE_PACKED; + + /* Decode h */ + k = 0; + for(i = 0; i < K; ++i) { + for(j = 0; j < N; ++j) + h->vec[i].coeffs[j] = 0; + + if(sig[OMEGA + i] < k || sig[OMEGA + i] > OMEGA) + return 1; + + for(j = k; j < sig[OMEGA + i]; ++j) { + /* Coefficients are ordered for strong unforgeability */ + if(j > k && sig[j] <= sig[j-1]) return 1; + h->vec[i].coeffs[sig[j]] = 1; + } + + k = sig[OMEGA + i]; + } + + /* Extra indices are zero for strong unforgeability */ + for(j = k; j < OMEGA; ++j) + if(sig[j]) + return 1; + + sig += OMEGA + K; + + /* Decode c */ + for(i = 0; i < N; ++i) + c->coeffs[i] = 0; + + signs = 0; + for(i = 0; i < 8; ++i) + signs |= (uint64_t)sig[N/8+i] << 8*i; + + /* Extra sign bits are zero for strong unforgeability */ + if(signs >> 60) + return 1; + + mask = 1; + for(i = 0; i < N/8; ++i) { + for(j = 0; j < 8; ++j) { + if((sig[i] >> j) & 0x01) { + c->coeffs[8*i+j] = (signs & mask) ? Q - 1 : 1; + mask <<= 1; + } + } + } + + return 0; +} +//#include +//#include "test/cpucycles.h" +//#include "fips202.h" +//#include "params.h" +//#include "reduce.h" +//#include "rounding.h" +//#include "ntt.h" +//#include "poly.h" + +#ifdef DBENCH +extern const uint64_t timing_overhead; +extern uint64_t *tred, *tadd, *tmul, *tround, *tsample, *tpack; +#endif + +/************************************************* +* Name: poly_reduce +* +* Description: Reduce all coefficients of input polynomial to representative +* in [0,2*Q[. +* +* Arguments: - poly *a: pointer to input/output polynomial +**************************************************/ +void poly_reduce(poly *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a->coeffs[i] = reduce32(a->coeffs[i]); + + DBENCH_STOP(*tred); +} + +/************************************************* +* Name: poly_csubq +* +* Description: For all coefficients of input polynomial subtract Q if +* coefficient is bigger than Q. +* +* Arguments: - poly *a: pointer to input/output polynomial +**************************************************/ +void poly_csubq(poly *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a->coeffs[i] = csubq(a->coeffs[i]); + + DBENCH_STOP(*tred); +} + +/************************************************* +* Name: poly_freeze +* +* Description: Reduce all coefficients of the polynomial to standard +* representatives. +* +* Arguments: - poly *a: pointer to input/output polynomial +**************************************************/ +void poly_freeze(poly *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a->coeffs[i] = freeze(a->coeffs[i]); + + DBENCH_STOP(*tred); +} + +/************************************************* +* Name: poly_add +* +* Description: Add polynomials. No modular reduction is performed. +* +* Arguments: - poly *c: pointer to output polynomial +* - const poly *a: pointer to first summand +* - const poly *b: pointer to second summand +**************************************************/ +void poly_add(poly *c, const poly *a, const poly *b) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + c->coeffs[i] = a->coeffs[i] + b->coeffs[i]; + + DBENCH_STOP(*tadd); +} + +/************************************************* +* Name: poly_sub +* +* Description: Subtract polynomials. Assumes coefficients of second input +* polynomial to be less than 2*Q. No modular reduction is +* performed. +* +* Arguments: - poly *c: pointer to output polynomial +* - const poly *a: pointer to first input polynomial +* - const poly *b: pointer to second input polynomial to be +* subtraced from first input polynomial +**************************************************/ +void poly_sub(poly *c, const poly *a, const poly *b) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + c->coeffs[i] = a->coeffs[i] + 2*Q - b->coeffs[i]; + + DBENCH_STOP(*tadd); +} + +/************************************************* +* Name: poly_neg +* +* Description: Negate polynomial. Assumes input coefficients to be standard +* representatives. +* +* Arguments: - poly *a: pointer to input/output polynomial +**************************************************/ +void poly_neg(poly *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a->coeffs[i] = Q - a->coeffs[i]; + + DBENCH_STOP(*tadd); +} + +/************************************************* +* Name: poly_shiftl +* +* Description: Multiply polynomial by 2^k without modular reduction. Assumes +* input coefficients to be less than 2^{32-k}. +* +* Arguments: - poly *a: pointer to input/output polynomial +* - uint32_t k: exponent +**************************************************/ +void poly_shiftl(poly *a, uint32_t k) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a->coeffs[i] <<= k; + + DBENCH_STOP(*tmul); +} + +/************************************************* +* Name: poly_ntt +* +* Description: Forward NTT. Output coefficients can be up to 16*Q larger than +* input coefficients. +* +* Arguments: - poly *a: pointer to input/output polynomial +**************************************************/ +void poly_ntt(poly *a) { + DBENCH_START(); + + ntt(a->coeffs); + + DBENCH_STOP(*tmul); +} + +/************************************************* +* Name: poly_invntt_montgomery +* +* Description: Inverse NTT and multiplication with 2^{32}. Input coefficients +* need to be less than 2*Q. Output coefficients are less than 2*Q. +* +* Arguments: - poly *a: pointer to input/output polynomial +**************************************************/ +void poly_invntt_montgomery(poly *a) { + DBENCH_START(); + + invntt_frominvmont(a->coeffs); + + DBENCH_STOP(*tmul); +} + +/************************************************* +* Name: poly_pointwise_invmontgomery +* +* Description: Pointwise multiplication of polynomials in NTT domain +* representation and multiplication of resulting polynomial +* with 2^{-32}. Output coefficients are less than 2*Q if input +* coefficient are less than 22*Q. +* +* Arguments: - poly *c: pointer to output polynomial +* - const poly *a: pointer to first input polynomial +* - const poly *b: pointer to second input polynomial +**************************************************/ +void poly_pointwise_invmontgomery(poly *c, const poly *a, const poly *b) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + c->coeffs[i] = montgomery_reduce((uint64_t)a->coeffs[i] * b->coeffs[i]); + + DBENCH_STOP(*tmul); +} + +/************************************************* +* Name: poly_power2round +* +* Description: For all coefficients c of the input polynomial, +* compute c0, c1 such that c mod Q = c1*2^D + c0 +* with -2^{D-1} < c0 <= 2^{D-1}. Assumes coefficients to be +* standard representatives. +* +* Arguments: - poly *a1: pointer to output polynomial with coefficients c1 +* - poly *a0: pointer to output polynomial with coefficients Q + a0 +* - const poly *v: pointer to input polynomial +**************************************************/ +void poly_power2round(poly *a1, poly *a0, const poly *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a1->coeffs[i] = power2round(a->coeffs[i], a0->coeffs+i); + + DBENCH_STOP(*tround); +} + +/************************************************* +* Name: poly_decompose +* +* Description: For all coefficients c of the input polynomial, +* compute high and low bits c0, c1 such c mod Q = c1*ALPHA + c0 +* with -ALPHA/2 < c0 <= ALPHA/2 except c1 = (Q-1)/ALPHA where we +* set c1 = 0 and -ALPHA/2 <= c0 = c mod Q - Q < 0. +* Assumes coefficients to be standard representatives. +* +* Arguments: - poly *a1: pointer to output polynomial with coefficients c1 +* - poly *a0: pointer to output polynomial with coefficients Q + a0 +* - const poly *c: pointer to input polynomial +**************************************************/ +void poly_decompose(poly *a1, poly *a0, const poly *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a1->coeffs[i] = decompose(a->coeffs[i], a0->coeffs+i); + + DBENCH_STOP(*tround); +} + +/************************************************* +* Name: poly_make_hint +* +* Description: Compute hint polynomial. The coefficients of which indicate +* whether the high bits of the corresponding coefficients +* of the first input polynomial and of the sum of the input +* polynomials differ. +* +* Arguments: - poly *h: pointer to output hint polynomial +* - const poly *a: pointer to first input polynomial +* - const poly *b: pointer to second input polynomial +* +* Returns number of 1 bits. +**************************************************/ +uint32_t poly_make_hint(poly *h, const poly *a, const poly *b) { + uint32_t i, s = 0; + DBENCH_START(); + + for(i = 0; i < N; ++i) { + h->coeffs[i] = make_hint(a->coeffs[i], b->coeffs[i]); + s += h->coeffs[i]; + } + + DBENCH_STOP(*tround); + return s; +} + +/************************************************* +* Name: poly_use_hint +* +* Description: Use hint polynomial to correct the high bits of a polynomial. +* +* Arguments: - poly *a: pointer to output polynomial with corrected high bits +* - const poly *b: pointer to input polynomial +* - const poly *h: pointer to input hint polynomial +**************************************************/ +void poly_use_hint(poly *a, const poly *b, const poly *h) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N; ++i) + a->coeffs[i] = use_hint(b->coeffs[i], h->coeffs[i]); + + DBENCH_STOP(*tround); +} + +/************************************************* +* Name: poly_chknorm +* +* Description: Check infinity norm of polynomial against given bound. +* Assumes input coefficients to be standard representatives. +* +* Arguments: - const poly *a: pointer to polynomial +* - uint32_t B: norm bound +* +* Returns 0 if norm is strictly smaller than B and 1 otherwise. +**************************************************/ +int poly_chknorm(const poly *a, uint32_t B) { + uint32_t i; + int32_t t; + DBENCH_START(); + + /* It is ok to leak which coefficient violates the bound since + the probability for each coefficient is independent of secret + data but we must not leak the sign of the centralized representative. */ + for(i = 0; i < N; ++i) { + /* Absolute value of centralized representative */ + t = (Q-1)/2 - a->coeffs[i]; + t ^= (t >> 31); + t = (Q-1)/2 - t; + + if((uint32_t)t >= B) { + DBENCH_STOP(*tsample); + return 1; + } + } + + DBENCH_STOP(*tsample); + return 0; +} + +/************************************************* +* Name: poly_uniform +* +* Description: Sample uniformly random polynomial using stream of random bytes. +* Assumes that enough random bytes are given (e.g. +* 5*SHAKE128_RATE bytes). +* +* Arguments: - poly *a: pointer to output polynomial +* - const uint8_t *buf: array of random bytes +**************************************************/ +void poly_uniform(poly *a, const uint8_t *buf) { + uint32_t ctr, pos; + uint32_t t; + DBENCH_START(); + + ctr = pos = 0; + while(ctr < N) { + t = buf[pos++]; + t |= (uint32_t)buf[pos++] << 8; + t |= (uint32_t)buf[pos++] << 16; + t &= 0x7FFFFF; + + if(t < Q) + a->coeffs[ctr++] = t; + } + + DBENCH_STOP(*tsample); +} + +/************************************************* +* Name: rej_eta +* +* Description: Sample uniformly random coefficients in [-ETA, ETA] by +* performing rejection sampling using array of random bytes. +* +* Arguments: - uint32_t *a: pointer to output array (allocated) +* - uint32_t len: number of coefficients to be sampled +* - const uint8_t *buf: array of random bytes +* - uint32_t buflen: length of array of random bytes +* +* Returns number of sampled coefficients. Can be smaller than len if not enough +* random bytes were given. +**************************************************/ +static uint32_t rej_eta(uint32_t *a, + uint32_t len, + const uint8_t *buf, + uint32_t buflen) +{ +#if ETA > 7 +#error "rej_eta() assumes ETA <= 7" +#endif + uint32_t ctr, pos; + uint8_t t0, t1; + DBENCH_START(); + + ctr = pos = 0; + while(ctr < len && pos < buflen) { +#if ETA <= 3 + t0 = buf[pos] & 0x07; + t1 = buf[pos++] >> 5; +#else + t0 = buf[pos] & 0x0F; + t1 = buf[pos++] >> 4; +#endif + + if(t0 <= 2*ETA) + a[ctr++] = Q + ETA - t0; + if(t1 <= 2*ETA && ctr < len) + a[ctr++] = Q + ETA - t1; + } + + DBENCH_STOP(*tsample); + return ctr; +} + +/************************************************* +* Name: poly_uniform_eta +* +* Description: Sample polynomial with uniformly random coefficients +* in [-ETA,ETA] by performing rejection sampling using the +* output stream from SHAKE256(seed|nonce). +* +* Arguments: - poly *a: pointer to output polynomial +* - const uint8_t seed[]: byte array with seed of length +* SEEDBYTES +* - uint8_t nonce: nonce byte +**************************************************/ +void poly_uniform_eta(poly *a, + const uint8_t seed[SEEDBYTES], + uint8_t nonce) +{ + uint32_t i, ctr; + uint8_t inbuf[SEEDBYTES + 1]; + /* Probability that we need more than 2 blocks: < 2^{-84} + Probability that we need more than 3 blocks: < 2^{-352} */ + uint8_t outbuf[2*SHAKE256_RATE]; + uint64_t state[25]; + + for(i= 0; i < SEEDBYTES; ++i) + inbuf[i] = seed[i]; + inbuf[SEEDBYTES] = nonce; + + shake256_absorb(state, inbuf, SEEDBYTES + 1); + shake256_squeezeblocks(outbuf, 2, state); + + ctr = rej_eta(a->coeffs, N, outbuf, 2*SHAKE256_RATE); + if(ctr < N) { + shake256_squeezeblocks(outbuf, 1, state); + rej_eta(a->coeffs + ctr, N - ctr, outbuf, SHAKE256_RATE); + } +} + +/************************************************* +* Name: rej_gamma1m1 +* +* Description: Sample uniformly random coefficients +* in [-(GAMMA1 - 1), GAMMA1 - 1] by performing rejection sampling +* using array of random bytes. +* +* Arguments: - uint32_t *a: pointer to output array (allocated) +* - uint32_t len: number of coefficients to be sampled +* - const uint8_t *buf: array of random bytes +* - uint32_t buflen: length of array of random bytes +* +* Returns number of sampled coefficients. Can be smaller than len if not enough +* random bytes were given. +**************************************************/ +static uint32_t rej_gamma1m1(uint32_t *a, + uint32_t len, + const uint8_t *buf, + uint32_t buflen) +{ +#if GAMMA1 > (1 << 19) +#error "rej_gamma1m1() assumes GAMMA1 - 1 fits in 19 bits" +#endif + uint32_t ctr, pos; + uint32_t t0, t1; + DBENCH_START(); + + ctr = pos = 0; + while(ctr < len && pos + 5 <= buflen) { + t0 = buf[pos]; + t0 |= (uint32_t)buf[pos + 1] << 8; + t0 |= (uint32_t)buf[pos + 2] << 16; + t0 &= 0xFFFFF; + + t1 = buf[pos + 2] >> 4; + t1 |= (uint32_t)buf[pos + 3] << 4; + t1 |= (uint32_t)buf[pos + 4] << 12; + + pos += 5; + + if(t0 <= 2*GAMMA1 - 2) + a[ctr++] = Q + GAMMA1 - 1 - t0; + if(t1 <= 2*GAMMA1 - 2 && ctr < len) + a[ctr++] = Q + GAMMA1 - 1 - t1; + } + + DBENCH_STOP(*tsample); + return ctr; +} + +/************************************************* +* Name: poly_uniform_gamma1m1 +* +* Description: Sample polynomial with uniformly random coefficients +* in [-(GAMMA1 - 1), GAMMA1 - 1] by performing rejection +* sampling on output stream of SHAKE256(seed|nonce). +* +* Arguments: - poly *a: pointer to output polynomial +* - const uint8_t seed[]: byte array with seed of length +* SEEDBYTES + CRHBYTES +* - uint16_t nonce: 16-bit nonce +**************************************************/ +void poly_uniform_gamma1m1(poly *a, + const uint8_t seed[SEEDBYTES + CRHBYTES], + uint16_t nonce) +{ + uint32_t i, ctr; + uint8_t inbuf[SEEDBYTES + CRHBYTES + 2]; + /* Probability that we need more than 5 blocks: < 2^{-81} + Probability that we need more than 6 blocks: < 2^{-467} */ + uint8_t outbuf[5*SHAKE256_RATE]; + uint64_t state[25]; + + for(i = 0; i < SEEDBYTES + CRHBYTES; ++i) + inbuf[i] = seed[i]; + inbuf[SEEDBYTES + CRHBYTES] = nonce & 0xFF; + inbuf[SEEDBYTES + CRHBYTES + 1] = nonce >> 8; + + shake256_absorb(state, inbuf, SEEDBYTES + CRHBYTES + 2); + shake256_squeezeblocks(outbuf, 5, state); + + ctr = rej_gamma1m1(a->coeffs, N, outbuf, 5*SHAKE256_RATE); + if(ctr < N) { + /* There are no bytes left in outbuf + since 5*SHAKE256_RATE is divisible by 5 */ + shake256_squeezeblocks(outbuf, 1, state); + rej_gamma1m1(a->coeffs + ctr, N - ctr, outbuf, SHAKE256_RATE); + } +} + +/************************************************* +* Name: polyeta_pack +* +* Description: Bit-pack polynomial with coefficients in [-ETA,ETA]. +* Input coefficients are assumed to lie in [Q-ETA,Q+ETA]. +* +* Arguments: - uint8_t *r: pointer to output byte array with at least +* POLETA_SIZE_PACKED bytes +* - const poly *a: pointer to input polynomial +**************************************************/ +void polyeta_pack(uint8_t *r, const poly *a) { +#if ETA > 7 +#error "polyeta_pack() assumes ETA <= 7" +#endif + uint32_t i; + uint8_t t[8]; + DBENCH_START(); + +#if ETA <= 3 + for(i = 0; i < N/8; ++i) { + t[0] = Q + ETA - a->coeffs[8*i+0]; + t[1] = Q + ETA - a->coeffs[8*i+1]; + t[2] = Q + ETA - a->coeffs[8*i+2]; + t[3] = Q + ETA - a->coeffs[8*i+3]; + t[4] = Q + ETA - a->coeffs[8*i+4]; + t[5] = Q + ETA - a->coeffs[8*i+5]; + t[6] = Q + ETA - a->coeffs[8*i+6]; + t[7] = Q + ETA - a->coeffs[8*i+7]; + + r[3*i+0] = t[0]; + r[3*i+0] |= t[1] << 3; + r[3*i+0] |= t[2] << 6; + r[3*i+1] = t[2] >> 2; + r[3*i+1] |= t[3] << 1; + r[3*i+1] |= t[4] << 4; + r[3*i+1] |= t[5] << 7; + r[3*i+2] = t[5] >> 1; + r[3*i+2] |= t[6] << 2; + r[3*i+2] |= t[7] << 5; + } +#else + for(i = 0; i < N/2; ++i) { + t[0] = Q + ETA - a->coeffs[2*i+0]; + t[1] = Q + ETA - a->coeffs[2*i+1]; + r[i] = t[0] | (t[1] << 4); + } +#endif + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyeta_unpack +* +* Description: Unpack polynomial with coefficients in [-ETA,ETA]. +* Output coefficients lie in [Q-ETA,Q+ETA]. +* +* Arguments: - poly *r: pointer to output polynomial +* - const uint8_t *a: byte array with bit-packed polynomial +**************************************************/ +void polyeta_unpack(poly *r, const uint8_t *a) { + uint32_t i; + DBENCH_START(); + +#if ETA <= 3 + for(i = 0; i < N/8; ++i) { + r->coeffs[8*i+0] = a[3*i+0] & 0x07; + r->coeffs[8*i+1] = (a[3*i+0] >> 3) & 0x07; + r->coeffs[8*i+2] = (a[3*i+0] >> 6) | ((a[3*i+1] & 0x01) << 2); + r->coeffs[8*i+3] = (a[3*i+1] >> 1) & 0x07; + r->coeffs[8*i+4] = (a[3*i+1] >> 4) & 0x07; + r->coeffs[8*i+5] = (a[3*i+1] >> 7) | ((a[3*i+2] & 0x03) << 1); + r->coeffs[8*i+6] = (a[3*i+2] >> 2) & 0x07; + r->coeffs[8*i+7] = (a[3*i+2] >> 5); + + r->coeffs[8*i+0] = Q + ETA - r->coeffs[8*i+0]; + r->coeffs[8*i+1] = Q + ETA - r->coeffs[8*i+1]; + r->coeffs[8*i+2] = Q + ETA - r->coeffs[8*i+2]; + r->coeffs[8*i+3] = Q + ETA - r->coeffs[8*i+3]; + r->coeffs[8*i+4] = Q + ETA - r->coeffs[8*i+4]; + r->coeffs[8*i+5] = Q + ETA - r->coeffs[8*i+5]; + r->coeffs[8*i+6] = Q + ETA - r->coeffs[8*i+6]; + r->coeffs[8*i+7] = Q + ETA - r->coeffs[8*i+7]; + } +#else + for(i = 0; i < N/2; ++i) { + r->coeffs[2*i+0] = a[i] & 0x0F; + r->coeffs[2*i+1] = a[i] >> 4; + r->coeffs[2*i+0] = Q + ETA - r->coeffs[2*i+0]; + r->coeffs[2*i+1] = Q + ETA - r->coeffs[2*i+1]; + } +#endif + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyt1_pack +* +* Description: Bit-pack polynomial t1 with coefficients fitting in 9 bits. +* Input coefficients are assumed to be standard representatives. +* +* Arguments: - uint8_t *r: pointer to output byte array with at least +* POLT1_SIZE_PACKED bytes +* - const poly *a: pointer to input polynomial +**************************************************/ +void polyt1_pack(uint8_t *r, const poly *a) { +#if D != 14 +#error "polyt1_pack() assumes D == 14" +#endif + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N/8; ++i) { + r[9*i+0] = a->coeffs[8*i+0] & 0xFF; + r[9*i+1] = (a->coeffs[8*i+0] >> 8) | ((a->coeffs[8*i+1] & 0x7F) << 1); + r[9*i+2] = (a->coeffs[8*i+1] >> 7) | ((a->coeffs[8*i+2] & 0x3F) << 2); + r[9*i+3] = (a->coeffs[8*i+2] >> 6) | ((a->coeffs[8*i+3] & 0x1F) << 3); + r[9*i+4] = (a->coeffs[8*i+3] >> 5) | ((a->coeffs[8*i+4] & 0x0F) << 4); + r[9*i+5] = (a->coeffs[8*i+4] >> 4) | ((a->coeffs[8*i+5] & 0x07) << 5); + r[9*i+6] = (a->coeffs[8*i+5] >> 3) | ((a->coeffs[8*i+6] & 0x03) << 6); + r[9*i+7] = (a->coeffs[8*i+6] >> 2) | ((a->coeffs[8*i+7] & 0x01) << 7); + r[9*i+8] = a->coeffs[8*i+7] >> 1; + } + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyt1_unpack +* +* Description: Unpack polynomial t1 with 9-bit coefficients. +* Output coefficients are standard representatives. +* +* Arguments: - poly *r: pointer to output polynomial +* - const uint8_t *a: byte array with bit-packed polynomial +**************************************************/ +void polyt1_unpack(poly *r, const uint8_t *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N/8; ++i) { + r->coeffs[8*i+0] = a[9*i+0] | ((uint32_t)(a[9*i+1] & 0x01) << 8); + r->coeffs[8*i+1] = (a[9*i+1] >> 1) | ((uint32_t)(a[9*i+2] & 0x03) << 7); + r->coeffs[8*i+2] = (a[9*i+2] >> 2) | ((uint32_t)(a[9*i+3] & 0x07) << 6); + r->coeffs[8*i+3] = (a[9*i+3] >> 3) | ((uint32_t)(a[9*i+4] & 0x0F) << 5); + r->coeffs[8*i+4] = (a[9*i+4] >> 4) | ((uint32_t)(a[9*i+5] & 0x1F) << 4); + r->coeffs[8*i+5] = (a[9*i+5] >> 5) | ((uint32_t)(a[9*i+6] & 0x3F) << 3); + r->coeffs[8*i+6] = (a[9*i+6] >> 6) | ((uint32_t)(a[9*i+7] & 0x7F) << 2); + r->coeffs[8*i+7] = (a[9*i+7] >> 7) | ((uint32_t)(a[9*i+8] & 0xFF) << 1); + } + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyt0_pack +* +* Description: Bit-pack polynomial t0 with coefficients in ]-2^{D-1}, 2^{D-1}]. +* Input coefficients are assumed to lie in ]Q-2^{D-1}, Q+2^{D-1}]. +* +* Arguments: - uint8_t *r: pointer to output byte array with at least +* POLT0_SIZE_PACKED bytes +* - const poly *a: pointer to input polynomial +**************************************************/ +void polyt0_pack(uint8_t *r, const poly *a) { + uint32_t i; + uint32_t t[4]; + DBENCH_START(); + + for(i = 0; i < N/4; ++i) { + t[0] = Q + (1 << (D-1)) - a->coeffs[4*i+0]; + t[1] = Q + (1 << (D-1)) - a->coeffs[4*i+1]; + t[2] = Q + (1 << (D-1)) - a->coeffs[4*i+2]; + t[3] = Q + (1 << (D-1)) - a->coeffs[4*i+3]; + + r[7*i+0] = t[0]; + r[7*i+1] = t[0] >> 8; + r[7*i+1] |= t[1] << 6; + r[7*i+2] = t[1] >> 2; + r[7*i+3] = t[1] >> 10; + r[7*i+3] |= t[2] << 4; + r[7*i+4] = t[2] >> 4; + r[7*i+5] = t[2] >> 12; + r[7*i+5] |= t[3] << 2; + r[7*i+6] = t[3] >> 6; + } + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyt0_unpack +* +* Description: Unpack polynomial t0 with coefficients in ]-2^{D-1}, 2^{D-1}]. +* Output coefficients lie in ]Q-2^{D-1},Q+2^{D-1}]. +* +* Arguments: - poly *r: pointer to output polynomial +* - const uint8_t *a: byte array with bit-packed polynomial +**************************************************/ +void polyt0_unpack(poly *r, const uint8_t *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N/4; ++i) { + r->coeffs[4*i+0] = a[7*i+0]; + r->coeffs[4*i+0] |= (uint32_t)(a[7*i+1] & 0x3F) << 8; + + r->coeffs[4*i+1] = a[7*i+1] >> 6; + r->coeffs[4*i+1] |= (uint32_t)a[7*i+2] << 2; + r->coeffs[4*i+1] |= (uint32_t)(a[7*i+3] & 0x0F) << 10; + + r->coeffs[4*i+2] = a[7*i+3] >> 4; + r->coeffs[4*i+2] |= (uint32_t)a[7*i+4] << 4; + r->coeffs[4*i+2] |= (uint32_t)(a[7*i+5] & 0x03) << 12; + + r->coeffs[4*i+3] = a[7*i+5] >> 2; + r->coeffs[4*i+3] |= (uint32_t)a[7*i+6] << 6; + + r->coeffs[4*i+0] = Q + (1 << (D-1)) - r->coeffs[4*i+0]; + r->coeffs[4*i+1] = Q + (1 << (D-1)) - r->coeffs[4*i+1]; + r->coeffs[4*i+2] = Q + (1 << (D-1)) - r->coeffs[4*i+2]; + r->coeffs[4*i+3] = Q + (1 << (D-1)) - r->coeffs[4*i+3]; + } + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyz_pack +* +* Description: Bit-pack polynomial z with coefficients +* in [-(GAMMA1 - 1), GAMMA1 - 1]. +* Input coefficients are assumed to be standard representatives. +* +* Arguments: - uint8_t *r: pointer to output byte array with at least +* POLZ_SIZE_PACKED bytes +* - const poly *a: pointer to input polynomial +**************************************************/ +void polyz_pack(uint8_t *r, const poly *a) { +#if GAMMA1 > (1 << 19) +#error "polyz_pack() assumes GAMMA1 <= 2^{19}" +#endif + uint32_t i; + uint32_t t[2]; + DBENCH_START(); + + for(i = 0; i < N/2; ++i) { + /* Map to {0,...,2*GAMMA1 - 2} */ + t[0] = GAMMA1 - 1 - a->coeffs[2*i+0]; + t[0] += ((int32_t)t[0] >> 31) & Q; + t[1] = GAMMA1 - 1 - a->coeffs[2*i+1]; + t[1] += ((int32_t)t[1] >> 31) & Q; + + r[5*i+0] = t[0]; + r[5*i+1] = t[0] >> 8; + r[5*i+2] = t[0] >> 16; + r[5*i+2] |= t[1] << 4; + r[5*i+3] = t[1] >> 4; + r[5*i+4] = t[1] >> 12; + } + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyz_unpack +* +* Description: Unpack polynomial z with coefficients +* in [-(GAMMA1 - 1), GAMMA1 - 1]. +* Output coefficients are standard representatives. +* +* Arguments: - poly *r: pointer to output polynomial +* - const uint8_t *a: byte array with bit-packed polynomial +**************************************************/ +void polyz_unpack(poly *r, const uint8_t *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N/2; ++i) { + r->coeffs[2*i+0] = a[5*i+0]; + r->coeffs[2*i+0] |= (uint32_t)a[5*i+1] << 8; + r->coeffs[2*i+0] |= (uint32_t)(a[5*i+2] & 0x0F) << 16; + + r->coeffs[2*i+1] = a[5*i+2] >> 4; + r->coeffs[2*i+1] |= (uint32_t)a[5*i+3] << 4; + r->coeffs[2*i+1] |= (uint32_t)a[5*i+4] << 12; + + r->coeffs[2*i+0] = GAMMA1 - 1 - r->coeffs[2*i+0]; + r->coeffs[2*i+0] += ((int32_t)r->coeffs[2*i+0] >> 31) & Q; + r->coeffs[2*i+1] = GAMMA1 - 1 - r->coeffs[2*i+1]; + r->coeffs[2*i+1] += ((int32_t)r->coeffs[2*i+1] >> 31) & Q; + } + + DBENCH_STOP(*tpack); +} + +/************************************************* +* Name: polyw1_pack +* +* Description: Bit-pack polynomial w1 with coefficients in [0, 15]. +* Input coefficients are assumed to be standard representatives. +* +* Arguments: - uint8_t *r: pointer to output byte array with at least +* POLW1_SIZE_PACKED bytes +* - const poly *a: pointer to input polynomial +**************************************************/ +void polyw1_pack(uint8_t *r, const poly *a) { + uint32_t i; + DBENCH_START(); + + for(i = 0; i < N/2; ++i) + r[i] = a->coeffs[2*i+0] | (a->coeffs[2*i+1] << 4); + + DBENCH_STOP(*tpack); +} +//#include +//#include "params.h" +//#include "poly.h" +//#include "polyvec.h" + +/**************************************************************/ +/************ Vectors of polynomials of length L **************/ +/**************************************************************/ + +/************************************************* +* Name: polyvecl_freeze +* +* Description: Reduce coefficients of polynomials in vector of length L +* to standard representatives. +* +* Arguments: - polyvecl *v: pointer to input/output vector +**************************************************/ +void polyvecl_freeze(polyvecl *v) { + uint32_t i; + + for(i = 0; i < L; ++i) + poly_freeze(v->vec+i); +} + +/************************************************* +* Name: polyvecl_add +* +* Description: Add vectors of polynomials of length L. +* No modular reduction is performed. +* +* Arguments: - polyvecl *w: pointer to output vector +* - const polyvecl *u: pointer to first summand +* - const polyvecl *v: pointer to second summand +**************************************************/ +void polyvecl_add(polyvecl *w, const polyvecl *u, const polyvecl *v) { + uint32_t i; + + for(i = 0; i < L; ++i) + poly_add(w->vec+i, u->vec+i, v->vec+i); +} + +/************************************************* +* Name: polyvecl_ntt +* +* Description: Forward NTT of all polynomials in vector of length L. Output +* coefficients can be up to 16*Q larger than input coefficients. +* +* Arguments: - polyvecl *v: pointer to input/output vector +**************************************************/ +void polyvecl_ntt(polyvecl *v) { + uint32_t i; + + for(i = 0; i < L; ++i) + poly_ntt(v->vec+i); +} + +/************************************************* +* Name: polyvecl_pointwise_acc_invmontgomery +* +* Description: Pointwise multiply vectors of polynomials of length L, multiply +* resulting vector by 2^{-32} and add (accumulate) polynomials +* in it. Input/output vectors are in NTT domain representation. +* Input coefficients are assumed to be less than 22*Q. Output +* coeffcient are less than 2*L*Q. +* +* Arguments: - poly *w: output polynomial +* - const polyvecl *u: pointer to first input vector +* - const polyvecl *v: pointer to second input vector +**************************************************/ +void polyvecl_pointwise_acc_invmontgomery(poly *w, + const polyvecl *u, + const polyvecl *v) +{ + uint32_t i; + poly t; + + poly_pointwise_invmontgomery(w, u->vec+0, v->vec+0); + + for(i = 1; i < L; ++i) { + poly_pointwise_invmontgomery(&t, u->vec+i, v->vec+i); + poly_add(w, w, &t); + } +} + +/************************************************* +* Name: polyvecl_chknorm +* +* Description: Check infinity norm of polynomials in vector of length L. +* Assumes input coefficients to be standard representatives. +* +* Arguments: - const polyvecl *v: pointer to vector +* - uint32_t B: norm bound +* +* Returns 0 if norm of all polynomials is strictly smaller than B and 1 +* otherwise. +**************************************************/ +int polyvecl_chknorm(const polyvecl *v, uint32_t bound) { + uint32_t i; + int ret = 0; + + for(i = 0; i < L; ++i) + ret |= poly_chknorm(v->vec+i, bound); + + return ret; +} + +/**************************************************************/ +/************ Vectors of polynomials of length K **************/ +/**************************************************************/ + + +/************************************************* +* Name: polyveck_reduce +* +* Description: Reduce coefficients of polynomials in vector of length K +* to representatives in [0,2*Q[. +* +* Arguments: - polyveck *v: pointer to input/output vector +**************************************************/ +void polyveck_reduce(polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_reduce(v->vec+i); +} + +/************************************************* +* Name: polyveck_csubq +* +* Description: For all coefficients of polynomials in vector of length K +* subtract Q if coefficient is bigger than Q. +* +* Arguments: - polyveck *v: pointer to input/output vector +**************************************************/ +void polyveck_csubq(polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_csubq(v->vec+i); +} + +/************************************************* +* Name: polyveck_freeze +* +* Description: Reduce coefficients of polynomials in vector of length K +* to standard representatives. +* +* Arguments: - polyveck *v: pointer to input/output vector +**************************************************/ +void polyveck_freeze(polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_freeze(v->vec+i); +} + +/************************************************* +* Name: polyveck_add +* +* Description: Add vectors of polynomials of length K. +* No modular reduction is performed. +* +* Arguments: - polyveck *w: pointer to output vector +* - const polyveck *u: pointer to first summand +* - const polyveck *v: pointer to second summand +**************************************************/ +void polyveck_add(polyveck *w, const polyveck *u, const polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_add(w->vec+i, u->vec+i, v->vec+i); +} + +/************************************************* +* Name: polyveck_sub +* +* Description: Subtract vectors of polynomials of length K. +* Assumes coefficients of polynomials in second input vector +* to be less than 2*Q. No modular reduction is performed. +* +* Arguments: - polyveck *w: pointer to output vector +* - const polyveck *u: pointer to first input vector +* - const polyveck *v: pointer to second input vector to be +* subtracted from first input vector +**************************************************/ +void polyveck_sub(polyveck *w, const polyveck *u, const polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_sub(w->vec+i, u->vec+i, v->vec+i); +} + +/************************************************* +* Name: polyveck_shiftl +* +* Description: Multiply vector of polynomials of Length K by 2^k without modular +* reduction. Assumes input coefficients to be less than 2^{32-k}. +* +* Arguments: - polyveck *v: pointer to input/output vector +* - uint32_t k: exponent +**************************************************/ +void polyveck_shiftl(polyveck *v, uint32_t k) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_shiftl(v->vec+i, k); +} + +/************************************************* +* Name: polyveck_ntt +* +* Description: Forward NTT of all polynomials in vector of length K. Output +* coefficients can be up to 16*Q larger than input coefficients. +* +* Arguments: - polyveck *v: pointer to input/output vector +**************************************************/ +void polyveck_ntt(polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_ntt(v->vec+i); +} + +/************************************************* +* Name: polyveck_invntt_montgomery +* +* Description: Inverse NTT and multiplication by 2^{32} of polynomials +* in vector of length K. Input coefficients need to be less +* than 2*Q. +* +* Arguments: - polyveck *v: pointer to input/output vector +**************************************************/ +void polyveck_invntt_montgomery(polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_invntt_montgomery(v->vec+i); +} + +/************************************************* +* Name: polyveck_chknorm +* +* Description: Check infinity norm of polynomials in vector of length K. +* Assumes input coefficients to be standard representatives. +* +* Arguments: - const polyveck *v: pointer to vector +* - uint32_t B: norm bound +* +* Returns 0 if norm of all polynomials are strictly smaller than B and 1 +* otherwise. +**************************************************/ +int polyveck_chknorm(const polyveck *v, uint32_t bound) { + uint32_t i; + int ret = 0; + + for(i = 0; i < K; ++i) + ret |= poly_chknorm(v->vec+i, bound); + + return ret; +} + +/************************************************* +* Name: polyveck_power2round +* +* Description: For all coefficients a of polynomials in vector of length K, +* compute a0, a1 such that a mod Q = a1*2^D + a0 +* with -2^{D-1} < a0 <= 2^{D-1}. Assumes coefficients to be +* standard representatives. +* +* Arguments: - polyveck *v1: pointer to output vector of polynomials with +* coefficients a1 +* - polyveck *v0: pointer to output vector of polynomials with +* coefficients Q + a0 +* - const polyveck *v: pointer to input vector +**************************************************/ +void polyveck_power2round(polyveck *v1, polyveck *v0, const polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_power2round(v1->vec+i, v0->vec+i, v->vec+i); +} + +/************************************************* +* Name: polyveck_decompose +* +* Description: For all coefficients a of polynomials in vector of length K, +* compute high and low bits a0, a1 such a mod Q = a1*ALPHA + a0 +* with -ALPHA/2 < a0 <= ALPHA/2 except a1 = (Q-1)/ALPHA where we +* set a1 = 0 and -ALPHA/2 <= a0 = a mod Q - Q < 0. +* Assumes coefficients to be standard representatives. +* +* Arguments: - polyveck *v1: pointer to output vector of polynomials with +* coefficients a1 +* - polyveck *v0: pointer to output vector of polynomials with +* coefficients Q + a0 +* - const polyveck *v: pointer to input vector +**************************************************/ +void polyveck_decompose(polyveck *v1, polyveck *v0, const polyveck *v) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_decompose(v1->vec+i, v0->vec+i, v->vec+i); +} + +/************************************************* +* Name: polyveck_make_hint +* +* Description: Compute hint vector. +* +* Arguments: - polyveck *h: pointer to output vector +* - const polyveck *u: pointer to first input vector +* - const polyveck *u: pointer to second input vector +* +* Returns number of 1 bits. +**************************************************/ +uint32_t polyveck_make_hint(polyveck *h, + const polyveck *u, + const polyveck *v) +{ + uint32_t i, s = 0; + + for(i = 0; i < K; ++i) + s += poly_make_hint(h->vec+i, u->vec+i, v->vec+i); + + return s; +} + +/************************************************* +* Name: polyveck_use_hint +* +* Description: Use hint vector to correct the high bits of input vector. +* +* Arguments: - polyveck *w: pointer to output vector of polynomials with +* corrected high bits +* - const polyveck *u: pointer to input vector +* - const polyveck *h: pointer to input hint vector +**************************************************/ +void polyveck_use_hint(polyveck *w, const polyveck *u, const polyveck *h) { + uint32_t i; + + for(i = 0; i < K; ++i) + poly_use_hint(w->vec+i, u->vec+i, h->vec+i); +} +//#include +//#include "params.h" +//#include "reduce.h" + +/************************************************* +* Name: montgomery_reduce +* +* Description: For finite field element a with 0 <= a <= Q*2^32, +* compute r \equiv a*2^{-32} (mod Q) such that 0 <= r < 2*Q. +* +* Arguments: - uint64_t: finite field element a +* +* Returns r. +**************************************************/ +uint32_t montgomery_reduce(uint64_t a) { + uint64_t t; + + t = a * QINV; + t &= (1ULL << 32) - 1; + t *= Q; + t = a + t; + t >>= 32; + return t; +} + +/************************************************* +* Name: reduce32 +* +* Description: For finite field element a, compute r \equiv a (mod Q) +* such that 0 <= r < 2*Q. +* +* Arguments: - uint32_t: finite field element a +* +* Returns r. +**************************************************/ +uint32_t reduce32(uint32_t a) { + uint32_t t; + + t = a & 0x7FFFFF; + a >>= 23; + t += (a << 13) - a; + return t; +} + +/************************************************* +* Name: csubq +* +* Description: Subtract Q if input coefficient is bigger than Q. +* +* Arguments: - uint32_t: finite field element a +* +* Returns r. +**************************************************/ +uint32_t csubq(uint32_t a) { + a -= Q; + a += ((int32_t)a >> 31) & Q; + return a; +} + +/************************************************* +* Name: freeze +* +* Description: For finite field element a, compute standard +* representative r = a mod Q. +* +* Arguments: - uint32_t: finite field element a +* +* Returns r. +**************************************************/ +uint32_t freeze(uint32_t a) { + a = reduce32(a); + a = csubq(a); + return a; +} +//#include +//#include "params.h" + +/************************************************* +* Name: power2round +* +* Description: For finite field element a, compute a0, a1 such that +* a mod Q = a1*2^D + a0 with -2^{D-1} < a0 <= 2^{D-1}. +* Assumes a to be standard representative. +* +* Arguments: - uint32_t a: input element +* - uint32_t *a0: pointer to output element Q + a0 +* +* Returns a1. +**************************************************/ +uint32_t power2round(uint32_t a, uint32_t *a0) { + int32_t t; + + /* Centralized remainder mod 2^D */ + t = a & ((1 << D) - 1); + t -= (1 << (D-1)) + 1; + t += (t >> 31) & (1 << D); + t -= (1 << (D-1)) - 1; + *a0 = Q + t; + a = (a - t) >> D; + return a; +} + +/************************************************* +* Name: decompose +* +* Description: For finite field element a, compute high and low bits a0, a1 such +* that a mod Q = a1*ALPHA + a0 with -ALPHA/2 < a0 <= ALPHA/2 except +* if a1 = (Q-1)/ALPHA where we set a1 = 0 and +* -ALPHA/2 <= a0 = a mod Q - Q < 0. Assumes a to be standard +* representative. +* +* Arguments: - uint32_t a: input element +* - uint32_t *a0: pointer to output element Q + a0 +* +* Returns a1. +**************************************************/ +uint32_t decompose(uint32_t a, uint32_t *a0) { +#if ALPHA != (Q-1)/16 +#error "decompose assumes ALPHA == (Q-1)/16" +#endif + int32_t t, u; + + /* Centralized remainder mod ALPHA */ + t = a & 0x7FFFF; + t += (a >> 19) << 9; + t -= ALPHA/2 + 1; + t += (t >> 31) & ALPHA; + t -= ALPHA/2 - 1; + a -= t; + + /* Divide by ALPHA (possible to avoid) */ + u = a - 1; + u >>= 31; + a = (a >> 19) + 1; + a -= u & 1; + + /* Border case */ + *a0 = Q + t - (a >> 4); + a &= 0xF; + return a; +} + +/************************************************* +* Name: make_hint +* +* Description: Compute hint bit indicating whether or not high bits of two +* finite field elements differ. Assumes input elements to be +* standard representatives. +* +* Arguments: - uint32_t a: first input element +* - uint32_t b: second input element +* +* Returns 1 if high bits of a and b differ and 0 otherwise. +**************************************************/ +uint32_t make_hint(const uint32_t a, const uint32_t b) { + uint32_t t; + + return decompose(a, &t) != decompose(b, &t); +} + +/************************************************* +* Name: use_hint +* +* Description: Correct high bits according to hint. +* +* Arguments: - uint32_t a: input element +* - uint32_t hint: hint bit +* +* Returns corrected high bits. +**************************************************/ +uint32_t use_hint(const uint32_t a, const uint32_t hint) { + uint32_t a0, a1; + + a1 = decompose(a, &a0); + if(hint == 0) + return a1; + else if(a0 > Q) + return (a1 + 1) & 0xF; + else + return (a1 - 1) & 0xF; + + /* If decompose does not divide out ALPHA: + if(hint == 0) + return a1; + else if(a0 > Q) + return (a1 + ALPHA) % (Q - 1); + else + return (a1 - ALPHA) % (Q - 1); + */ +} +//#include +//#include "params.h" +//#include "sign.h" +//#include "randombytes.h" +//#include "fips202.h" +//#include "poly.h" +//#include "polyvec.h" +//#include "packing.h" +#ifdef STANDALONE +#ifdef _WIN32 +#include +void randombytes(unsigned char *x,long xlen) +{ + HCRYPTPROV prov = 0; + CryptAcquireContextW(&prov, NULL, NULL,PROV_RSA_FULL, CRYPT_VERIFYCONTEXT | CRYPT_SILENT); + CryptGenRandom(prov, xlen, x); + CryptReleaseContext(prov, 0); +} +#else +#include +#include +#include +void randombytes(unsigned char *x,long xlen) +{ + static int fd = -1; + int32_t i; + if (fd == -1) { + for (;;) { + fd = open("/dev/urandom",O_RDONLY); + if (fd != -1) break; + sleep(1); + } + } + while (xlen > 0) { + if (xlen < 1048576) i = (int32_t)xlen; else i = 1048576; + i = (int32_t)read(fd,x,i); + if (i < 1) { + sleep(1); + continue; + } + if ( 0 ) + { + int32_t j; + for (j=0; j %p\n",x); + } + x += i; + xlen -= i; + } +} +#endif +#endif + +/************************************************* +* Name: expand_mat +* +* Description: Implementation of ExpandA. Generates matrix A with uniformly +* random coefficients a_{i,j} by performing rejection +* sampling on the output stream of SHAKE128(rho|i|j). +* +* Arguments: - polyvecl mat[K]: output matrix +* - const uint8_t rho[]: byte array containing seed rho +**************************************************/ +void expand_mat(polyvecl mat[K], const uint8_t rho[SEEDBYTES]) { + uint32_t i, j; + uint8_t inbuf[SEEDBYTES + 1]; + /* Don't change this to smaller values, + * sampling later assumes sufficient SHAKE output! + * Probability that we need more than 5 blocks: < 2^{-132}. + * Probability that we need more than 6 blocks: < 2^{-546}. */ + uint8_t outbuf[5*SHAKE128_RATE]; + + for(i = 0; i < SEEDBYTES; ++i) + inbuf[i] = rho[i]; + + for(i = 0; i < K; ++i) { + for(j = 0; j < L; ++j) { + inbuf[SEEDBYTES] = i + (j << 4); + shake128(outbuf, sizeof(outbuf), inbuf, SEEDBYTES + 1); + poly_uniform(mat[i].vec+j, outbuf); + } + } +} + +/************************************************* +* Name: challenge +* +* Description: Implementation of H. Samples polynomial with 60 nonzero +* coefficients in {-1,1} using the output stream of +* SHAKE256(mu|w1). +* +* Arguments: - poly *c: pointer to output polynomial +* - const uint8_t mu[]: byte array containing mu +* - const polyveck *w1: pointer to vector w1 +**************************************************/ +void challenge(poly *c, + const uint8_t mu[CRHBYTES], + const polyveck *w1) +{ + uint32_t i, b, pos; + uint8_t inbuf[CRHBYTES + K*POLW1_SIZE_PACKED]; + uint8_t outbuf[SHAKE256_RATE]; + uint64_t state[25], signs, mask; + + for(i = 0; i < CRHBYTES; ++i) + inbuf[i] = mu[i]; + for(i = 0; i < K; ++i) + polyw1_pack(inbuf + CRHBYTES + i*POLW1_SIZE_PACKED, w1->vec+i); + + shake256_absorb(state, inbuf, sizeof(inbuf)); + shake256_squeezeblocks(outbuf, 1, state); + + signs = 0; + for(i = 0; i < 8; ++i) + signs |= (uint64_t)outbuf[i] << 8*i; + + pos = 8; + mask = 1; + + for(i = 0; i < N; ++i) + c->coeffs[i] = 0; + + for(i = 196; i < 256; ++i) { + do { + if(pos >= SHAKE256_RATE) { + shake256_squeezeblocks(outbuf, 1, state); + pos = 0; + } + + b = outbuf[pos++]; + } while(b > i); + + c->coeffs[i] = c->coeffs[b]; + c->coeffs[b] = (signs & mask) ? Q - 1 : 1; + mask <<= 1; + } +} + +/************************************************* +* Name: dilithium_keypair +* +* Description: Generates public and private key. +* +* Arguments: - uint8_t *pk: pointer to output public key (allocated +* array of CRYPTO_PUBLICKEYBYTES bytes) +* - uint8_t *sk: pointer to output private key (allocated +* array of CRYPTO_SECRETKEYBYTES bytes) +* +* Returns 0 (success) +**************************************************/ +int dilithium_keypair(uint8_t *pk, uint8_t *sk) { + uint32_t i; + uint8_t seedbuf[3*SEEDBYTES]; + uint8_t tr[CRHBYTES]; + uint8_t *rho, *rhoprime, *key; + uint16_t nonce = 0; + polyvecl mat[K]; + polyvecl s1, s1hat; + polyveck s2, t, t1, t0; + + /* Expand 32 bytes of randomness into rho, rhoprime and key */ + randombytes(seedbuf, SEEDBYTES); + shake256(seedbuf, 3*SEEDBYTES, seedbuf, SEEDBYTES); + rho = seedbuf; + rhoprime = rho + SEEDBYTES; + key = rho + 2*SEEDBYTES; + + /* Expand matrix */ + expand_mat(mat, rho); + + /* Sample short vectors s1 and s2 */ + for(i = 0; i < L; ++i) + poly_uniform_eta(s1.vec+i, rhoprime, nonce++); + for(i = 0; i < K; ++i) + poly_uniform_eta(s2.vec+i, rhoprime, nonce++); + + /* Matrix-vector multiplication */ + s1hat = s1; + polyvecl_ntt(&s1hat); + for(i = 0; i < K; ++i) { + polyvecl_pointwise_acc_invmontgomery(t.vec+i, mat+i, &s1hat); + poly_reduce(t.vec+i); + poly_invntt_montgomery(t.vec+i); + } + + /* Add noise vector s2 */ + polyveck_add(&t, &t, &s2); + + /* Extract t1 and write public key */ + polyveck_freeze(&t); + polyveck_power2round(&t1, &t0, &t); + pack_pk(pk, rho, &t1); + + /* Compute CRH(rho, t1) and write secret key */ + shake256(tr, CRHBYTES, pk, CRYPTO_PUBLICKEYBYTES); + pack_sk(sk, rho, key, tr, &s1, &s2, &t0); + + return 0; +} + +/************************************************* +* Name: dilithium_sign +* +* Description: Compute signed message. +* +* Arguments: - uint8_t *sm: pointer to output signed message (allocated +* array with CRYPTO_BYTES + mlen bytes), +* can be equal to m +* - int32_t *smlen: pointer to output length of signed +* message +* - const uint8_t *m: pointer to message to be signed +* - int32_t mlen: length of message +* - const uint8_t *sk: pointer to bit-packed secret key +* +* Returns 0 (success) +**************************************************/ +int dilithium_sign(uint8_t *sm, + int32_t *smlen, + const uint8_t *m, + int32_t mlen, + const uint8_t *sk) +{ + int32_t i, j; + uint32_t n; + uint8_t seedbuf[2*SEEDBYTES + CRHBYTES]; // TODO: nonce in seedbuf (2x) + uint8_t tr[CRHBYTES]; + uint8_t *rho, *key, *mu; + uint16_t nonce = 0; + poly c, chat; + polyvecl mat[K], s1, y, yhat, z; + polyveck s2, t0, w, w1; + polyveck h, wcs2, wcs20, ct0, tmp; + + rho = seedbuf; + key = seedbuf + SEEDBYTES; + mu = seedbuf + 2*SEEDBYTES; + unpack_sk(rho, key, tr, &s1, &s2, &t0, sk); + + /* Copy tr and message into the sm buffer, + * backwards since m and sm can be equal in SUPERCOP API */ + for(i = 1; i <= mlen; ++i) + sm[CRYPTO_BYTES + mlen - i] = m[mlen - i]; + for(i = 0; i < CRHBYTES; ++i) + sm[CRYPTO_BYTES - CRHBYTES + i] = tr[i]; + + /* Compute CRH(tr, msg) */ + shake256(mu, CRHBYTES, sm + CRYPTO_BYTES - CRHBYTES, CRHBYTES + mlen); + + /* Expand matrix and transform vectors */ + expand_mat(mat, rho); + polyvecl_ntt(&s1); + polyveck_ntt(&s2); + polyveck_ntt(&t0); + + rej: + /* Sample intermediate vector y */ + for(i = 0; i < L; ++i) + poly_uniform_gamma1m1(y.vec+i, key, nonce++); + + /* Matrix-vector multiplication */ + yhat = y; + polyvecl_ntt(&yhat); + for(i = 0; i < K; ++i) { + polyvecl_pointwise_acc_invmontgomery(w.vec+i, mat+i, &yhat); + poly_reduce(w.vec+i); + poly_invntt_montgomery(w.vec+i); + } + + /* Decompose w and call the random oracle */ + polyveck_csubq(&w); + polyveck_decompose(&w1, &tmp, &w); + challenge(&c, mu, &w1); + + /* Compute z, reject if it reveals secret */ + chat = c; + poly_ntt(&chat); + for(i = 0; i < L; ++i) { + poly_pointwise_invmontgomery(z.vec+i, &chat, s1.vec+i); + poly_invntt_montgomery(z.vec+i); + } + polyvecl_add(&z, &z, &y); + polyvecl_freeze(&z); + if(polyvecl_chknorm(&z, GAMMA1 - BETA)) + goto rej; + + /* Compute w - cs2, reject if w1 can not be computed from it */ + for(i = 0; i < K; ++i) { + poly_pointwise_invmontgomery(wcs2.vec+i, &chat, s2.vec+i); + poly_invntt_montgomery(wcs2.vec+i); + } + polyveck_sub(&wcs2, &w, &wcs2); + polyveck_freeze(&wcs2); + polyveck_decompose(&tmp, &wcs20, &wcs2); + polyveck_csubq(&wcs20); + if(polyveck_chknorm(&wcs20, GAMMA2 - BETA)) + goto rej; + + for(i = 0; i < K; ++i) + for(j = 0; j < N; ++j) + if(tmp.vec[i].coeffs[j] != w1.vec[i].coeffs[j]) + goto rej; + + /* Compute hints for w1 */ + for(i = 0; i < K; ++i) { + poly_pointwise_invmontgomery(ct0.vec+i, &chat, t0.vec+i); + poly_invntt_montgomery(ct0.vec+i); + } + + polyveck_csubq(&ct0); + if(polyveck_chknorm(&ct0, GAMMA2)) + goto rej; + + polyveck_add(&tmp, &wcs2, &ct0); + polyveck_csubq(&tmp); + n = polyveck_make_hint(&h, &wcs2, &tmp); + if(n > OMEGA) + goto rej; + + /* Write signature */ + pack_sig(sm, &z, &h, &c); + + *smlen = mlen + CRYPTO_BYTES; + return 0; +} + +/************************************************* +* Name: dilithium_verify +* +* Description: Verify signed message. +* +* Arguments: - uint8_t *m: pointer to output message (allocated +* array with smlen bytes), can be equal to sm +* - int32_t *mlen: pointer to output length of message +* - const uint8_t *sm: pointer to signed message +* - int32_t smlen: length of signed message +* - const uint8_t *pk: pointer to bit-packed public key +* +* Returns 0 if signed message could be verified correctly and -1 otherwise +**************************************************/ +int dilithium_verify(uint8_t *m, + int32_t *mlen, + const uint8_t *sm, + int32_t smlen, + const uint8_t *pk) +{ + int32_t i; + uint8_t rho[SEEDBYTES]; + uint8_t mu[CRHBYTES]; + poly c, chat, cp; + polyvecl mat[K], z; + polyveck t1, w1, h, tmp1, tmp2; + + if(smlen < CRYPTO_BYTES) + goto badsig; + + *mlen = smlen - CRYPTO_BYTES; + + unpack_pk(rho, &t1, pk); + if(unpack_sig(&z, &h, &c, sm)) + goto badsig; + if(polyvecl_chknorm(&z, GAMMA1 - BETA)) + goto badsig; + + /* Compute CRH(CRH(rho, t1), msg) using m as "playground" buffer */ + if(sm != m) + for(i = 0; i < *mlen; ++i) + m[CRYPTO_BYTES + i] = sm[CRYPTO_BYTES + i]; + + shake256(m + CRYPTO_BYTES - CRHBYTES, CRHBYTES, pk, CRYPTO_PUBLICKEYBYTES); + shake256(mu, CRHBYTES, m + CRYPTO_BYTES - CRHBYTES, CRHBYTES + *mlen); + + /* Matrix-vector multiplication; compute Az - c2^dt1 */ + expand_mat(mat, rho); + polyvecl_ntt(&z); + for(i = 0; i < K ; ++i) + polyvecl_pointwise_acc_invmontgomery(tmp1.vec+i, mat+i, &z); + + chat = c; + poly_ntt(&chat); + polyveck_shiftl(&t1, D); + polyveck_ntt(&t1); + for(i = 0; i < K; ++i) + poly_pointwise_invmontgomery(tmp2.vec+i, &chat, t1.vec+i); + + polyveck_sub(&tmp1, &tmp1, &tmp2); + polyveck_reduce(&tmp1); + polyveck_invntt_montgomery(&tmp1); + + /* Reconstruct w1 */ + polyveck_csubq(&tmp1); + polyveck_use_hint(&w1, &tmp1, &h); + + /* Call random oracle and verify challenge */ + challenge(&cp, mu, &w1); + for(i = 0; i < N; ++i) + if(c.coeffs[i] != cp.coeffs[i]) + { + /* Signature verification failed */ + badsig: + *mlen = (int32_t) -1; + for(i = 0; i < smlen; ++i) + m[i] = 0; + + return -1; + } + + /* All good, copy msg, return 0 */ + for(i = 0; i < *mlen; ++i) + m[i] = sm[CRYPTO_BYTES + i]; + return 0; +} + +#ifdef STANDALONE +/////////////////////////////////////////////////////////////////////////////// +#include +#include + +#define MLEN 59 +#define NTESTS 10000 + +int64_t timing_overhead; +#ifdef DBENCH +int64_t *tred, *tadd, *tmul, *tround, *tsample, *tpack, *tshake; +#endif + +static int cmp_llu(const void *a, const void*b) +{ + if(*(int64_t *)a < *(int64_t *)b) return -1; + if(*(int64_t *)a > *(int64_t *)b) return 1; + return 0; +} + +static int64_t median(int64_t *l, size_t llen) +{ + qsort(l,llen,sizeof(uint64_t),cmp_llu); + + if(llen%2) return l[llen/2]; + else return (l[llen/2-1]+l[llen/2])/2; +} + +static int64_t average(int64_t *t, size_t tlen) +{ + uint64_t acc=0; + size_t i; + for(i=0;i + +#ifndef CPUCYCLES_H +#define CPUCYCLES_H + +#ifdef DBENCH +#define DBENCH_START() uint64_t time = cpucycles_start() +#define DBENCH_STOP(t) t += cpucycles_stop() - time - timing_overhead +#else +#define DBENCH_START() +#define DBENCH_STOP(t) +#endif + +#ifdef USE_RDPMC /* Needs echo 2 > /sys/devices/cpu/rdpmc */ +#ifdef SERIALIZE_RDC + +static inline uint64_t cpucycles_start(void) { + const uint32_t ecx = (1U << 30) + 1; + uint64_t result; + + asm volatile("cpuid; movl %1,%%ecx; rdpmc; shlq $32,%%rdx; orq %%rdx,%%rax" + : "=&a" (result) : "r" (ecx) : "rbx", "rcx", "rdx"); + + return result; +} + +static inline uint64_t cpucycles_stop(void) { + const uint32_t ecx = (1U << 30) + 1; + uint64_t result, dummy; + + asm volatile("rdpmc; shlq $32,%%rdx; orq %%rdx,%%rax; movq %%rax,%0; cpuid" + : "=&r" (result), "=c" (dummy) : "c" (ecx) : "rax", "rbx", "rdx"); + + return result; +} + +#else + +static inline uint64_t cpucycles_start(void) { + const uint32_t ecx = (1U << 30) + 1; + uint64_t result; + + asm volatile("rdpmc; shlq $32,%%rdx; orq %%rdx,%%rax" + : "=a" (result) : "c" (ecx) : "rdx"); + + return result; +} + +static inline uint64_t cpucycles_stop(void) { + const uint32_t ecx = (1U << 30) + 1; + uint64_t result; + + asm volatile("rdpmc; shlq $32,%%rdx; orq %%rdx,%%rax" + : "=a" (result) : "c" (ecx) : "rdx"); + + return result; +} + +#endif +#else +#ifdef SERIALIZE_RDC + +static inline uint64_t cpucycles_start(void) { + uint64_t result; + + asm volatile("cpuid; rdtsc; shlq $32,%%rdx; orq %%rdx,%%rax" + : "=a" (result) : : "%rbx", "%rcx", "%rdx"); + + return result; +} + +static inline uint64_t cpucycles_stop(void) { + uint64_t result; + + asm volatile("rdtscp; shlq $32,%%rdx; orq %%rdx,%%rax; mov %%rax,%0; cpuid" + : "=r" (result) : : "%rax", "%rbx", "%rcx", "%rdx"); + + return result; +} + +#else + +static inline uint64_t cpucycles_start(void) { + uint64_t result; + + asm volatile("rdtsc; shlq $32,%%rdx; orq %%rdx,%%rax" + : "=a" (result) : : "%rdx"); + + return result; +} + +static inline uint64_t cpucycles_stop(void) { + uint64_t result; + + asm volatile("rdtsc; shlq $32,%%rdx; orq %%rdx,%%rax" + : "=a" (result) : : "%rdx"); + + return result; +} + +#endif +#endif + +int64_t cpucycles_overhead(void); + +#endif + +#ifndef FIPS202_H +#define FIPS202_H + + +#define SHAKE128_RATE 168 +#define SHAKE256_RATE 136 + +void shake128_absorb(uint64_t *s, + const uint8_t *input, + int32_t inlen); + +void shake128_squeezeblocks(uint8_t *output, + int32_t nblocks, + uint64_t *s); + +void shake256_absorb(uint64_t *s, + const uint8_t *input, + int32_t inlen); + +void shake256_squeezeblocks(uint8_t *output, + int32_t nblocks, + uint64_t *s); + +void shake128(uint8_t *output, + int32_t outlen, + const uint8_t *input, + int32_t inlen); + +void shake256(uint8_t *output, + int32_t outlen, + const uint8_t *input, + int32_t inlen); + +#endif + +#ifndef PARAMS_H +#define PARAMS_H + +#ifndef MODE +#define MODE 2 +#endif + +#define SEEDBYTES 32U +#define CRHBYTES 48U +#define N 256U +#define Q 8380417U +#define QBITS 23U +#define ROOT_OF_UNITY 1753U +#define D 14U +#define GAMMA1 ((Q - 1U)/16U) +#define GAMMA2 (GAMMA1/2U) +#define ALPHA (2U*GAMMA2) + +#if MODE == 0 +#define K 3U +#define L 2U +#define ETA 7U +#define SETABITS 4U +#define BETA 375U +#define OMEGA 64U + +#elif MODE == 1 +#define K 4U +#define L 3U +#define ETA 6U +#define SETABITS 4U +#define BETA 325U +#define OMEGA 80U + +#elif MODE == 2 +#define K 5U +#define L 4U +#define ETA 5U +#define SETABITS 4U +#define BETA 275U +#define OMEGA 96U + +#elif MODE == 3 +#define K 6U +#define L 5U +#define ETA 3U +#define SETABITS 3U +#define BETA 175U +#define OMEGA 120U + +#endif + +#define POL_SIZE_PACKED ((N*QBITS)/8) +#define POLT1_SIZE_PACKED ((N*(QBITS - D))/8) +#define POLT0_SIZE_PACKED ((N*D)/8) +#define POLETA_SIZE_PACKED ((N*SETABITS)/8) +#define POLZ_SIZE_PACKED ((N*(QBITS - 3))/8) +#define POLW1_SIZE_PACKED ((N*4)/8) +#define POLVECK_SIZE_PACKED (K*POL_SIZE_PACKED) +#define POLVECL_SIZE_PACKED (L*POL_SIZE_PACKED) + +#define CRYPTO_PUBLICKEYBYTES (SEEDBYTES + K*POLT1_SIZE_PACKED) +#define CRYPTO_SECRETKEYBYTES (2*SEEDBYTES + (L + K)*POLETA_SIZE_PACKED + CRHBYTES + K*POLT0_SIZE_PACKED) +#define CRYPTO_BYTES (L*POLZ_SIZE_PACKED + (OMEGA + K) + (N/8 + 8)) + +#endif +#ifndef POLY_H +#define POLY_H + +//#include +//#include "params.h" +//#include "fips202.h" + +typedef struct { + uint32_t coeffs[N]; +} poly __attribute__((aligned(32))); + +void poly_reduce(poly *a); +void poly_csubq(poly *a); +void poly_freeze(poly *a); + +void poly_add(poly *c, const poly *a, const poly *b); +void poly_sub(poly *c, const poly *a, const poly *b); +void poly_neg(poly *a); +void poly_shiftl(poly *a, uint32_t k); + +void poly_ntt(poly *a); +void poly_invntt_montgomery(poly *a); +void poly_pointwise_invmontgomery(poly *c, const poly *a, const poly *b); + +void poly_power2round(poly *a1, poly *a0, const poly *a); +void poly_decompose(poly *a1, poly *a0, const poly *a); +uint32_t poly_make_hint(poly *h, const poly *a, const poly *b); +void poly_use_hint(poly *a, const poly *b, const poly *h); + +int poly_chknorm(const poly *a, uint32_t B); +void poly_uniform(poly *a, const uint8_t *buf); +void poly_uniform_eta(poly *a, + const uint8_t seed[SEEDBYTES], + uint8_t nonce); +void poly_uniform_gamma1m1(poly *a, + const uint8_t seed[SEEDBYTES + CRHBYTES], + uint16_t nonce); + +void polyeta_pack(uint8_t *r, const poly *a); +void polyeta_unpack(poly *r, const uint8_t *a); + +void polyt1_pack(uint8_t *r, const poly *a); +void polyt1_unpack(poly *r, const uint8_t *a); + +void polyt0_pack(uint8_t *r, const poly *a); +void polyt0_unpack(poly *r, const uint8_t *a); + +void polyz_pack(uint8_t *r, const poly *a); +void polyz_unpack(poly *r, const uint8_t *a); + +void polyw1_pack(uint8_t *r, const poly *a); +#endif +#ifndef POLYVEC_H +#define POLYVEC_H + +//#include +//#include "params.h" +//#include "poly.h" + +/* Vectors of polynomials of length L */ +typedef struct { + poly vec[L]; +} polyvecl; + +void polyvecl_freeze(polyvecl *v); + +void polyvecl_add(polyvecl *w, const polyvecl *u, const polyvecl *v); + +void polyvecl_ntt(polyvecl *v); +void polyvecl_pointwise_acc_invmontgomery(poly *w, + const polyvecl *u, + const polyvecl *v); + +int polyvecl_chknorm(const polyvecl *v, uint32_t B); + + + +/* Vectors of polynomials of length K */ +typedef struct { + poly vec[K]; +} polyveck; + +void polyveck_reduce(polyveck *v); +void polyveck_csubq(polyveck *v); +void polyveck_freeze(polyveck *v); + +void polyveck_add(polyveck *w, const polyveck *u, const polyveck *v); +void polyveck_sub(polyveck *w, const polyveck *u, const polyveck *v); +void polyveck_shiftl(polyveck *v, uint32_t k); + +void polyveck_ntt(polyveck *v); +void polyveck_invntt_montgomery(polyveck *v); + +int polyveck_chknorm(const polyveck *v, uint32_t B); + +void polyveck_power2round(polyveck *v1, polyveck *v0, const polyveck *v); +void polyveck_decompose(polyveck *v1, polyveck *v0, const polyveck *v); +uint32_t polyveck_make_hint(polyveck *h, + const polyveck *u, + const polyveck *v); +void polyveck_use_hint(polyveck *w, const polyveck *v, const polyveck *h); + +#endif + +#ifndef NTT_H +#define NTT_H + +//#include +//#include "params.h" + +void ntt(uint32_t p[N]); +void invntt_frominvmont(uint32_t p[N]); + +#endif +#ifndef PACKING_H +#define PACKING_H + +//#include "params.h" +//#include "polyvec.h" + +void pack_pk(uint8_t pk[CRYPTO_PUBLICKEYBYTES], + const uint8_t rho[SEEDBYTES], const polyveck *t1); +void pack_sk(uint8_t sk[CRYPTO_SECRETKEYBYTES], + const uint8_t rho[SEEDBYTES], + const uint8_t key[SEEDBYTES], + const uint8_t tr[CRHBYTES], + const polyvecl *s1, + const polyveck *s2, + const polyveck *t0); +void pack_sig(uint8_t sig[CRYPTO_BYTES], + const polyvecl *z, const polyveck *h, const poly *c); + +void unpack_pk(uint8_t rho[SEEDBYTES], polyveck *t1, + const uint8_t pk[CRYPTO_PUBLICKEYBYTES]); +void unpack_sk(uint8_t rho[SEEDBYTES], + uint8_t key[SEEDBYTES], + uint8_t tr[CRHBYTES], + polyvecl *s1, + polyveck *s2, + polyveck *t0, + const uint8_t sk[CRYPTO_SECRETKEYBYTES]); +int unpack_sig(polyvecl *z, polyveck *h, poly *c, + const uint8_t sig[CRYPTO_BYTES]); + +#endif +#ifndef REDUCE_H +#define REDUCE_H + +//#include + +#define MONT 4193792U // 2^32 % Q +#define QINV 4236238847U // -q^(-1) mod 2^32 + +/* a <= Q*2^32 => r < 2*Q */ +uint32_t montgomery_reduce(uint64_t a); + +/* r < 2*Q */ +uint32_t reduce32(uint32_t a); + +/* a < 2*Q => r < Q */ +uint32_t csubq(uint32_t a); + +/* r < Q */ +uint32_t freeze(uint32_t a); + +#endif +#ifndef ROUNDING_H +#define ROUNDING_H + +//#include + +uint32_t power2round(const uint32_t a, uint32_t *a0); +uint32_t decompose(uint32_t a, uint32_t *a0); +uint32_t make_hint(const uint32_t a, const uint32_t b); +uint32_t use_hint(const uint32_t a, const uint32_t hint); + +#endif +#ifndef SIGN_H +#define SIGN_H + +//#include "params.h" +//#include "poly.h" +//#include "polyvec.h" + +void expand_mat(polyvecl mat[K], const uint8_t rho[SEEDBYTES]); +void challenge(poly *c, const uint8_t mu[CRHBYTES], + const polyveck *w1); + +int crypto_sign_keypair(uint8_t *pk, uint8_t *sk); + +int crypto_sign(uint8_t *sm, int32_t *smlen, + const uint8_t *msg, int32_t len, + const uint8_t *sk); + +int crypto_sign_open(uint8_t *m, int32_t *mlen, + const uint8_t *sm, int32_t smlen, + const uint8_t *pk); + +#endif + +#ifndef API_H +#define API_H + +#ifndef MODE +#define MODE 2 +#endif + +#if MODE == 0 +#if CRYPTO_PUBLICKEYBYTES -896U +CRYPTO_PUBLICKEYBYTES size error +#endif +#if CRYPTO_SECRETKEYBYTES -2096U +CRYPTO_SECRETKEYBYTES size error +#endif +#if CRYPTO_BYTES -1387U +CRYPTO_BYTES size error +#endif + +#elif MODE == 1 +#if CRYPTO_PUBLICKEYBYTES -1184U +CRYPTO_PUBLICKEYBYTES size error +#endif +#if CRYPTO_SECRETKEYBYTES -2800U +CRYPTO_SECRETKEYBYTES size error +#endif +#if CRYPTO_BYTES -2044U +CRYPTO_BYTES size error +#endif + +#elif MODE == 2 +#if CRYPTO_PUBLICKEYBYTES -1472U +CRYPTO_PUBLICKEYBYTES size error +#endif +#if CRYPTO_SECRETKEYBYTES -3504U +CRYPTO_SECRETKEYBYTES size error +#endif +#if CRYPTO_BYTES -2701U +CRYPTO_BYTES size error +#endif + +#elif MODE == 3 +#if CRYPTO_PUBLICKEYBYTES -1760U +CRYPTO_PUBLICKEYBYTES size error +#endif +#if CRYPTO_SECRETKEYBYTES -3856U +CRYPTO_SECRETKEYBYTES size error +#endif +#if CRYPTO_BYTES -3366U +CRYPTO_BYTES size error +#endif + +#endif + +#define CRYPTO_ALGNAME "Dilithium" + +int crypto_sign_keypair(uint8_t *pk, uint8_t *sk); + +int crypto_sign(uint8_t *sm, int32_t *smlen, + const uint8_t *msg, int32_t len, + const uint8_t *sk); + +int crypto_sign_open(uint8_t *m, int32_t *mlen, + const uint8_t *sm, int32_t smlen, + const uint8_t *pk); + +#endif diff --git a/src/cc/makecclib b/src/cc/makecclib index f4d2bd01b..adac757c3 100755 --- a/src/cc/makecclib +++ b/src/cc/makecclib @@ -1,2 +1,2 @@ #!/bin/sh -gcc -std=c++11 -I../secp256k1/include -I../univalue/include -I../cryptoconditions/include -I../cryptoconditions/src -I../cryptoconditions/src/asn -I.. -I. -fPIC -shared -c -o ../libcc.so cclib.cpp +gcc -O3 -std=c++11 -I../secp256k1/include -I../univalue/include -I../cryptoconditions/include -I../cryptoconditions/src -I../cryptoconditions/src/asn -I.. -I. -fPIC -shared -c -o ../libcc.so cclib.cpp diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index bd3d74a95..6dbab482a 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -659,12 +659,12 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, partialsig")); } -int testmain(void); +//int testmain(void); UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; UniValue result(UniValue::VOBJ); int32_t i,n; uint8_t msg[32],musig64[64]; secp256k1_pubkey combined_pk; secp256k1_schnorrsig musig; char str[129]; - testmain(); + //testmain(); if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) From ad439274bd21d003280c35468f937ef152ceac35 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 21:07:37 -1100 Subject: [PATCH 060/132] include --- src/cc/cclib.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index 84f229069..c7372907e 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -581,7 +581,7 @@ uint256 juint256(cJSON *obj) #else #include "sudoku.cpp" #include "musig.cpp" -#inclide "dilithium.c" +#include "dilithium.c" //#include "../secp256k1/src/modules/musig/example.c" #endif From fc0b7b15c8f46618794734d27449f031acc8f34c Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 21:16:25 -1100 Subject: [PATCH 061/132] Revert to boost 1.66 --- depends/packages/boost.mk | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/depends/packages/boost.mk b/depends/packages/boost.mk index 7a0439ba7..3c180b0ce 100644 --- a/depends/packages/boost.mk +++ b/depends/packages/boost.mk @@ -1,8 +1,8 @@ package=boost -$(package)_version=1_69_0 -$(package)_download_path=https://dl.bintray.com/boostorg/release/1.69.0/source +$(package)_version=1_66_0 +$(package)_download_path=https://dl.bintray.com/boostorg/release/1.66.0/source $(package)_file_name=$(package)_$($(package)_version).tar.bz2 -$(package)_sha256_hash=8f32d4617390d1c2d16f26a27ab60d97807b35440d45891fa340fc2648b04406 +$(package)_sha256_hash=5721818253e6a0989583192f96782c4a98eb6204965316df9f5ad75819225ca9 define $(package)_set_vars $(package)_config_opts_release=variant=release From 33f126914ed4152f7832c660299980af972b847c Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 21:45:03 -1100 Subject: [PATCH 062/132] Dilithium key pair --- src/cc/cclib.cpp | 33 +++++++++++++++++++++++++++++++++ src/cc/dilithium.c | 39 +++++++++++++++++++++++++++++++++++++++ src/cc/dilithium.h | 9 +++++---- 3 files changed, 77 insertions(+), 4 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index c7372907e..46a5f4736 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -37,6 +37,7 @@ std::string MYCCLIBNAME = (char *)"rogue"; #define EVAL_SUDOKU 17 #define EVAL_MUSIG 18 +#define EVAL_DILITHIUM 19 std::string MYCCLIBNAME = (char *)"sudoku"; #endif @@ -80,6 +81,11 @@ CClib_methods[] = { (char *)"musig", (char *)"verify", (char *)"msg sig pubkey", 3, 3, 'V', EVAL_MUSIG }, { (char *)"musig", (char *)"send", (char *)"combined_pk amount", 2, 2, 'x', EVAL_MUSIG }, { (char *)"musig", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_MUSIG }, + { (char *)"dilithium", (char *)"keypair", (char *)"", 0, 0, 'K', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"sign", (char *)"msg privkey", 2, 2, 'S', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"verify", (char *)"msg sig pubtxid", 3, 3, 'V', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"send", (char *)"pubtxid amount", 2, 2, 'x', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_DILITHIUM }, #endif }; @@ -119,6 +125,13 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); + +UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); +UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); +UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); +UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); +UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); + #endif cJSON *cclib_reparse(int32_t *nump,char *jsonstr) // assumes origparams will be freed by caller @@ -243,6 +256,26 @@ UniValue CClib_method(struct CCcontract_info *cp,char *method,char *jsonstr) return(result); } } + else if ( cp->evalcode == EVAL_DILITHIUM ) + { + if ( strcmp(method,"send") == 0 ) + return(dilithium_send(txfee,cp,params)); + else if ( strcmp(method,"spend") == 0 ) + return(dilithium_spend(txfee,cp,params)); + else if ( strcmp(method,"keypair") == 0 ) + return(dilithium_keypair(txfee,cp,params)); + else if ( strcmp(method,"sign") == 0 ) + return(dilithium_sign(txfee,cp,params)); + else if ( strcmp(method,"verify") == 0 ) + return(dilithium_verify(txfee,cp,params)); + else + { + result.push_back(Pair("result","error")); + result.push_back(Pair("error","invalid dilithium method")); + result.push_back(Pair("method",method)); + return(result); + } + } #endif else { diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index b6624353e..902a3ca49 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2835,3 +2835,42 @@ int32_t main(void) } #endif +UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) +{ + UniValue result(UniValue::VOBJ); uint8_t pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i; + dilithium_keypair(pk,sk); + for (i=0; i +/* #ifndef CPUCYCLES_H #define CPUCYCLES_H @@ -11,7 +12,7 @@ #define DBENCH_STOP(t) #endif -#ifdef USE_RDPMC /* Needs echo 2 > /sys/devices/cpu/rdpmc */ +#ifdef USE_RDPMC // Needs echo 2 > /sys/devices/cpu/rdpmc #ifdef SERIALIZE_RDC static inline uint64_t cpucycles_start(void) { @@ -103,7 +104,7 @@ static inline uint64_t cpucycles_stop(void) { int64_t cpucycles_overhead(void); -#endif +#endif*/ #ifndef FIPS202_H #define FIPS202_H @@ -144,7 +145,7 @@ void shake256(uint8_t *output, #define PARAMS_H #ifndef MODE -#define MODE 2 +#define MODE 3 #endif #define SEEDBYTES 32U @@ -410,7 +411,7 @@ int crypto_sign_open(uint8_t *m, int32_t *mlen, #define API_H #ifndef MODE -#define MODE 2 +#define MODE 3 #endif #if MODE == 0 From 3846555d1914b38bb95455e3e2143bc1b427252f Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 21:46:51 -1100 Subject: [PATCH 063/132] Dbench start/stop --- src/cc/dilithium.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 902a3ca49..6a7f90d83 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -6,6 +6,10 @@ * by Gilles Van Assche, Daniel J. Bernstein, and Peter Schwabe */ #include + +#define DBENCH_START() +#define DBENCH_STOP() + #include "dilithium.h" From 54e28a8ebf715800b4d3436a1adf445f07760070 Mon Sep 17 00:00:00 2001 From: jl777 Date: Fri, 22 Feb 2019 21:48:26 -1100 Subject: [PATCH 064/132] Arg --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 6a7f90d83..cfe3b253f 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -8,7 +8,7 @@ #include #define DBENCH_START() -#define DBENCH_STOP() +#define DBENCH_STOP(arg) #include "dilithium.h" From 99f94425ebc6d1b1eedaaf50cb871092f97fc09e Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 03:18:52 -1100 Subject: [PATCH 065/132] +prints --- src/cc/dilithium.c | 22 ++++++++++++---------- src/cc/rogue_rpc.cpp | 9 ++++++--- 2 files changed, 18 insertions(+), 13 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index cfe3b253f..9103a6037 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2426,7 +2426,7 @@ void challenge(poly *c, } /************************************************* -* Name: dilithium_keypair +* Name: _dilithium_keypair * * Description: Generates public and private key. * @@ -2437,7 +2437,7 @@ void challenge(poly *c, * * Returns 0 (success) **************************************************/ -int dilithium_keypair(uint8_t *pk, uint8_t *sk) { +int _dilithium_keypair(uint8_t *pk, uint8_t *sk) { uint32_t i; uint8_t seedbuf[3*SEEDBYTES]; uint8_t tr[CRHBYTES]; @@ -2488,7 +2488,7 @@ int dilithium_keypair(uint8_t *pk, uint8_t *sk) { } /************************************************* -* Name: dilithium_sign +* Name: _dilithium_sign * * Description: Compute signed message. * @@ -2503,7 +2503,7 @@ int dilithium_keypair(uint8_t *pk, uint8_t *sk) { * * Returns 0 (success) **************************************************/ -int dilithium_sign(uint8_t *sm, +int _dilithium_sign(uint8_t *sm, int32_t *smlen, const uint8_t *m, int32_t mlen, @@ -2613,7 +2613,7 @@ int dilithium_sign(uint8_t *sm, } /************************************************* -* Name: dilithium_verify +* Name: _dilithium_verify * * Description: Verify signed message. * @@ -2626,7 +2626,7 @@ int dilithium_sign(uint8_t *sm, * * Returns 0 if signed message could be verified correctly and -1 otherwise **************************************************/ -int dilithium_verify(uint8_t *m, +int _dilithium_verify(uint8_t *m, int32_t *mlen, const uint8_t *sm, int32_t smlen, @@ -2785,7 +2785,7 @@ int32_t main(void) tkeygen[i] = cpucycles_start(); #endif - dilithium_keypair(pk, sk); // 1.3 + _dilithium_keypair(pk, sk); // 1.3 #ifdef DBENCH tkeygen[i] = cpucycles_stop() - tkeygen[i] - timing_overhead; // tred = tadd = tmul = tround = tsample = tpack = tshake = &dummy; @@ -2793,13 +2793,13 @@ int32_t main(void) #endif randombytes(m, MLEN); // 1.27 - dilithium_sign(sm, &smlen, m, MLEN, sk); // 7.2 + _dilithium_sign(sm, &smlen, m, MLEN, sk); // 7.2 #ifdef DBENCH tsign[i] = cpucycles_stop() - tsign[i] - timing_overhead; tverify[i] = cpucycles_start(); #endif - ret = dilithium_verify(m2, &mlen, sm, smlen, pk); + ret = _dilithium_verify(m2, &mlen, sm, smlen, pk); #ifdef DBENCH tverify[i] = cpucycles_stop() - tverify[i] - timing_overhead; #endif @@ -2842,7 +2842,7 @@ int32_t main(void) UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); uint8_t pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i; - dilithium_keypair(pk,sk); + _dilithium_keypair(pk,sk); for (i=0; i>16,endP.level,endP.experience,endP.dungeonlevel); fprintf(stderr,"%s\n",str); + *numkeysp = numkeys; + return(keystrokes); } else num = 0; } else fprintf(stderr,"extractgame: couldnt find baton\n"); } else fprintf(stderr,"extractgame: invalid game\n"); - *numkeysp = numkeys; - return(keystrokes); + return(0); } UniValue rogue_extract(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) From 504fed539e7b2d8759ebf72d13a4e1469affa649 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 03:30:44 -1100 Subject: [PATCH 066/132] +prints --- src/cc/rogue_rpc.cpp | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index edac1d813..fd068aca4 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -890,8 +890,15 @@ char *rogue_extractgame(int32_t makefiles,char *str,int32_t *numkeysp,std::vecto *numkeysp = numkeys; return(keystrokes); } else num = 0; - } else fprintf(stderr,"extractgame: couldnt find baton\n"); + } + else + { + fprintf(stderr,"extractgame: couldnt find baton keystrokes.%p\n",keystrokes); + if ( keystrokes != 0 ) + free(keystrokes), keystrokes = 0; + } } else fprintf(stderr,"extractgame: invalid game\n"); + fprintf(stderr,"extract %s\n",gametxid.GetHex().c_str()); return(0); } @@ -1248,6 +1255,7 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp //fprintf(stderr,"call extractgame\n"); if ( (keystrokes= rogue_extractgame(0,str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) { + fprintf(stderr,"numkeys.%d rogue_extractgame %s\n",numkeys,gametxid.GetHex().c_str()); free(keystrokes); //fprintf(stderr,"extracted.(%s)\n",str); if ( newdata == playerdata ) @@ -1273,6 +1281,7 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp fprintf(stderr,"%s playerdata: gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",gametxid.GetHex().c_str(),P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel); fprintf(stderr,"newdata[%d] != playerdata[%d], numkeys.%d %s pub.%s playertxid.%s good.%d bad.%d\n",(int32_t)newdata.size(),(int32_t)playerdata.size(),numkeys,rogueaddr,pubkey33_str(str2,(uint8_t *)&pk),playertxid.GetHex().c_str(),good,bad); } + fprintf(stderr,"no keys rogue_extractgame %s\n",gametxid.GetHex().c_str()); return(-1); } From 348d6df6a520382ef91be6e94d93e7dd60579865 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 03:40:13 -1100 Subject: [PATCH 067/132] -print --- src/cc/rogue_rpc.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index fd068aca4..5aa5b3a8d 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -898,7 +898,7 @@ char *rogue_extractgame(int32_t makefiles,char *str,int32_t *numkeysp,std::vecto free(keystrokes), keystrokes = 0; } } else fprintf(stderr,"extractgame: invalid game\n"); - fprintf(stderr,"extract %s\n",gametxid.GetHex().c_str()); + //fprintf(stderr,"extract %s\n",gametxid.GetHex().c_str()); return(0); } @@ -1255,7 +1255,7 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp //fprintf(stderr,"call extractgame\n"); if ( (keystrokes= rogue_extractgame(0,str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) { - fprintf(stderr,"numkeys.%d rogue_extractgame %s\n",numkeys,gametxid.GetHex().c_str()); + //fprintf(stderr,"numkeys.%d rogue_extractgame %s\n",numkeys,gametxid.GetHex().c_str()); free(keystrokes); //fprintf(stderr,"extracted.(%s)\n",str); if ( newdata == playerdata ) @@ -1281,7 +1281,7 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp fprintf(stderr,"%s playerdata: gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",gametxid.GetHex().c_str(),P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel); fprintf(stderr,"newdata[%d] != playerdata[%d], numkeys.%d %s pub.%s playertxid.%s good.%d bad.%d\n",(int32_t)newdata.size(),(int32_t)playerdata.size(),numkeys,rogueaddr,pubkey33_str(str2,(uint8_t *)&pk),playertxid.GetHex().c_str(),good,bad); } - fprintf(stderr,"no keys rogue_extractgame %s\n",gametxid.GetHex().c_str()); + //fprintf(stderr,"no keys rogue_extractgame %s\n",gametxid.GetHex().c_str()); return(-1); } From 09b5de739be060ae95474754497e4749adc65cfe Mon Sep 17 00:00:00 2001 From: CHMEX <33424502+CHMEX@users.noreply.github.com> Date: Sat, 23 Feb 2019 16:11:56 +0100 Subject: [PATCH 068/132] OUR OUR is notarized but missing. --- src/assetchains.json | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/src/assetchains.json b/src/assetchains.json index 1b23bc616..91baf9829 100644 --- a/src/assetchains.json +++ b/src/assetchains.json @@ -224,5 +224,21 @@ "addnode": [ "37.187.225.231" ] - } + }, + { + "ac_name": "OUR", + "ac_reward": "1478310502", + "ac_halving": "525600", + "ac_cc": "42", + "ac_supply": "100000000", + "ac_perc": "77700", + "ac_staked": "93", + "ac_pubkey": "02652a3f3e00b3a1875a918314f0bac838d6dd189a346fa623f5efe9541ac0b98c", + "ac_public": "1", + "addnode": [ + "51.255.195.65", + "217.182.129.38", + "95.216.150.177" + ] +} ] From 1b5d9b5032f41422113868eca35d182c07529f7e Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sat, 23 Feb 2019 23:24:17 +0800 Subject: [PATCH 069/132] show --- src/cc/musig.cpp | 106 +++++++++++++--------- src/musigtest.py | 189 +++++++++++++++++++++++++++++++++++++++ src/wallet/rpcwallet.cpp | 8 +- 3 files changed, 255 insertions(+), 48 deletions(-) create mode 100755 src/musigtest.py diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index bd3d74a95..cdf53be09 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -89,7 +89,7 @@ the "msg" is what needs to be signed to create a valid spend "numsigners": 2, "commitment": "bbea1f2562eca01b9a1393c5dc188bdd44551aebf684f4459930f59dde01f7ae", "result": "success" - } +} on node with pubkey: 0255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4 ./komodo-cli -ac_name=MUSIG cclib session 18 '[1,2,"03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b","5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b","f7fb85d1412814e3c2f98b990802af6ee33dad368c6ba05c2050e9e5506fcd75"]' @@ -221,7 +221,9 @@ struct musig_info secp256k1_musig_partial_signature *partial_sig; //[N_SIGNERS]; int32_t myind,num; uint8_t msg[32],pkhash[32],combpk[33]; -} *MUSIG; +}; + +std::vector MUSIG; struct musig_info *musig_infocreate(int32_t myind,int32_t num) { @@ -431,14 +433,15 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) num = juint(jitem(params,1),0); if ( myind < 0 || myind >= num || num <= 0 ) return(cclib_error(result,"illegal myindex and numsigners")); - if ( MUSIG != 0 ) - musig_infofree(MUSIG), MUSIG = 0; - MUSIG = musig_infocreate(myind,num); - if ( musig_parsepubkey(ctx,MUSIG->combined_pk,jitem(params,2)) < 0 ) + //if ( MUSIG[myind] != 0 ) + // musig_infofree(MUSIG[myind]), MUSIG[myind] = 0; + struct musig_info *temp_musig = musig_infocreate(myind,num); + MUSIG.push_back(temp_musig); + if ( musig_parsepubkey(ctx,MUSIG[myind]->combined_pk,jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing combined_pubkey")); - else if ( musig_parsehash(MUSIG->pkhash,jitem(params,3),32) < 0 ) + else if ( musig_parsehash(MUSIG[myind]->pkhash,jitem(params,3),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( musig_parsehash(MUSIG->msg,jitem(params,4),32) < 0 ) + else if ( musig_parsehash(MUSIG[myind]->msg,jitem(params,4),32) < 0 ) return(cclib_error(result,"error parsing msg")); Myprivkey(privkey); GetRandBytes(session,32); @@ -468,13 +471,13 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * my_index: index of this signer in the signers array * seckey: the signer's 32-byte secret key (cannot be NULL) */ - if ( secp256k1_musig_session_initialize(ctx,&MUSIG->session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) + if ( secp256k1_musig_session_initialize(ctx,&MUSIG[myind]->session,MUSIG[myind]->signer_data, &MUSIG[myind]->nonce_commitments[MUSIG[myind]->myind * 32],session,MUSIG[myind]->msg,&MUSIG[myind]->combined_pk,MUSIG[myind]->pkhash,MUSIG[myind]->num,MUSIG[myind]->myind,privkey) > 0 ) { memset(session,0,sizeof(session)); result.push_back(Pair("myind",(int64_t)myind)); result.push_back(Pair("numsigners",(int64_t)num)); for (i=0; i<32; i++) - sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitments[MUSIG->myind*32 + i]); + sprintf(&str[i<<1],"%02x",MUSIG[myind]->nonce_commitments[MUSIG[myind]->myind*32 + i]); str[64] = 0; result.push_back(Pair("commitment",str)); result.push_back(Pair("result","success")); @@ -492,18 +495,20 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; size_t clen = CPubKey::PUBLIC_KEY_SIZE; - UniValue result(UniValue::VOBJ); int32_t i,n,ind; uint8_t pkhash[32]; CPubKey pk; char str[67]; + UniValue result(UniValue::VOBJ); int32_t i,n,ind,myind; uint8_t pkhash[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 4 ) { - if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) + if ( (myind= juint(jitem(params,0),0)) < 0 ) + return(cclib_error(result,"myind is wrong")); + if ( musig_parsehash(pkhash,jitem(params,1),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG[myind]->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); - else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + else if ( (ind= juint(jitem(params,2),0)) < 0 || ind >= MUSIG[myind]->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash(&MUSIG->nonce_commitments[ind*32],jitem(params,2),32) < 0 ) + else if ( musig_parsehash(&MUSIG[myind]->nonce_commitments[ind*32],jitem(params,3),32) < 0 ) return(cclib_error(result,"error parsing commitment")); /** Gets the signer's public nonce given a list of all signers' data with commitments * @@ -521,14 +526,15 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * number of signers participating in the MuSig. */ result.push_back(Pair("added_index",ind)); - if ( secp256k1_musig_session_get_public_nonce(ctx,&MUSIG->session,MUSIG->signer_data,&MUSIG->nonces[MUSIG->myind],MUSIG->commitment_ptrs,MUSIG->num) > 0 ) + fprintf(stderr, "COMMIT: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); + if ( secp256k1_musig_session_get_public_nonce(ctx,&MUSIG[myind]->session,MUSIG[myind]->signer_data,&MUSIG[myind]->nonces[MUSIG[myind]->myind],MUSIG[myind]->commitment_ptrs,MUSIG[myind]->num) > 0 ) { - if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG->nonces[MUSIG->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) + if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG[myind]->nonces[MUSIG[myind]->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) { for (i=0; i<33; i++) sprintf(&str[i<<1],"%02x",((uint8_t *)pk.begin())[i]); str[66] = 0; - result.push_back(Pair("myind",MUSIG->myind)); + result.push_back(Pair("myind",MUSIG[myind]->myind)); result.push_back(Pair("nonce",str)); result.push_back(Pair("result","success")); } else return(cclib_error(result,"error serializing nonce (pubkey)")); @@ -539,26 +545,29 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) result.push_back(Pair("result","success")); } return(result); - } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, commitment")); + } else return(cclib_error(result,"wrong number of params, need 4: myind, pkhash, ind, commitment")); } UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t i,n,ind; uint8_t pkhash[32],psig[32]; CPubKey pk; char str[67]; + UniValue result(UniValue::VOBJ); int32_t i,n,ind,myind; uint8_t pkhash[32],psig[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 4 ) { - if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) + if ( (myind= juint(jitem(params,0),0)) < 0 ) + return(cclib_error(result,"myind is wrong")); + if ( musig_parsehash(pkhash,jitem(params,1),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG[myind]->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); - else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + else if ( (ind= juint(jitem(params,2),0)) < 0 || ind >= MUSIG[myind]->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsepubkey(ctx,MUSIG->nonces[ind],jitem(params,2)) < 0 ) + else if ( musig_parsepubkey(ctx,MUSIG[myind]->nonces[ind],jitem(params,3)) < 0 ) return(cclib_error(result,"error parsing nonce")); result.push_back(Pair("added_index",ind)); + fprintf(stderr, "NONCE: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); /** Checks a signer's public nonce against a commitment to said nonce, and update * data structure if they match * @@ -569,10 +578,16 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * been used with `musig_session_get_public_nonce` or initialized * with `musig_session_initialize_verifier`. * In: nonce: signer's alleged public nonce (cannot be NULL) - */ - for (i=0; inum; i++) + * + if ( ind != MUSIG[myind]->num-1 ) { - if ( secp256k1_musig_set_nonce(ctx,&MUSIG->signer_data[i],&MUSIG->nonces[i]) == 0 ) + fprintf(stderr, "ind.%i MUSIG[myind]->num.%i\n", ind, MUSIG[myind]->num); + return(cclib_error(result,"need rest of nonce's to continue")); + }*/ + for (i=0; inum; i++) + { + fprintf(stderr, "setting nonce for index.%i\n",i); + if ( secp256k1_musig_set_nonce(ctx,&MUSIG[myind]->signer_data[i],&MUSIG[myind]->nonces[i]) == 0 ) return(cclib_error(result,"error setting nonce")); } /** Updates a session with the combined public nonce of all signers. The combined @@ -593,45 +608,48 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * adaptor: point to add to the combined public nonce. If NULL, nothing is * added to the combined nonce. */ - if ( secp256k1_musig_session_combine_nonces(ctx,&MUSIG->session,MUSIG->signer_data,MUSIG->num,NULL,NULL) > 0 ) + if ( secp256k1_musig_session_combine_nonces(ctx,&MUSIG[myind]->session,MUSIG[myind]->signer_data,MUSIG[myind]->num,NULL,NULL) > 0 ) { - if ( secp256k1_musig_partial_sign(ctx,&MUSIG->session,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + if ( secp256k1_musig_partial_sign(ctx,&MUSIG[myind]->session,&MUSIG[myind]->partial_sig[MUSIG[myind]->myind]) > 0 ) { - if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG[myind]->partial_sig[MUSIG[myind]->myind]) > 0 ) { for (i=0; i<32; i++) sprintf(&str[i<<1],"%02x",psig[i]); str[64] = 0; - result.push_back(Pair("myind",MUSIG->myind)); + result.push_back(Pair("myind",MUSIG[myind]->myind)); result.push_back(Pair("partialsig",str)); result.push_back(Pair("result","success")); return(result); } else return(cclib_error(result,"error serializing partial sig")); } else return(cclib_error(result,"error making partial sig")); } else return(cclib_error(result,"error combining nonces")); - } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, nonce")); + } else return(cclib_error(result,"wrong number of params, need 4: myind, pkhash, ind, nonce")); } UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t i,ind,n; uint8_t pkhash[32],psig[32],out64[64]; char str[129]; secp256k1_schnorrsig sig; + UniValue result(UniValue::VOBJ); int32_t i,ind,myind,n; uint8_t pkhash[32],psig[32],out64[64]; char str[129]; secp256k1_schnorrsig sig; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 4 ) { - if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) + if ( (myind= juint(jitem(params,0),0)) < 0 ) + return(cclib_error(result,"myind is wrong")); + if ( musig_parsehash(pkhash,jitem(params,1),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG[myind]->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); - else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + else if ( (ind= juint(jitem(params,2),0)) < 0 || ind >= MUSIG[myind]->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash(psig,jitem(params,2),32) < 0 ) + else if ( musig_parsehash(psig,jitem(params,3),32) < 0 ) return(cclib_error(result,"error parsing psig")); - else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG->partial_sig[ind],psig) == 0 ) + else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG[myind]->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); result.push_back(Pair("added_index",ind)); - if ( secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) + fprintf(stderr, "PARTIALSIG: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); + if ( secp256k1_musig_partial_sig_combine(ctx,&MUSIG[myind]->session,&sig,MUSIG[myind]->partial_sig,MUSIG[myind]->num) > 0 ) { if ( secp256k1_schnorrsig_serialize(ctx,out64,&sig) > 0 ) { @@ -644,7 +662,7 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param } else { - if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG[myind]->partial_sig[MUSIG[myind]->myind]) > 0 ) { result.push_back(Pair("myind",ind)); for (i=0; i<32; i++) @@ -656,7 +674,7 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param } else return(cclib_error(result,"error generating my partialsig")); } return(result); - } else return(cclib_error(result,"wrong number of params, need 3: pkhash, ind, partialsig")); + } else return(cclib_error(result,"wrong number of params, need 4: myind, pkhash, ind, partialsig")); } int testmain(void); diff --git a/src/musigtest.py b/src/musigtest.py new file mode 100755 index 000000000..26f09d588 --- /dev/null +++ b/src/musigtest.py @@ -0,0 +1,189 @@ +#!/usr/bin/env python3 +import platform +import os +import re +import json +import random +import base58 +import binascii +import hashlib +import sys +import time +from slickrpc import Proxy + +# fucntion to define rpc_connection +def def_credentials(chain): + rpcport = ''; + operating_system = platform.system() + if operating_system == 'Darwin': + ac_dir = os.environ['HOME'] + '/Library/Application Support/Komodo' + elif operating_system == 'Linux': + ac_dir = os.environ['HOME'] + '/.komodo' + elif operating_system == 'Windows': + ac_dir = '%s/komodo/' % os.environ['APPDATA'] + if chain == 'KMD': + coin_config_file = str(ac_dir + '/komodo.conf') + else: + coin_config_file = str(ac_dir + '/' + chain + '/' + chain + '.conf') + with open(coin_config_file, 'r') as f: + for line in f: + l = line.rstrip() + if re.search('rpcuser', l): + rpcuser = l.replace('rpcuser=', '') + elif re.search('rpcpassword', l): + rpcpassword = l.replace('rpcpassword=', '') + elif re.search('rpcport', l): + rpcport = l.replace('rpcport=', '') + if len(rpcport) == 0: + if chain == 'KMD': + rpcport = 7771 + else: + print("rpcport not in conf file, exiting") + print("check " + coin_config_file) + exit(1) + return (Proxy("http://%s:%s@127.0.0.1:%d" % (rpcuser, rpcpassword, int(rpcport)))) + + +# generate address, validate address, dump private key +def genvaldump(rpc_connection): + # get new address + address = rpc_connection.getnewaddress() + # validate address + validateaddress_result = rpc_connection.validateaddress(address) + pubkey = validateaddress_result['pubkey'] + address = validateaddress_result['address'] + # dump private key for the address + privkey = rpc_connection.dumpprivkey(address) + # function output + output = [pubkey, privkey, address] + return(output) + +CHAIN = 'MUSIG' #sys.argv[1] + +rpc = def_credentials(CHAIN) + +pubkeys = [] +address_info = [] +ret = input('Do you want to generate new pubkeys? ').lower() + +if ret.startswith('y'): + numpks = int(input('Enter number of pubkeys to combine: ')) + if os.path.isfile("list.json"): + print('Already have list.json, move it if you would like to generate a new set.') + sys.exit(0) + while len(address_info) < numpks: + addressinfo = genvaldump(rpc) + address_info.append(addressinfo) + f = open("list.json", "w+") + f.write(json.dumps(address_info)) +else: + if os.path.isfile("list.json"): + with open('list.json') as list: + address_info = json.load(list) + else: + sys.exit('No list.json you need to create new pubkeys!') + +for addressinfo in address_info: + pubkeys.append(addressinfo[0]) + +ret = rpc.setpubkey(pubkeys[0]) +ret = rpc.cclib("combine", "18", str(pubkeys)) +pkhash = str(ret['pkhash']) +combinedpk = str(ret['combined_pk']) +print('Your combined pubkey is: ' + combinedpk) +print('Your pkhash is: ' + pkhash) +amount = int(input('Enter amount to send: ')) +tmp = str([combinedpk, amount]) +hex = rpc.cclib("send", "18", tmp)['hex'] +senttxid = rpc.sendrawtransaction(hex) +print('Your senttxid is: ' + senttxid) + +print("Waiting for tx to be confirmed") +while True: + confirmed = int(rpc.gettransaction(senttxid)["confirmations"]) + if not confirmed: + time.sleep(10) + else: + print('SentTX confirmed') + break + +scriptPubKey = rpc.getrawtransaction(senttxid,1)['vout'][1]['scriptPubKey']['hex'] +print('Your scriptPubKey is: ' + scriptPubKey) +tmp = str([senttxid, scriptPubKey]) +msg = rpc.cclib("calcmsg", "18", tmp)['msg'] +print('Your msg is: ' + msg) + +i = 0; +commitments = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + tmp = str([i, len(pubkeys), combinedpk, pkhash, msg]) + commitments.append(rpc.cclib("session", "18", tmp)['commitment']) + i = i + 1 + +print(commitments) + +i = 0 +nonces = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + n = 0 + for commitment in commitments: + if n == i: + n = n + 1 + continue; + tmp = str([i, pkhash, n, commitment]) + ret = rpc.cclib("commit", "18", tmp) + if len(ret) == 4: + nonces.append(ret['nonce']) + n = n + 1 + i = i + 1 + +print(nonces) + +i = 0 +partialsigs = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + n = 0 + for nonce in nonces: + #if n == i: + # n = n + 1 + # continue; + tmp = str([i, pkhash, n, nonce]) + ret = rpc.cclib("nonce", "18", tmp) + print(ret) + if len(ret) == 4: + partialsigs.append(ret['partialsig']) + n = n + 1 + i = i + 1 + +print(partialsigs) + +i = 0 +combinedsigs = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + n = 0 + for partialsig in partialsigs: + if n == i: + n = n + 1 + continue; + tmp = str([i, pkhash, n, partialsig]) + ret = rpc.cclib("partialsig", "18", tmp) + if len(ret) == 4: + combinedsigs.append(ret['combinedsig']) + n = n + 1 + i = i + 1 + +print(combinedsigs) + +tmp = str([msg, combinedpk, combinedsigs[0]]) +ret = rpc.cclib("verify", "18", tmp) + +print(ret) + +tmp = str([sendtxid, scriptPubKey, combinedsigs[0]]) +ret = rpc.cclib("spend", "18", tmp) + +print(ret) diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp index 0ed2f866c..8cffd78f7 100644 --- a/src/wallet/rpcwallet.cpp +++ b/src/wallet/rpcwallet.cpp @@ -5308,8 +5308,8 @@ UniValue setpubkey(const UniValue& params, bool fHelp) char Raddress[64]; uint8_t pubkey33[33]; - if ( NOTARY_PUBKEY33[0] == 0 ) - { + //if ( NOTARY_PUBKEY33[0] == 0 ) + //{ if (strlen(params[0].get_str().c_str()) == 66) { decode_hex(pubkey33,33,(char *)params[0].get_str().c_str()); @@ -5337,14 +5337,14 @@ UniValue setpubkey(const UniValue& params, bool fHelp) USE_EXTERNAL_PUBKEY = 1; } } else result.push_back(Pair("error", "pubkey is wrong length, must be 66 char hex string.")); - } + /*} else { result.push_back(Pair("error", "Can only set pubkey once, to change it you need to restart your daemon, pubkey in use is below.")); pubkey2addr((char *)Raddress,(uint8_t *)NOTARY_PUBKEY33); std::string address_ret; address_ret.assign(Raddress); result.push_back(Pair("address",address_ret)); - } + }*/ result.push_back(Pair("pubkey", NOTARY_PUBKEY)); return result; } From 69a890fe53bfa7d2025b8cebb6d3e5feed164c09 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 04:56:59 -1100 Subject: [PATCH 070/132] Seed based dilithium key generation --- src/cc/cclib.cpp | 2 +- src/cc/dilithium.c | 26 +++++++++++++++++++++----- 2 files changed, 22 insertions(+), 6 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index 46a5f4736..4f539b7f9 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -81,7 +81,7 @@ CClib_methods[] = { (char *)"musig", (char *)"verify", (char *)"msg sig pubkey", 3, 3, 'V', EVAL_MUSIG }, { (char *)"musig", (char *)"send", (char *)"combined_pk amount", 2, 2, 'x', EVAL_MUSIG }, { (char *)"musig", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_MUSIG }, - { (char *)"dilithium", (char *)"keypair", (char *)"", 0, 0, 'K', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"keypair", (char *)"[hexseed]", 0, 1, 'K', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"sign", (char *)"msg privkey", 2, 2, 'S', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"verify", (char *)"msg sig pubtxid", 3, 3, 'V', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"send", (char *)"pubtxid amount", 2, 2, 'x', EVAL_DILITHIUM }, diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 9103a6037..10718d1c3 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2437,7 +2437,8 @@ void challenge(poly *c, * * Returns 0 (success) **************************************************/ -int _dilithium_keypair(uint8_t *pk, uint8_t *sk) { +int _dilithium_keypair(uint8_t *pk, uint8_t *sk,uint8_t *privkey) +{ uint32_t i; uint8_t seedbuf[3*SEEDBYTES]; uint8_t tr[CRHBYTES]; @@ -2448,7 +2449,8 @@ int _dilithium_keypair(uint8_t *pk, uint8_t *sk) { polyveck s2, t, t1, t0; /* Expand 32 bytes of randomness into rho, rhoprime and key */ - randombytes(seedbuf, SEEDBYTES); + //randombytes(seedbuf, SEEDBYTES); + memcpy(seedbuf,privkey,SEEDBYTES); shake256(seedbuf, 3*SEEDBYTES, seedbuf, SEEDBYTES); rho = seedbuf; rhoprime = rho + SEEDBYTES; @@ -2841,8 +2843,16 @@ int32_t main(void) UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); uint8_t pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i; - _dilithium_keypair(pk,sk); + UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; + //randombytes(seed,SEEDBYTES); + Myprivkey(seed); + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 1 ) + { + if ( musig_parsehash(seed,jitem(params,0),32) < 0 ) + return(cclib_error(result,"error parsing seed")); + else externalflag = 1; + } + _dilithium_keypair(pk,sk,seed); for (i=0; i Date: Sat, 23 Feb 2019 05:06:29 -1100 Subject: [PATCH 071/132] Pkaddr and skaddr --- src/cc/dilithium.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 10718d1c3..87d55c35d 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2843,7 +2843,7 @@ int32_t main(void) UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; + UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr,str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; //randombytes(seed,SEEDBYTES); Myprivkey(seed); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 1 ) @@ -2865,6 +2865,12 @@ UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *para sprintf(&str[i<<1],"%02x",seed[i]); str[i<<1] = 0; result.push_back(Pair("seed",str)); + calc_rmd160_sha256(rmd160,pk,CRYPTO_PUBLICKEYBYTES); + bitcoin_address(coinaddr,38,rmd160,20); + result.push_back(Pair("pkaddr",coinaddr)); + calc_rmd160_sha256(rmd160,sk,CRYPTO_SECRETKEYBYTES); + bitcoin_address(coinaddr,188,rmd160,20); + result.push_back(Pair("skaddr",coinaddr)); if ( externalflag == 0 ) result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); result.push_back(Pair("result","success")); From 6cdadf77f0f9035e8c7b7020930974d4e8a57ddd Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 05:07:51 -1100 Subject: [PATCH 072/132] define --- src/cc/dilithium.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 87d55c35d..730e76faa 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2841,6 +2841,9 @@ int32_t main(void) } #endif +void calc_rmd160_sha256(uint8_t rmd160[20],uint8_t *data,int32_t datalen); +char *bitcoin_address(char *coinaddr,uint8_t addrtype,uint8_t *pubkey_or_rmd160,int32_t len); + UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr,str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; From d689598506cb4b9770bfe1081316a077d3b5d0eb Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 05:09:30 -1100 Subject: [PATCH 073/132] [64] --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 730e76faa..65c17c8fb 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2846,7 +2846,7 @@ char *bitcoin_address(char *coinaddr,uint8_t addrtype,uint8_t *pubkey_or_rmd160, UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr,str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; + UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr[64],str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; //randombytes(seed,SEEDBYTES); Myprivkey(seed); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 1 ) From 03920374e4a6ea93530affad1631456ae43271b5 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 05:12:08 -1100 Subject: [PATCH 074/132] Try to map base58 address to P... and S.. --- src/cc/dilithium.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 65c17c8fb..cfc482290 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2869,10 +2869,10 @@ UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *para str[i<<1] = 0; result.push_back(Pair("seed",str)); calc_rmd160_sha256(rmd160,pk,CRYPTO_PUBLICKEYBYTES); - bitcoin_address(coinaddr,38,rmd160,20); + bitcoin_address(coinaddr,55,rmd160,20); result.push_back(Pair("pkaddr",coinaddr)); calc_rmd160_sha256(rmd160,sk,CRYPTO_SECRETKEYBYTES); - bitcoin_address(coinaddr,188,rmd160,20); + bitcoin_address(coinaddr,63,rmd160,20); result.push_back(Pair("skaddr",coinaddr)); if ( externalflag == 0 ) result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); From b6990f5f5ef7fc5a40251583873c9cda76620bb4 Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sun, 24 Feb 2019 01:05:18 +0800 Subject: [PATCH 075/132] working single node multi sign --- src/cc/musig.cpp | 24 +++++++++++++++++------- src/musigtest.py | 38 ++++++++++++++++++++------------------ 2 files changed, 37 insertions(+), 25 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index cdf53be09..d50ee92d8 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -525,8 +525,13 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * n_commitments: the length of commitments and signers array. Must be the total * number of signers participating in the MuSig. */ + if ( ind != MUSIG[myind]->num-1 ) + { + //fprintf(stderr, "ind.%i MUSIG[myind]->num.%i\n", ind, MUSIG[myind]->num); + return(cclib_error(result,"need rest of nonce's to continue")); + } result.push_back(Pair("added_index",ind)); - fprintf(stderr, "COMMIT: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); + //fprintf(stderr, "COMMIT: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); if ( secp256k1_musig_session_get_public_nonce(ctx,&MUSIG[myind]->session,MUSIG[myind]->signer_data,&MUSIG[myind]->nonces[MUSIG[myind]->myind],MUSIG[myind]->commitment_ptrs,MUSIG[myind]->num) > 0 ) { if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG[myind]->nonces[MUSIG[myind]->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) @@ -567,7 +572,7 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) else if ( musig_parsepubkey(ctx,MUSIG[myind]->nonces[ind],jitem(params,3)) < 0 ) return(cclib_error(result,"error parsing nonce")); result.push_back(Pair("added_index",ind)); - fprintf(stderr, "NONCE: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); + //fprintf(stderr, "NONCE: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); /** Checks a signer's public nonce against a commitment to said nonce, and update * data structure if they match * @@ -578,15 +583,15 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * been used with `musig_session_get_public_nonce` or initialized * with `musig_session_initialize_verifier`. * In: nonce: signer's alleged public nonce (cannot be NULL) - * + */ if ( ind != MUSIG[myind]->num-1 ) { - fprintf(stderr, "ind.%i MUSIG[myind]->num.%i\n", ind, MUSIG[myind]->num); + //fprintf(stderr, "ind.%i MUSIG[myind]->num.%i\n", ind, MUSIG[myind]->num); return(cclib_error(result,"need rest of nonce's to continue")); - }*/ + } for (i=0; inum; i++) { - fprintf(stderr, "setting nonce for index.%i\n",i); + //fprintf(stderr, "setting nonce for index.%i\n",i); if ( secp256k1_musig_set_nonce(ctx,&MUSIG[myind]->signer_data[i],&MUSIG[myind]->nonces[i]) == 0 ) return(cclib_error(result,"error setting nonce")); } @@ -648,7 +653,12 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG[myind]->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); result.push_back(Pair("added_index",ind)); - fprintf(stderr, "PARTIALSIG: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); + //fprintf(stderr, "PARTIALSIG: number of MUSIG structs.%li using struct.%i addedindex.%i\n",MUSIG.size(),myind,ind); + if ( ind != MUSIG[myind]->num-1 ) + { + //fprintf(stderr, "ind.%i MUSIG[myind]->num.%i\n", ind, MUSIG[myind]->num); + return(cclib_error(result,"need rest of nonce's to continue")); + } if ( secp256k1_musig_partial_sig_combine(ctx,&MUSIG[myind]->session,&sig,MUSIG[myind]->partial_sig,MUSIG[myind]->num) > 0 ) { if ( secp256k1_schnorrsig_serialize(ctx,out64,&sig) > 0 ) diff --git a/src/musigtest.py b/src/musigtest.py index 26f09d588..9a28bb2d4 100755 --- a/src/musigtest.py +++ b/src/musigtest.py @@ -121,7 +121,7 @@ for pubkey in pubkeys: commitments.append(rpc.cclib("session", "18", tmp)['commitment']) i = i + 1 -print(commitments) +#print(commitments) i = 0 nonces = [] @@ -129,17 +129,16 @@ for pubkey in pubkeys: ret = rpc.setpubkey(pubkey) n = 0 for commitment in commitments: - if n == i: - n = n + 1 - continue; tmp = str([i, pkhash, n, commitment]) ret = rpc.cclib("commit", "18", tmp) - if len(ret) == 4: + try: nonces.append(ret['nonce']) + except: + x = 1 n = n + 1 i = i + 1 -print(nonces) +#print(nonces) i = 0 partialsigs = [] @@ -147,18 +146,17 @@ for pubkey in pubkeys: ret = rpc.setpubkey(pubkey) n = 0 for nonce in nonces: - #if n == i: - # n = n + 1 - # continue; tmp = str([i, pkhash, n, nonce]) ret = rpc.cclib("nonce", "18", tmp) print(ret) - if len(ret) == 4: + try: partialsigs.append(ret['partialsig']) + except: + x = 1 n = n + 1 i = i + 1 -print(partialsigs) +#print(partialsigs) i = 0 combinedsigs = [] @@ -166,24 +164,28 @@ for pubkey in pubkeys: ret = rpc.setpubkey(pubkey) n = 0 for partialsig in partialsigs: - if n == i: - n = n + 1 - continue; tmp = str([i, pkhash, n, partialsig]) ret = rpc.cclib("partialsig", "18", tmp) - if len(ret) == 4: + print(ret) + try: combinedsigs.append(ret['combinedsig']) + except: + x = 1 n = n + 1 i = i + 1 -print(combinedsigs) +#print(combinedsigs) tmp = str([msg, combinedpk, combinedsigs[0]]) ret = rpc.cclib("verify", "18", tmp) -print(ret) +#print(ret) -tmp = str([sendtxid, scriptPubKey, combinedsigs[0]]) +tmp = str([senttxid, scriptPubKey, combinedsigs[0]]) ret = rpc.cclib("spend", "18", tmp) print(ret) + +ret = rpc.sendrawtransaction(ret['hex']) + +print(ret) From d25a12fb8403d1041d9f0f9d9436de2ad9585095 Mon Sep 17 00:00:00 2001 From: ca333 Date: Sun, 24 Feb 2019 00:30:29 +0100 Subject: [PATCH 076/132] fix build --- src/Makefile.am | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/Makefile.am b/src/Makefile.am index fa2c17b5d..c32551c2c 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -578,7 +578,8 @@ komodod_LDADD += libcc.dylib $(LIBSECP256K1) endif if TARGET_WINDOWS komodod_LDADD += libcc.dll $(LIBSECP256K1) -else +endif +if TARGET_LINUX komodod_LDADD += libcc.so $(LIBSECP256K1) endif From 6722c9bc2063b72e2884493a3227741b8ce5418e Mon Sep 17 00:00:00 2001 From: ca333 Date: Sun, 24 Feb 2019 00:52:39 +0100 Subject: [PATCH 077/132] add linux target --- src/Makefile.am | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/Makefile.am b/src/Makefile.am index c32551c2c..f06de8910 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -36,7 +36,8 @@ LIBBITCOIN_SERVER=libbitcoin_server.a -lcurl endif if TARGET_DARWIN LIBBITCOIN_SERVER=libbitcoin_server.a -lcurl -else +endif +if TARGET_LINUX LIBBITCOIN_SERVER=libbitcoin_server.a -lcurl endif From 2968a6b6339d72618549759d444fd707a1dca673 Mon Sep 17 00:00:00 2001 From: ca333 Date: Sun, 24 Feb 2019 00:57:05 +0100 Subject: [PATCH 078/132] add linux target --- configure.ac | 1 + 1 file changed, 1 insertion(+) diff --git a/configure.ac b/configure.ac index 9a1a75f53..12256c0cc 100644 --- a/configure.ac +++ b/configure.ac @@ -884,6 +884,7 @@ fi AM_CONDITIONAL([TARGET_DARWIN], [test x$TARGET_OS = xdarwin]) AM_CONDITIONAL([BUILD_DARWIN], [test x$BUILD_OS = xdarwin]) +AM_CONDITIONAL([TARGET_LINUX], [test x$TARGET_OS = xlinux]) AM_CONDITIONAL([TARGET_WINDOWS], [test x$TARGET_OS = xwindows]) AM_CONDITIONAL([ENABLE_WALLET],[test x$enable_wallet = xyes]) AM_CONDITIONAL([ENABLE_MINING],[test x$enable_mining = xyes]) From 41c82bee96a9fc6f30f82e0e9d604d80d98d09c3 Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Sun, 24 Feb 2019 11:53:17 +0800 Subject: [PATCH 079/132] stop print flood --- src/musigtest.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/musigtest.py b/src/musigtest.py index 9a28bb2d4..0880f1494 100755 --- a/src/musigtest.py +++ b/src/musigtest.py @@ -148,7 +148,6 @@ for pubkey in pubkeys: for nonce in nonces: tmp = str([i, pkhash, n, nonce]) ret = rpc.cclib("nonce", "18", tmp) - print(ret) try: partialsigs.append(ret['partialsig']) except: @@ -166,7 +165,6 @@ for pubkey in pubkeys: for partialsig in partialsigs: tmp = str([i, pkhash, n, partialsig]) ret = rpc.cclib("partialsig", "18", tmp) - print(ret) try: combinedsigs.append(ret['combinedsig']) except: From 74070330f5b68c0e164af1b3e186ce118e7ed3c7 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 20:31:30 -1100 Subject: [PATCH 080/132] Lose 20% gold if killed, remove single player reduction of gold conversion --- src/cc/dilithium.c | 3 +++ src/cc/rogue_rpc.cpp | 29 ++++++++++++++++++----------- 2 files changed, 21 insertions(+), 11 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index cfc482290..996d4f2b1 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2877,6 +2877,7 @@ UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *para if ( externalflag == 0 ) result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); result.push_back(Pair("result","success")); + // make a tx that has pubkey in opreturn return(result); } @@ -2897,11 +2898,13 @@ UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *param UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); + // copy musig method return(result); } UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { UniValue result(UniValue::VOBJ); + // copy musig method return(result); } diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 5aa5b3a8d..8cfb4379f 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -882,8 +882,9 @@ char *rogue_extractgame(int32_t makefiles,char *str,int32_t *numkeysp,std::vecto } if ( endP.gold <= 0 || endP.hitpoints <= 0 || (endP.strength&0xffff) <= 0 || endP.level <= 0 || endP.experience <= 0 || endP.dungeonlevel <= 0 ) { - fprintf(stderr,"zero value character was killed -> no playerdata\n"); - newdata.resize(0); + //fprintf(stderr,"zero value character was killed -> no playerdata\n"); + //newdata.resize(0); + P.gold = (P.gold * 8) / 10; } sprintf(str,"extracted $$$gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",endP.gold,endP.hitpoints,endP.strength&0xffff,endP.strength>>16,endP.level,endP.experience,endP.dungeonlevel); fprintf(stderr,"%s\n",str); @@ -1018,22 +1019,23 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param newdata[i] = player[i]; ((uint8_t *)&P)[i] = player[i]; } - if ( 0 && (P.gold <= 0 || P.hitpoints <= 0 || (P.strength&0xffff) <= 0 || P.level <= 0 || P.experience <= 0 || P.dungeonlevel <= 0) ) + if ( (P.gold <= 0 || P.hitpoints <= 0 || (P.strength&0xffff) <= 0 || P.level <= 0 || P.experience <= 0 || P.dungeonlevel <= 0) ) { - fprintf(stderr,"zero value character was killed -> no playerdata\n"); - newdata.resize(0); + //fprintf(stderr,"zero value character was killed -> no playerdata\n"); + //newdata.resize(0); + P.gold = (P.gold * 8) / 10; } - else + //else { - if ( maxplayers == 1 ) - mult /= 2; + //if ( maxplayers == 1 ) + // mult /= 2; cpTokens = CCinit(&tokensC, EVAL_TOKENS); mtx.vout.push_back(MakeCC1vout(EVAL_TOKENS, txfee, GetUnspendable(cpTokens,NULL))); // marker to token cc addr, burnable and validated mtx.vout.push_back(MakeTokensCC1vout(cp->evalcode,1,mypk)); - fprintf(stderr,"\nextracted $$$gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d n.%d amulet.%d\n",P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel,n,P.amulet); if ( P.amulet != 0 ) mult *= 5; cashout = (uint64_t)P.gold * mult; + fprintf(stderr,"\nextracted $$$gold.%d -> %.8f ROGUE hp.%d strength.%d/%d level.%d exp.%d dl.%d n.%d amulet.%d\n",P.gold,(double)cashout/COIN,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel,n,P.amulet); if ( funcid == 'H' && maxplayers > 1 ) { if ( (numplayers != maxplayers || (numplayers - rogue_playersalive(tmp,gametxid,maxplayers)) > 1) && P.amulet == 0 ) @@ -1271,13 +1273,18 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp fprintf(stderr,"%s matched after clearing maxstrength good.%d bad.%d\n",gametxid.GetHex().c_str(),good,bad); return(0); } - bad++; for (i=0; i no playerdata\n"); + fprintf(stderr,"zero value character was killed -> no playerdata, good.%d bad.%d\n",good,bad); + if ( newdata.size() == 0 ) + { + good++; + return(0); + } } + bad++; fprintf(stderr,"%s playerdata: gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",gametxid.GetHex().c_str(),P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel); fprintf(stderr,"newdata[%d] != playerdata[%d], numkeys.%d %s pub.%s playertxid.%s good.%d bad.%d\n",(int32_t)newdata.size(),(int32_t)playerdata.size(),numkeys,rogueaddr,pubkey33_str(str2,(uint8_t *)&pk),playertxid.GetHex().c_str(),good,bad); } From 4220a1cc929d39b00674849fb1d6e4c928c2fb37 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:07:14 -1100 Subject: [PATCH 081/132] Dilithium register, sign, verify rpc calls --- src/cc/cclib.cpp | 28 ++++++- src/cc/dilithium.c | 197 ++++++++++++++++++++++++++++++++++++++------- src/cc/musig.cpp | 47 +++-------- 3 files changed, 206 insertions(+), 66 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index 4f539b7f9..20cc8ee32 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -82,8 +82,9 @@ CClib_methods[] = { (char *)"musig", (char *)"send", (char *)"combined_pk amount", 2, 2, 'x', EVAL_MUSIG }, { (char *)"musig", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_MUSIG }, { (char *)"dilithium", (char *)"keypair", (char *)"[hexseed]", 0, 1, 'K', EVAL_DILITHIUM }, - { (char *)"dilithium", (char *)"sign", (char *)"msg privkey", 2, 2, 'S', EVAL_DILITHIUM }, - { (char *)"dilithium", (char *)"verify", (char *)"msg sig pubtxid", 3, 3, 'V', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"register", (char *)"handle, [hexseed]", 1, 2, 'R', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"sign", (char *)"msg [hexseed]", 1, 2, 'S', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"verify", (char *)"pubtxid msg sig", 3, 3, 'V', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"send", (char *)"pubtxid amount", 2, 2, 'x', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_DILITHIUM }, #endif @@ -126,6 +127,7 @@ UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); +UniValue dilithium_register(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); @@ -264,6 +266,8 @@ UniValue CClib_method(struct CCcontract_info *cp,char *method,char *jsonstr) return(dilithium_spend(txfee,cp,params)); else if ( strcmp(method,"keypair") == 0 ) return(dilithium_keypair(txfee,cp,params)); + else if ( strcmp(method,"register") == 0 ) + return(dilithium_register(txfee,cp,params)); else if ( strcmp(method,"sign") == 0 ) return(dilithium_sign(txfee,cp,params)); else if ( strcmp(method,"verify") == 0 ) @@ -573,6 +577,26 @@ uint256 juint256(cJSON *obj) return(revuint256(tmp)); } +int32_t cclib_parsepubkey(secp256k1_context *ctx,secp256k1_pubkey &spk,cJSON *item) +{ + char *hexstr; + if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == 66 ) + { + CPubKey pk(ParseHex(hexstr)); + if ( secp256k1_ec_pubkey_parse(ctx,&spk,pk.begin(),33) > 0 ) + return(1); + } else return(-1); +} + +int32_t cclib_parsehash(uint8_t *hash32,cJSON *item,int32_t len) +{ + char *hexstr; + if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == len*2 ) + { + decode_hex(hash32,len,hexstr); + return(0); + } else return(-1); +} #ifdef BUILD_ROGUE #include "rogue_rpc.cpp" diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 996d4f2b1..5881d0840 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2841,58 +2841,195 @@ int32_t main(void) } #endif +#define DILITHIUM_TXFEE 10000 + void calc_rmd160_sha256(uint8_t rmd160[20],uint8_t *data,int32_t datalen); char *bitcoin_address(char *coinaddr,uint8_t addrtype,uint8_t *pubkey_or_rmd160,int32_t len); +CScript dilithium_registeropret(std::string handle,CPubKey pk,std::vector bigpub) +{ + CScript opret; uint8_t evalcode = EVAL_DILITHIUM; + opret << OP_RETURN << E_MARSHAL(ss << evalcode << 'R' << handle << pk << bigpub); + return(opret); +} + +uint8_t dilithium_registeropretdecode(std::string &handle,CPubKey &pk,std::vector &bigpub,CScript scriptPubKey) +{ + std::vector vopret; uint8_t e,f; + GetOpReturnData(scriptPubKey,vopret); + if ( vopret.size() > 2 && E_UNMARSHAL(vopret,ss >> e; ss >> f; ss >> handle; ss >> pk; ss >> bigpub) != 0 && e == EVAL_DILITHIUM && f == 'R' ) + { + return(f); + } + return(0); +} + +UniValue dilithium_rawtxresult(UniValue &result,std::string rawtx) +{ + CTransaction tx; + if ( rawtx.size() > 0 ) + { + result.push_back(Pair("hex",rawtx)); + if ( DecodeHexTx(tx,rawtx) != 0 ) + { + //if ( broadcastflag != 0 && myAddtomempool(tx) != 0 ) + // RelayTransaction(tx); + result.push_back(Pair("txid",tx.GetHash().ToString())); + result.push_back(Pair("result","success")); + } else result.push_back(Pair("error","decode hex")); + } else result.push_back(Pair("error","couldnt finalize CCtx")); + return(result); +} + +char *dilithium_addr(char *coinaddr,uint8_t *buf,int32_t len) +{ + uint8_t rmd160[20],addrtype; + if ( len == CRYPTO_PUBLICKEYBYTES ) + addrtype = 55; + else if ( len == CRYPTO_SECRETKEYBYTES ) + addrtype = 63; + else + { + strcpy(coinaddr,"unexpected len.%d",len); + return(coinaddr); + } + calc_rmd160_sha256(rmd160,buf,len); + bitcoin_address(coinaddr,addrtype,rmd160,20); + return(coinaddr); +} + +char *dilithium_hexstr(char *str,uint8_t *buf,int32_t len) +{ + int32_t i; + for (i=0; i bigpub; + if ( myGetTransaction(pubtxid,tx,hashBlock) != 0 && (numvouts= tx.vout.size()) > 1 ) + { + if ( dilithium_registeropretdecode(handle,pk33,bigpub,tx.vout[numvouts-1].scriptPubKey) == 'R' && bigpub.size() == CRYPTO_PUBLICKEYBYTES ) + { + memcpy(pk,&bigpub[0],CRYPTO_PUBLICKEYBYTES); + return(0); + } else return(-2); + } + return(-1); +} + UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr[64],str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; - //randombytes(seed,SEEDBYTES); + UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr[64],str[CRYPTO_SECRETKEYBYTES*2+1]; int32_t i,n,externalflag=0; Myprivkey(seed); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 1 ) { - if ( musig_parsehash(seed,jitem(params,0),32) < 0 ) - return(cclib_error(result,"error parsing seed")); - else externalflag = 1; + if ( cclib_parsehash(seed,jitem(params,0),32) < 0 ) + { + randombytes(seed,SEEDBYTES); + result.push_back(Pair("status","using random high entropy seed")); + } + externalflag = 1; } _dilithium_keypair(pk,sk,seed); - for (i=0; i bigpub; int32_t i,n,warningflag = 0; + if ( txfee == 0 ) + txfee = DILITHIUM_TXFEE; + mypk = pubkey2pk(Mypubkey()); + dilithiumpk = GetUnspendable(cp,0); + if ( params != 0 && ((n= cJSON_GetArraySize(params)) == 1 || n == 2) ) + { + std::string handle(jstr(jitem(params,0),0)); + result.push_back(Pair("handle",handle)); + if ( n == 2 || cclib_parsehash(seed,jitem(params,1),32) < 0 ) + { + Myprivkey(seed); + result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); + } + _dilithium_keypair(pk,sk,seed); + result.push_back(Pair("seed",dilithium_hexstr(str,seed,SEEDBYTES))); + result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); + result.push_back(Pair("skaddr",dilithium_addr(coinaddr,sk,CRYPTO_SECRETKEYBYTES))); + for (i=0; i= 3*txfee ) + { + mtx.vout.push_back(MakeCC1vout(cp->evalcode,txfee,dilithiumpk)); + mtx.vout.push_back(MakeCC1vout(cp->evalcode,txfee,mypk)); + rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_registeropret('R',handle,mypk,bigpub)); + return(musig_rawtxresult(result,rawtx)); + } else return(cclib_error(result,"couldnt find enough funds")); + } else return(cclib_error(result,"not enough parameters")); +} + UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); - //_dilithium_sign(sm, &smlen, m, MLEN, sk); // 7.2 - - return(result); + UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],msg[32],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1],sm[32+CRYPTO_BYTES]; int32_t n,smlen; + if ( params != 0 && ((n= cJSON_GetArraySize(params)) == 1 || n == 2) ) + { + if ( cclib_parsehash(msg,jitem(params,0),32) < 0 ) + return(cclib_error(result,"couldnt parse message to sign")); + else if ( n == 2 || cclib_parsehash(seed,jitem(params,1),32) < 0 ) + { + Myprivkey(seed); + result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); + } + _dilithium_keypair(pk,sk,seed); + result.push_back(Pair("msg32",dilithium_hexstr(str,msg,32))); + result.push_back(Pair("seed",dilithium_hexstr(str,seed,SEEDBYTES))); + result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); + result.push_back(Pair("skaddr",dilithium_addr(coinaddr,sk,CRYPTO_SECRETKEYBYTES))); + _dilithium_sign(sm,&smlen,msg,32,sk); + if ( smlen == 32+CRYPTO_BYTES ) + { + result.push_back(Pair("signature",dilithium_hexstr(str,sm,smlen))); + calc_rmd160_sha256(rmd160,sm,smlen); + result.push_back(Pair("sighash",dilithium_hexstr(str,rmd160,20))); + } else return(cclib_error(result,"unexpected signed message len")); + } else return(cclib_error(result,"not enough parameters")); } UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); - return(result); + UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1],sm[32+CRYPTO_BYTES]; int32_t mlen,n; + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + { + pubtxid = juint256(jitem(params,0)); + if ( dilithium_bigpubget(handle,pk33,pk,pubtxid) < 0 ) + return(cclib_error(result,"couldnt parse message to sign")); + else if ( cclib_parsehash(msg,jitem(params,1),32) < 0 ) + return(cclib_error(result,"couldnt parse message to sign")); + else if ( cclib_parsehash(sm,jitem(params,2),32+CRYPTO_BYTES) < 0 ) + return(cclib_error(result,"couldnt parse sig")); + else if ( _dilithium_verify(msg2,&mlen,sm,smlen,pk) < 0 ) + return(cclib_error(result,"dilithium verify error")); + else if ( mlen != 32 ) + return(cclib_error(result,"message len mismatch")); + else if ( memcmp(msg2,msg,32) != 0 ) + return(cclib_error(result,"message content mismatch")); + result.push_back(Pair("msg32",dilithium_hexstr(str,msg,32))); + result.push_back(Pair("handle",handle)); + result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); + result.push_back(Pair("result","success")); + return(result); + } else return(cclib_error(result,"not enough parameters")); } UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 6dbab482a..f4ba51d47 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -362,27 +362,6 @@ UniValue musig_calcmsg(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) } else return(cclib_error(result,"couldnt parse params")); } -int32_t musig_parsepubkey(secp256k1_context *ctx,secp256k1_pubkey &spk,cJSON *item) -{ - char *hexstr; - if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == 66 ) - { - CPubKey pk(ParseHex(hexstr)); - if ( secp256k1_ec_pubkey_parse(ctx,&spk,pk.begin(),33) > 0 ) - return(1); - } else return(-1); -} - -int32_t musig_parsehash(uint8_t *hash32,cJSON *item,int32_t len) -{ - char *hexstr; - if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == len*2 ) - { - decode_hex(hash32,len,hexstr); - return(0); - } else return(-1); -} - UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; @@ -395,7 +374,7 @@ UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) //fprintf(stderr,"n.%d args.(%s)\n",n,jprint(params,0)); for (i=0; icombined_pk,jitem(params,2)) < 0 ) + if ( cclib_parsepubkey(ctx,MUSIG->combined_pk,jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing combined_pubkey")); - else if ( musig_parsehash(MUSIG->pkhash,jitem(params,3),32) < 0 ) + else if ( cclib_parsehash(MUSIG->pkhash,jitem(params,3),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( musig_parsehash(MUSIG->msg,jitem(params,4),32) < 0 ) + else if ( cclib_parsehash(MUSIG->msg,jitem(params,4),32) < 0 ) return(cclib_error(result,"error parsing msg")); Myprivkey(privkey); GetRandBytes(session,32); @@ -497,13 +476,13 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) + if ( cclib_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash(&MUSIG->nonce_commitments[ind*32],jitem(params,2),32) < 0 ) + else if ( cclib_parsehash(&MUSIG->nonce_commitments[ind*32],jitem(params,2),32) < 0 ) return(cclib_error(result,"error parsing commitment")); /** Gets the signer's public nonce given a list of all signers' data with commitments * @@ -550,13 +529,13 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) + if ( cclib_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsepubkey(ctx,MUSIG->nonces[ind],jitem(params,2)) < 0 ) + else if ( cclib_parsepubkey(ctx,MUSIG->nonces[ind],jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing nonce")); result.push_back(Pair("added_index",ind)); /** Checks a signer's public nonce against a commitment to said nonce, and update @@ -620,13 +599,13 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - if ( musig_parsehash(pkhash,jitem(params,0),32) < 0 ) + if ( cclib_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsehash(psig,jitem(params,2),32) < 0 ) + else if ( cclib_parsehash(psig,jitem(params,2),32) < 0 ) return(cclib_error(result,"error parsing psig")); else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); @@ -669,11 +648,11 @@ UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { - if ( musig_parsehash(msg,jitem(params,0),32) < 0 ) + if ( cclib_parsehash(msg,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( musig_parsepubkey(ctx,combined_pk,jitem(params,1)) < 0 ) + else if ( cclib_parsepubkey(ctx,combined_pk,jitem(params,1)) < 0 ) return(cclib_error(result,"error parsing combined_pk")); - else if ( musig_parsehash(musig64,jitem(params,2),64) < 0 ) + else if ( cclib_parsehash(musig64,jitem(params,2),64) < 0 ) return(cclib_error(result,"error parsing musig64")); for (i=0; i<32; i++) sprintf(&str[i*2],"%02x",msg[i]); From 4551484dc3da7d4fcc47e52fdc904da31ed4ff6b Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:09:23 -1100 Subject: [PATCH 082/132] Revert musig_parsepubkey --- src/cc/cclib.cpp | 11 ----------- src/cc/musig.cpp | 19 +++++++++++++++---- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index 20cc8ee32..8382ba8a0 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -577,17 +577,6 @@ uint256 juint256(cJSON *obj) return(revuint256(tmp)); } -int32_t cclib_parsepubkey(secp256k1_context *ctx,secp256k1_pubkey &spk,cJSON *item) -{ - char *hexstr; - if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == 66 ) - { - CPubKey pk(ParseHex(hexstr)); - if ( secp256k1_ec_pubkey_parse(ctx,&spk,pk.begin(),33) > 0 ) - return(1); - } else return(-1); -} - int32_t cclib_parsehash(uint8_t *hash32,cJSON *item,int32_t len) { char *hexstr; diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index f4ba51d47..d93792463 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -304,6 +304,17 @@ uint8_t musig_spendopretdecode(CPubKey &pk,std::vector &musig64,CScript return(0); } +int32_t musig_parsepubkey(secp256k1_context *ctx,secp256k1_pubkey &spk,cJSON *item) +{ + char *hexstr; + if ( (hexstr= jstr(item,0)) != 0 && is_hexstr(hexstr,0) == 66 ) + { + CPubKey pk(ParseHex(hexstr)); + if ( secp256k1_ec_pubkey_parse(ctx,&spk,pk.begin(),33) > 0 ) + return(1); + } else return(-1); +} + int32_t musig_msghash(uint8_t *msg,uint256 prevhash,int32_t prevn,CTxOut vout,CPubKey pk) { CScript data; uint256 hash; int32_t len = 0; @@ -374,7 +385,7 @@ UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) //fprintf(stderr,"n.%d args.(%s)\n",n,jprint(params,0)); for (i=0; icombined_pk,jitem(params,2)) < 0 ) + if ( musig_parsepubkey(ctx,MUSIG->combined_pk,jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing combined_pubkey")); else if ( cclib_parsehash(MUSIG->pkhash,jitem(params,3),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); @@ -535,7 +546,7 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) return(cclib_error(result,"pkhash doesnt match session pkhash")); else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) return(cclib_error(result,"illegal ind for session")); - else if ( cclib_parsepubkey(ctx,MUSIG->nonces[ind],jitem(params,2)) < 0 ) + else if ( musig_parsepubkey(ctx,MUSIG->nonces[ind],jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing nonce")); result.push_back(Pair("added_index",ind)); /** Checks a signer's public nonce against a commitment to said nonce, and update @@ -650,7 +661,7 @@ UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { if ( cclib_parsehash(msg,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( cclib_parsepubkey(ctx,combined_pk,jitem(params,1)) < 0 ) + else if ( musig_parsepubkey(ctx,combined_pk,jitem(params,1)) < 0 ) return(cclib_error(result,"error parsing combined_pk")); else if ( cclib_parsehash(musig64,jitem(params,2),64) < 0 ) return(cclib_error(result,"error parsing musig64")); From 89d221c232400573fe5231d292b4fa8cf3c1d28d Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:10:45 -1100 Subject: [PATCH 083/132] Syntax --- src/cc/dilithium.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 5881d0840..46b05cc50 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2890,7 +2890,7 @@ char *dilithium_addr(char *coinaddr,uint8_t *buf,int32_t len) addrtype = 63; else { - strcpy(coinaddr,"unexpected len.%d",len); + sprintf(coinaddr,"unexpected len.%d",len); return(coinaddr); } calc_rmd160_sha256(rmd160,buf,len); @@ -2968,12 +2968,12 @@ UniValue dilithium_register(uint64_t txfee,struct CCcontract_info *cp,cJSON *par result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); result.push_back(Pair("skaddr",dilithium_addr(coinaddr,sk,CRYPTO_SECRETKEYBYTES))); for (i=0; i= 3*txfee ) { mtx.vout.push_back(MakeCC1vout(cp->evalcode,txfee,dilithiumpk)); mtx.vout.push_back(MakeCC1vout(cp->evalcode,txfee,mypk)); - rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_registeropret('R',handle,mypk,bigpub)); + rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_registeropret(handle,mypk,bigpub)); return(musig_rawtxresult(result,rawtx)); } else return(cclib_error(result,"couldnt find enough funds")); } else return(cclib_error(result,"not enough parameters")); From 2eec7b0bfb696b06988427609a621e5e1f720b53 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:12:20 -1100 Subject: [PATCH 084/132] Syntax --- src/cc/dilithium.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 46b05cc50..c7ab0d4cb 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2981,7 +2981,7 @@ UniValue dilithium_register(uint64_t txfee,struct CCcontract_info *cp,cJSON *par UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],msg[32],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1],sm[32+CRYPTO_BYTES]; int32_t n,smlen; + UniValue result(UniValue::VOBJ); uint8_t seed[SEEDBYTES],msg[32],rmd160[20],pk[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES],sm[32+CRYPTO_BYTES]; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t n,smlen; if ( params != 0 && ((n= cJSON_GetArraySize(params)) == 1 || n == 2) ) { if ( cclib_parsehash(msg,jitem(params,0),32) < 0 ) @@ -3008,7 +3008,7 @@ UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1],sm[32+CRYPTO_BYTES]; int32_t mlen,n; + UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1],sm[32+CRYPTO_BYTES]; int32_t mlen,n; std::string handle; if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { pubtxid = juint256(jitem(params,0)); From cdd14fd61a312a61d7b3d8dcdf252bd27c717e1e Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:13:13 -1100 Subject: [PATCH 085/132] uint8 --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index c7ab0d4cb..e4a7e24ac 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3008,7 +3008,7 @@ UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1],sm[32+CRYPTO_BYTES]; int32_t mlen,n; std::string handle; + UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES],sm[32+CRYPTO_BYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t mlen,n; std::string handle; if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { pubtxid = juint256(jitem(params,0)); From 4acaa5e7fb546c3ae5d0201c1f3a8ff881025e5f Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:14:10 -1100 Subject: [PATCH 086/132] Smell --- src/cc/dilithium.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index e4a7e24ac..59f53e829 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3008,7 +3008,7 @@ UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES],sm[32+CRYPTO_BYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t mlen,n; std::string handle; + UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES],sm[32+CRYPTO_BYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t smlen=32+CRYPTO_BYTES,mlen,n; std::string handle; if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { pubtxid = juint256(jitem(params,0)); @@ -3016,7 +3016,7 @@ UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *param return(cclib_error(result,"couldnt parse message to sign")); else if ( cclib_parsehash(msg,jitem(params,1),32) < 0 ) return(cclib_error(result,"couldnt parse message to sign")); - else if ( cclib_parsehash(sm,jitem(params,2),32+CRYPTO_BYTES) < 0 ) + else if ( cclib_parsehash(sm,jitem(params,2),smlen) < 0 ) return(cclib_error(result,"couldnt parse sig")); else if ( _dilithium_verify(msg2,&mlen,sm,smlen,pk) < 0 ) return(cclib_error(result,"dilithium verify error")); From 27564336b7c94232b7c1819db73404c25f826b37 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:25:28 -1100 Subject: [PATCH 087/132] Off by one --- src/cc/dilithium.c | 30 +++++++++++++++++++++++++----- 1 file changed, 25 insertions(+), 5 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 59f53e829..d8fcef08c 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2841,6 +2841,28 @@ int32_t main(void) } #endif +////////////////////////////////////////////////////// +/* First register a pubkey,ie. bind handle, pub33 and bigpub together and then can be referred by pubtxid in other calls + + cclib register 19 \"[%22jl777%22]\" + { + "handle": "jl777", + "warning": "test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!", + "pkaddr": "PNoTcVH8G5TBTQigyVZTsaMMNYYRvywUNu", + "skaddr": "SejsccjwGrZKaziD1kpfgQhXA32xvzP75i", + "hex": "0400008085202f89010184fa95fce1a13d441e6c87631f7d0ca5f22ad8b28ae4321e02177b125b5f2400000000494830450221009fb8ff0ea4e810f34e54f0a872952f364e6eb697bb4ab34ea571fd213299b685022017c0b09fc71ec2d2abf49e435a72d32ecc874d14aac39be7b9753704fad7d06c01ffffffff041027000000000000302ea22c8020979f9b424db4e028cdba433622c6cd17b9193763e68b4572cd7f3727dcd335978....00000000000", + "txid": "9d856b2be6e54c8f04ae3f86aef722b0535180b3e9eb926c53740e481a1715f9", + "result": "success" + } + + sendrawtransaction from above -> pubtxid 9d856b2be6e54c8f04ae3f86aef722b0535180b3e9eb926c53740e481a1715f9 + + now test signing some random 32 byte message + + cclib sign 19 \"[%22aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848%22]\" + + */ + #define DILITHIUM_TXFEE 10000 void calc_rmd160_sha256(uint8_t rmd160[20],uint8_t *data,int32_t datalen); @@ -2931,13 +2953,13 @@ UniValue dilithium_keypair(uint64_t txfee,struct CCcontract_info *cp,cJSON *para { randombytes(seed,SEEDBYTES); result.push_back(Pair("status","using random high entropy seed")); + result.push_back(Pair("seed",dilithium_hexstr(str,seed,SEEDBYTES))); } externalflag = 1; } _dilithium_keypair(pk,sk,seed); result.push_back(Pair("pubkey",dilithium_hexstr(str,pk,CRYPTO_PUBLICKEYBYTES))); result.push_back(Pair("privkey",dilithium_hexstr(str,sk,CRYPTO_SECRETKEYBYTES))); - result.push_back(Pair("seed",dilithium_hexstr(str,seed,SEEDBYTES))); result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); result.push_back(Pair("skaddr",dilithium_addr(coinaddr,sk,CRYPTO_SECRETKEYBYTES))); if ( externalflag == 0 ) @@ -2958,13 +2980,12 @@ UniValue dilithium_register(uint64_t txfee,struct CCcontract_info *cp,cJSON *par { std::string handle(jstr(jitem(params,0),0)); result.push_back(Pair("handle",handle)); - if ( n == 2 || cclib_parsehash(seed,jitem(params,1),32) < 0 ) + if ( n == 1 || cclib_parsehash(seed,jitem(params,1),32) < 0 ) { Myprivkey(seed); result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); } _dilithium_keypair(pk,sk,seed); - result.push_back(Pair("seed",dilithium_hexstr(str,seed,SEEDBYTES))); result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); result.push_back(Pair("skaddr",dilithium_addr(coinaddr,sk,CRYPTO_SECRETKEYBYTES))); for (i=0; i Date: Sat, 23 Feb 2019 22:26:39 -1100 Subject: [PATCH 088/132] Return result --- src/cc/dilithium.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index d8fcef08c..35902f266 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3022,6 +3022,7 @@ UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) result.push_back(Pair("signature",dilithium_hexstr(str,sm,smlen))); calc_rmd160_sha256(rmd160,sm,smlen); result.push_back(Pair("sighash",dilithium_hexstr(str,rmd160,20))); + return(result); } else return(cclib_error(result,"unexpected signed message len")); } else return(cclib_error(result,"not enough parameters")); } From a0ece6b680f0bdb5a9742d4d7552ba1454e9fd08 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:31:29 -1100 Subject: [PATCH 089/132] Add sighash for easy compare --- src/cc/dilithium.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 35902f266..a60c63527 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2860,7 +2860,18 @@ int32_t main(void) now test signing some random 32 byte message cclib sign 19 \"[%22aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848%22]\" + { + "warning": "test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!", + "msg32": "aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848", + "pkaddr": "PNoTcVH8G5TBTQigyVZTsaMMNYYRvywUNu", + "skaddr": "SejsccjwGrZKaziD1kpfgQhXA32xvzP75i", + "signature": "be067f4bd81b9b0b772e0e2872cc086f6c2ff4c558a465afe80ab71c2c7b39a25ad8300629337c022d8c477cf7728cd11a3f6135bccfdbd68de5cd4517e70a70ec3b836041dc9c2f1abed65f2519e43a31ca6ad4991ce98460a14ee70d28c47f5a1d967c25b1ac93afea7e2b11...836b0f0efbcb26ee679f4f4848", + "sighash": "cfed6d7f059b87635bde6cb31accd736bf99ff3d" + } + it is a very big signature, but that seems to be dilithium sig size. let us verify it: + + cclib verify 19 \"[%229d856b2be6e54c8f04ae3f86aef722b0535180b3e9eb926c53740e481a1715f9%22,%22aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848%22,%22be067f4bd81b9b0b772e0e2872cc086f6c2ff4c558a465afe80ab71c2c7b39a25ad8300629337c022d8c477cf7728cd11a3f6135bccfdbd68de5cd4517e70a70ec3b836041dc9c2f1abed65f2519e43a31ca6ad4991ce98460a14ee70d28c47f5a1d967c25b1ac93afea7e2b11aa2fb715ac08bd3eac739425c67974ecd682f711a0b175b30278febfe55586650ed8b0098de745944450a6836b6ab23e0c5ebdd7503188428c3159f1671ca27d9d529d344d246e116b2001dbba085afe1bfcdd12d88ae2efbcead268b10cec4f76531aba594887dd239b59c4c676b348a56a1cc2e0032590c74513cfba7f03f8b6d7a14bb6f6a16ae743317ecd8551b3362dc892bcae550032682d130772f65b2e96a5ad4ce2b8e9a41a48c2a52c80f349c99dc110807e7c662f7ef960f628001ca9a9f249b53b23c4680e3a6acec89e3c26d0265b617353654f55a752f9ea3689570c068a414793c3575fae66f6fa425ce282a574981228a52e2ede14fbde3ac66a8e061a538bee737d17fbb48afc39cd914518ef2a182ce1feb66b1a8bf9934b6fef491f2bd3598e3421399fe11754bc61e149e8846f74d44d96c7dc47f06d04d6c09dc2b2c9d78e76a713722eec637f8e3fb5cd5adfd8ba2ce05dacdf2f9522e89bff2ee745d49873755a0079835e982c6c55fd9a96597505d79090da8df4feb422422b1d6427fde4242aafcb6ed581d8e4ffd722daf56fd45b017a2a2fa2f4e30a3a457686bdd184505461fc6749e4a20b7faa2a1d9a295a445ea564b84c1b820d9cf5c06142353671f989565a3767bd6ddabfc3bf1368acdae8870580f21baa2093cea4447688e35719bd78c785821f944ecc9a093f9a65bf2584f1a0c68f70f11f2485e02f288c2c8b6692883983607960aa16065d22082121f6fd6588f07cd3fb57bba624fbb9c7077cb1400fe4edf48156b7622fab70cce1cbd17bde2f4c24b9a86d485727df413e06a6c31cab27284a69fd46e00fc6e80872ed5291b598c74964488ffdb19d0dc94fce37db3f5230d947cb4d83ae55e0357aab1ec86b63fe606f86a77aa78fc4fe986be450b74f1ffbb5ba9eeaea11c7c7ffa6d87a9d49767ce761614bd6cc5df3767ed6396b84354a9634bb3e35606e961fc023504473bf3b7e13244f19d1dee101af1854f80899f95409bb402a5267ad21ddba80e2dd0dd513d0fc88067ac4078e69c12bd19807c03a916d2a42cdbe7b4cdac4bc2314fe3369723d16c30bf277db823c1457f5ff64f3117b82b991ee8b65b7e6b8f7814a15b4ca8cebe88d12236cf1b7dd06b75cab506d78c2072fddf2002be366f43ca68866f87fe9a56808ab7f82aa925091e1f0fba371642039316939446b769973a9c93efe3104699ad3eceac89eb1c2507b65b43d21388f93ff28b194110d7114b97a10cb212515127ede0287d455791e1c6d554b0d8a4e75f2701bc3430786cc69081dbd96a73a308fc6a60fc773fdc7df49b1865c3e989f2a528872fd4c1715dadb11c801c1492ce07bde59e25a801bb542e2caef35f99ca4cb0a3f1d2c2c6e3895c94001a0b2cc648057c2e44c780655f93d56a2cd62a9d55eb8de45e9ec75bfa3d121223aba700062ba3f54162fb9ba136aca6aeb119bca9a0d6bf18e89f54d9ff09c6a2036f767098fbbaf20e10db25e43386ecda201c05e794805269f1a77e50657052d16ae1e154d706a7fa81c419b9d262766e8edb8fd6343f509bed44098ef741f10a6206474c3490354695762a5a4532dd0279abc38ef75a44899a5d8d0e77af638aedd07071f37a3c5f82bbbd05a7b4c0e23d2fc3a5bbc40a52f588c8592f02fb30be56ae0990b24a80690c0b5c9df29549f7dec89f62920a37d05c62c27a62ee01fea164bf28937cdc7d3f2937a5756ada91c2615ce7ed20f0ed07cf486b76d0a63d193363567746eff0ff90ace3dbdfb770d55161c84ccdebca1a600337e7ffed0fdfbc041ed44e0014cced03d1af55ae9fa14d87d60dfe96ac7cde67a1d8ea2150c00ba5fb9a0ec0eff5bd9f734da71edbe7e2f71b6465984c411de8a3cc77a337b2ffdee6ab6d904a79316c15d15176401bc7e72fabb1e9571c7e7188ba09a295400437e4b96549d9827fba6d3493bc6f58f95e240b0a0159054014e5e3103e3af4eef77d3896290c7bf930edbe77615d56aa0a93034c92830c1382c0c06726d2ec7d6c2ed45d3a9fb9646892402812f1df9a003705d3f549d84f9ed3b5fe3c40fcb0bcb28a0d32f2fa27fcdb82509a0725d7314a3eb99a701169fae9e3dcdc2cc20d73aa8b2c5feb645556a8b946581e4e9e82f6a19a21f5babd35d49810dc88923c4908eca3690b774f367a41c3a37b54af9847d73a7eed1ee45edaaed0f316d551c08e3e642cebc97ce71a811664ee9296e7fedffb90011cc353302acd931bc0d152d7e6332a8f0d71059987c3b90f3f57178dec3f30c58ded0bc80eb65b0c9b8d16ec73ebe17e31259181b2376405db17e279419f1c685ad71b6cc91c81a120de2db2c532e67bc3a58d22b549fae61f32398d03cb1f5e245cfec65c40c9dfd0b8a93812f67840c653c5304402a1ff6189fd24f8ce3482e5cf92b3581445009c3b586bb421459ce9457868787c78b787bd45df7e55c3165a92194d38b913a6ef6f31af4c2afcfd0158eb8eb2820f7d41e3efca9367528a0b6fe6ec3fd01082bc60a9fe2a13ab3705b3b0c07173d4d762c8de4b6598d30b97e32339aeb706de47170e1033603267c6ce8caa2977990cbda75984de4e5ede6e36ff889b53b2cbbebc37f9e56e78c62ff856bcb27aba8892ace8fcaae09b31d7f5f850596014e868003d632c9dc12e7c83f6de676d9ae4328862326572e2e0353d5547f7f73fdf5b0227b6d108ae28e3dc622d5ac3dcf98bd1461917d78468ac2912329027c1085611dce7a6b7b3fa8451a5c3c6b448b1b9ad9dd84308991e4688595bcb289ec4b99f63db0c18969bd4b5cdc14d85007d683f936ab3207b59e3971f86f8fb388e72bdc7c9fb3b466061223e85138ee6a5657e8862ca51819c9d92b339ac6900e9f60a71d4a1eb09707cedc32bb477c91a8b5792e850606e1de57122d017a2025423d40b48e0bbe711ec03381630b9003ff55e10ac6f0031dfc54ed54ccd3309abd17ee026958fdf23bb74d53b84d8e2ef150fb2216265454c5f6446e221ab1c95c086571cad14251f618c9c58a9dfb83f9a8c58c9c5c026b9bc8f90860acde16557c064f95b178a9776e463b2d7d658e4acfa1ea30c429c0b813a5872b02d7b0bafcc095e979f737834933fbbf1220c05a0b0346f5932c669c534e22ab5ab42c39fd0e062abff05a2d34060e6f539c7ae9244903d981095fac6cff5d20ac9d298de27cb1ea7079d6dcc47504f988e3bdd1c48ca23f9ec305950459446c51b879a62e75cbc3570d2dbf93594f299111e27b60e5193d6e766a40130ee5d33a43eb43aba5c5701de878fdeaa16c998607e7fbf6c8827cb1f914db9d73c6ae48a0cb416218cc50b335f171e4df050561dfb1669939ccf2c498ff1d8f53a7d7c77195348502c4ffd5c18362f4eb4c3077e504853ff1e84c6166e1f889781bf5dcccf0daf8ac0881ee7202650abdff8d6cda2f8bf3b6a96d23f5ffa0104ee72dd1e8ae7cd08258d36b50cb40048756216845815a3e01efd33d5fae86a0680920422325893296dcb2af0d6df21c7193e387092b61408aac63df4a79c3b1e54869ba3c43ae2a54446e64053c061dd8bb3e132be46d9a83b6675791f49aa9617345801e97be7f4f7159ba1d7da623c7868ad281ddbb0f75fec7fe56ff0a44a8ac3b51a1f784b2b039d6434f92d3254fd83b4221ca18883637a0eb12217ebc8e149681c21e0edbd11289cfa7f78d536d8858a60056b8c28916e1d34ce1a6d344034b2e72162a5fc92b137354c2b791e7ad6ee4679f71181188ba69c9ded078421885a6cc18bc58c383d190c11d236e53eaa39a99d157e4dd74bc4aa2ce1354511128d6b407007dbcaeb9c3b712ed2b334de23c66735f534a9dddb7ab2d06c6a4669d2bd38c8c812b287b39b3591ac77e617834ea7c4c38b1133f2cafdf51f9afca7f44e9b527d3e0e840b05ec8bf57fcceb8a28546a3593ff1b94ee6a8d7d28b8e6007d0ea7da80552e4382b3ff3b6152175083717f42c5c902131b0a27e23bbcf4ba03140a6dc3bcccbc8ca93ba6161fe3c36a1835e9e02695bac571a07f6b2267998213aa0c4c7b93c2ed3a58e12cab5a51edf462a30df14e7e32727b4da1f7f29e9ea30f65ab090b22e9ae00ae9419bf26a44482d536812e2b4c2e1fd2af622d827b04b67eac1052d2ccee68207b3b6ca3d96bc4de4039a3a3e50c58a17786edb08caad6091dab0e7beffd0acb748d5c5ef6a171d8d113c7c310f18712a53607dbf01653157090cdd19c5845c1b7e11a4a61c2229cbb1e6927c74f187964c646b007051841b1b83e670611c1e9eb0b2406ee432122613a4c7e9f60c2cf8db2d6032225604c1d5468b1e90bb57651c2223363743516164a4aab0b4bac2d70d1a254f687384889daee2fc2d32365d78878b8c9aabbbbcc8d7f4fb191d23283f4d5359767e8c99a1b8c8cddfe5040c1e2339606e788ca9cad6f2fc0712236a70c9cdd6fb0000000000000000000000000000000000000000000000000000000000000000000000101c2c3e4c55b80404422409560084401072601824140801b8244ae84401008080081022408cdea5834e5fd1220daff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848%22]\" */ #define DILITHIUM_TXFEE 10000 @@ -3029,7 +3040,7 @@ UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES],sm[32+CRYPTO_BYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t smlen=32+CRYPTO_BYTES,mlen,n; std::string handle; + UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t rmd160[20],msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES],sm[32+CRYPTO_BYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t smlen=32+CRYPTO_BYTES,mlen,n; std::string handle; if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { pubtxid = juint256(jitem(params,0)); @@ -3048,6 +3059,8 @@ UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *param result.push_back(Pair("msg32",dilithium_hexstr(str,msg,32))); result.push_back(Pair("handle",handle)); result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); + calc_rmd160_sha256(rmd160,sm,smlen); + result.push_back(Pair("sighash",dilithium_hexstr(str,rmd160,20))); result.push_back(Pair("result","success")); return(result); } else return(cclib_error(result,"not enough parameters")); From 16953993cce2f6ce0ffd23b8e38880457ceacec9 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 22:33:48 -1100 Subject: [PATCH 090/132] Reorder --- src/cc/dilithium.c | 29 ++++++++++++++++------------- 1 file changed, 16 insertions(+), 13 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index a60c63527..a41e1ea59 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3050,19 +3050,22 @@ UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *param return(cclib_error(result,"couldnt parse message to sign")); else if ( cclib_parsehash(sm,jitem(params,2),smlen) < 0 ) return(cclib_error(result,"couldnt parse sig")); - else if ( _dilithium_verify(msg2,&mlen,sm,smlen,pk) < 0 ) - return(cclib_error(result,"dilithium verify error")); - else if ( mlen != 32 ) - return(cclib_error(result,"message len mismatch")); - else if ( memcmp(msg2,msg,32) != 0 ) - return(cclib_error(result,"message content mismatch")); - result.push_back(Pair("msg32",dilithium_hexstr(str,msg,32))); - result.push_back(Pair("handle",handle)); - result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); - calc_rmd160_sha256(rmd160,sm,smlen); - result.push_back(Pair("sighash",dilithium_hexstr(str,rmd160,20))); - result.push_back(Pair("result","success")); - return(result); + else + { + calc_rmd160_sha256(rmd160,sm,smlen); + result.push_back(Pair("sighash",dilithium_hexstr(str,rmd160,20))); + if ( _dilithium_verify(msg2,&mlen,sm,smlen,pk) < 0 ) + return(cclib_error(result,"dilithium verify error")); + else if ( mlen != 32 ) + return(cclib_error(result,"message len mismatch")); + else if ( memcmp(msg2,msg,32) != 0 ) + return(cclib_error(result,"message content mismatch")); + result.push_back(Pair("msg32",dilithium_hexstr(str,msg,32))); + result.push_back(Pair("handle",handle)); + result.push_back(Pair("pkaddr",dilithium_addr(coinaddr,pk,CRYPTO_PUBLICKEYBYTES))); + result.push_back(Pair("result","success")); + return(result); + } } else return(cclib_error(result,"not enough parameters")); } From 16771b99f2eb4c719ff4cf5bbcfc4843942df73a Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 23:07:50 -1100 Subject: [PATCH 091/132] Dilithium send --- src/cc/cclib.cpp | 2 +- src/cc/dilithium.c | 39 ++++++++++++++++++++++++++++++++++++--- 2 files changed, 37 insertions(+), 4 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index 8382ba8a0..c64ac025b 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -85,7 +85,7 @@ CClib_methods[] = { (char *)"dilithium", (char *)"register", (char *)"handle, [hexseed]", 1, 2, 'R', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"sign", (char *)"msg [hexseed]", 1, 2, 'S', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"verify", (char *)"pubtxid msg sig", 3, 3, 'V', EVAL_DILITHIUM }, - { (char *)"dilithium", (char *)"send", (char *)"pubtxid amount", 2, 2, 'x', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"send", (char *)"handle pubtxid amount", 3, 3, 'x', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_DILITHIUM }, #endif }; diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index a41e1ea59..8406b0c00 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2872,6 +2872,18 @@ int32_t main(void) it is a very big signature, but that seems to be dilithium sig size. let us verify it: cclib verify 19 \"[%229d856b2be6e54c8f04ae3f86aef722b0535180b3e9eb926c53740e481a1715f9%22,%22aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848%22,%22be067f4bd81b9b0b772e0e2872cc086f6c2ff4c558a465afe80ab71c2c7b39a25ad8300629337c022d8c477cf7728cd11a3f6135bccfdbd68de5cd4517e70a70ec3b836041dc9c2f1abed65f2519e43a31ca6ad4991ce98460a14ee70d28c47f5a1d967c25b1ac93afea7e2b11aa2fb715ac08bd3eac739425c67974ecd682f711a0b175b30278febfe55586650ed8b0098de745944450a6836b6ab23e0c5ebdd7503188428c3159f1671ca27d9d529d344d246e116b2001dbba085afe1bfcdd12d88ae2efbcead268b10cec4f76531aba594887dd239b59c4c676b348a56a1cc2e0032590c74513cfba7f03f8b6d7a14bb6f6a16ae743317ecd8551b3362dc892bcae550032682d130772f65b2e96a5ad4ce2b8e9a41a48c2a52c80f349c99dc110807e7c662f7ef960f628001ca9a9f249b53b23c4680e3a6acec89e3c26d0265b617353654f55a752f9ea3689570c068a414793c3575fae66f6fa425ce282a574981228a52e2ede14fbde3ac66a8e061a538bee737d17fbb48afc39cd914518ef2a182ce1feb66b1a8bf9934b6fef491f2bd3598e3421399fe11754bc61e149e8846f74d44d96c7dc47f06d04d6c09dc2b2c9d78e76a713722eec637f8e3fb5cd5adfd8ba2ce05dacdf2f9522e89bff2ee745d49873755a0079835e982c6c55fd9a96597505d79090da8df4feb422422b1d6427fde4242aafcb6ed581d8e4ffd722daf56fd45b017a2a2fa2f4e30a3a457686bdd184505461fc6749e4a20b7faa2a1d9a295a445ea564b84c1b820d9cf5c06142353671f989565a3767bd6ddabfc3bf1368acdae8870580f21baa2093cea4447688e35719bd78c785821f944ecc9a093f9a65bf2584f1a0c68f70f11f2485e02f288c2c8b6692883983607960aa16065d22082121f6fd6588f07cd3fb57bba624fbb9c7077cb1400fe4edf48156b7622fab70cce1cbd17bde2f4c24b9a86d485727df413e06a6c31cab27284a69fd46e00fc6e80872ed5291b598c74964488ffdb19d0dc94fce37db3f5230d947cb4d83ae55e0357aab1ec86b63fe606f86a77aa78fc4fe986be450b74f1ffbb5ba9eeaea11c7c7ffa6d87a9d49767ce761614bd6cc5df3767ed6396b84354a9634bb3e35606e961fc023504473bf3b7e13244f19d1dee101af1854f80899f95409bb402a5267ad21ddba80e2dd0dd513d0fc88067ac4078e69c12bd19807c03a916d2a42cdbe7b4cdac4bc2314fe3369723d16c30bf277db823c1457f5ff64f3117b82b991ee8b65b7e6b8f7814a15b4ca8cebe88d12236cf1b7dd06b75cab506d78c2072fddf2002be366f43ca68866f87fe9a56808ab7f82aa925091e1f0fba371642039316939446b769973a9c93efe3104699ad3eceac89eb1c2507b65b43d21388f93ff28b194110d7114b97a10cb212515127ede0287d455791e1c6d554b0d8a4e75f2701bc3430786cc69081dbd96a73a308fc6a60fc773fdc7df49b1865c3e989f2a528872fd4c1715dadb11c801c1492ce07bde59e25a801bb542e2caef35f99ca4cb0a3f1d2c2c6e3895c94001a0b2cc648057c2e44c780655f93d56a2cd62a9d55eb8de45e9ec75bfa3d121223aba700062ba3f54162fb9ba136aca6aeb119bca9a0d6bf18e89f54d9ff09c6a2036f767098fbbaf20e10db25e43386ecda201c05e794805269f1a77e50657052d16ae1e154d706a7fa81c419b9d262766e8edb8fd6343f509bed44098ef741f10a6206474c3490354695762a5a4532dd0279abc38ef75a44899a5d8d0e77af638aedd07071f37a3c5f82bbbd05a7b4c0e23d2fc3a5bbc40a52f588c8592f02fb30be56ae0990b24a80690c0b5c9df29549f7dec89f62920a37d05c62c27a62ee01fea164bf28937cdc7d3f2937a5756ada91c2615ce7ed20f0ed07cf486b76d0a63d193363567746eff0ff90ace3dbdfb770d55161c84ccdebca1a600337e7ffed0fdfbc041ed44e0014cced03d1af55ae9fa14d87d60dfe96ac7cde67a1d8ea2150c00ba5fb9a0ec0eff5bd9f734da71edbe7e2f71b6465984c411de8a3cc77a337b2ffdee6ab6d904a79316c15d15176401bc7e72fabb1e9571c7e7188ba09a295400437e4b96549d9827fba6d3493bc6f58f95e240b0a0159054014e5e3103e3af4eef77d3896290c7bf930edbe77615d56aa0a93034c92830c1382c0c06726d2ec7d6c2ed45d3a9fb9646892402812f1df9a003705d3f549d84f9ed3b5fe3c40fcb0bcb28a0d32f2fa27fcdb82509a0725d7314a3eb99a701169fae9e3dcdc2cc20d73aa8b2c5feb645556a8b946581e4e9e82f6a19a21f5babd35d49810dc88923c4908eca3690b774f367a41c3a37b54af9847d73a7eed1ee45edaaed0f316d551c08e3e642cebc97ce71a811664ee9296e7fedffb90011cc353302acd931bc0d152d7e6332a8f0d71059987c3b90f3f57178dec3f30c58ded0bc80eb65b0c9b8d16ec73ebe17e31259181b2376405db17e279419f1c685ad71b6cc91c81a120de2db2c532e67bc3a58d22b549fae61f32398d03cb1f5e245cfec65c40c9dfd0b8a93812f67840c653c5304402a1ff6189fd24f8ce3482e5cf92b3581445009c3b586bb421459ce9457868787c78b787bd45df7e55c3165a92194d38b913a6ef6f31af4c2afcfd0158eb8eb2820f7d41e3efca9367528a0b6fe6ec3fd01082bc60a9fe2a13ab3705b3b0c07173d4d762c8de4b6598d30b97e32339aeb706de47170e1033603267c6ce8caa2977990cbda75984de4e5ede6e36ff889b53b2cbbebc37f9e56e78c62ff856bcb27aba8892ace8fcaae09b31d7f5f850596014e868003d632c9dc12e7c83f6de676d9ae4328862326572e2e0353d5547f7f73fdf5b0227b6d108ae28e3dc622d5ac3dcf98bd1461917d78468ac2912329027c1085611dce7a6b7b3fa8451a5c3c6b448b1b9ad9dd84308991e4688595bcb289ec4b99f63db0c18969bd4b5cdc14d85007d683f936ab3207b59e3971f86f8fb388e72bdc7c9fb3b466061223e85138ee6a5657e8862ca51819c9d92b339ac6900e9f60a71d4a1eb09707cedc32bb477c91a8b5792e850606e1de57122d017a2025423d40b48e0bbe711ec03381630b9003ff55e10ac6f0031dfc54ed54ccd3309abd17ee026958fdf23bb74d53b84d8e2ef150fb2216265454c5f6446e221ab1c95c086571cad14251f618c9c58a9dfb83f9a8c58c9c5c026b9bc8f90860acde16557c064f95b178a9776e463b2d7d658e4acfa1ea30c429c0b813a5872b02d7b0bafcc095e979f737834933fbbf1220c05a0b0346f5932c669c534e22ab5ab42c39fd0e062abff05a2d34060e6f539c7ae9244903d981095fac6cff5d20ac9d298de27cb1ea7079d6dcc47504f988e3bdd1c48ca23f9ec305950459446c51b879a62e75cbc3570d2dbf93594f299111e27b60e5193d6e766a40130ee5d33a43eb43aba5c5701de878fdeaa16c998607e7fbf6c8827cb1f914db9d73c6ae48a0cb416218cc50b335f171e4df050561dfb1669939ccf2c498ff1d8f53a7d7c77195348502c4ffd5c18362f4eb4c3077e504853ff1e84c6166e1f889781bf5dcccf0daf8ac0881ee7202650abdff8d6cda2f8bf3b6a96d23f5ffa0104ee72dd1e8ae7cd08258d36b50cb40048756216845815a3e01efd33d5fae86a0680920422325893296dcb2af0d6df21c7193e387092b61408aac63df4a79c3b1e54869ba3c43ae2a54446e64053c061dd8bb3e132be46d9a83b6675791f49aa9617345801e97be7f4f7159ba1d7da623c7868ad281ddbb0f75fec7fe56ff0a44a8ac3b51a1f784b2b039d6434f92d3254fd83b4221ca18883637a0eb12217ebc8e149681c21e0edbd11289cfa7f78d536d8858a60056b8c28916e1d34ce1a6d344034b2e72162a5fc92b137354c2b791e7ad6ee4679f71181188ba69c9ded078421885a6cc18bc58c383d190c11d236e53eaa39a99d157e4dd74bc4aa2ce1354511128d6b407007dbcaeb9c3b712ed2b334de23c66735f534a9dddb7ab2d06c6a4669d2bd38c8c812b287b39b3591ac77e617834ea7c4c38b1133f2cafdf51f9afca7f44e9b527d3e0e840b05ec8bf57fcceb8a28546a3593ff1b94ee6a8d7d28b8e6007d0ea7da80552e4382b3ff3b6152175083717f42c5c902131b0a27e23bbcf4ba03140a6dc3bcccbc8ca93ba6161fe3c36a1835e9e02695bac571a07f6b2267998213aa0c4c7b93c2ed3a58e12cab5a51edf462a30df14e7e32727b4da1f7f29e9ea30f65ab090b22e9ae00ae9419bf26a44482d536812e2b4c2e1fd2af622d827b04b67eac1052d2ccee68207b3b6ca3d96bc4de4039a3a3e50c58a17786edb08caad6091dab0e7beffd0acb748d5c5ef6a171d8d113c7c310f18712a53607dbf01653157090cdd19c5845c1b7e11a4a61c2229cbb1e6927c74f187964c646b007051841b1b83e670611c1e9eb0b2406ee432122613a4c7e9f60c2cf8db2d6032225604c1d5468b1e90bb57651c2223363743516164a4aab0b4bac2d70d1a254f687384889daee2fc2d32365d78878b8c9aabbbbcc8d7f4fb191d23283f4d5359767e8c99a1b8c8cddfe5040c1e2339606e788ca9cad6f2fc0712236a70c9cdd6fb0000000000000000000000000000000000000000000000000000000000000000000000101c2c3e4c55b80404422409560084401072601824140801b8244ae84401008080081022408cdea5834e5fd1220daff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848%22]\" + { + "sighash": "cfed6d7f059b87635bde6cb31accd736bf99ff3d", + "msg32": "aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848", + "handle": "jl777", + "pkaddr": "PNoTcVH8G5TBTQigyVZTsaMMNYYRvywUNu", + "result": "success" + } + + the basics are working, now it is time to send and spend + + cclib send 19 \"[%22jl777%22,%229d856b2be6e54c8f04ae3f86aef722b0535180b3e9eb926c53740e481a1715f9%22,7.77]\" + */ #define DILITHIUM_TXFEE 10000 @@ -3071,9 +3083,30 @@ UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *param UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); - // copy musig method - return(result); + CMutableTransaction mtx = CreateNewContextualCMutableTransaction(Params().GetConsensus(), komodo_nextheight()); + UniValue result(UniValue::VOBJ); std::string rawtx,checkhandle; CPubKey destpub33,mypk,dilithiumpk; int32_t i,n; int64_t amount; uint256 destpubtxid; uint8_t pk[CRYPTO_PUBLICKEYBYTES]; + if ( txfee == 0 ) + txfee = DILITHIUM_TXFEE; + mypk = pubkey2pk(Mypubkey()); + dilithiumpk = GetUnspendable(cp,0); + if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + { + amount = jdouble(jitem(params,2),0)*COIN + 0.0000000049; + std::string handle(jstr(jitem(params,0),0)); + result.push_back(Pair("handle",handle)); + destpubtxid = juint256(jitem(params,1)); + if ( dilithium_bigpubget(checkhandle,destpub33,pk,pubtxid) < 0 ) + return(cclib_error(result,"couldnt parse message to sign")); + else if ( handle == checkhandle ) + { + if ( AddNormalinputs(mtx,mypk,amount+txfee,64) >= amount+txfee ) + { + mtx.vout.push_back(MakeCC1vout(cp->evalcode,amount,destpub33)); + rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_sendopret(destpubtxid)); + return(musig_rawtxresult(result,rawtx)); + } else return(cclib_error(result,"couldnt find enough funds")); + } else return(cclib_error(result,"handle mismatch")); + } else return(cclib_error(result,"not enough parameters")); } UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) From 60c8bda1305697f429364c0b74309222968b10e1 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 23:09:13 -1100 Subject: [PATCH 092/132] Opret --- src/cc/dilithium.c | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 8406b0c00..47c447f88 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2909,6 +2909,24 @@ uint8_t dilithium_registeropretdecode(std::string &handle,CPubKey &pk,std::vecto return(0); } +CScript dilithium_sendopret(uint256 destpubtxid) +{ + CScript opret; uint8_t evalcode = EVAL_DILITHIUM; + opret << OP_RETURN << E_MARSHAL(ss << evalcode << 'x' << destpubtxid); + return(opret); +} + +uint8_t dilithium_sendopretdecode(uint256 &destpubtxid,CScript scriptPubKey) +{ + std::vector vopret; uint8_t e,f; + GetOpReturnData(scriptPubKey,vopret); + if ( vopret.size() > 2 && E_UNMARSHAL(vopret,ss >> e; ss >> f; ss >> handle; ss >> destpubtxid) != 0 && e == EVAL_DILITHIUM && f == 'x' ) + { + return(f); + } + return(0); +} + UniValue dilithium_rawtxresult(UniValue &result,std::string rawtx) { CTransaction tx; From f86cdd74f9dad20ba2a3a6ead53e8c02507cadcb Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 23:10:10 -1100 Subject: [PATCH 093/132] Destpubtxid --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 47c447f88..5db52bd00 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3113,7 +3113,7 @@ UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) std::string handle(jstr(jitem(params,0),0)); result.push_back(Pair("handle",handle)); destpubtxid = juint256(jitem(params,1)); - if ( dilithium_bigpubget(checkhandle,destpub33,pk,pubtxid) < 0 ) + if ( dilithium_bigpubget(checkhandle,destpub33,pk,destpubtxid) < 0 ) return(cclib_error(result,"couldnt parse message to sign")); else if ( handle == checkhandle ) { From 461ed55d093d71448179fa18f42d99704bebac92 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 23:10:59 -1100 Subject: [PATCH 094/132] Fix --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 5db52bd00..3e485f893 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2920,7 +2920,7 @@ uint8_t dilithium_sendopretdecode(uint256 &destpubtxid,CScript scriptPubKey) { std::vector vopret; uint8_t e,f; GetOpReturnData(scriptPubKey,vopret); - if ( vopret.size() > 2 && E_UNMARSHAL(vopret,ss >> e; ss >> f; ss >> handle; ss >> destpubtxid) != 0 && e == EVAL_DILITHIUM && f == 'x' ) + if ( vopret.size() > 2 && E_UNMARSHAL(vopret,ss >> e; ss >> f; ss >> destpubtxid) != 0 && e == EVAL_DILITHIUM && f == 'x' ) { return(f); } From 7d623078f3e3146e111590609b613c70ec55de82 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 23:44:43 -1100 Subject: [PATCH 095/132] Docs --- src/cc/dilithium.c | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 3e485f893..ed0956c62 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2842,7 +2842,18 @@ int32_t main(void) #endif ////////////////////////////////////////////////////// -/* First register a pubkey,ie. bind handle, pub33 and bigpub together and then can be referred by pubtxid in other calls + +/* + dilithium has very big pubkeys and privkeys, so some practical things are done to make them more manageable. luckily the big privkey can be generated from a normal 256bit seed in about 100 microseconds. Of course, if you use a normal privkey that is also having its pubkey known, it defeats the purpose of using quantum secure protocol. however it is convenient for testing. just make sure to use externally generated seeds that never get used for secp256k1 if you want to keep it quantum secure. + + there are some useful "addresses" starting with 'P' and 'S' that are the base58 encoded dilithium pubkey and privkey. this is just so you can make sure the right one was used in an operation as the ~3kb of hex is very hard to compare visually. + + Now comes the cool part. Instead of having to specify these giant pubkeys in each spend and maybe even send, we send to a pubtxid instead. the pubtxid is the txid of a registration tx where a handle, secp256k1 pubkey and the dilithium pubkey are bound together. So by referring to the txid, you refer to all three. Again, for convenience it is possible to use the same secp256k1 pubkey that is derived from the 256bit seed that the dilithium pubkey is generated, but that offers no additonal quantum protection. To gain the quantum protection, use an externally provided seed to generate the dilithium pubkey. there should be no algorithmic linkage between the pubtxid secp256k1 pubkey and the dilithium pubkey. They are linked simply by being in the same register transaction. + + Once you have registered the pubkey(s), then you can do a send to it. Both pubkeys are used so that to spend you need to have a proper CC signature and a dilithium signature. The spend will necessarily need to have the almost 4kb signature in the opreturn, but at least the big pubkey is only referenced via the pubtxid + + + First register a pubkey,ie. bind handle, pub33 and bigpub together and then can be referred by pubtxid in other calls cclib register 19 \"[%22jl777%22]\" { @@ -2883,6 +2894,15 @@ int32_t main(void) the basics are working, now it is time to send and spend cclib send 19 \"[%22jl777%22,%229d856b2be6e54c8f04ae3f86aef722b0535180b3e9eb926c53740e481a1715f9%22,7.77]\" + { + "handle": "jl777", + "hex": "0400008085202f8901ff470ca3fb4f935a32dd312db801dcabce0e8b49c7774bb4f1d39a45b3a68bab0100000049483045022100d1c29d5f870dd18aa865e12632fa0cc8df9a8a770a23360e9c443d39cb141c5f0220304c7c77a6d711888d4bcb836530b6509eabe158496029b0bf57b5716f24beb101ffffffff034014502e00000000302ea22c8020b09ee47b12b5b9a2edcf0e7c4fb2a517b879eb88ac98b16185dfef476506b1dd8103120c008203000401cc3cd0ff7646070000232102aff51dad774a1c612dc82e63f85f07b992b665836b0f0efbcb26ee679f4f4848ac0000000000000000246a221378f915171a480e74536c92ebe9b3805153b022f7ae863fae048f4ce5e62b6b859d00000000120c00000000000000000000000000", + "txid": "4aac73ebe82c12665d1d005a0ae1a1493cb1e2c714680ef9d016f48a7c77b4a2", + "result": "success" + } + dont forget to broadcast it: 4aac73ebe82c12665d1d005a0ae1a1493cb1e2c714680ef9d016f48a7c77b4a2 + notice how small the tx is! 289 bytes as it is sent to the destpubtxid, which in turn contains the handle, pub33 and bigpub. the handle is used for error check, pub33 is used to make the destination CC address, so the normal CC signing needs to be passed in addition to the spend restrictions for dilithium. + */ From 4136857e21370a9c44a9afb0f3a963bc95bfb27b Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 23:50:15 -1100 Subject: [PATCH 096/132] Guard against combining before having num music --- src/cc/musig.cpp | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index d93792463..33695aeaa 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -219,7 +219,7 @@ struct musig_info secp256k1_musig_session_signer_data *signer_data; //[N_SIGNERS]; secp256k1_pubkey *nonces; //[N_SIGNERS]; secp256k1_musig_partial_signature *partial_sig; //[N_SIGNERS]; - int32_t myind,num; + int32_t myind,num,numcommits,numnonces,numpartials; uint8_t msg[32],pkhash[32],combpk[33]; } *MUSIG; @@ -511,7 +511,8 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * number of signers participating in the MuSig. */ result.push_back(Pair("added_index",ind)); - if ( secp256k1_musig_session_get_public_nonce(ctx,&MUSIG->session,MUSIG->signer_data,&MUSIG->nonces[MUSIG->myind],MUSIG->commitment_ptrs,MUSIG->num) > 0 ) + MUSIG->numcommits++; + if ( MUSIG->numcommits >= MUSIG->num && secp256k1_musig_session_get_public_nonce(ctx,&MUSIG->session,MUSIG->signer_data,&MUSIG->nonces[MUSIG->myind],MUSIG->commitment_ptrs,MUSIG->num) > 0 ) { if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG->nonces[MUSIG->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) { @@ -583,7 +584,8 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * adaptor: point to add to the combined public nonce. If NULL, nothing is * added to the combined nonce. */ - if ( secp256k1_musig_session_combine_nonces(ctx,&MUSIG->session,MUSIG->signer_data,MUSIG->num,NULL,NULL) > 0 ) + MUSIG->numnonces++; + if ( MUSIG->numnonces >= MUSIG->num && secp256k1_musig_session_combine_nonces(ctx,&MUSIG->session,MUSIG->signer_data,MUSIG->num,NULL,NULL) > 0 ) { if ( secp256k1_musig_partial_sign(ctx,&MUSIG->session,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) { @@ -621,7 +623,8 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); result.push_back(Pair("added_index",ind)); - if ( secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) + MUSIG->numpartials++; + if ( MUSIG->numpartials >= MUSIG->num && secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) { if ( secp256k1_schnorrsig_serialize(ctx,out64,&sig) > 0 ) { From 8bfc74cef033bf4ed8d796a85e827a9acca0239f Mon Sep 17 00:00:00 2001 From: jl777 Date: Sat, 23 Feb 2019 23:52:24 -1100 Subject: [PATCH 097/132] Set numb to 1 --- src/cc/musig.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 33695aeaa..5986f8716 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -466,6 +466,7 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) for (i=0; i<32; i++) sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitments[MUSIG->myind*32 + i]); str[64] = 0; + MUSIG->numcommits = 1; result.push_back(Pair("commitment",str)); result.push_back(Pair("result","success")); return(result); @@ -519,6 +520,7 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) for (i=0; i<33; i++) sprintf(&str[i<<1],"%02x",((uint8_t *)pk.begin())[i]); str[66] = 0; + MUSIG->numnonces = 1; result.push_back(Pair("myind",MUSIG->myind)); result.push_back(Pair("nonce",str)); result.push_back(Pair("result","success")); @@ -597,6 +599,7 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) result.push_back(Pair("myind",MUSIG->myind)); result.push_back(Pair("partialsig",str)); result.push_back(Pair("result","success")); + MUSIG->numpartials = 1; return(result); } else return(cclib_error(result,"error serializing partial sig")); } else return(cclib_error(result,"error making partial sig")); From 9dcb99c828800311803140e37298d3f0204ced7e Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:08:21 -1100 Subject: [PATCH 098/132] Dilithium spend --- src/cc/cclib.cpp | 4 +-- src/cc/dilithium.c | 74 ++++++++++++++++++++++++++++++++++++++++++++-- 2 files changed, 73 insertions(+), 5 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index c64ac025b..b7b2db059 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -80,13 +80,13 @@ CClib_methods[] = { (char *)"musig", (char *)"partialsig", (char *)"pkhash,ind,partialsig", 3, 3, 'S', EVAL_MUSIG }, { (char *)"musig", (char *)"verify", (char *)"msg sig pubkey", 3, 3, 'V', EVAL_MUSIG }, { (char *)"musig", (char *)"send", (char *)"combined_pk amount", 2, 2, 'x', EVAL_MUSIG }, - { (char *)"musig", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_MUSIG }, + { (char *)"musig", (char *)"spend", (char *)"sendtxid sig scriptPubKey", 3, 3, 'y', EVAL_MUSIG }, { (char *)"dilithium", (char *)"keypair", (char *)"[hexseed]", 0, 1, 'K', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"register", (char *)"handle, [hexseed]", 1, 2, 'R', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"sign", (char *)"msg [hexseed]", 1, 2, 'S', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"verify", (char *)"pubtxid msg sig", 3, 3, 'V', EVAL_DILITHIUM }, { (char *)"dilithium", (char *)"send", (char *)"handle pubtxid amount", 3, 3, 'x', EVAL_DILITHIUM }, - { (char *)"dilithium", (char *)"spend", (char *)"sendtxid sig destpubkey", 3, 3, 'y', EVAL_DILITHIUM }, + { (char *)"dilithium", (char *)"spend", (char *)"sendtxid scriptPubKey [hexseed]", 2, 3, 'y', EVAL_DILITHIUM }, #endif }; diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index ed0956c62..30fd2a3bd 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2947,6 +2947,24 @@ uint8_t dilithium_sendopretdecode(uint256 &destpubtxid,CScript scriptPubKey) return(0); } +CScript dilithium_spendopret(uint256 destpubtxid,std::vector sig) +{ + CScript opret; uint8_t evalcode = EVAL_DILITHIUM; + opret << OP_RETURN << E_MARSHAL(ss << evalcode << 'y' << destpubtxid << sig); + return(opret); +} + +uint8_t dilithium_spendopretdecode(uint256 &destpubtxid,std::vector &sig,CScript scriptPubKey) +{ + std::vector vopret; uint8_t e,f; + GetOpReturnData(scriptPubKey,vopret); + if ( vopret.size() > 2 && E_UNMARSHAL(vopret,ss >> e; ss >> f; ss >> destpubtxid; ss > sig) != 0 && e == EVAL_DILITHIUM && f == 'y' ) + { + return(f); + } + return(0); +} + UniValue dilithium_rawtxresult(UniValue &result,std::string rawtx) { CTransaction tx; @@ -3147,9 +3165,59 @@ UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) } else return(cclib_error(result,"not enough parameters")); } +/* + ultimately what is needed is to be able to scan all utxos to the CC address and be able to spend many vins in the same tx. to do this the opreturn would need to be able to have txid of special with the sigs. However, it is complicated by the need to create a specific message to sign that is the desired outputs and all the inputs. Also, to properly be able to do change and keep everything in dilithium outputs, there needs to be a second destpub. + + so the proposed opreturn for spend would be: + + destpubtxid0, destpubtxid1 (zeroid if only 1), vector of sigs/sigtxid where if it is len 32 it is a txid that just has the sig in the opreturn. + + however, for now, to keep things simple we will only support spending a specific txid to normal output to avoid needing a combined opreturn and other complications. + */ + UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); - // copy musig method - return(result); + CMutableTransaction mtx = CreateNewContextualCMutableTransaction(Params().GetConsensus(), komodo_nextheight()); + UniValue result(UniValue::VOBJ); std::string rawtx; CPubKey mypk,destpub33; char *scriptstr; uint8_t msg[32]; CTransaction vintx; uint256 prevhash,hashBlock,destpubtxid; int32_t i,smlen,n,numvouts; char str[129]; CTxOut vout; std::string handle; uint8_t pk[CRYPTO_PUBLICKEYBYTES],pk2[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; std::vector sig; + if ( txfee == 0 ) + txfee = DILITHIUM_TXFEE; + mypk = pubkey2pk(Mypubkey()); + if ( params != 0 && ((n= cJSON_GetArraySize(params)) == 2 || n == 3) ) + { + prevhash = juint256(jitem(params,0)); + scriptstr = jstr(jitem(params,1),0); + if ( n == 2 || cclib_parsehash(seed,jitem(params,2),32) < 0 ) + { + Myprivkey(seed); + result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); + } + _dilithium_keypair(pk,sk,seed); + if ( is_hexstr(scriptstr,0) != 0 ) + { + CScript scriptPubKey; + scriptPubKey.resize(strlen(scriptstr)/2); + decode_hex(&scriptPubKey[0],strlen(scriptstr)/2,scriptstr); + if ( myGetTransaction(prevhash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) + { + vout.nValue = vintx.vout[0].nValue - txfee; + vout.scriptPubKey = scriptPubKey; + musig_prevoutmsg(msg,prevhash,vout.scriptPubKey); + sig.resize(32+CRYPTO_SIZE); + if ( dilithium_bigpubget(handle,destpub33,pk2,destpubtxid) < 0 ) + return(cclib_error(result,"couldnt parse message to sign")); + else if ( memcmp(pk,pk2,sizeof(pk)) != 0 ) + return(cclib_error(result,"dilithium bigpub mismatch")); + else if ( destpub33 != mypk ) + return(cclib_error(result,"destpub33 is not for this -pubkey")); + else if ( _dilithium_sign(&sig[0],&smlen,msg,32,sk) < 0 ) + return(cclib_error(result,"dilithium signing error")); + else if ( smlen != 32+CRYPTO_SIZE ) + return(cclib_error(result,"siglen error")); + mtx.vin.push_back(CTxIn(prevhash,0)); + mtx.vout.push_back(vout); + rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_spendopret('y',destpubtxid,sig)); + return(dilithium_rawtxresult(result,rawtx)); + } else return(cclib_error(result,"couldnt find vin0")); + } else return(cclib_error(result,"script or bad destpubtxid is not hex")); + } else return(cclib_error(result,"need to have exactly 2 params sendtxid, scriptPubKey")); } From 1d4243bb951802fe5eed257161dcbbbdf307a10e Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:11:30 -1100 Subject: [PATCH 099/132] > -> >> --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 30fd2a3bd..cc41d2360 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2958,7 +2958,7 @@ uint8_t dilithium_spendopretdecode(uint256 &destpubtxid,std::vector &si { std::vector vopret; uint8_t e,f; GetOpReturnData(scriptPubKey,vopret); - if ( vopret.size() > 2 && E_UNMARSHAL(vopret,ss >> e; ss >> f; ss >> destpubtxid; ss > sig) != 0 && e == EVAL_DILITHIUM && f == 'y' ) + if ( vopret.size() > 2 && E_UNMARSHAL(vopret,ss >> e; ss >> f; ss >> destpubtxid; ss >> sig) != 0 && e == EVAL_DILITHIUM && f == 'y' ) { return(f); } From 852e7ce0162e18c31cbd500df5c7ed97c9e0e444 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:13:30 -1100 Subject: [PATCH 100/132] Syntax --- src/cc/dilithium.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index cc41d2360..197d62786 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3178,7 +3178,7 @@ UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { CMutableTransaction mtx = CreateNewContextualCMutableTransaction(Params().GetConsensus(), komodo_nextheight()); - UniValue result(UniValue::VOBJ); std::string rawtx; CPubKey mypk,destpub33; char *scriptstr; uint8_t msg[32]; CTransaction vintx; uint256 prevhash,hashBlock,destpubtxid; int32_t i,smlen,n,numvouts; char str[129]; CTxOut vout; std::string handle; uint8_t pk[CRYPTO_PUBLICKEYBYTES],pk2[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES]; std::vector sig; + UniValue result(UniValue::VOBJ); std::string rawtx; CPubKey mypk,destpub33; CTransaction vintx; uint256 prevhash,hashBlock,destpubtxid; int32_t i,smlen,n,numvouts; char str[129],*scriptstr; CTxOut vout; std::string handle; uint8_t pk[CRYPTO_PUBLICKEYBYTES],pk2[CRYPTO_PUBLICKEYBYTES],sk[CRYPTO_SECRETKEYBYTES],msg[32],seed[32]; std::vector sig; if ( txfee == 0 ) txfee = DILITHIUM_TXFEE; mypk = pubkey2pk(Mypubkey()); @@ -3211,11 +3211,11 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params return(cclib_error(result,"destpub33 is not for this -pubkey")); else if ( _dilithium_sign(&sig[0],&smlen,msg,32,sk) < 0 ) return(cclib_error(result,"dilithium signing error")); - else if ( smlen != 32+CRYPTO_SIZE ) + else if ( smlen != 32+CRYPTO_BYTES ) return(cclib_error(result,"siglen error")); mtx.vin.push_back(CTxIn(prevhash,0)); mtx.vout.push_back(vout); - rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_spendopret('y',destpubtxid,sig)); + rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_spendopret(destpubtxid,sig)); return(dilithium_rawtxresult(result,rawtx)); } else return(cclib_error(result,"couldnt find vin0")); } else return(cclib_error(result,"script or bad destpubtxid is not hex")); From 32a3cc94bbd6799754f083e0c2eb4fa86bb3f024 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:18:43 -1100 Subject: [PATCH 101/132] Prev --- src/cc/dilithium.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 197d62786..8a59ecba3 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2903,6 +2903,7 @@ int32_t main(void) dont forget to broadcast it: 4aac73ebe82c12665d1d005a0ae1a1493cb1e2c714680ef9d016f48a7c77b4a2 notice how small the tx is! 289 bytes as it is sent to the destpubtxid, which in turn contains the handle, pub33 and bigpub. the handle is used for error check, pub33 is used to make the destination CC address, so the normal CC signing needs to be passed in addition to the spend restrictions for dilithium. + cclib spend 19 \"[%224aac73ebe82c12665d1d005a0ae1a1493cb1e2c714680ef9d016f48a7c77b4a2%22,%22210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac%22]\" */ @@ -3182,6 +3183,7 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params if ( txfee == 0 ) txfee = DILITHIUM_TXFEE; mypk = pubkey2pk(Mypubkey()); + fprintf(stderr,"inside\n"); if ( params != 0 && ((n= cJSON_GetArraySize(params)) == 2 || n == 3) ) { prevhash = juint256(jitem(params,0)); @@ -3192,13 +3194,16 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); } _dilithium_keypair(pk,sk,seed); + fprintf(stderr,"after keypair\n"); if ( is_hexstr(scriptstr,0) != 0 ) { + fprintf(stderr,"have script\n"); CScript scriptPubKey; scriptPubKey.resize(strlen(scriptstr)/2); decode_hex(&scriptPubKey[0],strlen(scriptstr)/2,scriptstr); if ( myGetTransaction(prevhash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) { + fprintf(stderr,"got tx\n"); vout.nValue = vintx.vout[0].nValue - txfee; vout.scriptPubKey = scriptPubKey; musig_prevoutmsg(msg,prevhash,vout.scriptPubKey); @@ -3213,6 +3218,7 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params return(cclib_error(result,"dilithium signing error")); else if ( smlen != 32+CRYPTO_BYTES ) return(cclib_error(result,"siglen error")); + fprintf(stderr,"prepare tx\n"); mtx.vin.push_back(CTxIn(prevhash,0)); mtx.vout.push_back(vout); rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_spendopret(destpubtxid,sig)); From 93770abb7e0fd41b1e75e936305a91db112cbf2f Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:20:15 -1100 Subject: [PATCH 102/132] CRYPTO_BYTES --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 8a59ecba3..d1a700e0b 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3207,7 +3207,7 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params vout.nValue = vintx.vout[0].nValue - txfee; vout.scriptPubKey = scriptPubKey; musig_prevoutmsg(msg,prevhash,vout.scriptPubKey); - sig.resize(32+CRYPTO_SIZE); + sig.resize(32+CRYPTO_BYTES); if ( dilithium_bigpubget(handle,destpub33,pk2,destpubtxid) < 0 ) return(cclib_error(result,"couldnt parse message to sign")); else if ( memcmp(pk,pk2,sizeof(pk)) != 0 ) From 6deb58ad51184bfb28e48b6be1b1440d201ecb94 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:24:31 -1100 Subject: [PATCH 103/132] Fix --- src/cc/dilithium.c | 36 +++++++++++++++++------------------- 1 file changed, 17 insertions(+), 19 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index d1a700e0b..58a3fd514 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3183,7 +3183,6 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params if ( txfee == 0 ) txfee = DILITHIUM_TXFEE; mypk = pubkey2pk(Mypubkey()); - fprintf(stderr,"inside\n"); if ( params != 0 && ((n= cJSON_GetArraySize(params)) == 2 || n == 3) ) { prevhash = juint256(jitem(params,0)); @@ -3194,35 +3193,34 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params result.push_back(Pair("warning","test mode using privkey for -pubkey, only for testing. there is no point using quantum secure signing if you are using a privkey with a known secp256k1 pubkey!!")); } _dilithium_keypair(pk,sk,seed); - fprintf(stderr,"after keypair\n"); if ( is_hexstr(scriptstr,0) != 0 ) { - fprintf(stderr,"have script\n"); CScript scriptPubKey; scriptPubKey.resize(strlen(scriptstr)/2); decode_hex(&scriptPubKey[0],strlen(scriptstr)/2,scriptstr); if ( myGetTransaction(prevhash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) { - fprintf(stderr,"got tx\n"); vout.nValue = vintx.vout[0].nValue - txfee; vout.scriptPubKey = scriptPubKey; musig_prevoutmsg(msg,prevhash,vout.scriptPubKey); sig.resize(32+CRYPTO_BYTES); - if ( dilithium_bigpubget(handle,destpub33,pk2,destpubtxid) < 0 ) - return(cclib_error(result,"couldnt parse message to sign")); - else if ( memcmp(pk,pk2,sizeof(pk)) != 0 ) - return(cclib_error(result,"dilithium bigpub mismatch")); - else if ( destpub33 != mypk ) - return(cclib_error(result,"destpub33 is not for this -pubkey")); - else if ( _dilithium_sign(&sig[0],&smlen,msg,32,sk) < 0 ) - return(cclib_error(result,"dilithium signing error")); - else if ( smlen != 32+CRYPTO_BYTES ) - return(cclib_error(result,"siglen error")); - fprintf(stderr,"prepare tx\n"); - mtx.vin.push_back(CTxIn(prevhash,0)); - mtx.vout.push_back(vout); - rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_spendopret(destpubtxid,sig)); - return(dilithium_rawtxresult(result,rawtx)); + if ( dilithium_sendopretdecode(destpubtxid,tx.vout[numvouts-1].scriptPubKey) == 'x' ) + { + if ( dilithium_bigpubget(handle,destpub33,pk2,destpubtxid) < 0 ) + return(cclib_error(result,"couldnt parse message to sign")); + else if ( memcmp(pk,pk2,sizeof(pk)) != 0 ) + return(cclib_error(result,"dilithium bigpub mismatch")); + else if ( destpub33 != mypk ) + return(cclib_error(result,"destpub33 is not for this -pubkey")); + else if ( _dilithium_sign(&sig[0],&smlen,msg,32,sk) < 0 ) + return(cclib_error(result,"dilithium signing error")); + else if ( smlen != 32+CRYPTO_BYTES ) + return(cclib_error(result,"siglen error")); + mtx.vin.push_back(CTxIn(prevhash,0)); + mtx.vout.push_back(vout); + rawtx = FinalizeCCTx(0,cp,mtx,mypk,txfee,dilithium_spendopret(destpubtxid,sig)); + return(dilithium_rawtxresult(result,rawtx)); + } else return(cclib_error(result,"couldnt decode send opret")); } else return(cclib_error(result,"couldnt find vin0")); } else return(cclib_error(result,"script or bad destpubtxid is not hex")); } else return(cclib_error(result,"need to have exactly 2 params sendtxid, scriptPubKey")); From c16c21f664a3ef3f448046f3b8680b70da9324b9 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:25:08 -1100 Subject: [PATCH 104/132] Vent --- src/cc/dilithium.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 58a3fd514..94e2efc66 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3204,7 +3204,7 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params vout.scriptPubKey = scriptPubKey; musig_prevoutmsg(msg,prevhash,vout.scriptPubKey); sig.resize(32+CRYPTO_BYTES); - if ( dilithium_sendopretdecode(destpubtxid,tx.vout[numvouts-1].scriptPubKey) == 'x' ) + if ( dilithium_sendopretdecode(destpubtxid,vintx.vout[numvouts-1].scriptPubKey) == 'x' ) { if ( dilithium_bigpubget(handle,destpub33,pk2,destpubtxid) < 0 ) return(cclib_error(result,"couldnt parse message to sign")); From 57c1d1cc8c7303cf6bd81ca20b8e9358136e5fe0 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:43:30 -1100 Subject: [PATCH 105/132] Dilithium validate --- src/cc/cclib.cpp | 3 +++ src/cc/dilithium.c | 34 +++++++++++++++++++++++++++++++++- 2 files changed, 36 insertions(+), 1 deletion(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index b7b2db059..286008660 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -127,6 +127,7 @@ UniValue musig_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue musig_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); +bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx); UniValue dilithium_register(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue dilithium_send(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params); @@ -406,6 +407,8 @@ bool CClib_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C return(sudoku_validate(cp,height,eval,tx)); else if ( cp->evalcode == EVAL_MUSIG ) return(musig_validate(cp,height,eval,tx)); + else if ( cp->evalcode == DILITHIUM_MUSIG ) + return(dilithium_validate(cp,height,eval,tx)); else return eval->Invalid("invalid evalcode"); #endif } diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 94e2efc66..dc636d7e8 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3207,7 +3207,7 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params if ( dilithium_sendopretdecode(destpubtxid,vintx.vout[numvouts-1].scriptPubKey) == 'x' ) { if ( dilithium_bigpubget(handle,destpub33,pk2,destpubtxid) < 0 ) - return(cclib_error(result,"couldnt parse message to sign")); + return(cclib_error(result,"couldnt get bigpub")); else if ( memcmp(pk,pk2,sizeof(pk)) != 0 ) return(cclib_error(result,"dilithium bigpub mismatch")); else if ( destpub33 != mypk ) @@ -3225,3 +3225,35 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params } else return(cclib_error(result,"script or bad destpubtxid is not hex")); } else return(cclib_error(result,"need to have exactly 2 params sendtxid, scriptPubKey")); } + +bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) +{ + CPubKey destpub33; std::string handle; uint256 hashBlock,destpubtxid,checktxid; CTransaction vintx; int32_t numvouts,mlen,smlen=CRYPTO_BYTES+32; std::vector sig; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES]; + if ( tx.vout.size() != 2 ) + return eval->Invalid("numvouts != 2"); + else if ( tx.vin.size() != 1 ) + return eval->Invalid("numvins != 1"); + else if ( IsCCInput(tx.vin[0].scriptSig) == 0 ) + return eval->Invalid("illegal normal vin0"); + else if ( myGetTransaction(tx.vin[0].prevout.hash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) + { + if ( dilithium_sendopretdecode(destpubtxid,vintx.vout[numvouts-1].scriptPubKey) == 'x' ) + { + if ( dilithium_spendopretdecode(checktxid,sig,tx.vout[tx.vout.size()-1].scriptPubKey) == 'y' ) + { + if ( destpubtxid == checktxid ) + { + musig_prevoutmsg(msg,tx.vin[0].prevout.hash,tx.vout[0].scriptPubKey); + if ( dilithium_bigpubget(handle,destpub33,pk,destpubtxid) < 0 ) + return eval->Invalid(result,"couldnt get bigpub"); + else if ( _dilithium_verify(msg2,&mlen,&sig[0],(int32_t)sig.size(),pk) < 0 ) + return eval->Invalid("failed dilithium verify"); + else if ( mlen != 32 || memcmp(msg,msg2,32) != 0 ) + return eval->Invalid("failed dilithium msg verify"); + else return eval->Invalid("this is actually success!"); + } else return eval->Invalid("destpubtxid didnt match send opret"); + } else return eval->Invalid("failed decode dilithium spendopret"); + } else return eval->Invalid("couldnt decode send opret"); + } else return eval->Invalid("couldnt find vin0 tx"); +} + From 0ee7d2fed4c0988e49cc79bbcc182cc7a3078213 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:45:00 -1100 Subject: [PATCH 106/132] Fix --- src/cc/cclib.cpp | 2 +- src/cc/dilithium.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cc/cclib.cpp b/src/cc/cclib.cpp index 286008660..f7749d99f 100644 --- a/src/cc/cclib.cpp +++ b/src/cc/cclib.cpp @@ -407,7 +407,7 @@ bool CClib_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C return(sudoku_validate(cp,height,eval,tx)); else if ( cp->evalcode == EVAL_MUSIG ) return(musig_validate(cp,height,eval,tx)); - else if ( cp->evalcode == DILITHIUM_MUSIG ) + else if ( cp->evalcode == EVAL_DILITHIUM ) return(dilithium_validate(cp,height,eval,tx)); else return eval->Invalid("invalid evalcode"); #endif diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index dc636d7e8..cf52a98c2 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3245,7 +3245,7 @@ bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,con { musig_prevoutmsg(msg,tx.vin[0].prevout.hash,tx.vout[0].scriptPubKey); if ( dilithium_bigpubget(handle,destpub33,pk,destpubtxid) < 0 ) - return eval->Invalid(result,"couldnt get bigpub"); + return eval->Invalid("couldnt get bigpub"); else if ( _dilithium_verify(msg2,&mlen,&sig[0],(int32_t)sig.size(),pk) < 0 ) return eval->Invalid("failed dilithium verify"); else if ( mlen != 32 || memcmp(msg,msg2,32) != 0 ) From 7f601cbfc7b284aceea87bc87d8721cab85c640a Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:50:16 -1100 Subject: [PATCH 107/132] +print --- src/cc/dilithium.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index cf52a98c2..bb6b06e91 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3237,13 +3237,18 @@ bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,con return eval->Invalid("illegal normal vin0"); else if ( myGetTransaction(tx.vin[0].prevout.hash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) { + fprintf(stderr,"inside\n"); if ( dilithium_sendopretdecode(destpubtxid,vintx.vout[numvouts-1].scriptPubKey) == 'x' ) { + fprintf(stderr,"about to spendopret\n"); if ( dilithium_spendopretdecode(checktxid,sig,tx.vout[tx.vout.size()-1].scriptPubKey) == 'y' ) { - if ( destpubtxid == checktxid ) + fprintf(stderr,"checktxid.%s vs %s\n",destpubtxid.GetHex().c_str(),checktxid.GetHex().c_str()); + if ( destpubtxid == checktxid && sig.size() == CRYPTO_BYTES+32 ) { + fprintf(stderr,"call prevoutmsg\n"); musig_prevoutmsg(msg,tx.vin[0].prevout.hash,tx.vout[0].scriptPubKey); + fprintf(stderr,"call dilithium_bigpubget\n"); if ( dilithium_bigpubget(handle,destpub33,pk,destpubtxid) < 0 ) return eval->Invalid("couldnt get bigpub"); else if ( _dilithium_verify(msg2,&mlen,&sig[0],(int32_t)sig.size(),pk) < 0 ) @@ -3251,7 +3256,7 @@ bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,con else if ( mlen != 32 || memcmp(msg,msg2,32) != 0 ) return eval->Invalid("failed dilithium msg verify"); else return eval->Invalid("this is actually success!"); - } else return eval->Invalid("destpubtxid didnt match send opret"); + } else return eval->Invalid("destpubtxid or sig size didnt match send opret"); } else return eval->Invalid("failed decode dilithium spendopret"); } else return eval->Invalid("couldnt decode send opret"); } else return eval->Invalid("couldnt find vin0 tx"); From 97db451dc1e635801dcacf277af8d94538590247 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:55:31 -1100 Subject: [PATCH 108/132] Bigger msg2 --- src/cc/dilithium.c | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index bb6b06e91..5e6b926fa 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3109,7 +3109,7 @@ UniValue dilithium_sign(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue dilithium_verify(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { - UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t rmd160[20],msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES],sm[32+CRYPTO_BYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t smlen=32+CRYPTO_BYTES,mlen,n; std::string handle; + UniValue result(UniValue::VOBJ); CPubKey pk33; uint8_t rmd160[20],msg[32],msg2[CRYPTO_BYTES+32],pk[CRYPTO_PUBLICKEYBYTES],sm[32+CRYPTO_BYTES]; uint256 pubtxid; char coinaddr[64],str[(32+CRYPTO_BYTES)*2+1]; int32_t smlen=32+CRYPTO_BYTES,mlen,n; std::string handle; if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) { pubtxid = juint256(jitem(params,0)); @@ -3228,7 +3228,7 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) { - CPubKey destpub33; std::string handle; uint256 hashBlock,destpubtxid,checktxid; CTransaction vintx; int32_t numvouts,mlen,smlen=CRYPTO_BYTES+32; std::vector sig; uint8_t msg[32],msg2[32],pk[CRYPTO_PUBLICKEYBYTES]; + CPubKey destpub33; std::string handle; uint256 hashBlock,destpubtxid,checktxid; CTransaction vintx; int32_t numvouts,mlen,smlen=CRYPTO_BYTES+32; std::vector sig; uint8_t msg[32],msg2[CRYPTO_BYTES+32],pk[CRYPTO_PUBLICKEYBYTES]; if ( tx.vout.size() != 2 ) return eval->Invalid("numvouts != 2"); else if ( tx.vin.size() != 1 ) @@ -3244,18 +3244,22 @@ bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,con if ( dilithium_spendopretdecode(checktxid,sig,tx.vout[tx.vout.size()-1].scriptPubKey) == 'y' ) { fprintf(stderr,"checktxid.%s vs %s\n",destpubtxid.GetHex().c_str(),checktxid.GetHex().c_str()); - if ( destpubtxid == checktxid && sig.size() == CRYPTO_BYTES+32 ) + if ( destpubtxid == checktxid && sig.size() == smlen ) { fprintf(stderr,"call prevoutmsg\n"); musig_prevoutmsg(msg,tx.vin[0].prevout.hash,tx.vout[0].scriptPubKey); fprintf(stderr,"call dilithium_bigpubget\n"); if ( dilithium_bigpubget(handle,destpub33,pk,destpubtxid) < 0 ) return eval->Invalid("couldnt get bigpub"); - else if ( _dilithium_verify(msg2,&mlen,&sig[0],(int32_t)sig.size(),pk) < 0 ) - return eval->Invalid("failed dilithium verify"); - else if ( mlen != 32 || memcmp(msg,msg2,32) != 0 ) - return eval->Invalid("failed dilithium msg verify"); - else return eval->Invalid("this is actually success!"); + else + { + fprintf(stderr,"call _dilithium_verify\n"); + if ( _dilithium_verify(msg2,&mlen,&sig[0],smlen,pk) < 0 ) + return eval->Invalid("failed dilithium verify"); + else if ( mlen != 32 || memcmp(msg,msg2,32) != 0 ) + return eval->Invalid("failed dilithium msg verify"); + else return eval->Invalid("this is actually success!"); + } } else return eval->Invalid("destpubtxid or sig size didnt match send opret"); } else return eval->Invalid("failed decode dilithium spendopret"); } else return eval->Invalid("couldnt decode send opret"); From 38a94fefae6a9a7f448a056dbcc47a1993c370e8 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 06:58:12 -1100 Subject: [PATCH 109/132] Test bad sig --- src/cc/dilithium.c | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 5e6b926fa..8c56b0bc7 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3237,23 +3237,18 @@ bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,con return eval->Invalid("illegal normal vin0"); else if ( myGetTransaction(tx.vin[0].prevout.hash,vintx,hashBlock) != 0 && (numvouts= vintx.vout.size()) > 1 ) { - fprintf(stderr,"inside\n"); if ( dilithium_sendopretdecode(destpubtxid,vintx.vout[numvouts-1].scriptPubKey) == 'x' ) { - fprintf(stderr,"about to spendopret\n"); if ( dilithium_spendopretdecode(checktxid,sig,tx.vout[tx.vout.size()-1].scriptPubKey) == 'y' ) { - fprintf(stderr,"checktxid.%s vs %s\n",destpubtxid.GetHex().c_str(),checktxid.GetHex().c_str()); if ( destpubtxid == checktxid && sig.size() == smlen ) { - fprintf(stderr,"call prevoutmsg\n"); musig_prevoutmsg(msg,tx.vin[0].prevout.hash,tx.vout[0].scriptPubKey); - fprintf(stderr,"call dilithium_bigpubget\n"); if ( dilithium_bigpubget(handle,destpub33,pk,destpubtxid) < 0 ) return eval->Invalid("couldnt get bigpub"); else { - fprintf(stderr,"call _dilithium_verify\n"); + sig[777] ^= 0xaa; if ( _dilithium_verify(msg2,&mlen,&sig[0],smlen,pk) < 0 ) return eval->Invalid("failed dilithium verify"); else if ( mlen != 32 || memcmp(msg,msg2,32) != 0 ) From ddae255171e120b7fdb00bfef1a744a98352c6a2 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 07:00:21 -1100 Subject: [PATCH 110/132] Dlithium validation active, hardforking change --- src/cc/dilithium.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index 8c56b0bc7..ab8ca9ae5 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -2905,6 +2905,9 @@ int32_t main(void) cclib spend 19 \"[%224aac73ebe82c12665d1d005a0ae1a1493cb1e2c714680ef9d016f48a7c77b4a2%22,%22210255c46dbce584e3751081b39d7fc054fc807100557e73fc444481618b5706afb4ac%22]\" + this generates a really big hex, broadcast it and if all went well it will get confirmed. + a dilithium spend! + */ #define DILITHIUM_TXFEE 10000 @@ -3248,12 +3251,11 @@ bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,con return eval->Invalid("couldnt get bigpub"); else { - sig[777] ^= 0xaa; if ( _dilithium_verify(msg2,&mlen,&sig[0],smlen,pk) < 0 ) return eval->Invalid("failed dilithium verify"); else if ( mlen != 32 || memcmp(msg,msg2,32) != 0 ) return eval->Invalid("failed dilithium msg verify"); - else return eval->Invalid("this is actually success!"); + else return(true); } } else return eval->Invalid("destpubtxid or sig size didnt match send opret"); } else return eval->Invalid("failed decode dilithium spendopret"); From 98d8d03e2f8928e74cc8b3700c041806a3cf39ba Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 07:27:30 -1100 Subject: [PATCH 111/132] Gold * gold payout algo change --- src/cc/rogue_rpc.cpp | 106 ++++++++++++++++++++++--------------------- 1 file changed, 54 insertions(+), 52 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 8cfb4379f..16c09fbe9 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -947,6 +947,56 @@ UniValue rogue_extract(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) return(result); } +int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp,std::vector playerdata,uint256 gametxid,CPubKey pk) +{ + static uint32_t good,bad; static uint256 prevgame; + char str[512],*keystrokes,rogueaddr[64],str2[67]; int32_t i,numkeys; std::vector newdata; uint64_t seed; CPubKey roguepk; struct rogue_player P; + if ( gametxid == prevgame ) + return(0); + prevgame = gametxid; + roguepk = GetUnspendable(cp,0); + GetCCaddress1of2(cp,rogueaddr,roguepk,pk); + //fprintf(stderr,"call extractgame\n"); + if ( (keystrokes= rogue_extractgame(0,str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) + { + //fprintf(stderr,"numkeys.%d rogue_extractgame %s\n",numkeys,gametxid.GetHex().c_str()); + free(keystrokes); + //fprintf(stderr,"extracted.(%s)\n",str); + if ( newdata == playerdata ) + { + good++; + fprintf(stderr,"%s good.%d bad.%d\n",gametxid.GetHex().c_str(),good,bad); + return(0); + } + newdata[10] = newdata[11] = playerdata[10] = playerdata[11] = 0; + if ( newdata == playerdata ) + { + good++; + fprintf(stderr,"%s matched after clearing maxstrength good.%d bad.%d\n",gametxid.GetHex().c_str(),good,bad); + return(0); + } + for (i=0; i no playerdata, good.%d bad.%d\n",good,bad); + } + bad++; + fprintf(stderr,"%s playerdata: gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",gametxid.GetHex().c_str(),P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel); + fprintf(stderr,"newdata[%d] != playerdata[%d], numkeys.%d %s pub.%s playertxid.%s good.%d bad.%d\n",(int32_t)newdata.size(),(int32_t)playerdata.size(),numkeys,rogueaddr,pubkey33_str(str2,(uint8_t *)&pk),playertxid.GetHex().c_str(),good,bad); + } + //fprintf(stderr,"no keys rogue_extractgame %s\n",gametxid.GetHex().c_str()); + return(-1); +} + UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *params,char *method) { //vin0 -> highlander vout from creategame TCBOO @@ -975,12 +1025,12 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param if ( strcmp(method,"bailout") == 0 ) { funcid = 'Q'; - mult = 100000; + mult = 100; //100000; } else { funcid = 'H'; - mult = 200000; + mult = 200; //200000; } if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) { @@ -1005,7 +1055,7 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param { num = rogue_replay2(player,seed,keystrokes,numkeys,playerdata.size()==0?0:&P,0); if ( keystrokes != 0 ) - free(keystrokes); + free(keystrokes), keystrokes = 0; } else num = 0; mtx.vin.push_back(CTxIn(batontxid,batonvout,CScript())); mtx.vin.push_back(CTxIn(gametxid,1+maxplayers+regslot,CScript())); @@ -1034,7 +1084,7 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param mtx.vout.push_back(MakeTokensCC1vout(cp->evalcode,1,mypk)); if ( P.amulet != 0 ) mult *= 5; - cashout = (uint64_t)P.gold * mult; + cashout = (uint64_t)P.gold * P.gold * mult; fprintf(stderr,"\nextracted $$$gold.%d -> %.8f ROGUE hp.%d strength.%d/%d level.%d exp.%d dl.%d n.%d amulet.%d\n",P.gold,(double)cashout/COIN,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel,n,P.amulet); if ( funcid == 'H' && maxplayers > 1 ) { @@ -1051,7 +1101,6 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param } } mtx.vout.push_back(MakeCC1vout(cp->evalcode,CCchange + (batonvalue-3*txfee),roguepk)); - Myprivkey(mypriv); CCaddr1of2set(cp,roguepk,mypk,mypriv,myrogueaddr); CScript opret; @@ -1245,53 +1294,6 @@ UniValue rogue_setname(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) return(result); } -int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp,std::vector playerdata,uint256 gametxid,CPubKey pk) -{ - static uint32_t good,bad; static uint256 prevgame; - char str[512],*keystrokes,rogueaddr[64],str2[67]; int32_t i,numkeys; std::vector newdata; uint64_t seed; CPubKey roguepk; struct rogue_player P; - if ( gametxid == prevgame ) - return(0); - prevgame = gametxid; - roguepk = GetUnspendable(cp,0); - GetCCaddress1of2(cp,rogueaddr,roguepk,pk); - //fprintf(stderr,"call extractgame\n"); - if ( (keystrokes= rogue_extractgame(0,str,&numkeys,newdata,seed,playertxid,cp,gametxid,rogueaddr)) != 0 ) - { - //fprintf(stderr,"numkeys.%d rogue_extractgame %s\n",numkeys,gametxid.GetHex().c_str()); - free(keystrokes); - //fprintf(stderr,"extracted.(%s)\n",str); - if ( newdata == playerdata ) - { - good++; - fprintf(stderr,"%s good.%d bad.%d\n",gametxid.GetHex().c_str(),good,bad); - return(0); - } - newdata[10] = newdata[11] = playerdata[10] = playerdata[11] = 0; - if ( newdata == playerdata ) - { - good++; - fprintf(stderr,"%s matched after clearing maxstrength good.%d bad.%d\n",gametxid.GetHex().c_str(),good,bad); - return(0); - } - for (i=0; i no playerdata, good.%d bad.%d\n",good,bad); - if ( newdata.size() == 0 ) - { - good++; - return(0); - } - } - bad++; - fprintf(stderr,"%s playerdata: gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",gametxid.GetHex().c_str(),P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel); - fprintf(stderr,"newdata[%d] != playerdata[%d], numkeys.%d %s pub.%s playertxid.%s good.%d bad.%d\n",(int32_t)newdata.size(),(int32_t)playerdata.size(),numkeys,rogueaddr,pubkey33_str(str2,(uint8_t *)&pk),playertxid.GetHex().c_str(),good,bad); - } - //fprintf(stderr,"no keys rogue_extractgame %s\n",gametxid.GetHex().c_str()); - return(-1); -} - bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) { CScript scriptPubKey; std::vector vopret; uint8_t *script,e,f,funcid; int32_t i,maxplayers,decoded=0,regslot,ind,err,dispflag,gameheight,score,numvouts; CTransaction vintx,gametx; CPubKey pk; uint256 hashBlock,gametxid,tokenid,batontxid,playertxid,ptxid; int64_t buyin; std::vector playerdata,keystrokes; std::string symbol,pname; From 4dcef6624bc8f2c1da09a9e8e78bca8357872028 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 08:17:20 -1100 Subject: [PATCH 112/132] Delay after keystrokes --- src/cc/rogue/main.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index 165f01dfd..4dba36f2b 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -726,9 +726,10 @@ void rogue_progress(struct rogue_state *rs,uint64_t seed,char *keystrokes,int32_ sprintf(params,"[\"keystrokes\",\"17\",\"[%%22%s%%22,%%22%s%%22]\"]",Gametxidstr,hexstr); if ( (retstr= komodo_issuemethod(USERPASS,"cclib",params,ROGUE_PORT)) != 0 ) { - //fprintf(stderr,"KEYSTROKES.(%s)\n",retstr); + fprintf(stderr,"KEYSTROKES.(%s)\n",retstr); free(retstr); } + sleep(1); } } } From b88129c21cfeb98a32131056daafdcfc462652b7 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 08:19:09 -1100 Subject: [PATCH 113/132] Force keystrokes --- src/cc/rogue/rogue.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/cc/rogue/rogue.c b/src/cc/rogue/rogue.c index e8de063de..52d41435c 100644 --- a/src/cc/rogue/rogue.c +++ b/src/cc/rogue/rogue.c @@ -567,6 +567,8 @@ playit(struct rogue_state *rs) } } } + if ( rs->guiflag != 0 ) + flushkeystrokes(rs); endit(0); } From 46055e824fbf3d9b1e132863026faef9eb30236e Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 08:29:21 -1100 Subject: [PATCH 114/132] Log keystrokes to keystrokes.log --- src/cc/rogue/main.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index 4dba36f2b..5de27317e 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -723,10 +723,17 @@ void rogue_progress(struct rogue_state *rs,uint64_t seed,char *keystrokes,int32_ } else { + static FILE *fp; + if ( fp == 0 ) + fp = fopen("keystrokes.log","a"); sprintf(params,"[\"keystrokes\",\"17\",\"[%%22%s%%22,%%22%s%%22]\"]",Gametxidstr,hexstr); if ( (retstr= komodo_issuemethod(USERPASS,"cclib",params,ROGUE_PORT)) != 0 ) { - fprintf(stderr,"KEYSTROKES.(%s)\n",retstr); + if ( fp != 0 ) + { + fprintf(fp,"%s\n",retstr); + fflush(fp); + } free(retstr); } sleep(1); From df66ea2b9da0a3bcafc4517077736607cf255f8e Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 08:37:33 -1100 Subject: [PATCH 115/132] Kill the zombies --- src/cc/rogue/state.c | 2 +- src/cc/rogue_rpc.cpp | 33 +++++++++++++++++++++------------ 2 files changed, 22 insertions(+), 13 deletions(-) diff --git a/src/cc/rogue/state.c b/src/cc/rogue/state.c index 7a0e2e4c6..b0176a042 100644 --- a/src/cc/rogue/state.c +++ b/src/cc/rogue/state.c @@ -1432,7 +1432,7 @@ rs_write_object(struct rogue_state *rs,FILE *savef, THING *o) if ( o->_o._o_packch != 0 ) { item = &rs->P.roguepack[rs->P.packsize]; - if ( 0 && pstats.s_hpt <= 0 ) + if ( 1 && pstats.s_hpt <= 0 ) { //fprintf(stderr,"KILLED\n"); rs->P.gold = -1; diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 16c09fbe9..4790932d1 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -883,13 +883,22 @@ char *rogue_extractgame(int32_t makefiles,char *str,int32_t *numkeysp,std::vecto if ( endP.gold <= 0 || endP.hitpoints <= 0 || (endP.strength&0xffff) <= 0 || endP.level <= 0 || endP.experience <= 0 || endP.dungeonlevel <= 0 ) { //fprintf(stderr,"zero value character was killed -> no playerdata\n"); - //newdata.resize(0); - P.gold = (P.gold * 8) / 10; + newdata.resize(0); + //P.gold = (P.gold * 8) / 10; + if ( keystrokes != 0 ) + { + free(keystrokes); + keystrokes = 0; + *numkeysp = 0; + } + } + else + { + sprintf(str,"extracted $$$gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",endP.gold,endP.hitpoints,endP.strength&0xffff,endP.strength>>16,endP.level,endP.experience,endP.dungeonlevel); + fprintf(stderr,"%s\n",str); + *numkeysp = numkeys; + return(keystrokes); } - sprintf(str,"extracted $$$gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",endP.gold,endP.hitpoints,endP.strength&0xffff,endP.strength>>16,endP.level,endP.experience,endP.dungeonlevel); - fprintf(stderr,"%s\n",str); - *numkeysp = numkeys; - return(keystrokes); } else num = 0; } else @@ -979,9 +988,9 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp ((uint8_t *)&P)[i] = playerdata[i]; if ( P.gold <= 0 || P.hitpoints <= 0 || (P.strength&0xffff) <= 0 || P.level <= 0 || P.experience <= 0 || P.dungeonlevel <= 0 ) { - P.gold = (P.gold * 8) / 10; - for (i=0; i no playerdata\n"); - //newdata.resize(0); - P.gold = (P.gold * 8) / 10; + newdata.resize(0); + //P.gold = (P.gold * 8) / 10; } - //else + else { //if ( maxplayers == 1 ) // mult /= 2; From b0735e2f327ce7ca08224e274b86a3a177a9d2d7 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 09:11:38 -1100 Subject: [PATCH 116/132] Gold payout = (gold * gold * level * 10) satoshi --- src/cc/rogue_rpc.cpp | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 4790932d1..1a4f7c1cd 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -1020,7 +1020,7 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param // vout0 -> 1% ingame gold // get any playerdata, get all keystrokes, replay game and compare final state CMutableTransaction mtx = CreateNewContextualCMutableTransaction(Params().GetConsensus(), komodo_nextheight()); - UniValue result(UniValue::VOBJ); std::string rawtx,symbol,pname; CTransaction gametx; uint64_t seed,mult; int64_t buyin,batonvalue,inputsum,cashout,CCchange=0; int32_t i,err,gameheight,tmp,numplayers,regslot,n,num,numkeys,maxplayers,batonht,batonvout; char myrogueaddr[64],*keystrokes = 0; std::vector playerdata,newdata,nodata; uint256 batontxid,playertxid,gametxid; CPubKey mypk,roguepk; uint8_t player[10000],mypriv[32],funcid; + UniValue result(UniValue::VOBJ); std::string rawtx,symbol,pname; CTransaction gametx; uint64_t seed,mult; int64_t buyin,batonvalue,inputsum,cashout,CCchange=0; int32_t i,err,gameheight,tmp,numplayers,regslot,n,num,dungeonlevel,numkeys,maxplayers,batonht,batonvout; char myrogueaddr[64],*keystrokes = 0; std::vector playerdata,newdata,nodata; uint256 batontxid,playertxid,gametxid; CPubKey mypk,roguepk; uint8_t player[10000],mypriv[32],funcid; struct CCcontract_info *cpTokens, tokensC; if ( txfee == 0 ) @@ -1034,12 +1034,12 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param if ( strcmp(method,"bailout") == 0 ) { funcid = 'Q'; - mult = 100; //100000; + mult = 10; //100000; } else { funcid = 'H'; - mult = 200; //200000; + mult = 20; //200000; } if ( params != 0 && (n= cJSON_GetArraySize(params)) > 0 ) { @@ -1093,7 +1093,10 @@ UniValue rogue_finishgame(uint64_t txfee,struct CCcontract_info *cp,cJSON *param mtx.vout.push_back(MakeTokensCC1vout(cp->evalcode,1,mypk)); if ( P.amulet != 0 ) mult *= 5; - cashout = (uint64_t)P.gold * P.gold * mult; + dungeonlevel = P.dungeonlevel; + if ( P.amulet != 0 && dungeonlevel < 21 ) + dungeonlevel = 21; + cashout = (uint64_t)P.gold * P.gold * mult * dungeonlevel; fprintf(stderr,"\nextracted $$$gold.%d -> %.8f ROGUE hp.%d strength.%d/%d level.%d exp.%d dl.%d n.%d amulet.%d\n",P.gold,(double)cashout/COIN,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel,n,P.amulet); if ( funcid == 'H' && maxplayers > 1 ) { From 8c5ba39d22f91af50e0bf93d1e7cd2f1dce5828f Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Mon, 25 Feb 2019 13:18:14 +0800 Subject: [PATCH 117/132] fix ipaddress --- src/cc/rogue/main.c | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index 5de27317e..02690a482 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -587,9 +587,9 @@ char *curl_post(CURL **cHandlep,char *url,char *userpass,char *postfields,char * return(chunk.memory); } -uint16_t _komodo_userpass(char *username, char *password, char *ipaddress, FILE *fp) +uint16_t _komodo_userpass(char *username, char *password, FILE *fp) { - char *rpcuser,*rpcpassword,*str,line[8192]; uint16_t port = 0; + char *rpcuser,*rpcpassword,*str,*ipaddress,line[8192]; uint16_t port = 0; rpcuser = rpcpassword = 0; username[0] = password[0] = 0; while ( fgets(line,sizeof(line),fp) != 0 ) @@ -609,6 +609,7 @@ uint16_t _komodo_userpass(char *username, char *password, char *ipaddress, FILE else if ( (str= strstr(line,(char *)"ipaddress")) != 0 ) { ipaddress = parse_conf_line(str,(char *)"ipaddress"); + strcpy(IPADDRESS,ipaddress); } } if ( rpcuser != 0 && rpcpassword != 0 ) @@ -616,7 +617,7 @@ uint16_t _komodo_userpass(char *username, char *password, char *ipaddress, FILE strcpy(username,rpcuser); strcpy(password,rpcpassword); } - //printf("rpcuser.(%s) rpcpassword.(%s) KMDUSERPASS.(%s) %u\n",rpcuser,rpcpassword,KMDUSERPASS,port); + //printf("rpcuser.(%s) rpcpassword.(%s) %u ipaddress.%s\n",rpcuser,rpcpassword,port,ipaddress); if ( rpcuser != 0 ) free(rpcuser); if ( rpcpassword != 0 ) @@ -661,7 +662,7 @@ uint16_t _komodo_userpass(char *username, char *password, char *ipaddress, FILE //printf("test.(%s) -> [%s] statename.(%s) %s\n",test,ASSETCHAINS_SYMBOL,symbol,fname); }*/ -uint16_t komodo_userpass(char *userpass,char *symbol,char *ipaddress) +uint16_t komodo_userpass(char *userpass,char *symbol) { FILE *fp; uint16_t port = 0; char fname[512],username[512],password[512],confname[KOMODO_ASSETCHAIN_MAXLEN]; userpass[0] = 0; @@ -677,7 +678,7 @@ uint16_t komodo_userpass(char *userpass,char *symbol,char *ipaddress) //komodo_statefname(fname,symbol,confname); if ( (fp= fopen(confname,"rb")) != 0 ) { - port = _komodo_userpass(username,password,ipaddress,fp); + port = _komodo_userpass(username,password,fp); sprintf(userpass,"%s:%s",username,password); if ( strcmp(symbol,ASSETCHAINS_SYMBOL) == 0 ) strcpy(USERPASS,userpass); @@ -809,10 +810,10 @@ int main(int argc, char **argv, char **envp) ASSETCHAINS_SYMBOL[j++] = toupper(c); } ASSETCHAINS_SYMBOL[j++] = 0; - ROGUE_PORT = komodo_userpass(userpass,ASSETCHAINS_SYMBOL,IPADDRESS); + ROGUE_PORT = komodo_userpass(userpass,ASSETCHAINS_SYMBOL); if ( IPADDRESS[0] == 0 ) strcpy(IPADDRESS,"127.0.0.1"); - printf("ASSETCHAINS_SYMBOL.(%s) port.%u (%s)\n",ASSETCHAINS_SYMBOL,ROGUE_PORT,USERPASS); sleep(1); + printf("ASSETCHAINS_SYMBOL.(%s) port.%u (%s) IPADDRESS.%s \n",ASSETCHAINS_SYMBOL,ROGUE_PORT,USERPASS,IPADDRESS); sleep(1); if ( argc == 2 && (fp=fopen(argv[1],"rb")) == 0 ) { seed = atol(argv[1]); From 6f5d9655c903ae265eb0f0cb72da4cf9af4b0b9d Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Mon, 25 Feb 2019 13:20:48 +0800 Subject: [PATCH 118/132] fix --- src/musigtest.py | 189 --------------------------------------- src/wallet/rpcwallet.cpp | 8 +- 2 files changed, 4 insertions(+), 193 deletions(-) delete mode 100755 src/musigtest.py diff --git a/src/musigtest.py b/src/musigtest.py deleted file mode 100755 index 0880f1494..000000000 --- a/src/musigtest.py +++ /dev/null @@ -1,189 +0,0 @@ -#!/usr/bin/env python3 -import platform -import os -import re -import json -import random -import base58 -import binascii -import hashlib -import sys -import time -from slickrpc import Proxy - -# fucntion to define rpc_connection -def def_credentials(chain): - rpcport = ''; - operating_system = platform.system() - if operating_system == 'Darwin': - ac_dir = os.environ['HOME'] + '/Library/Application Support/Komodo' - elif operating_system == 'Linux': - ac_dir = os.environ['HOME'] + '/.komodo' - elif operating_system == 'Windows': - ac_dir = '%s/komodo/' % os.environ['APPDATA'] - if chain == 'KMD': - coin_config_file = str(ac_dir + '/komodo.conf') - else: - coin_config_file = str(ac_dir + '/' + chain + '/' + chain + '.conf') - with open(coin_config_file, 'r') as f: - for line in f: - l = line.rstrip() - if re.search('rpcuser', l): - rpcuser = l.replace('rpcuser=', '') - elif re.search('rpcpassword', l): - rpcpassword = l.replace('rpcpassword=', '') - elif re.search('rpcport', l): - rpcport = l.replace('rpcport=', '') - if len(rpcport) == 0: - if chain == 'KMD': - rpcport = 7771 - else: - print("rpcport not in conf file, exiting") - print("check " + coin_config_file) - exit(1) - return (Proxy("http://%s:%s@127.0.0.1:%d" % (rpcuser, rpcpassword, int(rpcport)))) - - -# generate address, validate address, dump private key -def genvaldump(rpc_connection): - # get new address - address = rpc_connection.getnewaddress() - # validate address - validateaddress_result = rpc_connection.validateaddress(address) - pubkey = validateaddress_result['pubkey'] - address = validateaddress_result['address'] - # dump private key for the address - privkey = rpc_connection.dumpprivkey(address) - # function output - output = [pubkey, privkey, address] - return(output) - -CHAIN = 'MUSIG' #sys.argv[1] - -rpc = def_credentials(CHAIN) - -pubkeys = [] -address_info = [] -ret = input('Do you want to generate new pubkeys? ').lower() - -if ret.startswith('y'): - numpks = int(input('Enter number of pubkeys to combine: ')) - if os.path.isfile("list.json"): - print('Already have list.json, move it if you would like to generate a new set.') - sys.exit(0) - while len(address_info) < numpks: - addressinfo = genvaldump(rpc) - address_info.append(addressinfo) - f = open("list.json", "w+") - f.write(json.dumps(address_info)) -else: - if os.path.isfile("list.json"): - with open('list.json') as list: - address_info = json.load(list) - else: - sys.exit('No list.json you need to create new pubkeys!') - -for addressinfo in address_info: - pubkeys.append(addressinfo[0]) - -ret = rpc.setpubkey(pubkeys[0]) -ret = rpc.cclib("combine", "18", str(pubkeys)) -pkhash = str(ret['pkhash']) -combinedpk = str(ret['combined_pk']) -print('Your combined pubkey is: ' + combinedpk) -print('Your pkhash is: ' + pkhash) -amount = int(input('Enter amount to send: ')) -tmp = str([combinedpk, amount]) -hex = rpc.cclib("send", "18", tmp)['hex'] -senttxid = rpc.sendrawtransaction(hex) -print('Your senttxid is: ' + senttxid) - -print("Waiting for tx to be confirmed") -while True: - confirmed = int(rpc.gettransaction(senttxid)["confirmations"]) - if not confirmed: - time.sleep(10) - else: - print('SentTX confirmed') - break - -scriptPubKey = rpc.getrawtransaction(senttxid,1)['vout'][1]['scriptPubKey']['hex'] -print('Your scriptPubKey is: ' + scriptPubKey) -tmp = str([senttxid, scriptPubKey]) -msg = rpc.cclib("calcmsg", "18", tmp)['msg'] -print('Your msg is: ' + msg) - -i = 0; -commitments = [] -for pubkey in pubkeys: - ret = rpc.setpubkey(pubkey) - tmp = str([i, len(pubkeys), combinedpk, pkhash, msg]) - commitments.append(rpc.cclib("session", "18", tmp)['commitment']) - i = i + 1 - -#print(commitments) - -i = 0 -nonces = [] -for pubkey in pubkeys: - ret = rpc.setpubkey(pubkey) - n = 0 - for commitment in commitments: - tmp = str([i, pkhash, n, commitment]) - ret = rpc.cclib("commit", "18", tmp) - try: - nonces.append(ret['nonce']) - except: - x = 1 - n = n + 1 - i = i + 1 - -#print(nonces) - -i = 0 -partialsigs = [] -for pubkey in pubkeys: - ret = rpc.setpubkey(pubkey) - n = 0 - for nonce in nonces: - tmp = str([i, pkhash, n, nonce]) - ret = rpc.cclib("nonce", "18", tmp) - try: - partialsigs.append(ret['partialsig']) - except: - x = 1 - n = n + 1 - i = i + 1 - -#print(partialsigs) - -i = 0 -combinedsigs = [] -for pubkey in pubkeys: - ret = rpc.setpubkey(pubkey) - n = 0 - for partialsig in partialsigs: - tmp = str([i, pkhash, n, partialsig]) - ret = rpc.cclib("partialsig", "18", tmp) - try: - combinedsigs.append(ret['combinedsig']) - except: - x = 1 - n = n + 1 - i = i + 1 - -#print(combinedsigs) - -tmp = str([msg, combinedpk, combinedsigs[0]]) -ret = rpc.cclib("verify", "18", tmp) - -#print(ret) - -tmp = str([senttxid, scriptPubKey, combinedsigs[0]]) -ret = rpc.cclib("spend", "18", tmp) - -print(ret) - -ret = rpc.sendrawtransaction(ret['hex']) - -print(ret) diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp index 8cffd78f7..0ed2f866c 100644 --- a/src/wallet/rpcwallet.cpp +++ b/src/wallet/rpcwallet.cpp @@ -5308,8 +5308,8 @@ UniValue setpubkey(const UniValue& params, bool fHelp) char Raddress[64]; uint8_t pubkey33[33]; - //if ( NOTARY_PUBKEY33[0] == 0 ) - //{ + if ( NOTARY_PUBKEY33[0] == 0 ) + { if (strlen(params[0].get_str().c_str()) == 66) { decode_hex(pubkey33,33,(char *)params[0].get_str().c_str()); @@ -5337,14 +5337,14 @@ UniValue setpubkey(const UniValue& params, bool fHelp) USE_EXTERNAL_PUBKEY = 1; } } else result.push_back(Pair("error", "pubkey is wrong length, must be 66 char hex string.")); - /*} + } else { result.push_back(Pair("error", "Can only set pubkey once, to change it you need to restart your daemon, pubkey in use is below.")); pubkey2addr((char *)Raddress,(uint8_t *)NOTARY_PUBKEY33); std::string address_ret; address_ret.assign(Raddress); result.push_back(Pair("address",address_ret)); - }*/ + } result.push_back(Pair("pubkey", NOTARY_PUBKEY)); return result; } From c5930804ab2789402fa7c0a0d73460a1aa32488b Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 18:24:33 -1100 Subject: [PATCH 119/132] Flush keystrokes every 1000 --- src/cc/rogue/rogue.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue/rogue.c b/src/cc/rogue/rogue.c index 52d41435c..53f6da353 100644 --- a/src/cc/rogue/rogue.c +++ b/src/cc/rogue/rogue.c @@ -560,7 +560,7 @@ playit(struct rogue_state *rs) } else { - if ( rs->needflush != 0 && rs->num > 8000 ) + if ( rs->needflush != 0 && rs->num > 1000 ) { if ( flushkeystrokes(rs) == 0 ) rs->needflush = 0; From 54ee605f7f5be48886c14e9bfbc56564096238f8 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 18:27:26 -1100 Subject: [PATCH 120/132] Save params in keystrokes.log --- src/cc/rogue/main.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/cc/rogue/main.c b/src/cc/rogue/main.c index 5de27317e..ec347dd12 100644 --- a/src/cc/rogue/main.c +++ b/src/cc/rogue/main.c @@ -731,6 +731,7 @@ void rogue_progress(struct rogue_state *rs,uint64_t seed,char *keystrokes,int32_ { if ( fp != 0 ) { + fprintf(fp,"%s\n",params); fprintf(fp,"%s\n",retstr); fflush(fp); } From e8a36b89826e934a20f95a229b3ab103a67414af Mon Sep 17 00:00:00 2001 From: blackjok3r Date: Mon, 25 Feb 2019 17:12:25 +0800 Subject: [PATCH 121/132] Update to enable using a single node with musigtest.py script. Fix crash in nonce step. --- src/cc/musig.cpp | 126 +++++++++++++++--------- src/musigtest.py | 200 +++++++++++++++++++++++++++++++++++++++ src/wallet/rpcwallet.cpp | 2 +- 3 files changed, 282 insertions(+), 46 deletions(-) create mode 100755 src/musigtest.py diff --git a/src/cc/musig.cpp b/src/cc/musig.cpp index 5986f8716..35293088c 100644 --- a/src/cc/musig.cpp +++ b/src/cc/musig.cpp @@ -33,7 +33,6 @@ } sendrawtransaction of the above hex. - ./komodo-cli -ac_name=MUSIG getrawtransaction 5ce74037a153ee210413b48d4e88638b99825a2de1a1f1aa0d36ebf93019824c 1 "vout": [ { @@ -83,7 +82,7 @@ the "msg" is what needs to be signed to create a valid spend 5 args: ind, numsigners, combined_pk, pkhash, message to be signed on node with pubkey: 02fb6aa0b96cad24d46b5da93eba3864c45ce07a73bba12da530ae841e140fcf28 - ./komodo-cli -ac_name=MUSIG cclib session 18 '[0,2,"03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b","c1b34139744f3b54b652dc741ebd0f9d5b53ad28795cc6614dd8ad3aaabf15ae","f5d91999b23b85630a4cbd0baea3736529411b052cf5f1f4345c5d181af12825"]' + ./komodo-cli -ac_name=MUSIG cclib session 18 '[0,2,"03f016c348437c7422eed92d865aa9789614f75327cada463eefc566126b54785b","5cb5a225064ca6ffc1438cb2a6ac2ac65fe2d5055dc7f6c7ebffb9a231f8912b","f7fb85d1412814e3c2f98b990802af6ee33dad368c6ba05c2050e9e5506fcd75"]' { "myind": 0, "numsigners": 2, @@ -221,7 +220,9 @@ struct musig_info secp256k1_musig_partial_signature *partial_sig; //[N_SIGNERS]; int32_t myind,num,numcommits,numnonces,numpartials; uint8_t msg[32],pkhash[32],combpk[33]; -} *MUSIG; +}; + +std::vector MUSIG; struct musig_info *musig_infocreate(int32_t myind,int32_t num) { @@ -412,23 +413,33 @@ UniValue musig_combine(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t i,n,myind,num; char *pkstr,*pkhashstr,*msgstr; uint8_t session[32],msg[32],pkhash[32],privkey[32],pub33[33]; CPubKey pk; char str[67]; + UniValue result(UniValue::VOBJ); int32_t i,n,myind,num,musiglocation; char *pkstr,*pkhashstr,*msgstr; uint8_t session[32],msg[32],pkhash[32],privkey[32],pub33[33]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) == 5 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) >= 5 ) { myind = juint(jitem(params,0),0); num = juint(jitem(params,1),0); if ( myind < 0 || myind >= num || num <= 0 ) return(cclib_error(result,"illegal myindex and numsigners")); - if ( MUSIG != 0 ) - musig_infofree(MUSIG), MUSIG = 0; - MUSIG = musig_infocreate(myind,num); - if ( musig_parsepubkey(ctx,MUSIG->combined_pk,jitem(params,2)) < 0 ) + if ( n > 5 ) + musiglocation = juint(jitem(params,5),0); + else if ( n == 5 ) + musiglocation = 0; + //printf("number of params.%i musiglocation.%i\n",n,musiglocation); + if ( MUSIG.size() > musiglocation ) + { + for (int i = 0; i < MUSIG.size()-1; i++) + musig_infofree(MUSIG[i]); + MUSIG.clear(); + } + struct musig_info *temp_musig = musig_infocreate(myind,num); + MUSIG.push_back(temp_musig); + if ( musig_parsepubkey(ctx,MUSIG[musiglocation]->combined_pk,jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing combined_pubkey")); - else if ( cclib_parsehash(MUSIG->pkhash,jitem(params,3),32) < 0 ) + else if ( cclib_parsehash(MUSIG[musiglocation]->pkhash,jitem(params,3),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( cclib_parsehash(MUSIG->msg,jitem(params,4),32) < 0 ) + else if ( cclib_parsehash(MUSIG[musiglocation]->msg,jitem(params,4),32) < 0 ) return(cclib_error(result,"error parsing msg")); Myprivkey(privkey); GetRandBytes(session,32); @@ -458,15 +469,17 @@ UniValue musig_session(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * my_index: index of this signer in the signers array * seckey: the signer's 32-byte secret key (cannot be NULL) */ - if ( secp256k1_musig_session_initialize(ctx,&MUSIG->session,MUSIG->signer_data, &MUSIG->nonce_commitments[MUSIG->myind * 32],session,MUSIG->msg,&MUSIG->combined_pk,MUSIG->pkhash,MUSIG->num,MUSIG->myind,privkey) > 0 ) + //fprintf(stderr, "SESSION: struct_size.%li using struct %i\n",MUSIG.size(), musiglocation); + if ( secp256k1_musig_session_initialize(ctx,&MUSIG[musiglocation]->session,MUSIG[musiglocation]->signer_data, &MUSIG[musiglocation]->nonce_commitments[MUSIG[musiglocation]->myind * 32],session,MUSIG[musiglocation]->msg,&MUSIG[musiglocation]->combined_pk,MUSIG[musiglocation]->pkhash,MUSIG[musiglocation]->num,MUSIG[musiglocation]->myind,privkey) > 0 ) { memset(session,0,sizeof(session)); result.push_back(Pair("myind",(int64_t)myind)); result.push_back(Pair("numsigners",(int64_t)num)); for (i=0; i<32; i++) - sprintf(&str[i<<1],"%02x",MUSIG->nonce_commitments[MUSIG->myind*32 + i]); + sprintf(&str[i<<1],"%02x",MUSIG[musiglocation]->nonce_commitments[MUSIG[musiglocation]->myind*32 + i]); str[64] = 0; - MUSIG->numcommits = 1; + if ( n == 5 ) + MUSIG[musiglocation]->numcommits = 1; result.push_back(Pair("commitment",str)); result.push_back(Pair("result","success")); return(result); @@ -483,18 +496,22 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; size_t clen = CPubKey::PUBLIC_KEY_SIZE; - UniValue result(UniValue::VOBJ); int32_t i,n,ind; uint8_t pkhash[32]; CPubKey pk; char str[67]; + UniValue result(UniValue::VOBJ); int32_t i,n,ind,myind; uint8_t pkhash[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) >= 3 ) { + if ( n > 3 ) + myind = juint(jitem(params,3),0); + else if ( n == 3 ) + myind = 0; if ( cclib_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG[myind]->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); - else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG[myind]->num ) return(cclib_error(result,"illegal ind for session")); - else if ( cclib_parsehash(&MUSIG->nonce_commitments[ind*32],jitem(params,2),32) < 0 ) + else if ( cclib_parsehash(&MUSIG[myind]->nonce_commitments[ind*32],jitem(params,2),32) < 0 ) return(cclib_error(result,"error parsing commitment")); /** Gets the signer's public nonce given a list of all signers' data with commitments * @@ -512,16 +529,18 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * number of signers participating in the MuSig. */ result.push_back(Pair("added_index",ind)); - MUSIG->numcommits++; - if ( MUSIG->numcommits >= MUSIG->num && secp256k1_musig_session_get_public_nonce(ctx,&MUSIG->session,MUSIG->signer_data,&MUSIG->nonces[MUSIG->myind],MUSIG->commitment_ptrs,MUSIG->num) > 0 ) + //fprintf(stderr, "COMMIT: struct_size.%li using_struct.%i added_index.%i\n",MUSIG.size(), myind, ind); + MUSIG[myind]->numcommits++; + if ( MUSIG[myind]->numcommits >= MUSIG[myind]->num && secp256k1_musig_session_get_public_nonce(ctx,&MUSIG[myind]->session,MUSIG[myind]->signer_data,&MUSIG[myind]->nonces[MUSIG[myind]->myind],MUSIG[myind]->commitment_ptrs,MUSIG[myind]->num) > 0 ) { - if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG->nonces[MUSIG->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) + if ( secp256k1_ec_pubkey_serialize(ctx,(uint8_t *)pk.begin(),&clen,&MUSIG[myind]->nonces[MUSIG[myind]->myind],SECP256K1_EC_COMPRESSED) > 0 && clen == 33 ) { for (i=0; i<33; i++) sprintf(&str[i<<1],"%02x",((uint8_t *)pk.begin())[i]); str[66] = 0; - MUSIG->numnonces = 1; - result.push_back(Pair("myind",MUSIG->myind)); + if ( n == 5 ) + MUSIG[myind]->numnonces = 1; + result.push_back(Pair("myind",MUSIG[myind]->myind)); result.push_back(Pair("nonce",str)); result.push_back(Pair("result","success")); } else return(cclib_error(result,"error serializing nonce (pubkey)")); @@ -538,18 +557,22 @@ UniValue musig_commit(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t i,n,ind; uint8_t pkhash[32],psig[32]; CPubKey pk; char str[67]; + UniValue result(UniValue::VOBJ); int32_t i,n,ind,myind; uint8_t pkhash[32],psig[32]; CPubKey pk; char str[67]; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) >= 3 ) { + if ( n > 3 ) + myind = juint(jitem(params,3),0); + else if ( n == 3 ) + myind = 0; if ( cclib_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG[myind]->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); - else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG[myind]->num ) return(cclib_error(result,"illegal ind for session")); - else if ( musig_parsepubkey(ctx,MUSIG->nonces[ind],jitem(params,2)) < 0 ) + else if ( musig_parsepubkey(ctx,MUSIG[myind]->nonces[ind],jitem(params,2)) < 0 ) return(cclib_error(result,"error parsing nonce")); result.push_back(Pair("added_index",ind)); /** Checks a signer's public nonce against a commitment to said nonce, and update @@ -563,9 +586,17 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * with `musig_session_initialize_verifier`. * In: nonce: signer's alleged public nonce (cannot be NULL) */ - for (i=0; inum; i++) + MUSIG[myind]->numnonces++; + //fprintf(stderr, "NONCE: struct_size.%li using_struct.%i added_index.%i numnounces.%i num.%i\n",MUSIG.size(), myind, ind, MUSIG[myind]->numnonces, MUSIG[myind]->num); + if ( MUSIG[myind]->numnonces < MUSIG[myind]->num ) { - if ( secp256k1_musig_set_nonce(ctx,&MUSIG->signer_data[i],&MUSIG->nonces[i]) == 0 ) + result.push_back(Pair("status","not enough nonces")); + result.push_back(Pair("result","success")); + return(result); + } + for (i=0; inum; i++) + { + if ( secp256k1_musig_set_nonce(ctx,&MUSIG[myind]->signer_data[i],&MUSIG[myind]->nonces[i]) == 0 ) return(cclib_error(result,"error setting nonce")); } /** Updates a session with the combined public nonce of all signers. The combined @@ -586,20 +617,20 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) * adaptor: point to add to the combined public nonce. If NULL, nothing is * added to the combined nonce. */ - MUSIG->numnonces++; - if ( MUSIG->numnonces >= MUSIG->num && secp256k1_musig_session_combine_nonces(ctx,&MUSIG->session,MUSIG->signer_data,MUSIG->num,NULL,NULL) > 0 ) + if ( secp256k1_musig_session_combine_nonces(ctx,&MUSIG[myind]->session,MUSIG[myind]->signer_data,MUSIG[myind]->num,NULL,NULL) > 0 ) { - if ( secp256k1_musig_partial_sign(ctx,&MUSIG->session,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + if ( secp256k1_musig_partial_sign(ctx,&MUSIG[myind]->session,&MUSIG[myind]->partial_sig[MUSIG[myind]->myind]) > 0 ) { - if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG[myind]->partial_sig[MUSIG[myind]->myind]) > 0 ) { for (i=0; i<32; i++) sprintf(&str[i<<1],"%02x",psig[i]); str[64] = 0; - result.push_back(Pair("myind",MUSIG->myind)); + result.push_back(Pair("myind",MUSIG[myind]->myind)); result.push_back(Pair("partialsig",str)); result.push_back(Pair("result","success")); - MUSIG->numpartials = 1; + if ( n == 5 ) + MUSIG[myind]->numpartials = 1; return(result); } else return(cclib_error(result,"error serializing partial sig")); } else return(cclib_error(result,"error making partial sig")); @@ -610,24 +641,29 @@ UniValue musig_nonce(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) { static secp256k1_context *ctx; - UniValue result(UniValue::VOBJ); int32_t i,ind,n; uint8_t pkhash[32],psig[32],out64[64]; char str[129]; secp256k1_schnorrsig sig; + UniValue result(UniValue::VOBJ); int32_t i,ind,n,myind; uint8_t pkhash[32],psig[32],out64[64]; char str[129]; secp256k1_schnorrsig sig; if ( ctx == 0 ) ctx = secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); - if ( params != 0 && (n= cJSON_GetArraySize(params)) == 3 ) + if ( params != 0 && (n= cJSON_GetArraySize(params)) >= 3 ) { + if ( n > 3 ) + myind = juint(jitem(params,3),0); + else if ( n == 3 ) + myind = 0; if ( cclib_parsehash(pkhash,jitem(params,0),32) < 0 ) return(cclib_error(result,"error parsing pkhash")); - else if ( memcmp(MUSIG->pkhash,pkhash,32) != 0 ) + else if ( memcmp(MUSIG[myind]->pkhash,pkhash,32) != 0 ) return(cclib_error(result,"pkhash doesnt match session pkhash")); - else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG->num ) + else if ( (ind= juint(jitem(params,1),0)) < 0 || ind >= MUSIG[myind]->num ) return(cclib_error(result,"illegal ind for session")); else if ( cclib_parsehash(psig,jitem(params,2),32) < 0 ) return(cclib_error(result,"error parsing psig")); - else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG->partial_sig[ind],psig) == 0 ) + else if ( secp256k1_musig_partial_signature_parse(ctx,&MUSIG[myind]->partial_sig[ind],psig) == 0 ) return(cclib_error(result,"error parsing partialsig")); result.push_back(Pair("added_index",ind)); - MUSIG->numpartials++; - if ( MUSIG->numpartials >= MUSIG->num && secp256k1_musig_partial_sig_combine(ctx,&MUSIG->session,&sig,MUSIG->partial_sig,MUSIG->num) > 0 ) + //fprintf(stderr, "SIG: struct_size.%li using_struct.%i added_index.%i\n",MUSIG.size(), myind, ind); + MUSIG[myind]->numpartials++; + if ( MUSIG[myind]->numpartials >= MUSIG[myind]->num && secp256k1_musig_partial_sig_combine(ctx,&MUSIG[myind]->session,&sig,MUSIG[myind]->partial_sig,MUSIG[myind]->num) > 0 ) { if ( secp256k1_schnorrsig_serialize(ctx,out64,&sig) > 0 ) { @@ -640,7 +676,7 @@ UniValue musig_partialsig(uint64_t txfee,struct CCcontract_info *cp,cJSON *param } else { - if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG->partial_sig[MUSIG->myind]) > 0 ) + if ( secp256k1_musig_partial_signature_serialize(ctx,psig,&MUSIG[myind]->partial_sig[MUSIG[myind]->myind]) > 0 ) { result.push_back(Pair("myind",ind)); for (i=0; i<32; i++) diff --git a/src/musigtest.py b/src/musigtest.py new file mode 100755 index 000000000..a452b7e97 --- /dev/null +++ b/src/musigtest.py @@ -0,0 +1,200 @@ +#!/usr/bin/env python3 +import platform +import os +import re +import json +import random +import base58 +import binascii +import hashlib +import sys +import time +from slickrpc import Proxy + +# fucntion to define rpc_connection +def def_credentials(chain): + rpcport = ''; + operating_system = platform.system() + if operating_system == 'Darwin': + ac_dir = os.environ['HOME'] + '/Library/Application Support/Komodo' + elif operating_system == 'Linux': + ac_dir = os.environ['HOME'] + '/.komodo' + elif operating_system == 'Windows': + ac_dir = '%s/komodo/' % os.environ['APPDATA'] + if chain == 'KMD': + coin_config_file = str(ac_dir + '/komodo.conf') + else: + coin_config_file = str(ac_dir + '/' + chain + '/' + chain + '.conf') + with open(coin_config_file, 'r') as f: + for line in f: + l = line.rstrip() + if re.search('rpcuser', l): + rpcuser = l.replace('rpcuser=', '') + elif re.search('rpcpassword', l): + rpcpassword = l.replace('rpcpassword=', '') + elif re.search('rpcport', l): + rpcport = l.replace('rpcport=', '') + if len(rpcport) == 0: + if chain == 'KMD': + rpcport = 7771 + else: + print("rpcport not in conf file, exiting") + print("check " + coin_config_file) + exit(1) + return (Proxy("http://%s:%s@127.0.0.1:%d" % (rpcuser, rpcpassword, int(rpcport)))) + + +# generate address, validate address, dump private key +def genvaldump(rpc_connection): + # get new address + address = rpc_connection.getnewaddress() + # validate address + validateaddress_result = rpc_connection.validateaddress(address) + pubkey = validateaddress_result['pubkey'] + address = validateaddress_result['address'] + # dump private key for the address + privkey = rpc_connection.dumpprivkey(address) + # function output + output = [pubkey, privkey, address] + return(output) + +CHAIN = 'MUSIG' #sys.argv[1] + +rpc = def_credentials(CHAIN) + +pubkeys = [] +address_info = [] +ret = input('Do you want to generate new pubkeys? ').lower() + +if ret.startswith('y'): + numpks = int(input('Enter number of pubkeys to combine: ')) + if os.path.isfile("list.json"): + print('Already have list.json, move it if you would like to generate a new set.') + sys.exit(0) + while len(address_info) < numpks: + addressinfo = genvaldump(rpc) + address_info.append(addressinfo) + f = open("list.json", "w+") + f.write(json.dumps(address_info)) +else: + if os.path.isfile("list.json"): + with open('list.json') as list: + address_info = json.load(list) + else: + sys.exit('No list.json you need to create new pubkeys!') + +for addressinfo in address_info: + pubkeys.append(addressinfo[0]) + +ret = rpc.setpubkey(pubkeys[0]) +ret = rpc.cclib("combine", "18", str(pubkeys)) +pkhash = str(ret['pkhash']) +combinedpk = str(ret['combined_pk']) +print('Your combined pubkey is: ' + combinedpk) +print('Your pkhash is: ' + pkhash) +amount = float(input('Enter amount to send: ')) +if amount == 0: + sys.exit('Cannot send 0 coins. Exiting.') +tmp = str([combinedpk, amount]) +hex = rpc.cclib("send", "18", tmp)['hex'] +senttxid = rpc.sendrawtransaction(hex) +print('Your senttxid is: ' + senttxid) + +print("Waiting for tx to be confirmed") +while True: + confirmed = int(rpc.gettransaction(senttxid)["confirmations"]) + if not confirmed: + time.sleep(10) + else: + print('SentTX confirmed') + break + +scriptPubKey = rpc.getrawtransaction(senttxid,1)['vout'][1]['scriptPubKey']['hex'] +print('Your scriptPubKey is: ' + scriptPubKey) +tmp = str([senttxid, scriptPubKey]) +msg = rpc.cclib("calcmsg", "18", tmp)['msg'] +print('Your msg is: ' + msg) + +i = 0; +commitments = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + tmp = str([i, len(pubkeys), combinedpk, pkhash, msg, i]) + commitments.append(rpc.cclib("session", "18", tmp)['commitment']) + i = i + 1 + +print("Created commitments sucessfully... Sending to all signers.") + +i = 0 +nonces = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + n = 0 + for commitment in commitments: + tmp = str([pkhash, n, commitment, i]) + ret = rpc.cclib("commit", "18", tmp) + try: + nonces.append(ret['nonce']) + except: + x = 1 + n = n + 1 + i = i + 1 + +print("Created nounce's sucessfully... Sending to all signers.") + +i = 0 +partialsigs = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + n = 0 + for nonce in nonces: + tmp = str([pkhash, n, nonce, i]) + ret = rpc.cclib("nonce", "18", tmp) + try: + partialsigs.append(ret['partialsig']) + except: + x = 1 + n = n + 1 + i = i + 1 + +print("Created partial sigs sucessfully... Sending to all signers.") + +i = 0 +combinedsigs = [] +for pubkey in pubkeys: + ret = rpc.setpubkey(pubkey) + n = 0 + for partialsig in partialsigs: + tmp = str([pkhash, n, partialsig, i]) + ret = rpc.cclib("partialsig", "18", tmp) + try: + combinedsigs.append(ret['combinedsig']) + except: + x = 1 + n = n + 1 + i = i + 1 + +print("Created combined sigs sucessfully... Verifying.") + +tmp = str([msg, combinedpk, combinedsigs[0]]) +ret = rpc.cclib("verify", "18", tmp) + +if ret['result'] != "success": + print(ret) + sys.exit('Could not verify signature.') + +print('Verified... Attempting to send.') + +tmp = str([senttxid, scriptPubKey, combinedsigs[0]]) +ret = rpc.cclib("spend", "18", tmp) + +if ret['result'] != "success": + print(ret) + sys.exit('Could not create spend transaction.') + +try: + ret = rpc.sendrawtransaction(ret['hex']) +except: + sys.exit('Could not send transaction.') + +print('Spent txid: ' + ret) diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp index 0ed2f866c..0e0ab9906 100644 --- a/src/wallet/rpcwallet.cpp +++ b/src/wallet/rpcwallet.cpp @@ -5308,7 +5308,7 @@ UniValue setpubkey(const UniValue& params, bool fHelp) char Raddress[64]; uint8_t pubkey33[33]; - if ( NOTARY_PUBKEY33[0] == 0 ) + if ( NOTARY_PUBKEY33[0] == 0 || (strcmp(ASSETCHAINS_SYMBOL, "MUSIG") == 0) ) { if (strlen(params[0].get_str().c_str()) == 66) { From 4d4a74d917c80d4dc2fa46bdf40348049ef3ec8d Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 22:44:40 -1100 Subject: [PATCH 122/132] Cashout prints --- src/cc/dilithium.c | 1 + src/cc/rogue_rpc.cpp | 65 ++++++++++++++++++++++++++++++-------------- 2 files changed, 46 insertions(+), 20 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index ab8ca9ae5..c0ff8f274 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3232,6 +3232,7 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) { CPubKey destpub33; std::string handle; uint256 hashBlock,destpubtxid,checktxid; CTransaction vintx; int32_t numvouts,mlen,smlen=CRYPTO_BYTES+32; std::vector sig; uint8_t msg[32],msg2[CRYPTO_BYTES+32],pk[CRYPTO_PUBLICKEYBYTES]; + // if all dilithium tx -> do multispend/send, else: if ( tx.vout.size() != 2 ) return eval->Invalid("numvouts != 2"); else if ( tx.vin.size() != 1 ) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 1a4f7c1cd..3d9b02115 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -894,7 +894,7 @@ char *rogue_extractgame(int32_t makefiles,char *str,int32_t *numkeysp,std::vecto } else { - sprintf(str,"extracted $$$gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",endP.gold,endP.hitpoints,endP.strength&0xffff,endP.strength>>16,endP.level,endP.experience,endP.dungeonlevel); + sprintf(str,"extracted $$$gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d",endP.gold,endP.hitpoints,endP.strength&0xffff,endP.strength>>16,endP.level,endP.experience,endP.dungeonlevel); fprintf(stderr,"%s\n",str); *numkeysp = numkeys; return(keystrokes); @@ -956,13 +956,11 @@ UniValue rogue_extract(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) return(result); } -int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp,std::vector playerdata,uint256 gametxid,CPubKey pk) +int32_t rogue_playerdata_validate(int64_t *cashoutp,uint256 &playertxid,struct CCcontract_info *cp,std::vector playerdata,uint256 gametxid,CPubKey pk) { static uint32_t good,bad; static uint256 prevgame; - char str[512],*keystrokes,rogueaddr[64],str2[67]; int32_t i,numkeys; std::vector newdata; uint64_t seed; CPubKey roguepk; struct rogue_player P; - if ( gametxid == prevgame ) - return(0); - prevgame = gametxid; + char str[512],*keystrokes,rogueaddr[64],str2[67]; int32_t i,dungeonlevel,numkeys; std::vector newdata; uint64_t seed,mult = 10; CPubKey roguepk; struct rogue_player P; + *cashoutp = 0; roguepk = GetUnspendable(cp,0); GetCCaddress1of2(cp,rogueaddr,roguepk,pk); //fprintf(stderr,"call extractgame\n"); @@ -971,21 +969,35 @@ int32_t rogue_playerdata_validate(uint256 &playertxid,struct CCcontract_info *cp //fprintf(stderr,"numkeys.%d rogue_extractgame %s\n",numkeys,gametxid.GetHex().c_str()); free(keystrokes); //fprintf(stderr,"extracted.(%s)\n",str); + for (i=0; i no playerdata, good.%d bad.%d\n",good,bad); + } + *cashoutp = 0; return(0); } - fprintf(stderr,"zero value character was killed -> no playerdata, good.%d bad.%d\n",good,bad); } - bad++; - fprintf(stderr,"%s playerdata: gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",gametxid.GetHex().c_str(),P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel); - fprintf(stderr,"newdata[%d] != playerdata[%d], numkeys.%d %s pub.%s playertxid.%s good.%d bad.%d\n",(int32_t)newdata.size(),(int32_t)playerdata.size(),numkeys,rogueaddr,pubkey33_str(str2,(uint8_t *)&pk),playertxid.GetHex().c_str(),good,bad); + if ( gametxid != prevgame ) + { + prevgame = gametxid; + bad++; + fprintf(stderr,"%s playerdata: gold.%d hp.%d strength.%d/%d level.%d exp.%d dl.%d\n",gametxid.GetHex().c_str(),P.gold,P.hitpoints,P.strength&0xffff,P.strength>>16,P.level,P.experience,P.dungeonlevel); + fprintf(stderr,"newdata[%d] != playerdata[%d], numkeys.%d %s pub.%s playertxid.%s good.%d bad.%d\n",(int32_t)newdata.size(),(int32_t)playerdata.size(),numkeys,rogueaddr,pubkey33_str(str2,(uint8_t *)&pk),playertxid.GetHex().c_str(),good,bad); + } } //fprintf(stderr,"no keys rogue_extractgame %s\n",gametxid.GetHex().c_str()); return(-1); @@ -1308,7 +1329,7 @@ UniValue rogue_setname(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) { - CScript scriptPubKey; std::vector vopret; uint8_t *script,e,f,funcid; int32_t i,maxplayers,decoded=0,regslot,ind,err,dispflag,gameheight,score,numvouts; CTransaction vintx,gametx; CPubKey pk; uint256 hashBlock,gametxid,tokenid,batontxid,playertxid,ptxid; int64_t buyin; std::vector playerdata,keystrokes; std::string symbol,pname; + CScript scriptPubKey; std::vector vopret; uint8_t *script,e,f,funcid; int32_t i,maxplayers,decoded=0,regslot,ind,err,dispflag,gameheight,score,numvouts; CTransaction vintx,gametx; CPubKey pk; uint256 hashBlock,gametxid,tokenid,batontxid,playertxid,ptxid; int64_t buyin,cashout; std::vector playerdata,keystrokes; std::string symbol,pname; if ( strcmp(ASSETCHAINS_SYMBOL,"ROGUE") == 0 && height < 21274 ) return(true); if ( (numvouts= tx.vout.size()) > 1 ) @@ -1393,10 +1414,14 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C // verify pk belongs to this tx if ( playerdata.size() > 0 ) { - if ( rogue_playerdata_validate(ptxid,cp,playerdata,gametxid,pk) < 0 ) + if ( rogue_playerdata_validate(&cashout,ptxid,cp,playerdata,gametxid,pk) < 0 ) { //fprintf(stderr,"ht.%d gametxid.%s player.%s invalid playerdata[%d]\n",height,gametxid.GetHex().c_str(),ptxid.GetHex().c_str(),(int32_t)playerdata.size()); - } //else fprintf(stderr,"ht.%d playertxid.%s validated\n",height,ptxid.GetHex().c_str()); + } + if ( funcid == 'H' ) + cashout *= 2; + if ( tx.vout.size() > 2 ) + fprintf(stderr,"ht.%d playertxid.%s cashout %.8f vs vout2 %.8f\n",height,ptxid.GetHex().c_str(),(double)cashout/COIN,(double)tx.vout[2].nValue/COIN); } if ( funcid == 'Q' ) { From 4a09d29d0ddb199b94ddb3a35352343085409487 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 22:57:10 -1100 Subject: [PATCH 123/132] +print --- src/cc/rogue_rpc.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 3d9b02115..f2b6b7986 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -518,7 +518,7 @@ int32_t rogue_findbaton(struct CCcontract_info *cp,uint256 &playertxid,char **ke if ( active == zeroid || rogue_playerdata(cp,origplayergame,tid,pk,playerdata,symbol,pname,active) == 0 ) { txid = matchtx.GetHash(); - //fprintf(stderr,"scan forward active.%s spenttxid.%s\n",active.GetHex().c_str(),txid.GetHex().c_str()); + fprintf(stderr,"scan forward active.%s spenttxid.%s\n",active.GetHex().c_str(),txid.GetHex().c_str()); n = 0; while ( CCgettxout(txid,0,1) < 0 ) { @@ -532,6 +532,7 @@ int32_t rogue_findbaton(struct CCcontract_info *cp,uint256 &playertxid,char **ke return(-2); } txid = spenttxid; + fprintf(stderr,"next txid.%s/v%d\n",txid.GetHex().c_str(),spentvini); if ( spentvini != 0 ) return(-3); if ( keystrokesp != 0 && myGetTransaction(spenttxid,spenttx,hashBlock) != 0 && spenttx.vout.size() >= 2 ) From c8d3d0c13b79ed62e56aeb51c2b377b3cc1b6f03 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 22:59:31 -1100 Subject: [PATCH 124/132] Test --- src/cc/rogue_rpc.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index f2b6b7986..23204e225 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -505,7 +505,7 @@ int32_t rogue_findbaton(struct CCcontract_info *cp,uint256 &playertxid,char **ke } if ( matches == 1 ) { - if ( myIsutxo_spent(spenttxid,gametxid,maxplayers+i+1) < 0 ) + if ( 1 || myIsutxo_spent(spenttxid,gametxid,maxplayers+i+1) < 0 ) { numvouts = matchtx.vout.size(); //fprintf(stderr,"matchtxid.%s matches.%d numvouts.%d\n",matchtx.GetHash().GetHex().c_str(),matches,numvouts); @@ -576,7 +576,7 @@ int32_t rogue_findbaton(struct CCcontract_info *cp,uint256 &playertxid,char **ke else { fprintf(stderr,"already played\n"); - return(-5); + return(-6); } } return(-1); From 957343c1f4fbf420f3ff534c34b3cd2604fb9239 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 23:01:02 -1100 Subject: [PATCH 125/132] Fix can't find baton error --- src/cc/rogue_rpc.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 23204e225..305b6cd8f 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -518,7 +518,7 @@ int32_t rogue_findbaton(struct CCcontract_info *cp,uint256 &playertxid,char **ke if ( active == zeroid || rogue_playerdata(cp,origplayergame,tid,pk,playerdata,symbol,pname,active) == 0 ) { txid = matchtx.GetHash(); - fprintf(stderr,"scan forward active.%s spenttxid.%s\n",active.GetHex().c_str(),txid.GetHex().c_str()); + //fprintf(stderr,"scan forward active.%s spenttxid.%s\n",active.GetHex().c_str(),txid.GetHex().c_str()); n = 0; while ( CCgettxout(txid,0,1) < 0 ) { @@ -532,7 +532,7 @@ int32_t rogue_findbaton(struct CCcontract_info *cp,uint256 &playertxid,char **ke return(-2); } txid = spenttxid; - fprintf(stderr,"next txid.%s/v%d\n",txid.GetHex().c_str(),spentvini); + //fprintf(stderr,"next txid.%s/v%d\n",txid.GetHex().c_str(),spentvini); if ( spentvini != 0 ) return(-3); if ( keystrokesp != 0 && myGetTransaction(spenttxid,spenttx,hashBlock) != 0 && spenttx.vout.size() >= 2 ) From 8fa093fad2fce1a3470f9374418493864c30620b Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 23:06:30 -1100 Subject: [PATCH 126/132] Test --- src/cc/rogue_rpc.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 305b6cd8f..4ce8a4748 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -1417,7 +1417,7 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C { if ( rogue_playerdata_validate(&cashout,ptxid,cp,playerdata,gametxid,pk) < 0 ) { - //fprintf(stderr,"ht.%d gametxid.%s player.%s invalid playerdata[%d]\n",height,gametxid.GetHex().c_str(),ptxid.GetHex().c_str(),(int32_t)playerdata.size()); + fprintf(stderr,"ht.%d gametxid.%s player.%s invalid playerdata[%d]\n",height,gametxid.GetHex().c_str(),ptxid.GetHex().c_str(),(int32_t)playerdata.size()); } if ( funcid == 'H' ) cashout *= 2; From 9340287d340f9625e25f807d89858792161523d7 Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 23:08:08 -1100 Subject: [PATCH 127/132] txid --- src/cc/rogue_rpc.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 4ce8a4748..d6a325fa1 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -1330,11 +1330,12 @@ UniValue rogue_setname(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) { - CScript scriptPubKey; std::vector vopret; uint8_t *script,e,f,funcid; int32_t i,maxplayers,decoded=0,regslot,ind,err,dispflag,gameheight,score,numvouts; CTransaction vintx,gametx; CPubKey pk; uint256 hashBlock,gametxid,tokenid,batontxid,playertxid,ptxid; int64_t buyin,cashout; std::vector playerdata,keystrokes; std::string symbol,pname; + CScript scriptPubKey; std::vector vopret; uint8_t *script,e,f,funcid; int32_t i,maxplayers,decoded=0,regslot,ind,err,dispflag,gameheight,score,numvouts; CTransaction vintx,gametx; CPubKey pk; uint256 hashBlock,gametxid,txid,tokenid,batontxid,playertxid,ptxid; int64_t buyin,cashout; std::vector playerdata,keystrokes; std::string symbol,pname; if ( strcmp(ASSETCHAINS_SYMBOL,"ROGUE") == 0 && height < 21274 ) return(true); if ( (numvouts= tx.vout.size()) > 1 ) { + txid = tx.GetHash(); scriptPubKey = tx.vout[numvouts-1].scriptPubKey; GetOpReturnData(scriptPubKey,vopret); if ( vopret.size() > 2 ) @@ -1422,7 +1423,7 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C if ( funcid == 'H' ) cashout *= 2; if ( tx.vout.size() > 2 ) - fprintf(stderr,"ht.%d playertxid.%s cashout %.8f vs vout2 %.8f\n",height,ptxid.GetHex().c_str(),(double)cashout/COIN,(double)tx.vout[2].nValue/COIN); + fprintf(stderr,"ht.%d txid.%s cashout %.8f vs vout2 %.8f\n",height,txid.GetHex().c_str(),(double)cashout/COIN,(double)tx.vout[2].nValue/COIN); } if ( funcid == 'Q' ) { From 9a9204085bbce2aa2441c0ed55e358ef7772c59d Mon Sep 17 00:00:00 2001 From: jl777 Date: Sun, 24 Feb 2019 23:18:35 -1100 Subject: [PATCH 128/132] -print --- src/cc/rogue_rpc.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index d6a325fa1..c8e37d161 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -1422,7 +1422,7 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C } if ( funcid == 'H' ) cashout *= 2; - if ( tx.vout.size() > 2 ) + if ( tx.vout.size() > 3 ) // orig of 't' has 0 cashout fprintf(stderr,"ht.%d txid.%s cashout %.8f vs vout2 %.8f\n",height,txid.GetHex().c_str(),(double)cashout/COIN,(double)tx.vout[2].nValue/COIN); } if ( funcid == 'Q' ) From 208aff399794b5eecc5f4c4ac79d7b9536d8391e Mon Sep 17 00:00:00 2001 From: jl777 Date: Mon, 25 Feb 2019 01:58:46 -1100 Subject: [PATCH 129/132] Skip revalidating playertxid for asset tx --- src/cc/rogue_rpc.cpp | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index c8e37d161..d98a77711 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -1406,6 +1406,16 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C break; } } + else // this is asset transaction, which means playerdata txid already confirmed + { + switch ( funcid ) + { + case 'H': // win + case 'Q': // bailout + return(true); + break; + } + } switch ( funcid ) { case 'R': // register From b711cfaee314f503d5897f14c1cf882eea5b450d Mon Sep 17 00:00:00 2001 From: jl777 Date: Mon, 25 Feb 2019 02:18:53 -1100 Subject: [PATCH 130/132] Test --- src/cc/dilithium.c | 5 ++++- src/cc/rogue_rpc.cpp | 8 +++++--- 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/src/cc/dilithium.c b/src/cc/dilithium.c index c0ff8f274..9a9c4de71 100644 --- a/src/cc/dilithium.c +++ b/src/cc/dilithium.c @@ -3231,8 +3231,11 @@ UniValue dilithium_spend(uint64_t txfee,struct CCcontract_info *cp,cJSON *params bool dilithium_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) { - CPubKey destpub33; std::string handle; uint256 hashBlock,destpubtxid,checktxid; CTransaction vintx; int32_t numvouts,mlen,smlen=CRYPTO_BYTES+32; std::vector sig; uint8_t msg[32],msg2[CRYPTO_BYTES+32],pk[CRYPTO_PUBLICKEYBYTES]; + CPubKey destpub33; std::string handle; uint256 hashBlock,destpubtxid,checktxid; CTransaction vintx; int32_t numvouts,numvins,mlen,smlen=CRYPTO_BYTES+32; std::vector sig; uint8_t msg[32],msg2[CRYPTO_BYTES+32],pk[CRYPTO_PUBLICKEYBYTES]; // if all dilithium tx -> do multispend/send, else: + numvouts = tx.vout.size(); + numvins = tx.vin.size(); + if ( tx.vout.size() != 2 ) return eval->Invalid("numvouts != 2"); else if ( tx.vin.size() != 1 ) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index d98a77711..9accfe7f7 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -1330,7 +1330,7 @@ UniValue rogue_setname(uint64_t txfee,struct CCcontract_info *cp,cJSON *params) bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const CTransaction tx) { - CScript scriptPubKey; std::vector vopret; uint8_t *script,e,f,funcid; int32_t i,maxplayers,decoded=0,regslot,ind,err,dispflag,gameheight,score,numvouts; CTransaction vintx,gametx; CPubKey pk; uint256 hashBlock,gametxid,txid,tokenid,batontxid,playertxid,ptxid; int64_t buyin,cashout; std::vector playerdata,keystrokes; std::string symbol,pname; + CScript scriptPubKey; std::vector vopret; uint8_t *script,e,f,funcid,tokentx=0; int32_t i,maxplayers,decoded=0,regslot,ind,err,dispflag,gameheight,score,numvouts; CTransaction vintx,gametx; CPubKey pk; uint256 hashBlock,gametxid,txid,tokenid,batontxid,playertxid,ptxid; int64_t buyin,cashout; std::vector playerdata,keystrokes; std::string symbol,pname; if ( strcmp(ASSETCHAINS_SYMBOL,"ROGUE") == 0 && height < 21274 ) return(true); if ( (numvouts= tx.vout.size()) > 1 ) @@ -1344,6 +1344,7 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C funcid = script[1]; if ( (e= script[0]) == EVAL_TOKENS ) { + tokentx = 1; if ( (funcid= rogue_highlanderopretdecode(gametxid,tokenid,regslot,pk,playerdata,symbol,pname,scriptPubKey)) == 0 ) { if ( (funcid= rogue_registeropretdecode(gametxid,tokenid,playertxid,scriptPubKey)) == 0 ) @@ -1408,13 +1409,14 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C } else // this is asset transaction, which means playerdata txid already confirmed { - switch ( funcid ) + fprintf(stderr,"ht.%d tokentx.%d funcid.(%c)\n",height,tokentx,funcid); + /*switch ( funcid ) { case 'H': // win case 'Q': // bailout return(true); break; - } + }*/ } switch ( funcid ) { From 6e51ad8984a21a9e6e34b6bd96012f47978a2b4a Mon Sep 17 00:00:00 2001 From: jl777 Date: Mon, 25 Feb 2019 02:24:59 -1100 Subject: [PATCH 131/132] -print --- src/cc/rogue_rpc.cpp | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 9accfe7f7..88b669799 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -1407,17 +1407,6 @@ bool rogue_validate(struct CCcontract_info *cp,int32_t height,Eval *eval,const C break; } } - else // this is asset transaction, which means playerdata txid already confirmed - { - fprintf(stderr,"ht.%d tokentx.%d funcid.(%c)\n",height,tokentx,funcid); - /*switch ( funcid ) - { - case 'H': // win - case 'Q': // bailout - return(true); - break; - }*/ - } switch ( funcid ) { case 'R': // register From 3ac0038a15b63d913863981a068dfe4bd6097a03 Mon Sep 17 00:00:00 2001 From: jl777 Date: Mon, 25 Feb 2019 02:41:02 -1100 Subject: [PATCH 132/132] Rescue cancelled warriors --- src/cc/rogue_rpc.cpp | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/src/cc/rogue_rpc.cpp b/src/cc/rogue_rpc.cpp index 88b669799..aee151530 100644 --- a/src/cc/rogue_rpc.cpp +++ b/src/cc/rogue_rpc.cpp @@ -472,12 +472,25 @@ int32_t rogue_playerdata(struct CCcontract_info *cp,uint256 &origplayergame,uint int32_t rogue_playerdataspend(CMutableTransaction &mtx,uint256 playertxid,int32_t vout,uint256 origplayergame) { - int64_t txfee = 10000; + int64_t txfee = 10000; CTransaction tx; uint256 hashBlock; if ( CCgettxout(playertxid,vout,1) == 1 ) // not sure if this is enough validation { mtx.vin.push_back(CTxIn(playertxid,vout,CScript())); return(0); - } else return(-1); + } + else + { + vout = 0; + if ( myGetTransaction(playertxid,tx,hashBlock) != 0 && tx.vout[vout].nValue == 1 && tx.vout[vout].scriptPubKey.IsPayToCryptoCondition() != 0 ) + { + if ( CCgettxout(playertxid,vout,1) == 1 ) // not sure if this is enough validation + { + mtx.vin.push_back(CTxIn(playertxid,vout,CScript())); + return(0); + } + } + return(-1); + } } int32_t rogue_findbaton(struct CCcontract_info *cp,uint256 &playertxid,char **keystrokesp,int32_t &numkeys,int32_t ®slot,std::vector &playerdata,uint256 &batontxid,int32_t &batonvout,int64_t &batonvalue,int32_t &batonht,uint256 gametxid,CTransaction gametx,int32_t maxplayers,char *destaddr,int32_t &numplayers,std::string &symbol,std::string &pname)