From ad411f20756158659aa29812e29990e4726c3138 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Fri, 26 Oct 2018 08:06:58 -0700 Subject: [PATCH 01/15] Start adding DPoW confs --- src/komodo_defs.h | 13 + src/komodo_rpcblockchain.h | 16 + src/komodo_utils.h | 1765 ++++++++++++++++++++++++++++++++++++ 3 files changed, 1794 insertions(+) create mode 100644 src/komodo_defs.h create mode 100644 src/komodo_utils.h diff --git a/src/komodo_defs.h b/src/komodo_defs.h new file mode 100644 index 000000000..7c339856c --- /dev/null +++ b/src/komodo_defs.h @@ -0,0 +1,13 @@ +#ifndef KOMODO_DEFS_H +#define KOMODO_DEFS_H + +#define ASSETCHAINS_MINHEIGHT 128 +#define KOMODO_ELECTION_GAP 2000 +#define ROUNDROBIN_DELAY 61 +#define KOMODO_ASSETCHAIN_MAXLEN 65 +#define KOMODO_LIMITED_NETWORKSIZE 4 +#define IGUANA_MAXSCRIPTSIZE 10001 +#define KOMODO_MAXMEMPOOLTIME 3600 // affects consensus +#define CRYPTO777_PUBSECPSTR "020e46e79a2a8d12b9b5d12c7a91adb4e454edfae43c0a0cb805427d2ac7613fd9" + +#endif diff --git a/src/komodo_rpcblockchain.h b/src/komodo_rpcblockchain.h index a1b79cfc3..ed54e2fcc 100644 --- a/src/komodo_rpcblockchain.h +++ b/src/komodo_rpcblockchain.h @@ -17,11 +17,27 @@ #define komodo_rpcblockchain_h #include "main.h" +#include "komodo_utils.h" int32_t komodo_MoMdata(int32_t *notarized_htp,uint256 *MoMp,uint256 *kmdtxidp,int32_t height,uint256 *MoMoMp,int32_t *MoMoMoffsetp,int32_t *MoMoMdepthp,int32_t *kmdstartip,int32_t *kmdendip); uint256 komodo_calcMoM(int32_t height,int32_t MoMdepth); extern char ASSETCHAINS_SYMBOL[65]; +int32_t komodo_dpowconfs(int32_t txheight,int32_t numconfs) +{ + char symbol[KOMODO_ASSETCHAIN_MAXLEN],dest[KOMODO_ASSETCHAIN_MAXLEN]; struct komodo_state *sp; + if ( KOMODO_DPOWCONFS != 0 && txheight > 0 && numconfs > 0 && (sp= komodo_stateptr(symbol,dest)) != 0 ) + { + if ( sp->NOTARIZED_HEIGHT > 0 ) + { + if ( txheight < sp->NOTARIZED_HEIGHT ) + return(numconfs); + else return(1); + } + } + return(numconfs); +} + int32_t komodo_MoM(int32_t *notarized_heightp,uint256 *MoMp,uint256 *kmdtxidp,int32_t nHeight,uint256 *MoMoMp,int32_t *MoMoMoffsetp,int32_t *MoMoMdepthp,int32_t *kmdstartip,int32_t *kmdendip) { int32_t depth,notarized_ht; uint256 MoM,kmdtxid; diff --git a/src/komodo_utils.h b/src/komodo_utils.h new file mode 100644 index 000000000..75f68d87d --- /dev/null +++ b/src/komodo_utils.h @@ -0,0 +1,1765 @@ +/****************************************************************************** + * Copyright © 2014-2018 The SuperNET Developers. * + * * + * See the AUTHORS, DEVELOPER-AGREEMENT and LICENSE files at * + * the top-level directory of this distribution for the individual copyright * + * holder information and the developer policies on copyright and licensing. * + * * + * Unless otherwise agreed in a custom licensing agreement, no part of the * + * SuperNET software, including this file may be copied, modified, propagated * + * or distributed except according to the terms contained in the LICENSE file * + * * + * Removal or modification of this copyright notice is prohibited. * + * * + ******************************************************************************/ +#include "komodo_defs.h" + +#ifdef _WIN32 +#include +#include +#include +#endif + +#define SATOSHIDEN ((uint64_t)100000000L) +#define dstr(x) ((double)(x) / SATOSHIDEN) +#define portable_mutex_t pthread_mutex_t +#define portable_mutex_init(ptr) pthread_mutex_init(ptr,NULL) +#define portable_mutex_lock pthread_mutex_lock +#define portable_mutex_unlock pthread_mutex_unlock + +struct allocitem { uint32_t allocsize,type; }; +struct queueitem { struct queueitem *next,*prev; uint32_t allocsize,type; }; + +typedef struct queue +{ + struct queueitem *list; + pthread_mutex_t mutex; + char name[64],initflag; +} queue_t; + +#include "mini-gmp.c" + +#define CRYPTO777_PUBSECPSTR "020e46e79a2a8d12b9b5d12c7a91adb4e454edfae43c0a0cb805427d2ac7613fd9" +#define CRYPTO777_KMDADDR "RXL3YXG2ceaB6C5hfJcN4fvmLH2C34knhA" +#define CRYPTO777_RMD160STR "f1dce4182fce875748c4986b240ff7d7bc3fffb0" + +#define KOMODO_PUBTYPE 60 + +struct sha256_vstate { uint64_t length; uint32_t state[8],curlen; uint8_t buf[64]; }; +struct rmd160_vstate { uint64_t length; uint8_t buf[64]; uint32_t curlen, state[5]; }; + +// following is ported from libtom + +#define STORE32L(x, y) \ +{ (y)[3] = (uint8_t)(((x)>>24)&255); (y)[2] = (uint8_t)(((x)>>16)&255); \ +(y)[1] = (uint8_t)(((x)>>8)&255); (y)[0] = (uint8_t)((x)&255); } + +#define LOAD32L(x, y) \ +{ x = (uint32_t)(((uint64_t)((y)[3] & 255)<<24) | \ +((uint32_t)((y)[2] & 255)<<16) | \ +((uint32_t)((y)[1] & 255)<<8) | \ +((uint32_t)((y)[0] & 255))); } + +#define STORE64L(x, y) \ +{ (y)[7] = (uint8_t)(((x)>>56)&255); (y)[6] = (uint8_t)(((x)>>48)&255); \ +(y)[5] = (uint8_t)(((x)>>40)&255); (y)[4] = (uint8_t)(((x)>>32)&255); \ +(y)[3] = (uint8_t)(((x)>>24)&255); (y)[2] = (uint8_t)(((x)>>16)&255); \ +(y)[1] = (uint8_t)(((x)>>8)&255); (y)[0] = (uint8_t)((x)&255); } + +#define LOAD64L(x, y) \ +{ x = (((uint64_t)((y)[7] & 255))<<56)|(((uint64_t)((y)[6] & 255))<<48)| \ +(((uint64_t)((y)[5] & 255))<<40)|(((uint64_t)((y)[4] & 255))<<32)| \ +(((uint64_t)((y)[3] & 255))<<24)|(((uint64_t)((y)[2] & 255))<<16)| \ +(((uint64_t)((y)[1] & 255))<<8)|(((uint64_t)((y)[0] & 255))); } + +#define STORE32H(x, y) \ +{ (y)[0] = (uint8_t)(((x)>>24)&255); (y)[1] = (uint8_t)(((x)>>16)&255); \ +(y)[2] = (uint8_t)(((x)>>8)&255); (y)[3] = (uint8_t)((x)&255); } + +#define LOAD32H(x, y) \ +{ x = (uint32_t)(((uint64_t)((y)[0] & 255)<<24) | \ +((uint32_t)((y)[1] & 255)<<16) | \ +((uint32_t)((y)[2] & 255)<<8) | \ +((uint32_t)((y)[3] & 255))); } + +#define STORE64H(x, y) \ +{ (y)[0] = (uint8_t)(((x)>>56)&255); (y)[1] = (uint8_t)(((x)>>48)&255); \ +(y)[2] = (uint8_t)(((x)>>40)&255); (y)[3] = (uint8_t)(((x)>>32)&255); \ +(y)[4] = (uint8_t)(((x)>>24)&255); (y)[5] = (uint8_t)(((x)>>16)&255); \ +(y)[6] = (uint8_t)(((x)>>8)&255); (y)[7] = (uint8_t)((x)&255); } + +#define LOAD64H(x, y) \ +{ x = (((uint64_t)((y)[0] & 255))<<56)|(((uint64_t)((y)[1] & 255))<<48) | \ +(((uint64_t)((y)[2] & 255))<<40)|(((uint64_t)((y)[3] & 255))<<32) | \ +(((uint64_t)((y)[4] & 255))<<24)|(((uint64_t)((y)[5] & 255))<<16) | \ +(((uint64_t)((y)[6] & 255))<<8)|(((uint64_t)((y)[7] & 255))); } + +// Various logical functions +#define RORc(x, y) ( ((((uint32_t)(x)&0xFFFFFFFFUL)>>(uint32_t)((y)&31)) | ((uint32_t)(x)<<(uint32_t)(32-((y)&31)))) & 0xFFFFFFFFUL) +#define Ch(x,y,z) (z ^ (x & (y ^ z))) +#define Maj(x,y,z) (((x | y) & z) | (x & y)) +#define S(x, n) RORc((x),(n)) +#define R(x, n) (((x)&0xFFFFFFFFUL)>>(n)) +#define Sigma0(x) (S(x, 2) ^ S(x, 13) ^ S(x, 22)) +#define Sigma1(x) (S(x, 6) ^ S(x, 11) ^ S(x, 25)) +#define Gamma0(x) (S(x, 7) ^ S(x, 18) ^ R(x, 3)) +#define Gamma1(x) (S(x, 17) ^ S(x, 19) ^ R(x, 10)) +#define MIN(x, y) ( ((x)<(y))?(x):(y) ) + +static inline int32_t sha256_vcompress(struct sha256_vstate * md,uint8_t *buf) +{ + uint32_t S[8],W[64],t0,t1,i; + for (i=0; i<8; i++) // copy state into S + S[i] = md->state[i]; + for (i=0; i<16; i++) // copy the state into 512-bits into W[0..15] + LOAD32H(W[i],buf + (4*i)); + for (i=16; i<64; i++) // fill W[16..63] + W[i] = Gamma1(W[i - 2]) + W[i - 7] + Gamma0(W[i - 15]) + W[i - 16]; + +#define RND(a,b,c,d,e,f,g,h,i,ki) \ +t0 = h + Sigma1(e) + Ch(e, f, g) + ki + W[i]; \ +t1 = Sigma0(a) + Maj(a, b, c); \ +d += t0; \ +h = t0 + t1; + + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],0,0x428a2f98); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],1,0x71374491); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],2,0xb5c0fbcf); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],3,0xe9b5dba5); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],4,0x3956c25b); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],5,0x59f111f1); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],6,0x923f82a4); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],7,0xab1c5ed5); + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],8,0xd807aa98); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],9,0x12835b01); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],10,0x243185be); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],11,0x550c7dc3); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],12,0x72be5d74); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],13,0x80deb1fe); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],14,0x9bdc06a7); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],15,0xc19bf174); + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],16,0xe49b69c1); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],17,0xefbe4786); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],18,0x0fc19dc6); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],19,0x240ca1cc); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],20,0x2de92c6f); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],21,0x4a7484aa); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],22,0x5cb0a9dc); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],23,0x76f988da); + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],24,0x983e5152); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],25,0xa831c66d); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],26,0xb00327c8); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],27,0xbf597fc7); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],28,0xc6e00bf3); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],29,0xd5a79147); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],30,0x06ca6351); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],31,0x14292967); + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],32,0x27b70a85); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],33,0x2e1b2138); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],34,0x4d2c6dfc); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],35,0x53380d13); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],36,0x650a7354); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],37,0x766a0abb); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],38,0x81c2c92e); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],39,0x92722c85); + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],40,0xa2bfe8a1); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],41,0xa81a664b); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],42,0xc24b8b70); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],43,0xc76c51a3); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],44,0xd192e819); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],45,0xd6990624); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],46,0xf40e3585); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],47,0x106aa070); + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],48,0x19a4c116); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],49,0x1e376c08); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],50,0x2748774c); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],51,0x34b0bcb5); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],52,0x391c0cb3); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],53,0x4ed8aa4a); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],54,0x5b9cca4f); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],55,0x682e6ff3); + RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],56,0x748f82ee); + RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],57,0x78a5636f); + RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],58,0x84c87814); + RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],59,0x8cc70208); + RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],60,0x90befffa); + RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],61,0xa4506ceb); + RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],62,0xbef9a3f7); + RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],63,0xc67178f2); +#undef RND + for (i=0; i<8; i++) // feedback + md->state[i] = md->state[i] + S[i]; + return(0); +} + +#undef RORc +#undef Ch +#undef Maj +#undef S +#undef R +#undef Sigma0 +#undef Sigma1 +#undef Gamma0 +#undef Gamma1 + +static inline void sha256_vinit(struct sha256_vstate * md) +{ + md->curlen = 0; + md->length = 0; + md->state[0] = 0x6A09E667UL; + md->state[1] = 0xBB67AE85UL; + md->state[2] = 0x3C6EF372UL; + md->state[3] = 0xA54FF53AUL; + md->state[4] = 0x510E527FUL; + md->state[5] = 0x9B05688CUL; + md->state[6] = 0x1F83D9ABUL; + md->state[7] = 0x5BE0CD19UL; +} + +static inline int32_t sha256_vprocess(struct sha256_vstate *md,const uint8_t *in,uint64_t inlen) +{ + uint64_t n; int32_t err; + if ( md->curlen > sizeof(md->buf) ) + return(-1); + while ( inlen > 0 ) + { + if ( md->curlen == 0 && inlen >= 64 ) + { + if ( (err= sha256_vcompress(md,(uint8_t *)in)) != 0 ) + return(err); + md->length += 64 * 8, in += 64, inlen -= 64; + } + else + { + n = MIN(inlen,64 - md->curlen); + memcpy(md->buf + md->curlen,in,(size_t)n); + md->curlen += n, in += n, inlen -= n; + if ( md->curlen == 64 ) + { + if ( (err= sha256_vcompress(md,md->buf)) != 0 ) + return(err); + md->length += 8*64; + md->curlen = 0; + } + } + } + return(0); +} + +static inline int32_t sha256_vdone(struct sha256_vstate *md,uint8_t *out) +{ + int32_t i; + if ( md->curlen >= sizeof(md->buf) ) + return(-1); + md->length += md->curlen * 8; // increase the length of the message + md->buf[md->curlen++] = (uint8_t)0x80; // append the '1' bit + // if len > 56 bytes we append zeros then compress. Then we can fall back to padding zeros and length encoding like normal. + if ( md->curlen > 56 ) + { + while ( md->curlen < 64 ) + md->buf[md->curlen++] = (uint8_t)0; + sha256_vcompress(md,md->buf); + md->curlen = 0; + } + while ( md->curlen < 56 ) // pad upto 56 bytes of zeroes + md->buf[md->curlen++] = (uint8_t)0; + STORE64H(md->length,md->buf+56); // store length + sha256_vcompress(md,md->buf); + for (i=0; i<8; i++) // copy output + STORE32H(md->state[i],out+(4*i)); + return(0); +} + +void vcalc_sha256(char deprecated[(256 >> 3) * 2 + 1],uint8_t hash[256 >> 3],uint8_t *src,int32_t len) +{ + struct sha256_vstate md; + sha256_vinit(&md); + sha256_vprocess(&md,src,len); + sha256_vdone(&md,hash); +} + +bits256 bits256_doublesha256(char *deprecated,uint8_t *data,int32_t datalen) +{ + bits256 hash,hash2; int32_t i; + vcalc_sha256(0,hash.bytes,data,datalen); + vcalc_sha256(0,hash2.bytes,hash.bytes,sizeof(hash)); + for (i=0; i>(unsigned long)(32-((y)&31)))) & 0xFFFFFFFFUL) + +/* the ten basic operations FF() through III() */ +#define FF(a, b, c, d, e, x, s) \ +(a) += F((b), (c), (d)) + (x);\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define GG(a, b, c, d, e, x, s) \ +(a) += G((b), (c), (d)) + (x) + 0x5a827999UL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define HH(a, b, c, d, e, x, s) \ +(a) += H((b), (c), (d)) + (x) + 0x6ed9eba1UL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define II(a, b, c, d, e, x, s) \ +(a) += I((b), (c), (d)) + (x) + 0x8f1bbcdcUL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define JJ(a, b, c, d, e, x, s) \ +(a) += J((b), (c), (d)) + (x) + 0xa953fd4eUL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define FFF(a, b, c, d, e, x, s) \ +(a) += F((b), (c), (d)) + (x);\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define GGG(a, b, c, d, e, x, s) \ +(a) += G((b), (c), (d)) + (x) + 0x7a6d76e9UL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define HHH(a, b, c, d, e, x, s) \ +(a) += H((b), (c), (d)) + (x) + 0x6d703ef3UL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define III(a, b, c, d, e, x, s) \ +(a) += I((b), (c), (d)) + (x) + 0x5c4dd124UL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +#define JJJ(a, b, c, d, e, x, s) \ +(a) += J((b), (c), (d)) + (x) + 0x50a28be6UL;\ +(a) = ROLc((a), (s)) + (e);\ +(c) = ROLc((c), 10); + +static int32_t rmd160_vcompress(struct rmd160_vstate *md,uint8_t *buf) +{ + uint32_t aa,bb,cc,dd,ee,aaa,bbb,ccc,ddd,eee,X[16]; + int i; + + /* load words X */ + for (i = 0; i < 16; i++){ + LOAD32L(X[i], buf + (4 * i)); + } + + /* load state */ + aa = aaa = md->state[0]; + bb = bbb = md->state[1]; + cc = ccc = md->state[2]; + dd = ddd = md->state[3]; + ee = eee = md->state[4]; + + /* round 1 */ + FF(aa, bb, cc, dd, ee, X[ 0], 11); + FF(ee, aa, bb, cc, dd, X[ 1], 14); + FF(dd, ee, aa, bb, cc, X[ 2], 15); + FF(cc, dd, ee, aa, bb, X[ 3], 12); + FF(bb, cc, dd, ee, aa, X[ 4], 5); + FF(aa, bb, cc, dd, ee, X[ 5], 8); + FF(ee, aa, bb, cc, dd, X[ 6], 7); + FF(dd, ee, aa, bb, cc, X[ 7], 9); + FF(cc, dd, ee, aa, bb, X[ 8], 11); + FF(bb, cc, dd, ee, aa, X[ 9], 13); + FF(aa, bb, cc, dd, ee, X[10], 14); + FF(ee, aa, bb, cc, dd, X[11], 15); + FF(dd, ee, aa, bb, cc, X[12], 6); + FF(cc, dd, ee, aa, bb, X[13], 7); + FF(bb, cc, dd, ee, aa, X[14], 9); + FF(aa, bb, cc, dd, ee, X[15], 8); + + /* round 2 */ + GG(ee, aa, bb, cc, dd, X[ 7], 7); + GG(dd, ee, aa, bb, cc, X[ 4], 6); + GG(cc, dd, ee, aa, bb, X[13], 8); + GG(bb, cc, dd, ee, aa, X[ 1], 13); + GG(aa, bb, cc, dd, ee, X[10], 11); + GG(ee, aa, bb, cc, dd, X[ 6], 9); + GG(dd, ee, aa, bb, cc, X[15], 7); + GG(cc, dd, ee, aa, bb, X[ 3], 15); + GG(bb, cc, dd, ee, aa, X[12], 7); + GG(aa, bb, cc, dd, ee, X[ 0], 12); + GG(ee, aa, bb, cc, dd, X[ 9], 15); + GG(dd, ee, aa, bb, cc, X[ 5], 9); + GG(cc, dd, ee, aa, bb, X[ 2], 11); + GG(bb, cc, dd, ee, aa, X[14], 7); + GG(aa, bb, cc, dd, ee, X[11], 13); + GG(ee, aa, bb, cc, dd, X[ 8], 12); + + /* round 3 */ + HH(dd, ee, aa, bb, cc, X[ 3], 11); + HH(cc, dd, ee, aa, bb, X[10], 13); + HH(bb, cc, dd, ee, aa, X[14], 6); + HH(aa, bb, cc, dd, ee, X[ 4], 7); + HH(ee, aa, bb, cc, dd, X[ 9], 14); + HH(dd, ee, aa, bb, cc, X[15], 9); + HH(cc, dd, ee, aa, bb, X[ 8], 13); + HH(bb, cc, dd, ee, aa, X[ 1], 15); + HH(aa, bb, cc, dd, ee, X[ 2], 14); + HH(ee, aa, bb, cc, dd, X[ 7], 8); + HH(dd, ee, aa, bb, cc, X[ 0], 13); + HH(cc, dd, ee, aa, bb, X[ 6], 6); + HH(bb, cc, dd, ee, aa, X[13], 5); + HH(aa, bb, cc, dd, ee, X[11], 12); + HH(ee, aa, bb, cc, dd, X[ 5], 7); + HH(dd, ee, aa, bb, cc, X[12], 5); + + /* round 4 */ + II(cc, dd, ee, aa, bb, X[ 1], 11); + II(bb, cc, dd, ee, aa, X[ 9], 12); + II(aa, bb, cc, dd, ee, X[11], 14); + II(ee, aa, bb, cc, dd, X[10], 15); + II(dd, ee, aa, bb, cc, X[ 0], 14); + II(cc, dd, ee, aa, bb, X[ 8], 15); + II(bb, cc, dd, ee, aa, X[12], 9); + II(aa, bb, cc, dd, ee, X[ 4], 8); + II(ee, aa, bb, cc, dd, X[13], 9); + II(dd, ee, aa, bb, cc, X[ 3], 14); + II(cc, dd, ee, aa, bb, X[ 7], 5); + II(bb, cc, dd, ee, aa, X[15], 6); + II(aa, bb, cc, dd, ee, X[14], 8); + II(ee, aa, bb, cc, dd, X[ 5], 6); + II(dd, ee, aa, bb, cc, X[ 6], 5); + II(cc, dd, ee, aa, bb, X[ 2], 12); + + /* round 5 */ + JJ(bb, cc, dd, ee, aa, X[ 4], 9); + JJ(aa, bb, cc, dd, ee, X[ 0], 15); + JJ(ee, aa, bb, cc, dd, X[ 5], 5); + JJ(dd, ee, aa, bb, cc, X[ 9], 11); + JJ(cc, dd, ee, aa, bb, X[ 7], 6); + JJ(bb, cc, dd, ee, aa, X[12], 8); + JJ(aa, bb, cc, dd, ee, X[ 2], 13); + JJ(ee, aa, bb, cc, dd, X[10], 12); + JJ(dd, ee, aa, bb, cc, X[14], 5); + JJ(cc, dd, ee, aa, bb, X[ 1], 12); + JJ(bb, cc, dd, ee, aa, X[ 3], 13); + JJ(aa, bb, cc, dd, ee, X[ 8], 14); + JJ(ee, aa, bb, cc, dd, X[11], 11); + JJ(dd, ee, aa, bb, cc, X[ 6], 8); + JJ(cc, dd, ee, aa, bb, X[15], 5); + JJ(bb, cc, dd, ee, aa, X[13], 6); + + /* parallel round 1 */ + JJJ(aaa, bbb, ccc, ddd, eee, X[ 5], 8); + JJJ(eee, aaa, bbb, ccc, ddd, X[14], 9); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 7], 9); + JJJ(ccc, ddd, eee, aaa, bbb, X[ 0], 11); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 9], 13); + JJJ(aaa, bbb, ccc, ddd, eee, X[ 2], 15); + JJJ(eee, aaa, bbb, ccc, ddd, X[11], 15); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 4], 5); + JJJ(ccc, ddd, eee, aaa, bbb, X[13], 7); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 6], 7); + JJJ(aaa, bbb, ccc, ddd, eee, X[15], 8); + JJJ(eee, aaa, bbb, ccc, ddd, X[ 8], 11); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 1], 14); + JJJ(ccc, ddd, eee, aaa, bbb, X[10], 14); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 3], 12); + JJJ(aaa, bbb, ccc, ddd, eee, X[12], 6); + + /* parallel round 2 */ + III(eee, aaa, bbb, ccc, ddd, X[ 6], 9); + III(ddd, eee, aaa, bbb, ccc, X[11], 13); + III(ccc, ddd, eee, aaa, bbb, X[ 3], 15); + III(bbb, ccc, ddd, eee, aaa, X[ 7], 7); + III(aaa, bbb, ccc, ddd, eee, X[ 0], 12); + III(eee, aaa, bbb, ccc, ddd, X[13], 8); + III(ddd, eee, aaa, bbb, ccc, X[ 5], 9); + III(ccc, ddd, eee, aaa, bbb, X[10], 11); + III(bbb, ccc, ddd, eee, aaa, X[14], 7); + III(aaa, bbb, ccc, ddd, eee, X[15], 7); + III(eee, aaa, bbb, ccc, ddd, X[ 8], 12); + III(ddd, eee, aaa, bbb, ccc, X[12], 7); + III(ccc, ddd, eee, aaa, bbb, X[ 4], 6); + III(bbb, ccc, ddd, eee, aaa, X[ 9], 15); + III(aaa, bbb, ccc, ddd, eee, X[ 1], 13); + III(eee, aaa, bbb, ccc, ddd, X[ 2], 11); + + /* parallel round 3 */ + HHH(ddd, eee, aaa, bbb, ccc, X[15], 9); + HHH(ccc, ddd, eee, aaa, bbb, X[ 5], 7); + HHH(bbb, ccc, ddd, eee, aaa, X[ 1], 15); + HHH(aaa, bbb, ccc, ddd, eee, X[ 3], 11); + HHH(eee, aaa, bbb, ccc, ddd, X[ 7], 8); + HHH(ddd, eee, aaa, bbb, ccc, X[14], 6); + HHH(ccc, ddd, eee, aaa, bbb, X[ 6], 6); + HHH(bbb, ccc, ddd, eee, aaa, X[ 9], 14); + HHH(aaa, bbb, ccc, ddd, eee, X[11], 12); + HHH(eee, aaa, bbb, ccc, ddd, X[ 8], 13); + HHH(ddd, eee, aaa, bbb, ccc, X[12], 5); + HHH(ccc, ddd, eee, aaa, bbb, X[ 2], 14); + HHH(bbb, ccc, ddd, eee, aaa, X[10], 13); + HHH(aaa, bbb, ccc, ddd, eee, X[ 0], 13); + HHH(eee, aaa, bbb, ccc, ddd, X[ 4], 7); + HHH(ddd, eee, aaa, bbb, ccc, X[13], 5); + + /* parallel round 4 */ + GGG(ccc, ddd, eee, aaa, bbb, X[ 8], 15); + GGG(bbb, ccc, ddd, eee, aaa, X[ 6], 5); + GGG(aaa, bbb, ccc, ddd, eee, X[ 4], 8); + GGG(eee, aaa, bbb, ccc, ddd, X[ 1], 11); + GGG(ddd, eee, aaa, bbb, ccc, X[ 3], 14); + GGG(ccc, ddd, eee, aaa, bbb, X[11], 14); + GGG(bbb, ccc, ddd, eee, aaa, X[15], 6); + GGG(aaa, bbb, ccc, ddd, eee, X[ 0], 14); + GGG(eee, aaa, bbb, ccc, ddd, X[ 5], 6); + GGG(ddd, eee, aaa, bbb, ccc, X[12], 9); + GGG(ccc, ddd, eee, aaa, bbb, X[ 2], 12); + GGG(bbb, ccc, ddd, eee, aaa, X[13], 9); + GGG(aaa, bbb, ccc, ddd, eee, X[ 9], 12); + GGG(eee, aaa, bbb, ccc, ddd, X[ 7], 5); + GGG(ddd, eee, aaa, bbb, ccc, X[10], 15); + GGG(ccc, ddd, eee, aaa, bbb, X[14], 8); + + /* parallel round 5 */ + FFF(bbb, ccc, ddd, eee, aaa, X[12] , 8); + FFF(aaa, bbb, ccc, ddd, eee, X[15] , 5); + FFF(eee, aaa, bbb, ccc, ddd, X[10] , 12); + FFF(ddd, eee, aaa, bbb, ccc, X[ 4] , 9); + FFF(ccc, ddd, eee, aaa, bbb, X[ 1] , 12); + FFF(bbb, ccc, ddd, eee, aaa, X[ 5] , 5); + FFF(aaa, bbb, ccc, ddd, eee, X[ 8] , 14); + FFF(eee, aaa, bbb, ccc, ddd, X[ 7] , 6); + FFF(ddd, eee, aaa, bbb, ccc, X[ 6] , 8); + FFF(ccc, ddd, eee, aaa, bbb, X[ 2] , 13); + FFF(bbb, ccc, ddd, eee, aaa, X[13] , 6); + FFF(aaa, bbb, ccc, ddd, eee, X[14] , 5); + FFF(eee, aaa, bbb, ccc, ddd, X[ 0] , 15); + FFF(ddd, eee, aaa, bbb, ccc, X[ 3] , 13); + FFF(ccc, ddd, eee, aaa, bbb, X[ 9] , 11); + FFF(bbb, ccc, ddd, eee, aaa, X[11] , 11); + + /* combine results */ + ddd += cc + md->state[1]; /* final result for md->state[0] */ + md->state[1] = md->state[2] + dd + eee; + md->state[2] = md->state[3] + ee + aaa; + md->state[3] = md->state[4] + aa + bbb; + md->state[4] = md->state[0] + bb + ccc; + md->state[0] = ddd; + + return 0; +} + +/** + Initialize the hash state + @param md The hash state you wish to initialize + @return 0 if successful + */ +int rmd160_vinit(struct rmd160_vstate * md) +{ + md->state[0] = 0x67452301UL; + md->state[1] = 0xefcdab89UL; + md->state[2] = 0x98badcfeUL; + md->state[3] = 0x10325476UL; + md->state[4] = 0xc3d2e1f0UL; + md->curlen = 0; + md->length = 0; + return 0; +} +#define HASH_PROCESS(func_name, compress_name, state_var, block_size) \ +int func_name (struct rmd160_vstate * md, const unsigned char *in, unsigned long inlen) \ +{ \ +unsigned long n; \ +int err; \ +if (md->curlen > sizeof(md->buf)) { \ +return -1; \ +} \ +while (inlen > 0) { \ +if (md->curlen == 0 && inlen >= block_size) { \ +if ((err = compress_name (md, (unsigned char *)in)) != 0) { \ +return err; \ +} \ +md->length += block_size * 8; \ +in += block_size; \ +inlen -= block_size; \ +} else { \ +n = MIN(inlen, (block_size - md->curlen)); \ +memcpy(md->buf + md->curlen, in, (size_t)n); \ +md->curlen += n; \ +in += n; \ +inlen -= n; \ +if (md->curlen == block_size) { \ +if ((err = compress_name (md, md->buf)) != 0) { \ +return err; \ +} \ +md->length += 8*block_size; \ +md->curlen = 0; \ +} \ +} \ +} \ +return 0; \ +} + +/** + Process a block of memory though the hash + @param md The hash state + @param in The data to hash + @param inlen The length of the data (octets) + @return 0 if successful + */ +HASH_PROCESS(rmd160_vprocess, rmd160_vcompress, rmd160, 64) + +/** + Terminate the hash to get the digest + @param md The hash state + @param out [out] The destination of the hash (20 bytes) + @return 0 if successful + */ +int rmd160_vdone(struct rmd160_vstate * md, unsigned char *out) +{ + int i; + if (md->curlen >= sizeof(md->buf)) { + return -1; + } + /* increase the length of the message */ + md->length += md->curlen * 8; + + /* append the '1' bit */ + md->buf[md->curlen++] = (unsigned char)0x80; + + /* if the length is currently above 56 bytes we append zeros + * then compress. Then we can fall back to padding zeros and length + * encoding like normal. + */ + if (md->curlen > 56) { + while (md->curlen < 64) { + md->buf[md->curlen++] = (unsigned char)0; + } + rmd160_vcompress(md, md->buf); + md->curlen = 0; + } + /* pad upto 56 bytes of zeroes */ + while (md->curlen < 56) { + md->buf[md->curlen++] = (unsigned char)0; + } + /* store length */ + STORE64L(md->length, md->buf+56); + rmd160_vcompress(md, md->buf); + /* copy output */ + for (i = 0; i < 5; i++) { + STORE32L(md->state[i], out+(4*i)); + } + return 0; +} + +void calc_rmd160(char deprecated[41],uint8_t buf[20],uint8_t *msg,int32_t len) +{ + struct rmd160_vstate md; + rmd160_vinit(&md); + rmd160_vprocess(&md,msg,len); + rmd160_vdone(&md, buf); +} +#undef F +#undef G +#undef H +#undef I +#undef J +#undef ROLc +#undef FF +#undef GG +#undef HH +#undef II +#undef JJ +#undef FFF +#undef GGG +#undef HHH +#undef III +#undef JJJ + +static const uint32_t crc32_tab[] = { + 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, 0x706af48f, + 0xe963a535, 0x9e6495a3, 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988, + 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91, 0x1db71064, 0x6ab020f2, + 0xf3b97148, 0x84be41de, 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7, + 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9, + 0xfa0f3d63, 0x8d080df5, 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172, + 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b, 0x35b5a8fa, 0x42b2986c, + 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59, + 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423, + 0xcfba9599, 0xb8bda50f, 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924, + 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, 0x76dc4190, 0x01db7106, + 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433, + 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818, 0x7f6a0dbb, 0x086d3d2d, + 0x91646c97, 0xe6635c01, 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e, + 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457, 0x65b0d9c6, 0x12b7e950, + 0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65, + 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, 0x4adfa541, 0x3dd895d7, + 0xa4d1c46d, 0xd3d6f4fb, 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0, + 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9, 0x5005713c, 0x270241aa, + 0xbe0b1010, 0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f, + 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17, 0x2eb40d81, + 0xb7bd5c3b, 0xc0ba6cad, 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a, + 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683, 0xe3630b12, 0x94643b84, + 0x0d6d6a3e, 0x7a6a5aa8, 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1, + 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb, + 0x196c3671, 0x6e6b06e7, 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc, + 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5, 0xd6d6a3e8, 0xa1d1937e, + 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b, + 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55, + 0x316e8eef, 0x4669be79, 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236, + 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, 0xc5ba3bbe, 0xb2bd0b28, + 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d, + 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a, 0x9c0906a9, 0xeb0e363f, + 0x72076785, 0x05005713, 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38, + 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, 0x86d3d2d4, 0xf1d4e242, + 0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777, + 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, 0x8f659eff, 0xf862ae69, + 0x616bffd3, 0x166ccf45, 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2, + 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db, 0xaed16a4a, 0xd9d65adc, + 0x40df0b66, 0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9, + 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605, 0xcdd70693, + 0x54de5729, 0x23d967bf, 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94, + 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d +}; + +uint32_t calc_crc32(uint32_t crc,const void *buf,size_t size) +{ + const uint8_t *p; + + p = (const uint8_t *)buf; + crc = crc ^ ~0U; + + while (size--) + crc = crc32_tab[(crc ^ *p++) & 0xFF] ^ (crc >> 8); + + return crc ^ ~0U; +} + +void calc_rmd160_sha256(uint8_t rmd160[20],uint8_t *data,int32_t datalen) +{ + bits256 hash; + vcalc_sha256(0,hash.bytes,data,datalen); + calc_rmd160(0,rmd160,hash.bytes,sizeof(hash)); +} + +int32_t bitcoin_addr2rmd160(uint8_t *addrtypep,uint8_t rmd160[20],char *coinaddr) +{ + bits256 hash; uint8_t *buf,_buf[25]; int32_t len; + memset(rmd160,0,20); + *addrtypep = 0; + buf = _buf; + if ( (len= bitcoin_base58decode(buf,coinaddr)) >= 4 ) + { + // validate with trailing hash, then remove hash + hash = bits256_doublesha256(0,buf,21); + *addrtypep = *buf; + memcpy(rmd160,buf+1,20); + if ( (buf[21]&0xff) == hash.bytes[31] && (buf[22]&0xff) == hash.bytes[30] &&(buf[23]&0xff) == hash.bytes[29] && (buf[24]&0xff) == hash.bytes[28] ) + { + //printf("coinaddr.(%s) valid checksum addrtype.%02x\n",coinaddr,*addrtypep); + return(20); + } + else + { + int32_t i; + if ( len > 20 ) + { + hash = bits256_doublesha256(0,buf,len); + } + for (i=0; i= 0 ) + return(1); + else return(0); +} + +int32_t bitweight(uint64_t x) +{ + int i,wt = 0; + for (i=0; i<64; i++) + if ( (1LL << i) & x ) + wt++; + return(wt); +} + +int32_t _unhex(char c) +{ + if ( c >= '0' && c <= '9' ) + return(c - '0'); + else if ( c >= 'a' && c <= 'f' ) + return(c - 'a' + 10); + else if ( c >= 'A' && c <= 'F' ) + return(c - 'A' + 10); + return(-1); +} + +int32_t is_hexstr(char *str,int32_t n) +{ + int32_t i; + if ( str == 0 || str[0] == 0 ) + return(0); + for (i=0; str[i]!=0; i++) + { + if ( n > 0 && i >= n ) + break; + if ( _unhex(str[i]) < 0 ) + break; + } + if ( n == 0 ) + return(i); + return(i == n); +} + +int32_t unhex(char c) +{ + int32_t hex; + if ( (hex= _unhex(c)) < 0 ) + { + //printf("unhex: illegal hexchar.(%c)\n",c); + } + return(hex); +} + +unsigned char _decode_hex(char *hex) { return((unhex(hex[0])<<4) | unhex(hex[1])); } + +int32_t decode_hex(uint8_t *bytes,int32_t n,char *hex) +{ + int32_t adjust,i = 0; + //printf("decode.(%s)\n",hex); + if ( is_hexstr(hex,n) <= 0 ) + { + memset(bytes,0,n); + return(n); + } + if ( hex[n-1] == '\n' || hex[n-1] == '\r' ) + hex[--n] = 0; + if ( n == 0 || (hex[n*2+1] == 0 && hex[n*2] != 0) ) + { + if ( n > 0 ) + { + bytes[0] = unhex(hex[0]); + printf("decode_hex n.%d hex[0] (%c) -> %d hex.(%s) [n*2+1: %d] [n*2: %d %c] len.%ld\n",n,hex[0],bytes[0],hex,hex[n*2+1],hex[n*2],hex[n*2],(long)strlen(hex)); + } + bytes++; + hex++; + adjust = 1; + } else adjust = 0; + if ( n > 0 ) + { + for (i=0; i>4) & 0xf); + hexbytes[i*2 + 1] = hexbyte(message[i] & 0xf); + //printf("i.%d (%02x) [%c%c]\n",i,message[i],hexbytes[i*2],hexbytes[i*2+1]); + } + hexbytes[len*2] = 0; + //printf("len.%ld\n",len*2+1); + return((int32_t)len*2+1); +} + +char *bits256_str(char hexstr[65],bits256 x) +{ + init_hexbytes_noT(hexstr,x.bytes,sizeof(x)); + return(hexstr); +} + +int32_t iguana_rwnum(int32_t rwflag,uint8_t *serialized,int32_t len,void *endianedp) +{ + int32_t i; uint64_t x; + if ( rwflag == 0 ) + { + x = 0; + for (i=len-1; i>=0; i--) + { + x <<= 8; + x |= serialized[i]; + } + switch ( len ) + { + case 1: *(uint8_t *)endianedp = (uint8_t)x; break; + case 2: *(uint16_t *)endianedp = (uint16_t)x; break; + case 4: *(uint32_t *)endianedp = (uint32_t)x; break; + case 8: *(uint64_t *)endianedp = (uint64_t)x; break; + } + } + else + { + x = 0; + switch ( len ) + { + case 1: x = *(uint8_t *)endianedp; break; + case 2: x = *(uint16_t *)endianedp; break; + case 4: x = *(uint32_t *)endianedp; break; + case 8: x = *(uint64_t *)endianedp; break; + } + for (i=0; i>= 8) + serialized[i] = (uint8_t)(x & 0xff); + } + return(len); +} + +int32_t iguana_rwbignum(int32_t rwflag,uint8_t *serialized,int32_t len,uint8_t *endianedp) +{ + int32_t i; + if ( rwflag == 0 ) + { + for (i=0; i= 0x4c ) + { + if ( opretlen == 0x4c ) + opretlen = script[len++]; + else if ( opretlen == 0x4d ) + { + opretlen = script[len] + (script[len+1] << 8); + len += 2; + //opretlen = script[len++]; + //opretlen = (opretlen << 8) | script[len++]; + } + } + *opretlenp = opretlen; + return(len); +} + +int32_t komodo_opreturnscript(uint8_t *script,uint8_t type,uint8_t *opret,int32_t opretlen) +{ + int32_t offset = 0; + script[offset++] = 0x6a; + opretlen++; + if ( opretlen >= 0x4c ) + { + if ( opretlen > 0xff ) + { + script[offset++] = 0x4d; + script[offset++] = opretlen & 0xff; + script[offset++] = (opretlen >> 8) & 0xff; + } + else + { + script[offset++] = 0x4c; + script[offset++] = opretlen; + } + } else script[offset++] = opretlen; + script[offset++] = type; // covered by opretlen + memcpy(&script[offset],opret,opretlen-1); + return(offset + opretlen - 1); +} + +long _stripwhite(char *buf,int accept) +{ + int32_t i,j,c; + if ( buf == 0 || buf[0] == 0 ) + return(0); + for (i=j=0; buf[i]!=0; i++) + { + buf[j] = c = buf[i]; + if ( c == accept || (c != ' ' && c != '\n' && c != '\r' && c != '\t' && c != '\b') ) + j++; + } + buf[j] = 0; + return(j); +} + +char *clonestr(char *str) +{ + char *clone; + if ( str == 0 || str[0] == 0 ) + { + printf("warning cloning nullstr.%p\n",str); +#ifdef __APPLE__ + while ( 1 ) sleep(1); +#endif + str = (char *)""; + } + clone = (char *)malloc(strlen(str)+16); + strcpy(clone,str); + return(clone); +} + +int32_t safecopy(char *dest,char *src,long len) +{ + int32_t i = -1; + if ( src != 0 && dest != 0 && src != dest ) + { + if ( dest != 0 ) + memset(dest,0,len); + for (i=0; i 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 + +void lock_queue(queue_t *queue) +{ + if ( queue->initflag == 0 ) + { + portable_mutex_init(&queue->mutex); + queue->initflag = 1; + } + portable_mutex_lock(&queue->mutex); +} + +void queue_enqueue(char *name,queue_t *queue,struct queueitem *item) +{ + if ( queue->name[0] == 0 && name != 0 && name[0] != 0 ) + strcpy(queue->name,name); + if ( item == 0 ) + { + printf("FATAL type error: queueing empty value\n"); + return; + } + lock_queue(queue); + DL_APPEND(queue->list,item); + portable_mutex_unlock(&queue->mutex); +} + +struct queueitem *queue_dequeue(queue_t *queue) +{ + struct queueitem *item = 0; + lock_queue(queue); + if ( queue->list != 0 ) + { + item = queue->list; + DL_DELETE(queue->list,item); + } + portable_mutex_unlock(&queue->mutex); + return(item); +} + +void *queue_delete(queue_t *queue,struct queueitem *copy,int32_t copysize) +{ + struct queueitem *item = 0; + lock_queue(queue); + if ( queue->list != 0 ) + { + DL_FOREACH(queue->list,item) + { + #ifdef _WIN32 + if ( item == copy || (item->allocsize == copysize && memcmp((void *)((intptr_t)item + sizeof(struct queueitem)),(void *)((intptr_t)copy + sizeof(struct queueitem)),copysize) == 0) ) + #else + if ( item == copy || (item->allocsize == copysize && memcmp((void *)((long)item + sizeof(struct queueitem)),(void *)((long)copy + sizeof(struct queueitem)),copysize) == 0) ) + #endif + { + DL_DELETE(queue->list,item); + portable_mutex_unlock(&queue->mutex); + printf("name.(%s) deleted item.%p list.%p\n",queue->name,item,queue->list); + return(item); + } + } + } + portable_mutex_unlock(&queue->mutex); + return(0); +} + +void *queue_free(queue_t *queue) +{ + struct queueitem *item = 0; + lock_queue(queue); + if ( queue->list != 0 ) + { + DL_FOREACH(queue->list,item) + { + DL_DELETE(queue->list,item); + free(item); + } + //printf("name.(%s) dequeue.%p list.%p\n",queue->name,item,queue->list); + } + portable_mutex_unlock(&queue->mutex); + return(0); +} + +void *queue_clone(queue_t *clone,queue_t *queue,int32_t size) +{ + struct queueitem *ptr,*item = 0; + lock_queue(queue); + if ( queue->list != 0 ) + { + DL_FOREACH(queue->list,item) + { + ptr = (struct queueitem *)calloc(1,sizeof(*ptr)); + memcpy(ptr,item,size); + queue_enqueue(queue->name,clone,ptr); + } + //printf("name.(%s) dequeue.%p list.%p\n",queue->name,item,queue->list); + } + portable_mutex_unlock(&queue->mutex); + return(0); +} + +int32_t queue_size(queue_t *queue) +{ + int32_t count = 0; + struct queueitem *tmp; + lock_queue(queue); + DL_COUNT(queue->list,tmp,count); + portable_mutex_unlock(&queue->mutex); + return count; +} + +void iguana_initQ(queue_t *Q,char *name) +{ + struct queueitem *item,*I; + memset(Q,0,sizeof(*Q)); + I = (struct queueitem *)calloc(1,sizeof(*I)); + strcpy(Q->name,name); + queue_enqueue(name,Q,I); + if ( (item= queue_dequeue(Q)) != 0 ) + free(item); +} + +uint16_t _komodo_userpass(char *username,char *password,FILE *fp) +{ + char *rpcuser,*rpcpassword,*str,line[8192]; uint16_t port = 0; + rpcuser = rpcpassword = 0; + username[0] = password[0] = 0; + while ( fgets(line,sizeof(line),fp) != 0 ) + { + if ( line[0] == '#' ) + continue; + //printf("line.(%s) %p %p\n",line,strstr(line,(char *)"rpcuser"),strstr(line,(char *)"rpcpassword")); + if ( (str= strstr(line,(char *)"rpcuser")) != 0 ) + rpcuser = parse_conf_line(str,(char *)"rpcuser"); + else if ( (str= strstr(line,(char *)"rpcpassword")) != 0 ) + rpcpassword = parse_conf_line(str,(char *)"rpcpassword"); + else if ( (str= strstr(line,(char *)"rpcport")) != 0 ) + { + port = atoi(parse_conf_line(str,(char *)"rpcport")); + //fprintf(stderr,"rpcport.%u in file\n",port); + } + } + if ( rpcuser != 0 && rpcpassword != 0 ) + { + strcpy(username,rpcuser); + strcpy(password,rpcpassword); + } + //printf("rpcuser.(%s) rpcpassword.(%s) KMDUSERPASS.(%s) %u\n",rpcuser,rpcpassword,KMDUSERPASS,port); + if ( rpcuser != 0 ) + free(rpcuser); + if ( rpcpassword != 0 ) + free(rpcpassword); + return(port); +} + +void komodo_statefname(char *fname,char *symbol,char *str) +{ + int32_t n,len; + sprintf(fname,"%s",GetDataDir(false).string().c_str()); + if ( (n= (int32_t)strlen(ASSETCHAINS_SYMBOL)) != 0 ) + { + len = (int32_t)strlen(fname); + if ( strcmp(ASSETCHAINS_SYMBOL,&fname[len - n]) == 0 ) + fname[len - n] = 0; + else + { + printf("unexpected fname.(%s) vs %s [%s] n.%d len.%d (%s)\n",fname,symbol,ASSETCHAINS_SYMBOL,n,len,&fname[len - n]); + return; + } + } + else + { +#ifdef _WIN32 + strcat(fname,"\\"); +#else + strcat(fname,"/"); +#endif + } + if ( symbol != 0 && symbol[0] != 0 && strcmp("KMD",symbol) != 0 ) + { + strcat(fname,symbol); + //printf("statefname.(%s) -> (%s)\n",symbol,fname); +#ifdef _WIN32 + strcat(fname,"\\"); +#else + strcat(fname,"/"); +#endif + } + strcat(fname,str); + //printf("test.(%s) -> [%s] statename.(%s) %s\n",test,ASSETCHAINS_SYMBOL,symbol,fname); +} + +void komodo_configfile(char *symbol,uint16_t rpcport) +{ + static char myusername[512],mypassword[8192]; + FILE *fp; uint16_t kmdport; uint8_t buf2[33]; char fname[512],buf[128],username[512],password[8192]; uint32_t crc,r,r2,i; + if ( symbol != 0 && rpcport != 0 ) + { + r = (uint32_t)time(NULL); + r2 = OS_milliseconds(); + memcpy(buf,&r,sizeof(r)); + memcpy(&buf[sizeof(r)],&r2,sizeof(r2)); + memcpy(&buf[sizeof(r)+sizeof(r2)],symbol,strlen(symbol)); + crc = calc_crc32(0,(uint8_t *)buf,(int32_t)(sizeof(r)+sizeof(r2)+strlen(symbol))); + #ifdef _WIN32 + randombytes_buf(buf2,sizeof(buf2)); + #else + OS_randombytes(buf2,sizeof(buf2)); + #endif + for (i=0; i userpass.(%s)\n",fname,KMDUSERPASS); + } //else printf("couldnt open.(%s)\n",fname); +} + +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; + if ( strcmp("KMD",symbol) == 0 ) + { +#ifdef __APPLE__ + sprintf(confname,"Komodo.conf"); +#else + sprintf(confname,"komodo.conf"); +#endif + } + else sprintf(confname,"%s.conf",symbol); + komodo_statefname(fname,symbol,confname); + if ( (fp= fopen(fname,"rb")) != 0 ) + { + port = _komodo_userpass(username,password,fp); + sprintf(userpass,"%s:%s",username,password); + if ( strcmp(symbol,ASSETCHAINS_SYMBOL) == 0 ) + strcpy(ASSETCHAINS_USERPASS,userpass); + fclose(fp); + } + return(port); +} + +uint32_t komodo_assetmagic(char *symbol,uint64_t supply,uint8_t *extraptr,int32_t extralen) +{ + uint8_t buf[512]; uint32_t crc0=0; int32_t len = 0; bits256 hash; + if ( strcmp(symbol,"KMD") == 0 ) + return(0x8de4eef9); + len = iguana_rwnum(1,&buf[len],sizeof(supply),(void *)&supply); + strcpy((char *)&buf[len],symbol); + len += strlen(symbol); + if ( extraptr != 0 && extralen != 0 ) + { + vcalc_sha256(0,hash.bytes,extraptr,extralen); + crc0 = hash.uints[0]; + } + return(calc_crc32(crc0,buf,len)); +} + +uint16_t komodo_assetport(uint32_t magic,int32_t extralen) +{ + if ( magic == 0x8de4eef9 ) + return(7770); + else if ( extralen == 0 ) + return(8000 + (magic % 7777)); + else return(16000 + (magic % 49500)); +} + +uint16_t komodo_port(char *symbol,uint64_t supply,uint32_t *magicp,uint8_t *extraptr,int32_t extralen) +{ + if ( symbol == 0 || symbol[0] == 0 || strcmp("KMD",symbol) == 0 ) + { + *magicp = 0x8de4eef9; + return(7770); + } + *magicp = komodo_assetmagic(symbol,supply,extraptr,extralen); + return(komodo_assetport(*magicp,extralen)); +} + +/*void komodo_ports(uint16_t ports[MAX_CURRENCIES]) +{ + int32_t i; uint32_t magic; + for (i=0; i matches suffix (%s) -> ac_name.(%s)\n",argv0,argv0suffix[i],argv0names[i]); + name = argv0names[i]; + break; + } + } + } + KOMODO_STOPAT = GetArg("-stopat",0); + ASSETCHAINS_CC = GetArg("-ac_cc",0); + KOMODO_CCACTIVATE = GetArg("-ac_ccactivate",0); + ASSETCHAINS_PUBLIC = GetArg("-ac_public",0); + ASSETCHAINS_PRIVATE = GetArg("-ac_private",0); + if ( (KOMODO_REWIND= GetArg("-rewind",0)) != 0 ) + { + printf("KOMODO_REWIND %d\n",KOMODO_REWIND); + } + if ( name.c_str()[0] != 0 ) + { + MAX_BLOCK_SIGOPS = 60000; + ASSETCHAINS_SUPPLY = GetArg("-ac_supply",10); + ASSETCHAINS_ENDSUBSIDY = GetArg("-ac_end",0); + ASSETCHAINS_REWARD = GetArg("-ac_reward",0); + ASSETCHAINS_HALVING = GetArg("-ac_halving",0); + ASSETCHAINS_DECAY = GetArg("-ac_decay",0); + ASSETCHAINS_COMMISSION = GetArg("-ac_perc",0); + ASSETCHAINS_OVERRIDE_PUBKEY = GetArg("-ac_pubkey",""); + if ( (ASSETCHAINS_STAKED= GetArg("-ac_staked",0)) > 100 ) + ASSETCHAINS_STAKED = 100; + if ( ASSETCHAINS_STAKED != 0 && ASSETCHAINS_PRIVATE != 0 ) + { + printf("-ac_private chains cant have any PoS\n"); + exit(0); + } + if ( ASSETCHAINS_HALVING != 0 && ASSETCHAINS_HALVING < 1440 ) + { + ASSETCHAINS_HALVING = 1440; + printf("ASSETCHAINS_HALVING must be at least 1440 blocks\n"); + } + if ( ASSETCHAINS_DECAY == 100000000 && ASSETCHAINS_ENDSUBSIDY == 0 ) + { + ASSETCHAINS_DECAY = 0; + printf("ASSETCHAINS_DECAY of 100000000 means linear and that needs ASSETCHAINS_ENDSUBSIDY\n"); + } + else if ( ASSETCHAINS_DECAY > 100000000 ) + { + ASSETCHAINS_DECAY = 0; + printf("ASSETCHAINS_DECAY cant be more than 100000000\n"); + } + if ( strlen(ASSETCHAINS_OVERRIDE_PUBKEY.c_str()) == 66 ) + decode_hex(ASSETCHAINS_OVERRIDE_PUBKEY33,33,(char *)ASSETCHAINS_OVERRIDE_PUBKEY.c_str()); + else if ( ASSETCHAINS_COMMISSION != 0 ) + { + ASSETCHAINS_COMMISSION = 0; + printf("ASSETCHAINS_COMMISSION needs an ASETCHAINS_OVERRIDE_PUBKEY and cant be more than 100000000 (100%%)\n"); + } + if ( ASSETCHAINS_ENDSUBSIDY != 0 || ASSETCHAINS_REWARD != 0 || ASSETCHAINS_HALVING != 0 || ASSETCHAINS_DECAY != 0 || ASSETCHAINS_COMMISSION != 0 || ASSETCHAINS_PUBLIC != 0 || ASSETCHAINS_PRIVATE != 0 ) + { + fprintf(stderr,"end.%llu blocks, reward %.8f halving.%llu blocks, decay.%llu perc %.4f%% ac_pub=[%02x...]\n",(long long)ASSETCHAINS_ENDSUBSIDY,dstr(ASSETCHAINS_REWARD),(long long)ASSETCHAINS_HALVING,(long long)ASSETCHAINS_DECAY,dstr(ASSETCHAINS_COMMISSION)*100,ASSETCHAINS_OVERRIDE_PUBKEY33[0]); + extraptr = extrabuf; + memcpy(extraptr,ASSETCHAINS_OVERRIDE_PUBKEY33,33), extralen = 33; + extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_ENDSUBSIDY),(void *)&ASSETCHAINS_ENDSUBSIDY); + extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_REWARD),(void *)&ASSETCHAINS_REWARD); + extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_HALVING),(void *)&ASSETCHAINS_HALVING); + extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_DECAY),(void *)&ASSETCHAINS_DECAY); + val = ASSETCHAINS_COMMISSION | (((uint64_t)ASSETCHAINS_STAKED & 0xff) << 32) | (((uint64_t)ASSETCHAINS_CC & 0xffff) << 40) | ((ASSETCHAINS_PUBLIC != 0) << 7) | ((ASSETCHAINS_PRIVATE != 0) << 6); + extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(val),(void *)&val); + } + addn = GetArg("-seednode",""); + if ( strlen(addn.c_str()) > 0 ) + ASSETCHAINS_SEED = 1; + strncpy(ASSETCHAINS_SYMBOL,name.c_str(),64); + if ( (baseid= komodo_baseid(ASSETCHAINS_SYMBOL)) >= 0 && baseid < 32 ) + MAX_MONEY = komodo_maxallowed(baseid); + else if ( ASSETCHAINS_REWARD == 0 ) + MAX_MONEY = (ASSETCHAINS_SUPPLY+100) * SATOSHIDEN; + else MAX_MONEY = (ASSETCHAINS_SUPPLY+100) * SATOSHIDEN + ASSETCHAINS_REWARD * (ASSETCHAINS_ENDSUBSIDY==0 ? 10000000 : ASSETCHAINS_ENDSUBSIDY); + MAX_MONEY += (MAX_MONEY * ASSETCHAINS_COMMISSION) / SATOSHIDEN; + //printf("baseid.%d MAX_MONEY.%s %.8f\n",baseid,ASSETCHAINS_SYMBOL,(double)MAX_MONEY/SATOSHIDEN); + ASSETCHAINS_P2PPORT = komodo_port(ASSETCHAINS_SYMBOL,ASSETCHAINS_SUPPLY,&ASSETCHAINS_MAGIC,extraptr,extralen); + while ( (dirname= (char *)GetDataDir(false).string().c_str()) == 0 || dirname[0] == 0 ) + { + fprintf(stderr,"waiting for datadir\n"); + #ifndef _WIN32 + sleep(3); + #else + boost::this_thread::sleep(boost::posix_time::milliseconds(3000)); + #endif + } + //fprintf(stderr,"Got datadir.(%s)\n",dirname); + if ( ASSETCHAINS_SYMBOL[0] != 0 ) + { + int32_t komodo_baseid(char *origbase); + extern int COINBASE_MATURITY; + if ( strcmp(ASSETCHAINS_SYMBOL,"KMD") == 0 ) + { + fprintf(stderr,"cant have assetchain named KMD\n"); + exit(0); + } + if ( (port= komodo_userpass(ASSETCHAINS_USERPASS,ASSETCHAINS_SYMBOL)) != 0 ) + ASSETCHAINS_RPCPORT = port; + else komodo_configfile(ASSETCHAINS_SYMBOL,ASSETCHAINS_P2PPORT + 1); + COINBASE_MATURITY = 1; + //fprintf(stderr,"ASSETCHAINS_RPCPORT (%s) %u\n",ASSETCHAINS_SYMBOL,ASSETCHAINS_RPCPORT); + } + if ( ASSETCHAINS_RPCPORT == 0 ) + ASSETCHAINS_RPCPORT = ASSETCHAINS_P2PPORT + 1; + //ASSETCHAINS_NOTARIES = GetArg("-ac_notaries",""); + //komodo_assetchain_pubkeys((char *)ASSETCHAINS_NOTARIES.c_str()); + iguana_rwnum(1,magic,sizeof(ASSETCHAINS_MAGIC),(void *)&ASSETCHAINS_MAGIC); + for (i=0; i<4; i++) + sprintf(&magicstr[i<<1],"%02x",magic[i]); + magicstr[8] = 0; +#ifndef FROM_CLI + sprintf(fname,"%s_7776",ASSETCHAINS_SYMBOL); + if ( (fp= fopen(fname,"wb")) != 0 ) + { + fprintf(fp,iguanafmtstr,name.c_str(),name.c_str(),name.c_str(),name.c_str(),magicstr,ASSETCHAINS_P2PPORT,ASSETCHAINS_RPCPORT,"78.47.196.146"); + fclose(fp); + //printf("created (%s)\n",fname); + } else printf("error creating (%s)\n",fname); +#endif + if ( KOMODO_CCACTIVATE != 0 && ASSETCHAINS_CC < 2 ) + { + ASSETCHAINS_CC = 2; + fprintf(stderr,"smart utxo CC contracts will activate at height.%d\n",KOMODO_CCACTIVATE); + } + } + else + { + char fname[512],username[512],password[4096]; int32_t iter; FILE *fp; + ASSETCHAINS_P2PPORT = 7770; + ASSETCHAINS_RPCPORT = 7771; + for (iter=0; iter<2; iter++) + { + strcpy(fname,GetDataDir().string().c_str()); +#ifdef _WIN32 + while ( fname[strlen(fname)-1] != '\\' ) + fname[strlen(fname)-1] = 0; + if ( iter == 0 ) + strcat(fname,"Komodo\\komodo.conf"); + else strcat(fname,"Bitcoin\\bitcoin.conf"); +#else + while ( fname[strlen(fname)-1] != '/' ) + fname[strlen(fname)-1] = 0; +#ifdef __APPLE__ + if ( iter == 0 ) + strcat(fname,"Komodo/Komodo.conf"); + else strcat(fname,"Bitcoin/Bitcoin.conf"); +#else + if ( iter == 0 ) + strcat(fname,".komodo/komodo.conf"); + else strcat(fname,".bitcoin/bitcoin.conf"); +#endif +#endif + if ( (fp= fopen(fname,"rb")) != 0 ) + { + _komodo_userpass(username,password,fp); + sprintf(iter == 0 ? KMDUSERPASS : BTCUSERPASS,"%s:%s",username,password); + fclose(fp); + //printf("KOMODO.(%s) -> userpass.(%s)\n",fname,KMDUSERPASS); + } //else printf("couldnt open.(%s)\n",fname); + if ( IS_KOMODO_NOTARY == 0 ) + break; + } + } + if ( ASSETCHAINS_SYMBOL[0] != 0 ) + { + BITCOIND_RPCPORT = GetArg("-rpcport", ASSETCHAINS_RPCPORT); + //fprintf(stderr,"(%s) port.%u chain params initialized\n",ASSETCHAINS_SYMBOL,BITCOIND_RPCPORT); + if ( strcmp("PIRATE",ASSETCHAINS_SYMBOL) == 0 && ASSETCHAINS_HALVING == 77777 ) + { + ASSETCHAINS_HALVING *= 5; + fprintf(stderr,"PIRATE halving changed to %d %.1f days\n",(int32_t)ASSETCHAINS_HALVING,(double)ASSETCHAINS_HALVING/1440); + } + } else BITCOIND_RPCPORT = GetArg("-rpcport", BaseParams().RPCPort()); +} + +void komodo_nameset(char *symbol,char *dest,char *source) +{ + if ( source[0] == 0 ) + { + strcpy(symbol,(char *)"KMD"); + strcpy(dest,(char *)"BTC"); + } + else + { + strcpy(symbol,source); + strcpy(dest,(char *)"KMD"); + } +} + +struct komodo_state *komodo_stateptrget(char *base) +{ + int32_t baseid; + if ( base == 0 || base[0] == 0 || strcmp(base,(char *)"KMD") == 0 ) + return(&KOMODO_STATES[33]); + else if ( (baseid= komodo_baseid(base)) >= 0 ) + return(&KOMODO_STATES[baseid+1]); + else return(&KOMODO_STATES[0]); +} + +struct komodo_state *komodo_stateptr(char *symbol,char *dest) +{ + int32_t baseid; + komodo_nameset(symbol,dest,ASSETCHAINS_SYMBOL); + return(komodo_stateptrget(symbol)); +} + +void komodo_prefetch(FILE *fp) +{ + long fsize,fpos; int32_t incr = 16*1024*1024; + fpos = ftell(fp); + fseek(fp,0,SEEK_END); + fsize = ftell(fp); + if ( fsize > incr ) + { + char *ignore = (char *)malloc(incr); + if ( ignore != 0 ) + { + rewind(fp); + while ( fread(ignore,1,incr,fp) == incr ) // prefetch + fprintf(stderr,"."); + free(ignore); + } + } + fseek(fp,fpos,SEEK_SET); +} + From b03d169e137d8244ea3c98a1ecdfabc6e6a483b6 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Mon, 29 Oct 2018 18:41:50 -0700 Subject: [PATCH 02/15] Return new rawconfirmations key and dpowconfs in wallet tx json --- src/wallet/rpcwallet.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp index 5f3cfaa2c..a25669118 100644 --- a/src/wallet/rpcwallet.cpp +++ b/src/wallet/rpcwallet.cpp @@ -77,7 +77,8 @@ void EnsureWalletIsUnlocked() void WalletTxToJSON(const CWalletTx& wtx, UniValue& entry) { int confirms = wtx.GetDepthInMainChain(); - entry.push_back(Pair("confirmations", confirms)); + entry.push_back(Pair("rawconfirmations", confirms)); + entry.push_back(Pair("confirmations", komodo_dpowconfs((int32_t)mapBlockIndex[wtx.hashBlock]->nHeight,confirms))); if (wtx.IsCoinBase()) entry.push_back(Pair("generated", true)); if (confirms > 0) From b46080bb6cdaad865a31444680b144c01c05f14d Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Mon, 29 Oct 2018 18:44:17 -0700 Subject: [PATCH 03/15] Latest code with bugfix --- src/wallet/rpcwallet.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp index a25669118..d5ef796c0 100644 --- a/src/wallet/rpcwallet.cpp +++ b/src/wallet/rpcwallet.cpp @@ -78,15 +78,15 @@ void WalletTxToJSON(const CWalletTx& wtx, UniValue& entry) { int confirms = wtx.GetDepthInMainChain(); entry.push_back(Pair("rawconfirmations", confirms)); - entry.push_back(Pair("confirmations", komodo_dpowconfs((int32_t)mapBlockIndex[wtx.hashBlock]->nHeight,confirms))); if (wtx.IsCoinBase()) entry.push_back(Pair("generated", true)); if (confirms > 0) { + entry.push_back(Pair("confirmations", komodo_dpowconfs((int32_t)mapBlockIndex[wtx.hashBlock]->nHeight,confirms))); entry.push_back(Pair("blockhash", wtx.hashBlock.GetHex())); entry.push_back(Pair("blockindex", wtx.nIndex)); entry.push_back(Pair("blocktime", mapBlockIndex[wtx.hashBlock]->GetBlockTime())); - } + } else entry.push_back(Pair("confirmations", confirms)); uint256 hash = wtx.GetHash(); entry.push_back(Pair("txid", hash.GetHex())); UniValue conflicts(UniValue::VARR); From 04ca2ee4a103bd17aae71a536fe849a609c787c0 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Mon, 29 Oct 2018 18:57:04 -0700 Subject: [PATCH 04/15] Get -dpowconfs CLI arg --- src/komodo_utils.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/komodo_utils.h b/src/komodo_utils.h index 75f68d87d..cf2335783 100644 --- a/src/komodo_utils.h +++ b/src/komodo_utils.h @@ -1624,6 +1624,7 @@ void komodo_args(char *argv0) #endif } //fprintf(stderr,"Got datadir.(%s)\n",dirname); + int32_t dpowconfs = KOMODO_DPOWCONFS; if ( ASSETCHAINS_SYMBOL[0] != 0 ) { int32_t komodo_baseid(char *origbase); @@ -1710,6 +1711,7 @@ void komodo_args(char *argv0) fprintf(stderr,"PIRATE halving changed to %d %.1f days\n",(int32_t)ASSETCHAINS_HALVING,(double)ASSETCHAINS_HALVING/1440); } } else BITCOIND_RPCPORT = GetArg("-rpcport", BaseParams().RPCPort()); + KOMODO_DPOWCONFS = GetArg("-dpowconfs",dpowconfs); } void komodo_nameset(char *symbol,char *dest,char *source) From 7122a6d00498eed1228d0360c67569b0d66b20b5 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Tue, 30 Oct 2018 02:14:19 -0700 Subject: [PATCH 05/15] More dpowconfs --- src/rpcblockchain.cpp | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/src/rpcblockchain.cpp b/src/rpcblockchain.cpp index 8d7d85ccd..3ffd42b22 100644 --- a/src/rpcblockchain.cpp +++ b/src/rpcblockchain.cpp @@ -32,6 +32,7 @@ using namespace std; extern void TxToJSON(const CTransaction& tx, const uint256 hashBlock, UniValue& entry); void ScriptPubKeyToJSON(const CScript& scriptPubKey, UniValue& out, bool fIncludeHex); +int32_t komodo_dpowconfs(int32_t height,int32_t numconfs); double GetDifficultyINTERNAL(const CBlockIndex* blockindex, bool networkDifficulty) { @@ -112,7 +113,8 @@ UniValue blockheaderToJSON(const CBlockIndex* blockindex) // Only report confirmations if the block is on the main chain if (chainActive.Contains(blockindex)) confirmations = chainActive.Height() - blockindex->nHeight + 1; - result.push_back(Pair("confirmations", confirmations)); + result.push_back(Pair("confirmations", komodo_dpowconfs(blockindex->nHeight,confirmations))); + result.push_back(Pair("rawconfirmations", confirmations)); result.push_back(Pair("height", blockindex->nHeight)); result.push_back(Pair("version", blockindex->nVersion)); result.push_back(Pair("merkleroot", blockindex->hashMerkleRoot.GetHex())); @@ -144,7 +146,8 @@ UniValue blockToDeltasJSON(const CBlock& block, const CBlockIndex* blockindex) } else { throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block is an orphan"); } - result.push_back(Pair("confirmations", confirmations)); + result.push_back(Pair("confirmations", komodo_dpowconfs(blockindex->nHeight,confirmations))); + result.push_back(Pair("rawconfirmations", confirmations)); result.push_back(Pair("size", (int)::GetSerializeSize(block, SER_NETWORK, PROTOCOL_VERSION))); result.push_back(Pair("height", blockindex->nHeight)); result.push_back(Pair("version", block.nVersion)); @@ -248,7 +251,8 @@ UniValue blockToJSON(const CBlock& block, const CBlockIndex* blockindex, bool tx // Only report confirmations if the block is on the main chain if (chainActive.Contains(blockindex)) confirmations = chainActive.Height() - blockindex->nHeight + 1; - result.push_back(Pair("confirmations", confirmations)); + result.push_back(Pair("confirmations", komodo_dpowconfs(blockindex->nHeight,confirmations))); + result.push_back(Pair("rawconfirmations", confirmations)); result.push_back(Pair("size", (int)::GetSerializeSize(block, SER_NETWORK, PROTOCOL_VERSION))); result.push_back(Pair("height", blockindex->nHeight)); result.push_back(Pair("version", block.nVersion)); @@ -805,7 +809,10 @@ UniValue gettxout(const UniValue& params, bool fHelp) if ((unsigned int)coins.nHeight == MEMPOOL_HEIGHT) ret.push_back(Pair("confirmations", 0)); else - ret.push_back(Pair("confirmations", pindex->nHeight - coins.nHeight + 1)); + { + ret.push_back(Pair("confirmations", komodo_dpowconfs(coins.nHeight,pindex->nHeight - coins.nHeight + 1))); + ret.push_back(Pair("rawconfirmations", pindex->nHeight - coins.nHeight + 1)); + } ret.push_back(Pair("value", ValueFromAmount(coins.vout[n].nValue))); UniValue o(UniValue::VOBJ); ScriptPubKeyToJSON(coins.vout[n].scriptPubKey, o, true); From ad146967bca0be9398fd4b72be66695a15090b5f Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Tue, 30 Oct 2018 03:10:28 -0700 Subject: [PATCH 06/15] More dpowconfs --- src/rpcrawtransaction.cpp | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/rpcrawtransaction.cpp b/src/rpcrawtransaction.cpp index c69f49bfc..05a60f577 100644 --- a/src/rpcrawtransaction.cpp +++ b/src/rpcrawtransaction.cpp @@ -29,6 +29,7 @@ #include using namespace std; +int32_t komodo_dpowconfs(int32_t height,int32_t numconfs); void ScriptPubKeyToJSON(const CScript& scriptPubKey, UniValue& out, bool fIncludeHex) { @@ -183,7 +184,8 @@ void TxToJSONExpanded(const CTransaction& tx, const uint256 hashBlock, UniValue& if (nConfirmations > 0) { entry.push_back(Pair("height", nHeight)); - entry.push_back(Pair("confirmations", nConfirmations)); + entry.push_back(Pair("confirmations", komodo_dpowconfs(nHeight,nConfirmations))); + entry.push_back(Pair("rawconfirmations", nConfirmations)); entry.push_back(Pair("time", nBlockTime)); entry.push_back(Pair("blocktime", nBlockTime)); } else { @@ -242,7 +244,8 @@ void TxToJSON(const CTransaction& tx, const uint256 hashBlock, UniValue& entry) CBlockIndex* pindex = (*mi).second; if (chainActive.Contains(pindex)) { entry.push_back(Pair("height", pindex->nHeight)); - entry.push_back(Pair("confirmations", 1 + chainActive.Height() - pindex->nHeight)); + entry.push_back(Pair("rawconfirmations", 1 + chainActive.Height() - pindex->nHeight)); + entry.push_back(Pair("confirmations", komodo_dpowconfs(pindex->nHeight,1 + chainActive.Height() - pindex->nHeight))); entry.push_back(Pair("time", pindex->GetBlockTime())); entry.push_back(Pair("blocktime", pindex->GetBlockTime())); } else { @@ -1032,4 +1035,4 @@ UniValue sendrawtransaction(const UniValue& params, bool fHelp) RelayTransaction(tx); return hashTx.GetHex(); -} \ No newline at end of file +} From 271389623fa64a27790642cecd78c89cb2f89329 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Tue, 30 Oct 2018 03:50:07 -0700 Subject: [PATCH 07/15] Add basic regtests for dpowconfs --- qa/rpc-tests/dpowconfs.py | 35 +++++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) create mode 100755 qa/rpc-tests/dpowconfs.py diff --git a/qa/rpc-tests/dpowconfs.py b/qa/rpc-tests/dpowconfs.py new file mode 100755 index 000000000..72495331f --- /dev/null +++ b/qa/rpc-tests/dpowconfs.py @@ -0,0 +1,35 @@ +#!/usr/bin/env python2 +# Copyright (c) 2018 The Hush developers +# Distributed under the MIT software license, see the accompanying +# file COPYING or http://www.opensource.org/licenses/mit-license.php. + +from test_framework.test_framework import BitcoinTestFramework +from test_framework.util import assert_equal, initialize_chain_clean, \ + start_node, stop_node, wait_bitcoinds + + +class DPoWConfsTest(BitcoinTestFramework): + + def setup_chain(self): + print("Initializing test directory "+self.options.tmpdir) + num_nodes = 1 + initialize_chain_clean(self.options.tmpdir, num_nodes) + + def setup_network(self): + self.nodes = [] + self.is_network_split = False + self.nodes.append(start_node(0, self.options.tmpdir, [['-dpowconfs=1']])) + self.sync_all() + + def run_test(self): + self.nodes[0].generate(3) + rpc = self.nodes[0] + + result = rpc.getinfo() + # regtest should have no notarization data, this test makes sure we do not see mainnet values as well! + assert_equal(result['notarized'],0) + assert_equal(result['notarizedhash'],'0000000000000000000000000000000000000000000000000000000000000000') + assert_equal(result['notarizedtxid'],'0000000000000000000000000000000000000000000000000000000000000000') + +if __name__ == '__main__': + DPoWConfsTest().main() From 5f47971df873d8c127cf458a86920cd7f8cf6db3 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Wed, 31 Oct 2018 13:41:19 -0700 Subject: [PATCH 08/15] KMD statepointer and utils is not needed, use globals --- src/komodo_rpcblockchain.h | 8 +- src/komodo_utils.h | 1767 ------------------------------------ 2 files changed, 3 insertions(+), 1772 deletions(-) delete mode 100644 src/komodo_utils.h diff --git a/src/komodo_rpcblockchain.h b/src/komodo_rpcblockchain.h index ed54e2fcc..559d24505 100644 --- a/src/komodo_rpcblockchain.h +++ b/src/komodo_rpcblockchain.h @@ -17,7 +17,6 @@ #define komodo_rpcblockchain_h #include "main.h" -#include "komodo_utils.h" int32_t komodo_MoMdata(int32_t *notarized_htp,uint256 *MoMp,uint256 *kmdtxidp,int32_t height,uint256 *MoMoMp,int32_t *MoMoMoffsetp,int32_t *MoMoMdepthp,int32_t *kmdstartip,int32_t *kmdendip); uint256 komodo_calcMoM(int32_t height,int32_t MoMdepth); @@ -25,12 +24,11 @@ extern char ASSETCHAINS_SYMBOL[65]; int32_t komodo_dpowconfs(int32_t txheight,int32_t numconfs) { - char symbol[KOMODO_ASSETCHAIN_MAXLEN],dest[KOMODO_ASSETCHAIN_MAXLEN]; struct komodo_state *sp; - if ( KOMODO_DPOWCONFS != 0 && txheight > 0 && numconfs > 0 && (sp= komodo_stateptr(symbol,dest)) != 0 ) + if ( KOMODO_DPOWCONFS != 0 && txheight > 0 && numconfs > 0 ) { - if ( sp->NOTARIZED_HEIGHT > 0 ) + if ( NOTARIZED_HEIGHT > 0 ) { - if ( txheight < sp->NOTARIZED_HEIGHT ) + if ( txheight < NOTARIZED_HEIGHT ) return(numconfs); else return(1); } diff --git a/src/komodo_utils.h b/src/komodo_utils.h deleted file mode 100644 index cf2335783..000000000 --- a/src/komodo_utils.h +++ /dev/null @@ -1,1767 +0,0 @@ -/****************************************************************************** - * Copyright © 2014-2018 The SuperNET Developers. * - * * - * See the AUTHORS, DEVELOPER-AGREEMENT and LICENSE files at * - * the top-level directory of this distribution for the individual copyright * - * holder information and the developer policies on copyright and licensing. * - * * - * Unless otherwise agreed in a custom licensing agreement, no part of the * - * SuperNET software, including this file may be copied, modified, propagated * - * or distributed except according to the terms contained in the LICENSE file * - * * - * Removal or modification of this copyright notice is prohibited. * - * * - ******************************************************************************/ -#include "komodo_defs.h" - -#ifdef _WIN32 -#include -#include -#include -#endif - -#define SATOSHIDEN ((uint64_t)100000000L) -#define dstr(x) ((double)(x) / SATOSHIDEN) -#define portable_mutex_t pthread_mutex_t -#define portable_mutex_init(ptr) pthread_mutex_init(ptr,NULL) -#define portable_mutex_lock pthread_mutex_lock -#define portable_mutex_unlock pthread_mutex_unlock - -struct allocitem { uint32_t allocsize,type; }; -struct queueitem { struct queueitem *next,*prev; uint32_t allocsize,type; }; - -typedef struct queue -{ - struct queueitem *list; - pthread_mutex_t mutex; - char name[64],initflag; -} queue_t; - -#include "mini-gmp.c" - -#define CRYPTO777_PUBSECPSTR "020e46e79a2a8d12b9b5d12c7a91adb4e454edfae43c0a0cb805427d2ac7613fd9" -#define CRYPTO777_KMDADDR "RXL3YXG2ceaB6C5hfJcN4fvmLH2C34knhA" -#define CRYPTO777_RMD160STR "f1dce4182fce875748c4986b240ff7d7bc3fffb0" - -#define KOMODO_PUBTYPE 60 - -struct sha256_vstate { uint64_t length; uint32_t state[8],curlen; uint8_t buf[64]; }; -struct rmd160_vstate { uint64_t length; uint8_t buf[64]; uint32_t curlen, state[5]; }; - -// following is ported from libtom - -#define STORE32L(x, y) \ -{ (y)[3] = (uint8_t)(((x)>>24)&255); (y)[2] = (uint8_t)(((x)>>16)&255); \ -(y)[1] = (uint8_t)(((x)>>8)&255); (y)[0] = (uint8_t)((x)&255); } - -#define LOAD32L(x, y) \ -{ x = (uint32_t)(((uint64_t)((y)[3] & 255)<<24) | \ -((uint32_t)((y)[2] & 255)<<16) | \ -((uint32_t)((y)[1] & 255)<<8) | \ -((uint32_t)((y)[0] & 255))); } - -#define STORE64L(x, y) \ -{ (y)[7] = (uint8_t)(((x)>>56)&255); (y)[6] = (uint8_t)(((x)>>48)&255); \ -(y)[5] = (uint8_t)(((x)>>40)&255); (y)[4] = (uint8_t)(((x)>>32)&255); \ -(y)[3] = (uint8_t)(((x)>>24)&255); (y)[2] = (uint8_t)(((x)>>16)&255); \ -(y)[1] = (uint8_t)(((x)>>8)&255); (y)[0] = (uint8_t)((x)&255); } - -#define LOAD64L(x, y) \ -{ x = (((uint64_t)((y)[7] & 255))<<56)|(((uint64_t)((y)[6] & 255))<<48)| \ -(((uint64_t)((y)[5] & 255))<<40)|(((uint64_t)((y)[4] & 255))<<32)| \ -(((uint64_t)((y)[3] & 255))<<24)|(((uint64_t)((y)[2] & 255))<<16)| \ -(((uint64_t)((y)[1] & 255))<<8)|(((uint64_t)((y)[0] & 255))); } - -#define STORE32H(x, y) \ -{ (y)[0] = (uint8_t)(((x)>>24)&255); (y)[1] = (uint8_t)(((x)>>16)&255); \ -(y)[2] = (uint8_t)(((x)>>8)&255); (y)[3] = (uint8_t)((x)&255); } - -#define LOAD32H(x, y) \ -{ x = (uint32_t)(((uint64_t)((y)[0] & 255)<<24) | \ -((uint32_t)((y)[1] & 255)<<16) | \ -((uint32_t)((y)[2] & 255)<<8) | \ -((uint32_t)((y)[3] & 255))); } - -#define STORE64H(x, y) \ -{ (y)[0] = (uint8_t)(((x)>>56)&255); (y)[1] = (uint8_t)(((x)>>48)&255); \ -(y)[2] = (uint8_t)(((x)>>40)&255); (y)[3] = (uint8_t)(((x)>>32)&255); \ -(y)[4] = (uint8_t)(((x)>>24)&255); (y)[5] = (uint8_t)(((x)>>16)&255); \ -(y)[6] = (uint8_t)(((x)>>8)&255); (y)[7] = (uint8_t)((x)&255); } - -#define LOAD64H(x, y) \ -{ x = (((uint64_t)((y)[0] & 255))<<56)|(((uint64_t)((y)[1] & 255))<<48) | \ -(((uint64_t)((y)[2] & 255))<<40)|(((uint64_t)((y)[3] & 255))<<32) | \ -(((uint64_t)((y)[4] & 255))<<24)|(((uint64_t)((y)[5] & 255))<<16) | \ -(((uint64_t)((y)[6] & 255))<<8)|(((uint64_t)((y)[7] & 255))); } - -// Various logical functions -#define RORc(x, y) ( ((((uint32_t)(x)&0xFFFFFFFFUL)>>(uint32_t)((y)&31)) | ((uint32_t)(x)<<(uint32_t)(32-((y)&31)))) & 0xFFFFFFFFUL) -#define Ch(x,y,z) (z ^ (x & (y ^ z))) -#define Maj(x,y,z) (((x | y) & z) | (x & y)) -#define S(x, n) RORc((x),(n)) -#define R(x, n) (((x)&0xFFFFFFFFUL)>>(n)) -#define Sigma0(x) (S(x, 2) ^ S(x, 13) ^ S(x, 22)) -#define Sigma1(x) (S(x, 6) ^ S(x, 11) ^ S(x, 25)) -#define Gamma0(x) (S(x, 7) ^ S(x, 18) ^ R(x, 3)) -#define Gamma1(x) (S(x, 17) ^ S(x, 19) ^ R(x, 10)) -#define MIN(x, y) ( ((x)<(y))?(x):(y) ) - -static inline int32_t sha256_vcompress(struct sha256_vstate * md,uint8_t *buf) -{ - uint32_t S[8],W[64],t0,t1,i; - for (i=0; i<8; i++) // copy state into S - S[i] = md->state[i]; - for (i=0; i<16; i++) // copy the state into 512-bits into W[0..15] - LOAD32H(W[i],buf + (4*i)); - for (i=16; i<64; i++) // fill W[16..63] - W[i] = Gamma1(W[i - 2]) + W[i - 7] + Gamma0(W[i - 15]) + W[i - 16]; - -#define RND(a,b,c,d,e,f,g,h,i,ki) \ -t0 = h + Sigma1(e) + Ch(e, f, g) + ki + W[i]; \ -t1 = Sigma0(a) + Maj(a, b, c); \ -d += t0; \ -h = t0 + t1; - - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],0,0x428a2f98); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],1,0x71374491); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],2,0xb5c0fbcf); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],3,0xe9b5dba5); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],4,0x3956c25b); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],5,0x59f111f1); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],6,0x923f82a4); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],7,0xab1c5ed5); - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],8,0xd807aa98); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],9,0x12835b01); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],10,0x243185be); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],11,0x550c7dc3); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],12,0x72be5d74); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],13,0x80deb1fe); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],14,0x9bdc06a7); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],15,0xc19bf174); - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],16,0xe49b69c1); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],17,0xefbe4786); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],18,0x0fc19dc6); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],19,0x240ca1cc); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],20,0x2de92c6f); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],21,0x4a7484aa); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],22,0x5cb0a9dc); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],23,0x76f988da); - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],24,0x983e5152); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],25,0xa831c66d); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],26,0xb00327c8); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],27,0xbf597fc7); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],28,0xc6e00bf3); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],29,0xd5a79147); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],30,0x06ca6351); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],31,0x14292967); - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],32,0x27b70a85); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],33,0x2e1b2138); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],34,0x4d2c6dfc); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],35,0x53380d13); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],36,0x650a7354); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],37,0x766a0abb); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],38,0x81c2c92e); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],39,0x92722c85); - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],40,0xa2bfe8a1); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],41,0xa81a664b); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],42,0xc24b8b70); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],43,0xc76c51a3); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],44,0xd192e819); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],45,0xd6990624); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],46,0xf40e3585); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],47,0x106aa070); - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],48,0x19a4c116); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],49,0x1e376c08); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],50,0x2748774c); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],51,0x34b0bcb5); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],52,0x391c0cb3); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],53,0x4ed8aa4a); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],54,0x5b9cca4f); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],55,0x682e6ff3); - RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],56,0x748f82ee); - RND(S[7],S[0],S[1],S[2],S[3],S[4],S[5],S[6],57,0x78a5636f); - RND(S[6],S[7],S[0],S[1],S[2],S[3],S[4],S[5],58,0x84c87814); - RND(S[5],S[6],S[7],S[0],S[1],S[2],S[3],S[4],59,0x8cc70208); - RND(S[4],S[5],S[6],S[7],S[0],S[1],S[2],S[3],60,0x90befffa); - RND(S[3],S[4],S[5],S[6],S[7],S[0],S[1],S[2],61,0xa4506ceb); - RND(S[2],S[3],S[4],S[5],S[6],S[7],S[0],S[1],62,0xbef9a3f7); - RND(S[1],S[2],S[3],S[4],S[5],S[6],S[7],S[0],63,0xc67178f2); -#undef RND - for (i=0; i<8; i++) // feedback - md->state[i] = md->state[i] + S[i]; - return(0); -} - -#undef RORc -#undef Ch -#undef Maj -#undef S -#undef R -#undef Sigma0 -#undef Sigma1 -#undef Gamma0 -#undef Gamma1 - -static inline void sha256_vinit(struct sha256_vstate * md) -{ - md->curlen = 0; - md->length = 0; - md->state[0] = 0x6A09E667UL; - md->state[1] = 0xBB67AE85UL; - md->state[2] = 0x3C6EF372UL; - md->state[3] = 0xA54FF53AUL; - md->state[4] = 0x510E527FUL; - md->state[5] = 0x9B05688CUL; - md->state[6] = 0x1F83D9ABUL; - md->state[7] = 0x5BE0CD19UL; -} - -static inline int32_t sha256_vprocess(struct sha256_vstate *md,const uint8_t *in,uint64_t inlen) -{ - uint64_t n; int32_t err; - if ( md->curlen > sizeof(md->buf) ) - return(-1); - while ( inlen > 0 ) - { - if ( md->curlen == 0 && inlen >= 64 ) - { - if ( (err= sha256_vcompress(md,(uint8_t *)in)) != 0 ) - return(err); - md->length += 64 * 8, in += 64, inlen -= 64; - } - else - { - n = MIN(inlen,64 - md->curlen); - memcpy(md->buf + md->curlen,in,(size_t)n); - md->curlen += n, in += n, inlen -= n; - if ( md->curlen == 64 ) - { - if ( (err= sha256_vcompress(md,md->buf)) != 0 ) - return(err); - md->length += 8*64; - md->curlen = 0; - } - } - } - return(0); -} - -static inline int32_t sha256_vdone(struct sha256_vstate *md,uint8_t *out) -{ - int32_t i; - if ( md->curlen >= sizeof(md->buf) ) - return(-1); - md->length += md->curlen * 8; // increase the length of the message - md->buf[md->curlen++] = (uint8_t)0x80; // append the '1' bit - // if len > 56 bytes we append zeros then compress. Then we can fall back to padding zeros and length encoding like normal. - if ( md->curlen > 56 ) - { - while ( md->curlen < 64 ) - md->buf[md->curlen++] = (uint8_t)0; - sha256_vcompress(md,md->buf); - md->curlen = 0; - } - while ( md->curlen < 56 ) // pad upto 56 bytes of zeroes - md->buf[md->curlen++] = (uint8_t)0; - STORE64H(md->length,md->buf+56); // store length - sha256_vcompress(md,md->buf); - for (i=0; i<8; i++) // copy output - STORE32H(md->state[i],out+(4*i)); - return(0); -} - -void vcalc_sha256(char deprecated[(256 >> 3) * 2 + 1],uint8_t hash[256 >> 3],uint8_t *src,int32_t len) -{ - struct sha256_vstate md; - sha256_vinit(&md); - sha256_vprocess(&md,src,len); - sha256_vdone(&md,hash); -} - -bits256 bits256_doublesha256(char *deprecated,uint8_t *data,int32_t datalen) -{ - bits256 hash,hash2; int32_t i; - vcalc_sha256(0,hash.bytes,data,datalen); - vcalc_sha256(0,hash2.bytes,hash.bytes,sizeof(hash)); - for (i=0; i>(unsigned long)(32-((y)&31)))) & 0xFFFFFFFFUL) - -/* the ten basic operations FF() through III() */ -#define FF(a, b, c, d, e, x, s) \ -(a) += F((b), (c), (d)) + (x);\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define GG(a, b, c, d, e, x, s) \ -(a) += G((b), (c), (d)) + (x) + 0x5a827999UL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define HH(a, b, c, d, e, x, s) \ -(a) += H((b), (c), (d)) + (x) + 0x6ed9eba1UL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define II(a, b, c, d, e, x, s) \ -(a) += I((b), (c), (d)) + (x) + 0x8f1bbcdcUL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define JJ(a, b, c, d, e, x, s) \ -(a) += J((b), (c), (d)) + (x) + 0xa953fd4eUL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define FFF(a, b, c, d, e, x, s) \ -(a) += F((b), (c), (d)) + (x);\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define GGG(a, b, c, d, e, x, s) \ -(a) += G((b), (c), (d)) + (x) + 0x7a6d76e9UL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define HHH(a, b, c, d, e, x, s) \ -(a) += H((b), (c), (d)) + (x) + 0x6d703ef3UL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define III(a, b, c, d, e, x, s) \ -(a) += I((b), (c), (d)) + (x) + 0x5c4dd124UL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -#define JJJ(a, b, c, d, e, x, s) \ -(a) += J((b), (c), (d)) + (x) + 0x50a28be6UL;\ -(a) = ROLc((a), (s)) + (e);\ -(c) = ROLc((c), 10); - -static int32_t rmd160_vcompress(struct rmd160_vstate *md,uint8_t *buf) -{ - uint32_t aa,bb,cc,dd,ee,aaa,bbb,ccc,ddd,eee,X[16]; - int i; - - /* load words X */ - for (i = 0; i < 16; i++){ - LOAD32L(X[i], buf + (4 * i)); - } - - /* load state */ - aa = aaa = md->state[0]; - bb = bbb = md->state[1]; - cc = ccc = md->state[2]; - dd = ddd = md->state[3]; - ee = eee = md->state[4]; - - /* round 1 */ - FF(aa, bb, cc, dd, ee, X[ 0], 11); - FF(ee, aa, bb, cc, dd, X[ 1], 14); - FF(dd, ee, aa, bb, cc, X[ 2], 15); - FF(cc, dd, ee, aa, bb, X[ 3], 12); - FF(bb, cc, dd, ee, aa, X[ 4], 5); - FF(aa, bb, cc, dd, ee, X[ 5], 8); - FF(ee, aa, bb, cc, dd, X[ 6], 7); - FF(dd, ee, aa, bb, cc, X[ 7], 9); - FF(cc, dd, ee, aa, bb, X[ 8], 11); - FF(bb, cc, dd, ee, aa, X[ 9], 13); - FF(aa, bb, cc, dd, ee, X[10], 14); - FF(ee, aa, bb, cc, dd, X[11], 15); - FF(dd, ee, aa, bb, cc, X[12], 6); - FF(cc, dd, ee, aa, bb, X[13], 7); - FF(bb, cc, dd, ee, aa, X[14], 9); - FF(aa, bb, cc, dd, ee, X[15], 8); - - /* round 2 */ - GG(ee, aa, bb, cc, dd, X[ 7], 7); - GG(dd, ee, aa, bb, cc, X[ 4], 6); - GG(cc, dd, ee, aa, bb, X[13], 8); - GG(bb, cc, dd, ee, aa, X[ 1], 13); - GG(aa, bb, cc, dd, ee, X[10], 11); - GG(ee, aa, bb, cc, dd, X[ 6], 9); - GG(dd, ee, aa, bb, cc, X[15], 7); - GG(cc, dd, ee, aa, bb, X[ 3], 15); - GG(bb, cc, dd, ee, aa, X[12], 7); - GG(aa, bb, cc, dd, ee, X[ 0], 12); - GG(ee, aa, bb, cc, dd, X[ 9], 15); - GG(dd, ee, aa, bb, cc, X[ 5], 9); - GG(cc, dd, ee, aa, bb, X[ 2], 11); - GG(bb, cc, dd, ee, aa, X[14], 7); - GG(aa, bb, cc, dd, ee, X[11], 13); - GG(ee, aa, bb, cc, dd, X[ 8], 12); - - /* round 3 */ - HH(dd, ee, aa, bb, cc, X[ 3], 11); - HH(cc, dd, ee, aa, bb, X[10], 13); - HH(bb, cc, dd, ee, aa, X[14], 6); - HH(aa, bb, cc, dd, ee, X[ 4], 7); - HH(ee, aa, bb, cc, dd, X[ 9], 14); - HH(dd, ee, aa, bb, cc, X[15], 9); - HH(cc, dd, ee, aa, bb, X[ 8], 13); - HH(bb, cc, dd, ee, aa, X[ 1], 15); - HH(aa, bb, cc, dd, ee, X[ 2], 14); - HH(ee, aa, bb, cc, dd, X[ 7], 8); - HH(dd, ee, aa, bb, cc, X[ 0], 13); - HH(cc, dd, ee, aa, bb, X[ 6], 6); - HH(bb, cc, dd, ee, aa, X[13], 5); - HH(aa, bb, cc, dd, ee, X[11], 12); - HH(ee, aa, bb, cc, dd, X[ 5], 7); - HH(dd, ee, aa, bb, cc, X[12], 5); - - /* round 4 */ - II(cc, dd, ee, aa, bb, X[ 1], 11); - II(bb, cc, dd, ee, aa, X[ 9], 12); - II(aa, bb, cc, dd, ee, X[11], 14); - II(ee, aa, bb, cc, dd, X[10], 15); - II(dd, ee, aa, bb, cc, X[ 0], 14); - II(cc, dd, ee, aa, bb, X[ 8], 15); - II(bb, cc, dd, ee, aa, X[12], 9); - II(aa, bb, cc, dd, ee, X[ 4], 8); - II(ee, aa, bb, cc, dd, X[13], 9); - II(dd, ee, aa, bb, cc, X[ 3], 14); - II(cc, dd, ee, aa, bb, X[ 7], 5); - II(bb, cc, dd, ee, aa, X[15], 6); - II(aa, bb, cc, dd, ee, X[14], 8); - II(ee, aa, bb, cc, dd, X[ 5], 6); - II(dd, ee, aa, bb, cc, X[ 6], 5); - II(cc, dd, ee, aa, bb, X[ 2], 12); - - /* round 5 */ - JJ(bb, cc, dd, ee, aa, X[ 4], 9); - JJ(aa, bb, cc, dd, ee, X[ 0], 15); - JJ(ee, aa, bb, cc, dd, X[ 5], 5); - JJ(dd, ee, aa, bb, cc, X[ 9], 11); - JJ(cc, dd, ee, aa, bb, X[ 7], 6); - JJ(bb, cc, dd, ee, aa, X[12], 8); - JJ(aa, bb, cc, dd, ee, X[ 2], 13); - JJ(ee, aa, bb, cc, dd, X[10], 12); - JJ(dd, ee, aa, bb, cc, X[14], 5); - JJ(cc, dd, ee, aa, bb, X[ 1], 12); - JJ(bb, cc, dd, ee, aa, X[ 3], 13); - JJ(aa, bb, cc, dd, ee, X[ 8], 14); - JJ(ee, aa, bb, cc, dd, X[11], 11); - JJ(dd, ee, aa, bb, cc, X[ 6], 8); - JJ(cc, dd, ee, aa, bb, X[15], 5); - JJ(bb, cc, dd, ee, aa, X[13], 6); - - /* parallel round 1 */ - JJJ(aaa, bbb, ccc, ddd, eee, X[ 5], 8); - JJJ(eee, aaa, bbb, ccc, ddd, X[14], 9); - JJJ(ddd, eee, aaa, bbb, ccc, X[ 7], 9); - JJJ(ccc, ddd, eee, aaa, bbb, X[ 0], 11); - JJJ(bbb, ccc, ddd, eee, aaa, X[ 9], 13); - JJJ(aaa, bbb, ccc, ddd, eee, X[ 2], 15); - JJJ(eee, aaa, bbb, ccc, ddd, X[11], 15); - JJJ(ddd, eee, aaa, bbb, ccc, X[ 4], 5); - JJJ(ccc, ddd, eee, aaa, bbb, X[13], 7); - JJJ(bbb, ccc, ddd, eee, aaa, X[ 6], 7); - JJJ(aaa, bbb, ccc, ddd, eee, X[15], 8); - JJJ(eee, aaa, bbb, ccc, ddd, X[ 8], 11); - JJJ(ddd, eee, aaa, bbb, ccc, X[ 1], 14); - JJJ(ccc, ddd, eee, aaa, bbb, X[10], 14); - JJJ(bbb, ccc, ddd, eee, aaa, X[ 3], 12); - JJJ(aaa, bbb, ccc, ddd, eee, X[12], 6); - - /* parallel round 2 */ - III(eee, aaa, bbb, ccc, ddd, X[ 6], 9); - III(ddd, eee, aaa, bbb, ccc, X[11], 13); - III(ccc, ddd, eee, aaa, bbb, X[ 3], 15); - III(bbb, ccc, ddd, eee, aaa, X[ 7], 7); - III(aaa, bbb, ccc, ddd, eee, X[ 0], 12); - III(eee, aaa, bbb, ccc, ddd, X[13], 8); - III(ddd, eee, aaa, bbb, ccc, X[ 5], 9); - III(ccc, ddd, eee, aaa, bbb, X[10], 11); - III(bbb, ccc, ddd, eee, aaa, X[14], 7); - III(aaa, bbb, ccc, ddd, eee, X[15], 7); - III(eee, aaa, bbb, ccc, ddd, X[ 8], 12); - III(ddd, eee, aaa, bbb, ccc, X[12], 7); - III(ccc, ddd, eee, aaa, bbb, X[ 4], 6); - III(bbb, ccc, ddd, eee, aaa, X[ 9], 15); - III(aaa, bbb, ccc, ddd, eee, X[ 1], 13); - III(eee, aaa, bbb, ccc, ddd, X[ 2], 11); - - /* parallel round 3 */ - HHH(ddd, eee, aaa, bbb, ccc, X[15], 9); - HHH(ccc, ddd, eee, aaa, bbb, X[ 5], 7); - HHH(bbb, ccc, ddd, eee, aaa, X[ 1], 15); - HHH(aaa, bbb, ccc, ddd, eee, X[ 3], 11); - HHH(eee, aaa, bbb, ccc, ddd, X[ 7], 8); - HHH(ddd, eee, aaa, bbb, ccc, X[14], 6); - HHH(ccc, ddd, eee, aaa, bbb, X[ 6], 6); - HHH(bbb, ccc, ddd, eee, aaa, X[ 9], 14); - HHH(aaa, bbb, ccc, ddd, eee, X[11], 12); - HHH(eee, aaa, bbb, ccc, ddd, X[ 8], 13); - HHH(ddd, eee, aaa, bbb, ccc, X[12], 5); - HHH(ccc, ddd, eee, aaa, bbb, X[ 2], 14); - HHH(bbb, ccc, ddd, eee, aaa, X[10], 13); - HHH(aaa, bbb, ccc, ddd, eee, X[ 0], 13); - HHH(eee, aaa, bbb, ccc, ddd, X[ 4], 7); - HHH(ddd, eee, aaa, bbb, ccc, X[13], 5); - - /* parallel round 4 */ - GGG(ccc, ddd, eee, aaa, bbb, X[ 8], 15); - GGG(bbb, ccc, ddd, eee, aaa, X[ 6], 5); - GGG(aaa, bbb, ccc, ddd, eee, X[ 4], 8); - GGG(eee, aaa, bbb, ccc, ddd, X[ 1], 11); - GGG(ddd, eee, aaa, bbb, ccc, X[ 3], 14); - GGG(ccc, ddd, eee, aaa, bbb, X[11], 14); - GGG(bbb, ccc, ddd, eee, aaa, X[15], 6); - GGG(aaa, bbb, ccc, ddd, eee, X[ 0], 14); - GGG(eee, aaa, bbb, ccc, ddd, X[ 5], 6); - GGG(ddd, eee, aaa, bbb, ccc, X[12], 9); - GGG(ccc, ddd, eee, aaa, bbb, X[ 2], 12); - GGG(bbb, ccc, ddd, eee, aaa, X[13], 9); - GGG(aaa, bbb, ccc, ddd, eee, X[ 9], 12); - GGG(eee, aaa, bbb, ccc, ddd, X[ 7], 5); - GGG(ddd, eee, aaa, bbb, ccc, X[10], 15); - GGG(ccc, ddd, eee, aaa, bbb, X[14], 8); - - /* parallel round 5 */ - FFF(bbb, ccc, ddd, eee, aaa, X[12] , 8); - FFF(aaa, bbb, ccc, ddd, eee, X[15] , 5); - FFF(eee, aaa, bbb, ccc, ddd, X[10] , 12); - FFF(ddd, eee, aaa, bbb, ccc, X[ 4] , 9); - FFF(ccc, ddd, eee, aaa, bbb, X[ 1] , 12); - FFF(bbb, ccc, ddd, eee, aaa, X[ 5] , 5); - FFF(aaa, bbb, ccc, ddd, eee, X[ 8] , 14); - FFF(eee, aaa, bbb, ccc, ddd, X[ 7] , 6); - FFF(ddd, eee, aaa, bbb, ccc, X[ 6] , 8); - FFF(ccc, ddd, eee, aaa, bbb, X[ 2] , 13); - FFF(bbb, ccc, ddd, eee, aaa, X[13] , 6); - FFF(aaa, bbb, ccc, ddd, eee, X[14] , 5); - FFF(eee, aaa, bbb, ccc, ddd, X[ 0] , 15); - FFF(ddd, eee, aaa, bbb, ccc, X[ 3] , 13); - FFF(ccc, ddd, eee, aaa, bbb, X[ 9] , 11); - FFF(bbb, ccc, ddd, eee, aaa, X[11] , 11); - - /* combine results */ - ddd += cc + md->state[1]; /* final result for md->state[0] */ - md->state[1] = md->state[2] + dd + eee; - md->state[2] = md->state[3] + ee + aaa; - md->state[3] = md->state[4] + aa + bbb; - md->state[4] = md->state[0] + bb + ccc; - md->state[0] = ddd; - - return 0; -} - -/** - Initialize the hash state - @param md The hash state you wish to initialize - @return 0 if successful - */ -int rmd160_vinit(struct rmd160_vstate * md) -{ - md->state[0] = 0x67452301UL; - md->state[1] = 0xefcdab89UL; - md->state[2] = 0x98badcfeUL; - md->state[3] = 0x10325476UL; - md->state[4] = 0xc3d2e1f0UL; - md->curlen = 0; - md->length = 0; - return 0; -} -#define HASH_PROCESS(func_name, compress_name, state_var, block_size) \ -int func_name (struct rmd160_vstate * md, const unsigned char *in, unsigned long inlen) \ -{ \ -unsigned long n; \ -int err; \ -if (md->curlen > sizeof(md->buf)) { \ -return -1; \ -} \ -while (inlen > 0) { \ -if (md->curlen == 0 && inlen >= block_size) { \ -if ((err = compress_name (md, (unsigned char *)in)) != 0) { \ -return err; \ -} \ -md->length += block_size * 8; \ -in += block_size; \ -inlen -= block_size; \ -} else { \ -n = MIN(inlen, (block_size - md->curlen)); \ -memcpy(md->buf + md->curlen, in, (size_t)n); \ -md->curlen += n; \ -in += n; \ -inlen -= n; \ -if (md->curlen == block_size) { \ -if ((err = compress_name (md, md->buf)) != 0) { \ -return err; \ -} \ -md->length += 8*block_size; \ -md->curlen = 0; \ -} \ -} \ -} \ -return 0; \ -} - -/** - Process a block of memory though the hash - @param md The hash state - @param in The data to hash - @param inlen The length of the data (octets) - @return 0 if successful - */ -HASH_PROCESS(rmd160_vprocess, rmd160_vcompress, rmd160, 64) - -/** - Terminate the hash to get the digest - @param md The hash state - @param out [out] The destination of the hash (20 bytes) - @return 0 if successful - */ -int rmd160_vdone(struct rmd160_vstate * md, unsigned char *out) -{ - int i; - if (md->curlen >= sizeof(md->buf)) { - return -1; - } - /* increase the length of the message */ - md->length += md->curlen * 8; - - /* append the '1' bit */ - md->buf[md->curlen++] = (unsigned char)0x80; - - /* if the length is currently above 56 bytes we append zeros - * then compress. Then we can fall back to padding zeros and length - * encoding like normal. - */ - if (md->curlen > 56) { - while (md->curlen < 64) { - md->buf[md->curlen++] = (unsigned char)0; - } - rmd160_vcompress(md, md->buf); - md->curlen = 0; - } - /* pad upto 56 bytes of zeroes */ - while (md->curlen < 56) { - md->buf[md->curlen++] = (unsigned char)0; - } - /* store length */ - STORE64L(md->length, md->buf+56); - rmd160_vcompress(md, md->buf); - /* copy output */ - for (i = 0; i < 5; i++) { - STORE32L(md->state[i], out+(4*i)); - } - return 0; -} - -void calc_rmd160(char deprecated[41],uint8_t buf[20],uint8_t *msg,int32_t len) -{ - struct rmd160_vstate md; - rmd160_vinit(&md); - rmd160_vprocess(&md,msg,len); - rmd160_vdone(&md, buf); -} -#undef F -#undef G -#undef H -#undef I -#undef J -#undef ROLc -#undef FF -#undef GG -#undef HH -#undef II -#undef JJ -#undef FFF -#undef GGG -#undef HHH -#undef III -#undef JJJ - -static const uint32_t crc32_tab[] = { - 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, 0x706af48f, - 0xe963a535, 0x9e6495a3, 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988, - 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91, 0x1db71064, 0x6ab020f2, - 0xf3b97148, 0x84be41de, 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7, - 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9, - 0xfa0f3d63, 0x8d080df5, 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172, - 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b, 0x35b5a8fa, 0x42b2986c, - 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59, - 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423, - 0xcfba9599, 0xb8bda50f, 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924, - 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, 0x76dc4190, 0x01db7106, - 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433, - 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818, 0x7f6a0dbb, 0x086d3d2d, - 0x91646c97, 0xe6635c01, 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e, - 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457, 0x65b0d9c6, 0x12b7e950, - 0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65, - 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, 0x4adfa541, 0x3dd895d7, - 0xa4d1c46d, 0xd3d6f4fb, 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0, - 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9, 0x5005713c, 0x270241aa, - 0xbe0b1010, 0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f, - 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17, 0x2eb40d81, - 0xb7bd5c3b, 0xc0ba6cad, 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a, - 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683, 0xe3630b12, 0x94643b84, - 0x0d6d6a3e, 0x7a6a5aa8, 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1, - 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb, - 0x196c3671, 0x6e6b06e7, 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc, - 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5, 0xd6d6a3e8, 0xa1d1937e, - 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b, - 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55, - 0x316e8eef, 0x4669be79, 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236, - 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, 0xc5ba3bbe, 0xb2bd0b28, - 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d, - 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a, 0x9c0906a9, 0xeb0e363f, - 0x72076785, 0x05005713, 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38, - 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, 0x86d3d2d4, 0xf1d4e242, - 0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777, - 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, 0x8f659eff, 0xf862ae69, - 0x616bffd3, 0x166ccf45, 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2, - 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db, 0xaed16a4a, 0xd9d65adc, - 0x40df0b66, 0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9, - 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605, 0xcdd70693, - 0x54de5729, 0x23d967bf, 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94, - 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d -}; - -uint32_t calc_crc32(uint32_t crc,const void *buf,size_t size) -{ - const uint8_t *p; - - p = (const uint8_t *)buf; - crc = crc ^ ~0U; - - while (size--) - crc = crc32_tab[(crc ^ *p++) & 0xFF] ^ (crc >> 8); - - return crc ^ ~0U; -} - -void calc_rmd160_sha256(uint8_t rmd160[20],uint8_t *data,int32_t datalen) -{ - bits256 hash; - vcalc_sha256(0,hash.bytes,data,datalen); - calc_rmd160(0,rmd160,hash.bytes,sizeof(hash)); -} - -int32_t bitcoin_addr2rmd160(uint8_t *addrtypep,uint8_t rmd160[20],char *coinaddr) -{ - bits256 hash; uint8_t *buf,_buf[25]; int32_t len; - memset(rmd160,0,20); - *addrtypep = 0; - buf = _buf; - if ( (len= bitcoin_base58decode(buf,coinaddr)) >= 4 ) - { - // validate with trailing hash, then remove hash - hash = bits256_doublesha256(0,buf,21); - *addrtypep = *buf; - memcpy(rmd160,buf+1,20); - if ( (buf[21]&0xff) == hash.bytes[31] && (buf[22]&0xff) == hash.bytes[30] &&(buf[23]&0xff) == hash.bytes[29] && (buf[24]&0xff) == hash.bytes[28] ) - { - //printf("coinaddr.(%s) valid checksum addrtype.%02x\n",coinaddr,*addrtypep); - return(20); - } - else - { - int32_t i; - if ( len > 20 ) - { - hash = bits256_doublesha256(0,buf,len); - } - for (i=0; i= 0 ) - return(1); - else return(0); -} - -int32_t bitweight(uint64_t x) -{ - int i,wt = 0; - for (i=0; i<64; i++) - if ( (1LL << i) & x ) - wt++; - return(wt); -} - -int32_t _unhex(char c) -{ - if ( c >= '0' && c <= '9' ) - return(c - '0'); - else if ( c >= 'a' && c <= 'f' ) - return(c - 'a' + 10); - else if ( c >= 'A' && c <= 'F' ) - return(c - 'A' + 10); - return(-1); -} - -int32_t is_hexstr(char *str,int32_t n) -{ - int32_t i; - if ( str == 0 || str[0] == 0 ) - return(0); - for (i=0; str[i]!=0; i++) - { - if ( n > 0 && i >= n ) - break; - if ( _unhex(str[i]) < 0 ) - break; - } - if ( n == 0 ) - return(i); - return(i == n); -} - -int32_t unhex(char c) -{ - int32_t hex; - if ( (hex= _unhex(c)) < 0 ) - { - //printf("unhex: illegal hexchar.(%c)\n",c); - } - return(hex); -} - -unsigned char _decode_hex(char *hex) { return((unhex(hex[0])<<4) | unhex(hex[1])); } - -int32_t decode_hex(uint8_t *bytes,int32_t n,char *hex) -{ - int32_t adjust,i = 0; - //printf("decode.(%s)\n",hex); - if ( is_hexstr(hex,n) <= 0 ) - { - memset(bytes,0,n); - return(n); - } - if ( hex[n-1] == '\n' || hex[n-1] == '\r' ) - hex[--n] = 0; - if ( n == 0 || (hex[n*2+1] == 0 && hex[n*2] != 0) ) - { - if ( n > 0 ) - { - bytes[0] = unhex(hex[0]); - printf("decode_hex n.%d hex[0] (%c) -> %d hex.(%s) [n*2+1: %d] [n*2: %d %c] len.%ld\n",n,hex[0],bytes[0],hex,hex[n*2+1],hex[n*2],hex[n*2],(long)strlen(hex)); - } - bytes++; - hex++; - adjust = 1; - } else adjust = 0; - if ( n > 0 ) - { - for (i=0; i>4) & 0xf); - hexbytes[i*2 + 1] = hexbyte(message[i] & 0xf); - //printf("i.%d (%02x) [%c%c]\n",i,message[i],hexbytes[i*2],hexbytes[i*2+1]); - } - hexbytes[len*2] = 0; - //printf("len.%ld\n",len*2+1); - return((int32_t)len*2+1); -} - -char *bits256_str(char hexstr[65],bits256 x) -{ - init_hexbytes_noT(hexstr,x.bytes,sizeof(x)); - return(hexstr); -} - -int32_t iguana_rwnum(int32_t rwflag,uint8_t *serialized,int32_t len,void *endianedp) -{ - int32_t i; uint64_t x; - if ( rwflag == 0 ) - { - x = 0; - for (i=len-1; i>=0; i--) - { - x <<= 8; - x |= serialized[i]; - } - switch ( len ) - { - case 1: *(uint8_t *)endianedp = (uint8_t)x; break; - case 2: *(uint16_t *)endianedp = (uint16_t)x; break; - case 4: *(uint32_t *)endianedp = (uint32_t)x; break; - case 8: *(uint64_t *)endianedp = (uint64_t)x; break; - } - } - else - { - x = 0; - switch ( len ) - { - case 1: x = *(uint8_t *)endianedp; break; - case 2: x = *(uint16_t *)endianedp; break; - case 4: x = *(uint32_t *)endianedp; break; - case 8: x = *(uint64_t *)endianedp; break; - } - for (i=0; i>= 8) - serialized[i] = (uint8_t)(x & 0xff); - } - return(len); -} - -int32_t iguana_rwbignum(int32_t rwflag,uint8_t *serialized,int32_t len,uint8_t *endianedp) -{ - int32_t i; - if ( rwflag == 0 ) - { - for (i=0; i= 0x4c ) - { - if ( opretlen == 0x4c ) - opretlen = script[len++]; - else if ( opretlen == 0x4d ) - { - opretlen = script[len] + (script[len+1] << 8); - len += 2; - //opretlen = script[len++]; - //opretlen = (opretlen << 8) | script[len++]; - } - } - *opretlenp = opretlen; - return(len); -} - -int32_t komodo_opreturnscript(uint8_t *script,uint8_t type,uint8_t *opret,int32_t opretlen) -{ - int32_t offset = 0; - script[offset++] = 0x6a; - opretlen++; - if ( opretlen >= 0x4c ) - { - if ( opretlen > 0xff ) - { - script[offset++] = 0x4d; - script[offset++] = opretlen & 0xff; - script[offset++] = (opretlen >> 8) & 0xff; - } - else - { - script[offset++] = 0x4c; - script[offset++] = opretlen; - } - } else script[offset++] = opretlen; - script[offset++] = type; // covered by opretlen - memcpy(&script[offset],opret,opretlen-1); - return(offset + opretlen - 1); -} - -long _stripwhite(char *buf,int accept) -{ - int32_t i,j,c; - if ( buf == 0 || buf[0] == 0 ) - return(0); - for (i=j=0; buf[i]!=0; i++) - { - buf[j] = c = buf[i]; - if ( c == accept || (c != ' ' && c != '\n' && c != '\r' && c != '\t' && c != '\b') ) - j++; - } - buf[j] = 0; - return(j); -} - -char *clonestr(char *str) -{ - char *clone; - if ( str == 0 || str[0] == 0 ) - { - printf("warning cloning nullstr.%p\n",str); -#ifdef __APPLE__ - while ( 1 ) sleep(1); -#endif - str = (char *)""; - } - clone = (char *)malloc(strlen(str)+16); - strcpy(clone,str); - return(clone); -} - -int32_t safecopy(char *dest,char *src,long len) -{ - int32_t i = -1; - if ( src != 0 && dest != 0 && src != dest ) - { - if ( dest != 0 ) - memset(dest,0,len); - for (i=0; i 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 - -void lock_queue(queue_t *queue) -{ - if ( queue->initflag == 0 ) - { - portable_mutex_init(&queue->mutex); - queue->initflag = 1; - } - portable_mutex_lock(&queue->mutex); -} - -void queue_enqueue(char *name,queue_t *queue,struct queueitem *item) -{ - if ( queue->name[0] == 0 && name != 0 && name[0] != 0 ) - strcpy(queue->name,name); - if ( item == 0 ) - { - printf("FATAL type error: queueing empty value\n"); - return; - } - lock_queue(queue); - DL_APPEND(queue->list,item); - portable_mutex_unlock(&queue->mutex); -} - -struct queueitem *queue_dequeue(queue_t *queue) -{ - struct queueitem *item = 0; - lock_queue(queue); - if ( queue->list != 0 ) - { - item = queue->list; - DL_DELETE(queue->list,item); - } - portable_mutex_unlock(&queue->mutex); - return(item); -} - -void *queue_delete(queue_t *queue,struct queueitem *copy,int32_t copysize) -{ - struct queueitem *item = 0; - lock_queue(queue); - if ( queue->list != 0 ) - { - DL_FOREACH(queue->list,item) - { - #ifdef _WIN32 - if ( item == copy || (item->allocsize == copysize && memcmp((void *)((intptr_t)item + sizeof(struct queueitem)),(void *)((intptr_t)copy + sizeof(struct queueitem)),copysize) == 0) ) - #else - if ( item == copy || (item->allocsize == copysize && memcmp((void *)((long)item + sizeof(struct queueitem)),(void *)((long)copy + sizeof(struct queueitem)),copysize) == 0) ) - #endif - { - DL_DELETE(queue->list,item); - portable_mutex_unlock(&queue->mutex); - printf("name.(%s) deleted item.%p list.%p\n",queue->name,item,queue->list); - return(item); - } - } - } - portable_mutex_unlock(&queue->mutex); - return(0); -} - -void *queue_free(queue_t *queue) -{ - struct queueitem *item = 0; - lock_queue(queue); - if ( queue->list != 0 ) - { - DL_FOREACH(queue->list,item) - { - DL_DELETE(queue->list,item); - free(item); - } - //printf("name.(%s) dequeue.%p list.%p\n",queue->name,item,queue->list); - } - portable_mutex_unlock(&queue->mutex); - return(0); -} - -void *queue_clone(queue_t *clone,queue_t *queue,int32_t size) -{ - struct queueitem *ptr,*item = 0; - lock_queue(queue); - if ( queue->list != 0 ) - { - DL_FOREACH(queue->list,item) - { - ptr = (struct queueitem *)calloc(1,sizeof(*ptr)); - memcpy(ptr,item,size); - queue_enqueue(queue->name,clone,ptr); - } - //printf("name.(%s) dequeue.%p list.%p\n",queue->name,item,queue->list); - } - portable_mutex_unlock(&queue->mutex); - return(0); -} - -int32_t queue_size(queue_t *queue) -{ - int32_t count = 0; - struct queueitem *tmp; - lock_queue(queue); - DL_COUNT(queue->list,tmp,count); - portable_mutex_unlock(&queue->mutex); - return count; -} - -void iguana_initQ(queue_t *Q,char *name) -{ - struct queueitem *item,*I; - memset(Q,0,sizeof(*Q)); - I = (struct queueitem *)calloc(1,sizeof(*I)); - strcpy(Q->name,name); - queue_enqueue(name,Q,I); - if ( (item= queue_dequeue(Q)) != 0 ) - free(item); -} - -uint16_t _komodo_userpass(char *username,char *password,FILE *fp) -{ - char *rpcuser,*rpcpassword,*str,line[8192]; uint16_t port = 0; - rpcuser = rpcpassword = 0; - username[0] = password[0] = 0; - while ( fgets(line,sizeof(line),fp) != 0 ) - { - if ( line[0] == '#' ) - continue; - //printf("line.(%s) %p %p\n",line,strstr(line,(char *)"rpcuser"),strstr(line,(char *)"rpcpassword")); - if ( (str= strstr(line,(char *)"rpcuser")) != 0 ) - rpcuser = parse_conf_line(str,(char *)"rpcuser"); - else if ( (str= strstr(line,(char *)"rpcpassword")) != 0 ) - rpcpassword = parse_conf_line(str,(char *)"rpcpassword"); - else if ( (str= strstr(line,(char *)"rpcport")) != 0 ) - { - port = atoi(parse_conf_line(str,(char *)"rpcport")); - //fprintf(stderr,"rpcport.%u in file\n",port); - } - } - if ( rpcuser != 0 && rpcpassword != 0 ) - { - strcpy(username,rpcuser); - strcpy(password,rpcpassword); - } - //printf("rpcuser.(%s) rpcpassword.(%s) KMDUSERPASS.(%s) %u\n",rpcuser,rpcpassword,KMDUSERPASS,port); - if ( rpcuser != 0 ) - free(rpcuser); - if ( rpcpassword != 0 ) - free(rpcpassword); - return(port); -} - -void komodo_statefname(char *fname,char *symbol,char *str) -{ - int32_t n,len; - sprintf(fname,"%s",GetDataDir(false).string().c_str()); - if ( (n= (int32_t)strlen(ASSETCHAINS_SYMBOL)) != 0 ) - { - len = (int32_t)strlen(fname); - if ( strcmp(ASSETCHAINS_SYMBOL,&fname[len - n]) == 0 ) - fname[len - n] = 0; - else - { - printf("unexpected fname.(%s) vs %s [%s] n.%d len.%d (%s)\n",fname,symbol,ASSETCHAINS_SYMBOL,n,len,&fname[len - n]); - return; - } - } - else - { -#ifdef _WIN32 - strcat(fname,"\\"); -#else - strcat(fname,"/"); -#endif - } - if ( symbol != 0 && symbol[0] != 0 && strcmp("KMD",symbol) != 0 ) - { - strcat(fname,symbol); - //printf("statefname.(%s) -> (%s)\n",symbol,fname); -#ifdef _WIN32 - strcat(fname,"\\"); -#else - strcat(fname,"/"); -#endif - } - strcat(fname,str); - //printf("test.(%s) -> [%s] statename.(%s) %s\n",test,ASSETCHAINS_SYMBOL,symbol,fname); -} - -void komodo_configfile(char *symbol,uint16_t rpcport) -{ - static char myusername[512],mypassword[8192]; - FILE *fp; uint16_t kmdport; uint8_t buf2[33]; char fname[512],buf[128],username[512],password[8192]; uint32_t crc,r,r2,i; - if ( symbol != 0 && rpcport != 0 ) - { - r = (uint32_t)time(NULL); - r2 = OS_milliseconds(); - memcpy(buf,&r,sizeof(r)); - memcpy(&buf[sizeof(r)],&r2,sizeof(r2)); - memcpy(&buf[sizeof(r)+sizeof(r2)],symbol,strlen(symbol)); - crc = calc_crc32(0,(uint8_t *)buf,(int32_t)(sizeof(r)+sizeof(r2)+strlen(symbol))); - #ifdef _WIN32 - randombytes_buf(buf2,sizeof(buf2)); - #else - OS_randombytes(buf2,sizeof(buf2)); - #endif - for (i=0; i userpass.(%s)\n",fname,KMDUSERPASS); - } //else printf("couldnt open.(%s)\n",fname); -} - -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; - if ( strcmp("KMD",symbol) == 0 ) - { -#ifdef __APPLE__ - sprintf(confname,"Komodo.conf"); -#else - sprintf(confname,"komodo.conf"); -#endif - } - else sprintf(confname,"%s.conf",symbol); - komodo_statefname(fname,symbol,confname); - if ( (fp= fopen(fname,"rb")) != 0 ) - { - port = _komodo_userpass(username,password,fp); - sprintf(userpass,"%s:%s",username,password); - if ( strcmp(symbol,ASSETCHAINS_SYMBOL) == 0 ) - strcpy(ASSETCHAINS_USERPASS,userpass); - fclose(fp); - } - return(port); -} - -uint32_t komodo_assetmagic(char *symbol,uint64_t supply,uint8_t *extraptr,int32_t extralen) -{ - uint8_t buf[512]; uint32_t crc0=0; int32_t len = 0; bits256 hash; - if ( strcmp(symbol,"KMD") == 0 ) - return(0x8de4eef9); - len = iguana_rwnum(1,&buf[len],sizeof(supply),(void *)&supply); - strcpy((char *)&buf[len],symbol); - len += strlen(symbol); - if ( extraptr != 0 && extralen != 0 ) - { - vcalc_sha256(0,hash.bytes,extraptr,extralen); - crc0 = hash.uints[0]; - } - return(calc_crc32(crc0,buf,len)); -} - -uint16_t komodo_assetport(uint32_t magic,int32_t extralen) -{ - if ( magic == 0x8de4eef9 ) - return(7770); - else if ( extralen == 0 ) - return(8000 + (magic % 7777)); - else return(16000 + (magic % 49500)); -} - -uint16_t komodo_port(char *symbol,uint64_t supply,uint32_t *magicp,uint8_t *extraptr,int32_t extralen) -{ - if ( symbol == 0 || symbol[0] == 0 || strcmp("KMD",symbol) == 0 ) - { - *magicp = 0x8de4eef9; - return(7770); - } - *magicp = komodo_assetmagic(symbol,supply,extraptr,extralen); - return(komodo_assetport(*magicp,extralen)); -} - -/*void komodo_ports(uint16_t ports[MAX_CURRENCIES]) -{ - int32_t i; uint32_t magic; - for (i=0; i matches suffix (%s) -> ac_name.(%s)\n",argv0,argv0suffix[i],argv0names[i]); - name = argv0names[i]; - break; - } - } - } - KOMODO_STOPAT = GetArg("-stopat",0); - ASSETCHAINS_CC = GetArg("-ac_cc",0); - KOMODO_CCACTIVATE = GetArg("-ac_ccactivate",0); - ASSETCHAINS_PUBLIC = GetArg("-ac_public",0); - ASSETCHAINS_PRIVATE = GetArg("-ac_private",0); - if ( (KOMODO_REWIND= GetArg("-rewind",0)) != 0 ) - { - printf("KOMODO_REWIND %d\n",KOMODO_REWIND); - } - if ( name.c_str()[0] != 0 ) - { - MAX_BLOCK_SIGOPS = 60000; - ASSETCHAINS_SUPPLY = GetArg("-ac_supply",10); - ASSETCHAINS_ENDSUBSIDY = GetArg("-ac_end",0); - ASSETCHAINS_REWARD = GetArg("-ac_reward",0); - ASSETCHAINS_HALVING = GetArg("-ac_halving",0); - ASSETCHAINS_DECAY = GetArg("-ac_decay",0); - ASSETCHAINS_COMMISSION = GetArg("-ac_perc",0); - ASSETCHAINS_OVERRIDE_PUBKEY = GetArg("-ac_pubkey",""); - if ( (ASSETCHAINS_STAKED= GetArg("-ac_staked",0)) > 100 ) - ASSETCHAINS_STAKED = 100; - if ( ASSETCHAINS_STAKED != 0 && ASSETCHAINS_PRIVATE != 0 ) - { - printf("-ac_private chains cant have any PoS\n"); - exit(0); - } - if ( ASSETCHAINS_HALVING != 0 && ASSETCHAINS_HALVING < 1440 ) - { - ASSETCHAINS_HALVING = 1440; - printf("ASSETCHAINS_HALVING must be at least 1440 blocks\n"); - } - if ( ASSETCHAINS_DECAY == 100000000 && ASSETCHAINS_ENDSUBSIDY == 0 ) - { - ASSETCHAINS_DECAY = 0; - printf("ASSETCHAINS_DECAY of 100000000 means linear and that needs ASSETCHAINS_ENDSUBSIDY\n"); - } - else if ( ASSETCHAINS_DECAY > 100000000 ) - { - ASSETCHAINS_DECAY = 0; - printf("ASSETCHAINS_DECAY cant be more than 100000000\n"); - } - if ( strlen(ASSETCHAINS_OVERRIDE_PUBKEY.c_str()) == 66 ) - decode_hex(ASSETCHAINS_OVERRIDE_PUBKEY33,33,(char *)ASSETCHAINS_OVERRIDE_PUBKEY.c_str()); - else if ( ASSETCHAINS_COMMISSION != 0 ) - { - ASSETCHAINS_COMMISSION = 0; - printf("ASSETCHAINS_COMMISSION needs an ASETCHAINS_OVERRIDE_PUBKEY and cant be more than 100000000 (100%%)\n"); - } - if ( ASSETCHAINS_ENDSUBSIDY != 0 || ASSETCHAINS_REWARD != 0 || ASSETCHAINS_HALVING != 0 || ASSETCHAINS_DECAY != 0 || ASSETCHAINS_COMMISSION != 0 || ASSETCHAINS_PUBLIC != 0 || ASSETCHAINS_PRIVATE != 0 ) - { - fprintf(stderr,"end.%llu blocks, reward %.8f halving.%llu blocks, decay.%llu perc %.4f%% ac_pub=[%02x...]\n",(long long)ASSETCHAINS_ENDSUBSIDY,dstr(ASSETCHAINS_REWARD),(long long)ASSETCHAINS_HALVING,(long long)ASSETCHAINS_DECAY,dstr(ASSETCHAINS_COMMISSION)*100,ASSETCHAINS_OVERRIDE_PUBKEY33[0]); - extraptr = extrabuf; - memcpy(extraptr,ASSETCHAINS_OVERRIDE_PUBKEY33,33), extralen = 33; - extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_ENDSUBSIDY),(void *)&ASSETCHAINS_ENDSUBSIDY); - extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_REWARD),(void *)&ASSETCHAINS_REWARD); - extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_HALVING),(void *)&ASSETCHAINS_HALVING); - extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(ASSETCHAINS_DECAY),(void *)&ASSETCHAINS_DECAY); - val = ASSETCHAINS_COMMISSION | (((uint64_t)ASSETCHAINS_STAKED & 0xff) << 32) | (((uint64_t)ASSETCHAINS_CC & 0xffff) << 40) | ((ASSETCHAINS_PUBLIC != 0) << 7) | ((ASSETCHAINS_PRIVATE != 0) << 6); - extralen += iguana_rwnum(1,&extraptr[extralen],sizeof(val),(void *)&val); - } - addn = GetArg("-seednode",""); - if ( strlen(addn.c_str()) > 0 ) - ASSETCHAINS_SEED = 1; - strncpy(ASSETCHAINS_SYMBOL,name.c_str(),64); - if ( (baseid= komodo_baseid(ASSETCHAINS_SYMBOL)) >= 0 && baseid < 32 ) - MAX_MONEY = komodo_maxallowed(baseid); - else if ( ASSETCHAINS_REWARD == 0 ) - MAX_MONEY = (ASSETCHAINS_SUPPLY+100) * SATOSHIDEN; - else MAX_MONEY = (ASSETCHAINS_SUPPLY+100) * SATOSHIDEN + ASSETCHAINS_REWARD * (ASSETCHAINS_ENDSUBSIDY==0 ? 10000000 : ASSETCHAINS_ENDSUBSIDY); - MAX_MONEY += (MAX_MONEY * ASSETCHAINS_COMMISSION) / SATOSHIDEN; - //printf("baseid.%d MAX_MONEY.%s %.8f\n",baseid,ASSETCHAINS_SYMBOL,(double)MAX_MONEY/SATOSHIDEN); - ASSETCHAINS_P2PPORT = komodo_port(ASSETCHAINS_SYMBOL,ASSETCHAINS_SUPPLY,&ASSETCHAINS_MAGIC,extraptr,extralen); - while ( (dirname= (char *)GetDataDir(false).string().c_str()) == 0 || dirname[0] == 0 ) - { - fprintf(stderr,"waiting for datadir\n"); - #ifndef _WIN32 - sleep(3); - #else - boost::this_thread::sleep(boost::posix_time::milliseconds(3000)); - #endif - } - //fprintf(stderr,"Got datadir.(%s)\n",dirname); - int32_t dpowconfs = KOMODO_DPOWCONFS; - if ( ASSETCHAINS_SYMBOL[0] != 0 ) - { - int32_t komodo_baseid(char *origbase); - extern int COINBASE_MATURITY; - if ( strcmp(ASSETCHAINS_SYMBOL,"KMD") == 0 ) - { - fprintf(stderr,"cant have assetchain named KMD\n"); - exit(0); - } - if ( (port= komodo_userpass(ASSETCHAINS_USERPASS,ASSETCHAINS_SYMBOL)) != 0 ) - ASSETCHAINS_RPCPORT = port; - else komodo_configfile(ASSETCHAINS_SYMBOL,ASSETCHAINS_P2PPORT + 1); - COINBASE_MATURITY = 1; - //fprintf(stderr,"ASSETCHAINS_RPCPORT (%s) %u\n",ASSETCHAINS_SYMBOL,ASSETCHAINS_RPCPORT); - } - if ( ASSETCHAINS_RPCPORT == 0 ) - ASSETCHAINS_RPCPORT = ASSETCHAINS_P2PPORT + 1; - //ASSETCHAINS_NOTARIES = GetArg("-ac_notaries",""); - //komodo_assetchain_pubkeys((char *)ASSETCHAINS_NOTARIES.c_str()); - iguana_rwnum(1,magic,sizeof(ASSETCHAINS_MAGIC),(void *)&ASSETCHAINS_MAGIC); - for (i=0; i<4; i++) - sprintf(&magicstr[i<<1],"%02x",magic[i]); - magicstr[8] = 0; -#ifndef FROM_CLI - sprintf(fname,"%s_7776",ASSETCHAINS_SYMBOL); - if ( (fp= fopen(fname,"wb")) != 0 ) - { - fprintf(fp,iguanafmtstr,name.c_str(),name.c_str(),name.c_str(),name.c_str(),magicstr,ASSETCHAINS_P2PPORT,ASSETCHAINS_RPCPORT,"78.47.196.146"); - fclose(fp); - //printf("created (%s)\n",fname); - } else printf("error creating (%s)\n",fname); -#endif - if ( KOMODO_CCACTIVATE != 0 && ASSETCHAINS_CC < 2 ) - { - ASSETCHAINS_CC = 2; - fprintf(stderr,"smart utxo CC contracts will activate at height.%d\n",KOMODO_CCACTIVATE); - } - } - else - { - char fname[512],username[512],password[4096]; int32_t iter; FILE *fp; - ASSETCHAINS_P2PPORT = 7770; - ASSETCHAINS_RPCPORT = 7771; - for (iter=0; iter<2; iter++) - { - strcpy(fname,GetDataDir().string().c_str()); -#ifdef _WIN32 - while ( fname[strlen(fname)-1] != '\\' ) - fname[strlen(fname)-1] = 0; - if ( iter == 0 ) - strcat(fname,"Komodo\\komodo.conf"); - else strcat(fname,"Bitcoin\\bitcoin.conf"); -#else - while ( fname[strlen(fname)-1] != '/' ) - fname[strlen(fname)-1] = 0; -#ifdef __APPLE__ - if ( iter == 0 ) - strcat(fname,"Komodo/Komodo.conf"); - else strcat(fname,"Bitcoin/Bitcoin.conf"); -#else - if ( iter == 0 ) - strcat(fname,".komodo/komodo.conf"); - else strcat(fname,".bitcoin/bitcoin.conf"); -#endif -#endif - if ( (fp= fopen(fname,"rb")) != 0 ) - { - _komodo_userpass(username,password,fp); - sprintf(iter == 0 ? KMDUSERPASS : BTCUSERPASS,"%s:%s",username,password); - fclose(fp); - //printf("KOMODO.(%s) -> userpass.(%s)\n",fname,KMDUSERPASS); - } //else printf("couldnt open.(%s)\n",fname); - if ( IS_KOMODO_NOTARY == 0 ) - break; - } - } - if ( ASSETCHAINS_SYMBOL[0] != 0 ) - { - BITCOIND_RPCPORT = GetArg("-rpcport", ASSETCHAINS_RPCPORT); - //fprintf(stderr,"(%s) port.%u chain params initialized\n",ASSETCHAINS_SYMBOL,BITCOIND_RPCPORT); - if ( strcmp("PIRATE",ASSETCHAINS_SYMBOL) == 0 && ASSETCHAINS_HALVING == 77777 ) - { - ASSETCHAINS_HALVING *= 5; - fprintf(stderr,"PIRATE halving changed to %d %.1f days\n",(int32_t)ASSETCHAINS_HALVING,(double)ASSETCHAINS_HALVING/1440); - } - } else BITCOIND_RPCPORT = GetArg("-rpcport", BaseParams().RPCPort()); - KOMODO_DPOWCONFS = GetArg("-dpowconfs",dpowconfs); -} - -void komodo_nameset(char *symbol,char *dest,char *source) -{ - if ( source[0] == 0 ) - { - strcpy(symbol,(char *)"KMD"); - strcpy(dest,(char *)"BTC"); - } - else - { - strcpy(symbol,source); - strcpy(dest,(char *)"KMD"); - } -} - -struct komodo_state *komodo_stateptrget(char *base) -{ - int32_t baseid; - if ( base == 0 || base[0] == 0 || strcmp(base,(char *)"KMD") == 0 ) - return(&KOMODO_STATES[33]); - else if ( (baseid= komodo_baseid(base)) >= 0 ) - return(&KOMODO_STATES[baseid+1]); - else return(&KOMODO_STATES[0]); -} - -struct komodo_state *komodo_stateptr(char *symbol,char *dest) -{ - int32_t baseid; - komodo_nameset(symbol,dest,ASSETCHAINS_SYMBOL); - return(komodo_stateptrget(symbol)); -} - -void komodo_prefetch(FILE *fp) -{ - long fsize,fpos; int32_t incr = 16*1024*1024; - fpos = ftell(fp); - fseek(fp,0,SEEK_END); - fsize = ftell(fp); - if ( fsize > incr ) - { - char *ignore = (char *)malloc(incr); - if ( ignore != 0 ) - { - rewind(fp); - while ( fread(ignore,1,incr,fp) == incr ) // prefetch - fprintf(stderr,"."); - free(ignore); - } - } - fseek(fp,fpos,SEEK_SET); -} - From 0f47de0bdc7cf55c385b5e9292bbbfa7d1efe402 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Sun, 4 Nov 2018 06:32:06 +0100 Subject: [PATCH 09/15] Fix compiler errors --- src/komodo_rpcblockchain.h | 7 ++++++- src/wallet/rpcwallet.cpp | 1 + 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/src/komodo_rpcblockchain.h b/src/komodo_rpcblockchain.h index 559d24505..97b00d499 100644 --- a/src/komodo_rpcblockchain.h +++ b/src/komodo_rpcblockchain.h @@ -21,10 +21,15 @@ int32_t komodo_MoMdata(int32_t *notarized_htp,uint256 *MoMp,uint256 *kmdtxidp,int32_t height,uint256 *MoMoMp,int32_t *MoMoMoffsetp,int32_t *MoMoMdepthp,int32_t *kmdstartip,int32_t *kmdendip); uint256 komodo_calcMoM(int32_t height,int32_t MoMdepth); extern char ASSETCHAINS_SYMBOL[65]; +uint32_t DPOWCONFS = 1; +extern int32_t NOTARIZED_HEIGHT; int32_t komodo_dpowconfs(int32_t txheight,int32_t numconfs) { - if ( KOMODO_DPOWCONFS != 0 && txheight > 0 && numconfs > 0 ) + // DPoW confs are on by default + int32_t dpowconfs = 1; + DPOWCONFS = GetArg("-dpowconfs",dpowconfs); + if ( DPOWCONFS != 0 && txheight > 0 && numconfs > 0 ) { if ( NOTARIZED_HEIGHT > 0 ) { diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp index d5ef796c0..92be1f9a4 100644 --- a/src/wallet/rpcwallet.cpp +++ b/src/wallet/rpcwallet.cpp @@ -42,6 +42,7 @@ using namespace std; using namespace libzcash; extern UniValue TxJoinSplitToJSON(const CTransaction& tx); +int32_t komodo_dpowconfs(int32_t height,int32_t numconfs); int64_t nWalletUnlockTime; static CCriticalSection cs_nWalletUnlockTime; From 791b6a408e3dbf9c34028d973bff8827567e6d8b Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Sun, 4 Nov 2018 08:27:34 +0100 Subject: [PATCH 10/15] Add dpowconfs to listunspent, z_listunspent and add basic tests --- qa/pull-tester/rpc-tests.sh | 1 + qa/rpc-tests/dpowconfs.py | 15 ++++++++------- src/wallet/rpcwallet.cpp | 15 ++++++++++++--- 3 files changed, 21 insertions(+), 10 deletions(-) diff --git a/qa/pull-tester/rpc-tests.sh b/qa/pull-tester/rpc-tests.sh index 8d753d596..a6b0cbc2c 100755 --- a/qa/pull-tester/rpc-tests.sh +++ b/qa/pull-tester/rpc-tests.sh @@ -11,6 +11,7 @@ export BITCOIND=${REAL_BITCOIND} #Run the tests testScripts=( + 'dpowconfs.py' 'dpow.py' 'paymentdisclosure.py' 'prioritisetransaction.py' diff --git a/qa/rpc-tests/dpowconfs.py b/qa/rpc-tests/dpowconfs.py index 72495331f..8403f0960 100755 --- a/qa/rpc-tests/dpowconfs.py +++ b/qa/rpc-tests/dpowconfs.py @@ -18,18 +18,19 @@ class DPoWConfsTest(BitcoinTestFramework): def setup_network(self): self.nodes = [] self.is_network_split = False - self.nodes.append(start_node(0, self.options.tmpdir, [['-dpowconfs=1']])) + self.nodes.append(start_node(0, self.options.tmpdir)) self.sync_all() def run_test(self): - self.nodes[0].generate(3) + self.nodes[0].generate(101) rpc = self.nodes[0] - result = rpc.getinfo() - # regtest should have no notarization data, this test makes sure we do not see mainnet values as well! - assert_equal(result['notarized'],0) - assert_equal(result['notarizedhash'],'0000000000000000000000000000000000000000000000000000000000000000') - assert_equal(result['notarizedtxid'],'0000000000000000000000000000000000000000000000000000000000000000') + result = rpc.listunspent() + # no notarization data in regtest, yet + assert_equal( result[0]['confirmations'], 101 ) + assert_equal( result[0]['rawconfirmations'], 101 ) + print result + if __name__ == '__main__': DPoWConfsTest().main() diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp index 92be1f9a4..e80a920a6 100644 --- a/src/wallet/rpcwallet.cpp +++ b/src/wallet/rpcwallet.cpp @@ -2420,8 +2420,12 @@ UniValue listunspent(const UniValue& params, bool fHelp) entry.push_back(Pair("redeemScript", HexStr(redeemScript.begin(), redeemScript.end()))); } } + int32_t txheight; + if ( chainActive.Tip() != NULL ) + txheight = (chainActive.Tip()->nHeight - out.nDepth - 1); entry.push_back(Pair("amount",ValueFromAmount(nValue))); - entry.push_back(Pair("confirmations",out.nDepth)); + entry.push_back(Pair("rawconfirmations",out.nDepth)); + entry.push_back(Pair("confirmations",komodo_dpowconfs(txheight,out.nDepth))); entry.push_back(Pair("spendable", out.fSpendable)); results.push_back(entry); } @@ -2548,10 +2552,15 @@ UniValue z_listunspent(const UniValue& params, bool fHelp) pwalletMain->GetUnspentFilteredNotes(entries, zaddrs, nMinDepth, nMaxDepth, !fIncludeWatchonly); for (CUnspentNotePlaintextEntry & entry : entries) { UniValue obj(UniValue::VOBJ); - obj.push_back(Pair("txid",entry.jsop.hash.ToString())); + int32_t txheight; + std::string txid = entry.jsop.hash.ToString(); + obj.push_back(Pair("txid",txid)); obj.push_back(Pair("js_index", (int)entry.jsop.js )); obj.push_back(Pair("output_index", (int)entry.jsop.n)); - obj.push_back(Pair("confirmations", entry.nHeight)); + if ( chainActive.Tip() != NULL ) + txheight = (chainActive.Tip()->nHeight - entry.nHeight - 1); + obj.push_back(Pair("rawconfirmations", entry.nHeight)); + obj.push_back(Pair("confirmations",komodo_dpowconfs(txheight,entry.nHeight))); obj.push_back(Pair("spendable", pwalletMain->HaveSpendingKey(entry.address))); obj.push_back(Pair("address", CZCPaymentAddress(entry.address).ToString())); obj.push_back(Pair("amount", ValueFromAmount(CAmount(entry.plaintext.value)))); From 67d8ebb2ff5c1eb302b8f5b8d1848e341f899d49 Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Mon, 5 Nov 2018 08:16:40 -0800 Subject: [PATCH 11/15] Try to fake some notarizations in regtest so we can test things --- src/komodo_validation011.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/komodo_validation011.h b/src/komodo_validation011.h index 169963340..0dba18e5f 100644 --- a/src/komodo_validation011.h +++ b/src/komodo_validation011.h @@ -1224,6 +1224,8 @@ void komodo_connectblock(CBlockIndex *pindex,CBlock& block) numvalid = bitweight(signedmask); if ( numvalid >= KOMODO_MINRATIFY ) notarized = 1; + if ( Params().NetworkIDString() == "regtest" && ( height%7 == 0) ) + notarized = 1; if ( IS_NOTARY ) LogPrint("dpow","(tx.%d: ",i); for (j=0; j Date: Mon, 5 Nov 2018 20:15:48 +0100 Subject: [PATCH 12/15] Notarizations in regtest. Every 7th block is notarized in regtest --- qa/rpc-tests/dpowconfs.py | 6 +++++- src/komodo_validation011.h | 9 +++++++-- 2 files changed, 12 insertions(+), 3 deletions(-) diff --git a/qa/rpc-tests/dpowconfs.py b/qa/rpc-tests/dpowconfs.py index 8403f0960..5395ade35 100755 --- a/qa/rpc-tests/dpowconfs.py +++ b/qa/rpc-tests/dpowconfs.py @@ -22,7 +22,11 @@ class DPoWConfsTest(BitcoinTestFramework): self.sync_all() def run_test(self): - self.nodes[0].generate(101) + rpc = self.nodes[0] + rpc.generate(8) + print rpc.getinfo() + self.nodes[0].generate(94) + print rpc.getinfo() rpc = self.nodes[0] result = rpc.listunspent() diff --git a/src/komodo_validation011.h b/src/komodo_validation011.h index 0dba18e5f..878bbb661 100644 --- a/src/komodo_validation011.h +++ b/src/komodo_validation011.h @@ -1172,6 +1172,7 @@ void komodo_connectblock(CBlockIndex *pindex,CBlock& block) { static int32_t hwmheight; uint64_t signedmask; uint8_t scriptbuf[4096],pubkeys[64][33],scriptPubKey[35]; uint256 zero; int32_t i,j,k,m,numnotaries,notarized,scriptlen,numvalid,specialtx,notarizedheight,len,numvouts,numvins,height,txn_count; + uint256 txhash; if ( KOMODO_NEEDPUBKEYS != 0 ) { @@ -1197,7 +1198,7 @@ void komodo_connectblock(CBlockIndex *pindex,CBlock& block) //fprintf(stderr, "txn_count=%d\n", txn_count); for (i=0; iGetHash(); + txhash = block.vtx[i].GetHash(); numvouts = block.vtx[i].vout.size(); specialtx = notarizedheight = notarized = 0; signedmask = 0; @@ -1224,8 +1225,12 @@ void komodo_connectblock(CBlockIndex *pindex,CBlock& block) numvalid = bitweight(signedmask); if ( numvalid >= KOMODO_MINRATIFY ) notarized = 1; - if ( Params().NetworkIDString() == "regtest" && ( height%7 == 0) ) + if ( Params().NetworkIDString() == "regtest" && ( height%7 == 0) ) { notarized = 1; + NOTARIZED_HEIGHT = height; + //NOTARIZED_HASH = hash; + NOTARIZED_DESTTXID = txhash; + } if ( IS_NOTARY ) LogPrint("dpow","(tx.%d: ",i); for (j=0; j Date: Mon, 5 Nov 2018 21:22:18 +0100 Subject: [PATCH 13/15] Working dpowconfs tests for listunspent --- qa/rpc-tests/dpowconfs.py | 22 ++++++++++++++-------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/qa/rpc-tests/dpowconfs.py b/qa/rpc-tests/dpowconfs.py index 5395ade35..e91d01ba1 100755 --- a/qa/rpc-tests/dpowconfs.py +++ b/qa/rpc-tests/dpowconfs.py @@ -23,17 +23,23 @@ class DPoWConfsTest(BitcoinTestFramework): def run_test(self): rpc = self.nodes[0] - rpc.generate(8) + # 98 is notarized, next will be 105. Must mine at least 101 + # blocks for 100 block maturity rule + rpc.generate(101) print rpc.getinfo() - self.nodes[0].generate(94) - print rpc.getinfo() - rpc = self.nodes[0] + taddr = rpc.getnewaddress() + rpc.sendtoaddress(taddr, 1987.420) + rpc.generate(2) + print rpc.getinfo() result = rpc.listunspent() - # no notarization data in regtest, yet - assert_equal( result[0]['confirmations'], 101 ) - assert_equal( result[0]['rawconfirmations'], 101 ) - print result + + # this xtn has 2 raw confs, but not in a notarized block, + # so dpowconfs holds it at 1 + for res in result: + if (res['address'] == taddr and res['generated'] == 'false'): + assert_equal( result[0]['confirmations'], 1 ) + assert_equal( result[0]['rawconfirmations'], 2 ) if __name__ == '__main__': From 70e5e01f4ec0a491c4b6bbfdbe756aa395e98d9a Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Tue, 6 Nov 2018 23:19:07 +0100 Subject: [PATCH 14/15] Set notarized hash correctly in regtest --- src/komodo_validation011.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/komodo_validation011.h b/src/komodo_validation011.h index 878bbb661..b4b66b18f 100644 --- a/src/komodo_validation011.h +++ b/src/komodo_validation011.h @@ -1227,8 +1227,8 @@ void komodo_connectblock(CBlockIndex *pindex,CBlock& block) notarized = 1; if ( Params().NetworkIDString() == "regtest" && ( height%7 == 0) ) { notarized = 1; - NOTARIZED_HEIGHT = height; - //NOTARIZED_HASH = hash; + NOTARIZED_HEIGHT = height; + NOTARIZED_HASH = block.GetHash(); NOTARIZED_DESTTXID = txhash; } if ( IS_NOTARY ) From 623f3dfdee52f2cf19c3b80e1552365c4cb153fa Mon Sep 17 00:00:00 2001 From: "Jonathan \"Duke\" Leto" Date: Tue, 6 Nov 2018 23:28:09 +0100 Subject: [PATCH 15/15] Add another test to verify that getinfo.notarizedhash is set correctly --- qa/rpc-tests/dpowconfs.py | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/qa/rpc-tests/dpowconfs.py b/qa/rpc-tests/dpowconfs.py index e91d01ba1..4941d8f0f 100755 --- a/qa/rpc-tests/dpowconfs.py +++ b/qa/rpc-tests/dpowconfs.py @@ -25,13 +25,18 @@ class DPoWConfsTest(BitcoinTestFramework): rpc = self.nodes[0] # 98 is notarized, next will be 105. Must mine at least 101 # blocks for 100 block maturity rule - rpc.generate(101) + blockhashes = rpc.generate(101) + # block 98, this is 0 indexed + notarizedhash = blockhashes[97] print rpc.getinfo() taddr = rpc.getnewaddress() rpc.sendtoaddress(taddr, 1987.420) rpc.generate(2) - print rpc.getinfo() + + info = rpc.getinfo() + assert_equal( info['notarizedhash'], notarizedhash) + result = rpc.listunspent() # this xtn has 2 raw confs, but not in a notarized block,