2
.gitignore
vendored
2
.gitignore
vendored
@@ -121,3 +121,5 @@ qa/pull-tester/test.*/*
|
||||
/doc/doxygen/
|
||||
|
||||
libzcashconsensus.pc
|
||||
|
||||
src/fiat/-usd
|
||||
|
||||
@@ -1,32 +1,35 @@
|
||||
./komodod -ac_name=USD -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=EUR -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=JPY -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=GBP -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=AUD -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=CAD -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=CHF -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=NZD -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=CNY -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=RUB -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=MXN -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=BRL -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=INR -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=HKD -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=TRY -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=ZAR -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=PLN -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=NOK -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=SEK -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=DKK -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=CZK -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=HUF -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=ILS -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=KRW -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=MYR -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=PHP -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=RON -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=SGD -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=THB -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=BGN -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=IDR -addnode=78.47.196.146 &
|
||||
./komodod -ac_name=HRK -addnode=78.47.196.146 &
|
||||
source pubkey.txt
|
||||
echo $pubkey
|
||||
|
||||
./komodod -pubkey=$pubkey -ac_name=USD -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=EUR -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=JPY -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=GBP -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=AUD -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=CAD -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=CHF -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=NZD -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=CNY -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=RUB -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=MXN -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=BRL -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=INR -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=HKD -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=TRY -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=ZAR -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=PLN -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=NOK -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=SEK -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=DKK -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=CZK -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=HUF -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=ILS -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=KRW -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=MYR -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=PHP -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=RON -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=SGD -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=THB -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=BGN -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=IDR -addnode=78.47.196.146 &
|
||||
./komodod -pubkey=$pubkey -ac_name=HRK -addnode=78.47.196.146 &
|
||||
|
||||
@@ -34,6 +34,8 @@
|
||||
static bool fDaemon;
|
||||
extern char ASSETCHAINS_SYMBOL[16];
|
||||
void komodo_gateway_iteration(char *symbol);
|
||||
void komodo_iteration(char *symbol);
|
||||
int32_t komodo_is_issuer();
|
||||
|
||||
void WaitForShutdown(boost::thread_group* threadGroup)
|
||||
{
|
||||
@@ -42,8 +44,10 @@ void WaitForShutdown(boost::thread_group* threadGroup)
|
||||
while (!fShutdown)
|
||||
{
|
||||
MilliSleep(2000);
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
if ( komodo_is_issuer() != 0 )
|
||||
komodo_gateway_iteration(ASSETCHAINS_SYMBOL);
|
||||
else komodo_iteration((char *)"EUR");
|
||||
|
||||
fShutdown = ShutdownRequested();
|
||||
}
|
||||
if (threadGroup)
|
||||
@@ -59,6 +63,7 @@ void WaitForShutdown(boost::thread_group* threadGroup)
|
||||
//
|
||||
extern int32_t IS_KOMODO_NOTARY,USE_EXTERNAL_PUBKEY,ASSETCHAIN_INIT;
|
||||
extern std::string NOTARY_PUBKEY;
|
||||
int32_t komodo_is_issuer();
|
||||
|
||||
bool AppInit(int argc, char* argv[])
|
||||
{
|
||||
@@ -97,10 +102,12 @@ bool AppInit(int argc, char* argv[])
|
||||
try
|
||||
{
|
||||
void komodo_args();
|
||||
fprintf(stderr,"call komodo_args\n");
|
||||
komodo_args();
|
||||
fprintf(stderr,"call komodo_args NOTARY_PUBKEY.(%s)\n",NOTARY_PUBKEY.c_str());
|
||||
while ( ASSETCHAIN_INIT == 0 )
|
||||
{
|
||||
if ( komodo_is_issuer() != 0 )
|
||||
komodo_gateway_iteration(ASSETCHAINS_SYMBOL);
|
||||
sleep(1);
|
||||
}
|
||||
if (!boost::filesystem::is_directory(GetDataDir(false)))
|
||||
|
||||
@@ -137,7 +137,7 @@ void *chainparams_commandline(void *ptr)
|
||||
{
|
||||
sleep(1);
|
||||
}
|
||||
fprintf(stderr,">>>>>>>> port.%u\n",ASSETCHAINS_PORT);
|
||||
//fprintf(stderr,">>>>>>>> port.%u\n",ASSETCHAINS_PORT);
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
{
|
||||
mainParams.SetDefaultPort(ASSETCHAINS_PORT);
|
||||
|
||||
@@ -384,6 +384,7 @@ const CScript &CCoinsViewCache::GetSpendFor(const CTxIn& input) const
|
||||
}
|
||||
|
||||
uint64_t komodo_interest(int32_t txheight,uint64_t nValue,uint32_t nLockTime,uint32_t tiptime);
|
||||
extern char ASSETCHAINS_SYMBOL[16];
|
||||
|
||||
CAmount CCoinsViewCache::GetValueIn(int32_t nHeight,int64_t *interestp,const CTransaction& tx,uint32_t tiptime) const
|
||||
{
|
||||
@@ -398,7 +399,8 @@ CAmount CCoinsViewCache::GetValueIn(int32_t nHeight,int64_t *interestp,const CTr
|
||||
nResult += value;
|
||||
interest = komodo_interest(nHeight,value,tx.nLockTime,tiptime);
|
||||
#ifdef KOMODO_ENABLE_INTEREST
|
||||
nResult += interest;
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 && nHeight >= 60000 )
|
||||
nResult += interest;
|
||||
#endif
|
||||
(*interestp) += interest;
|
||||
}
|
||||
|
||||
3
src/fiat/_usd
Executable file
3
src/fiat/_usd
Executable file
@@ -0,0 +1,3 @@
|
||||
|
||||
|
||||
./komodo-cli -ac_name=-USD $1 $2 $3 $4
|
||||
@@ -1493,7 +1493,7 @@ bool AppInit2(boost::thread_group& threadGroup, CScheduler& scheduler)
|
||||
#ifdef ENABLE_WALLET
|
||||
// Generate coins in the background
|
||||
if (pwalletMain)
|
||||
GenerateBitcoins(GetBoolArg("-gen", true), pwalletMain, GetArg("-genproclimit", 1));
|
||||
GenerateBitcoins(GetBoolArg("-gen", false), pwalletMain, GetArg("-genproclimit", 1));
|
||||
#endif
|
||||
|
||||
// ********************************************************* Step 11: finished
|
||||
|
||||
58
src/komodo.h
58
src/komodo.h
@@ -17,6 +17,8 @@
|
||||
#define H_KOMODO_H
|
||||
|
||||
// Todo: handle reorg: clear all entries above reorged height
|
||||
// smooth consensus price
|
||||
//
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
@@ -24,14 +26,16 @@
|
||||
#include <ctype.h>
|
||||
|
||||
void komodo_stateupdate(int32_t height,uint8_t notarypubs[][33],uint8_t numnotaries,uint8_t notaryid,uint256 txhash,uint64_t voutmask,uint8_t numvouts,uint32_t *pvals,uint8_t numpvals,int32_t kheight,uint64_t opretvalue,uint8_t *opretbuf,uint16_t opretlen,uint16_t vout);
|
||||
void komodo_init();
|
||||
void komodo_init(int32_t height);
|
||||
int32_t komodo_notarizeddata(int32_t nHeight,uint256 *notarized_hashp,uint256 *notarized_desttxidp);
|
||||
char *komodo_issuemethod(char *method,char *params,uint16_t port);
|
||||
|
||||
#define GENESIS_NBITS 0x1f00ffff
|
||||
#define KOMODO_MINRATIFY 7
|
||||
|
||||
#include "komodo_globals.h"
|
||||
#include "komodo_utils.h"
|
||||
queue_t DepositsQ,PendingsQ;
|
||||
//queue_t DepositsQ,PendingsQ;
|
||||
|
||||
#include "cJSON.c"
|
||||
#include "komodo_bitcoind.h"
|
||||
@@ -148,7 +152,7 @@ void komodo_stateupdate(int32_t height,uint8_t notarypubs[][33],uint8_t numnotar
|
||||
}
|
||||
if ( height <= 0 )
|
||||
{
|
||||
printf("early return: stateupdate height.%d\n",height);
|
||||
//printf("early return: stateupdate height.%d\n",height);
|
||||
return;
|
||||
}
|
||||
if ( fp != 0 ) // write out funcid, height, other fields, call side effect function
|
||||
@@ -300,59 +304,75 @@ int32_t komodo_voutupdate(int32_t notaryid,uint8_t *scriptbuf,int32_t scriptlen,
|
||||
opretlen = scriptbuf[len++];
|
||||
opretlen = (opretlen << 8) + scriptbuf[len++];
|
||||
}
|
||||
//for (k=0; k<scriptlen; k++)
|
||||
// printf("%02x",scriptbuf[k]);
|
||||
//printf(" <- script ht.%d i.%d j.%d value %.8f\n",height,i,j,dstr(value));
|
||||
if ( j == 1 && opretlen >= 32*2+4 && strcmp(KOMODO_SOURCE,(char *)&scriptbuf[len+32*2+4]) == 0 )
|
||||
if ( j == 1 && opretlen >= 32*2+4 && strcmp(ASSETCHAINS_SYMBOL[0]==0?"KMD":ASSETCHAINS_SYMBOL,(char *)&scriptbuf[len+32*2+4]) == 0 )
|
||||
{
|
||||
len += iguana_rwbignum(0,&scriptbuf[len],32,(uint8_t *)&kmdtxid);
|
||||
len += iguana_rwnum(0,&scriptbuf[len],4,(uint8_t *)notarizedheightp);
|
||||
len += iguana_rwbignum(0,&scriptbuf[len],32,(uint8_t *)&desttxid);
|
||||
if ( *notarizedheightp > NOTARIZED_HEIGHT && *notarizedheightp < height )
|
||||
{
|
||||
printf("ht.%d NOTARIZED.%d KMD.%s BTCTXID.%s (%s)\n",height,*notarizedheightp,kmdtxid.ToString().c_str(),desttxid.ToString().c_str(),(char *)&scriptbuf[len]);
|
||||
printf("ht.%d NOTARIZED.%d %s.%s %sTXID.%s (%s)\n",height,*notarizedheightp,ASSETCHAINS_SYMBOL[0]==0?"KMD":ASSETCHAINS_SYMBOL,kmdtxid.ToString().c_str(),ASSETCHAINS_SYMBOL[0]==0?"BTC":"KMD",desttxid.ToString().c_str(),(char *)&scriptbuf[len]);
|
||||
NOTARIZED_HEIGHT = *notarizedheightp;
|
||||
NOTARIZED_HASH = kmdtxid;
|
||||
NOTARIZED_DESTTXID = desttxid;
|
||||
komodo_stateupdate(height,0,0,0,zero,0,0,0,0,0,0,0,0,0);
|
||||
} else printf("reject ht.%d NOTARIZED.%d %s.%s DESTTXID.%s (%s)\n",height,*notarizedheightp,KOMODO_SOURCE,kmdtxid.ToString().c_str(),desttxid.ToString().c_str(),(char *)&scriptbuf[len]);
|
||||
} else printf("reject ht.%d NOTARIZED.%d %s.%s DESTTXID.%s (%s)\n",height,*notarizedheightp,ASSETCHAINS_SYMBOL[0]==0?"KMD":ASSETCHAINS_SYMBOL,kmdtxid.ToString().c_str(),desttxid.ToString().c_str(),(char *)&scriptbuf[len]);
|
||||
}
|
||||
else if ( i == 0 && j == 1 && opretlen == 149 )
|
||||
komodo_paxpricefeed(height,&scriptbuf[len],opretlen);
|
||||
else komodo_stateupdate(height,0,0,0,txhash,0,0,0,0,0,value,&scriptbuf[len],opretlen,j);
|
||||
else
|
||||
{
|
||||
//int32_t k; for (k=0; k<scriptlen; k++)
|
||||
// printf("%02x",scriptbuf[k]);
|
||||
//printf(" <- script ht.%d i.%d j.%d value %.8f\n",height,i,j,dstr(value));
|
||||
komodo_stateupdate(height,0,0,0,txhash,0,0,0,0,0,value,&scriptbuf[len],opretlen,j);
|
||||
}
|
||||
}
|
||||
return(notaryid);
|
||||
}
|
||||
|
||||
int32_t komodo_isratify(int32_t isspecial,int32_t numvalid)
|
||||
{
|
||||
if ( isspecial != 0 && numvalid > 13 )
|
||||
if ( isspecial != 0 && numvalid >= KOMODO_MINRATIFY )
|
||||
return(1);
|
||||
else return(0);
|
||||
}
|
||||
|
||||
// Special tx have vout[0] -> CRYPTO777
|
||||
// with more than 13 pay2pubkey outputs -> ratify
|
||||
// with more than KOMODO_MINRATIFY pay2pubkey outputs -> ratify
|
||||
// if all outputs to notary -> notary utxo
|
||||
// if txi == 0 && 2 outputs and 2nd OP_RETURN, len == 32*2+4 -> notarized, 1st byte 'P' -> pricefeed
|
||||
// OP_RETURN: 'D' -> deposit, 'W' -> withdraw
|
||||
|
||||
void komodo_connectblock(CBlockIndex *pindex,CBlock& block)
|
||||
{
|
||||
static int32_t hwmheight;
|
||||
uint64_t signedmask,voutmask;
|
||||
uint8_t scriptbuf[4096],pubkeys[64][33]; uint256 kmdtxid,btctxid,txhash;
|
||||
int32_t i,j,k,numvalid,specialtx,notarizedheight,notaryid,len,numvouts,numvins,height,txn_count;
|
||||
komodo_init();
|
||||
komodo_init(pindex->nHeight);
|
||||
if ( pindex->nHeight > hwmheight )
|
||||
hwmheight = pindex->nHeight;
|
||||
else
|
||||
{
|
||||
printf("hwmheight.%d vs pindex->nHeight.%d reorg.%d\n",hwmheight,pindex->nHeight,hwmheight-pindex->nHeight);
|
||||
// reset komodostate
|
||||
}
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
{
|
||||
while ( KOMODO_REALTIME == 0 || time(NULL) <= KOMODO_REALTIME )
|
||||
{
|
||||
fprintf(stderr,"komodo_connect.(%s) waiting for realtime RT.%u now.%u\n",ASSETCHAINS_SYMBOL,KOMODO_REALTIME,(uint32_t)time(NULL));
|
||||
sleep(3);
|
||||
}
|
||||
}
|
||||
KOMODO_INITDONE = (uint32_t)time(NULL);
|
||||
#ifdef KOMODO_ISSUER
|
||||
komodo_gateway_issuer();
|
||||
#else
|
||||
komodo_gateway_redeemer();
|
||||
#endif
|
||||
if ( pindex != 0 )
|
||||
{
|
||||
height = pindex->nHeight;
|
||||
txn_count = block.vtx.size();
|
||||
if ( 0 && ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
printf("%s ht.%d connect txn_count.%d\n",ASSETCHAINS_SYMBOL,height,txn_count);
|
||||
for (i=0; i<txn_count; i++)
|
||||
{
|
||||
txhash = block.vtx[i].GetHash();
|
||||
@@ -419,7 +439,7 @@ void komodo_connectblock(CBlockIndex *pindex,CBlock& block)
|
||||
}
|
||||
}
|
||||
}
|
||||
if ( komodo_isratify(1,numvalid) > 13 )
|
||||
if ( komodo_isratify(1,numvalid) >= KOMODO_MINRATIFY && numvouts > 13 )
|
||||
{
|
||||
memset(&txhash,0,sizeof(txhash));
|
||||
komodo_stateupdate(height,pubkeys,numvalid,0,txhash,0,0,0,0,0,0,0,0,0);
|
||||
|
||||
@@ -23,6 +23,8 @@
|
||||
#include <curl/easy.h>
|
||||
#endif
|
||||
|
||||
#define issue_curl(cmdstr) bitcoind_RPC(0,(char *)"curl",(char *)"http://127.0.0.1:7775",0,(char *)(cmdstr),0)
|
||||
|
||||
struct MemoryStruct { char *memory; size_t size; };
|
||||
struct return_string { char *ptr; size_t len; };
|
||||
|
||||
@@ -137,7 +139,6 @@ char *post_process_bitcoind_RPC(char *debugstr,char *command,char *rpcstr,char *
|
||||
*
|
||||
************************************************************************/
|
||||
|
||||
|
||||
char *bitcoind_RPC(char **retstrp,char *debugstr,char *url,char *userpass,char *command,char *params)
|
||||
{
|
||||
static int didinit,count,count2; static double elapsedsum,elapsedsum2;
|
||||
@@ -227,7 +228,8 @@ try_again:
|
||||
free(s.ptr);
|
||||
return(0);
|
||||
}
|
||||
printf( "curl_easy_perform() failed: %s %s.(%s %s), retries: %d\n",curl_easy_strerror(res),debugstr,url,command,numretries);
|
||||
if ( (rand() % 1000) == 0 )
|
||||
printf( "curl_easy_perform() failed: %s %s.(%s %s), retries: %d\n",curl_easy_strerror(res),debugstr,url,command,numretries);
|
||||
free(s.ptr);
|
||||
sleep((1<<numretries));
|
||||
goto try_again;
|
||||
@@ -239,7 +241,7 @@ try_again:
|
||||
{
|
||||
count++;
|
||||
elapsedsum += (OS_milliseconds() - starttime);
|
||||
if ( (count % 10000) == 0)
|
||||
if ( (count % 1000000) == 0)
|
||||
printf("%d: ave %9.6f | elapsed %.3f millis | bitcoind_RPC.(%s) url.(%s)\n",count,elapsedsum/count,(OS_milliseconds() - starttime),command,url);
|
||||
if ( retstrp != 0 )
|
||||
{
|
||||
@@ -343,7 +345,6 @@ char *komodo_issuemethod(char *method,char *params,uint16_t port)
|
||||
}
|
||||
return(retstr2);
|
||||
}
|
||||
//curl --url "http://127.0.0.1:13033" --user "user1557335368:pass111720054" --data "{\"method\":\"getinfo\",\"params\":[]}"
|
||||
|
||||
uint32_t komodo_txtime(uint256 hash)
|
||||
{
|
||||
@@ -361,9 +362,25 @@ uint32_t komodo_txtime(uint256 hash)
|
||||
return(0);
|
||||
}
|
||||
|
||||
uint64_t komodo_seed(int32_t height)
|
||||
{
|
||||
uint256 hash; uint64_t seed = 0; CBlockIndex *pindex = chainActive[height];
|
||||
if ( pindex != 0 )
|
||||
{
|
||||
hash = pindex->GetBlockHash();
|
||||
seed = arith_uint256(hash.GetHex()).GetLow64();
|
||||
}
|
||||
return(seed);
|
||||
}
|
||||
|
||||
void komodo_disconnect(CBlockIndex *pindex,CBlock& block)
|
||||
{
|
||||
komodo_init();
|
||||
//int32_t i; uint256 hash;
|
||||
komodo_init(pindex->nHeight);
|
||||
//hash = block.GetHash();
|
||||
//for (i=0; i<32; i++)
|
||||
// printf("%02x",((uint8_t *)&hash)[i]);
|
||||
//printf(" <- disconnect block\n");
|
||||
//uint256 zero;
|
||||
//printf("disconnect ht.%d\n",pindex->nHeight);
|
||||
//memset(&zero,0,sizeof(zero));
|
||||
@@ -373,7 +390,6 @@ void komodo_disconnect(CBlockIndex *pindex,CBlock& block)
|
||||
int32_t komodo_block2height(CBlock *block)
|
||||
{
|
||||
int32_t i,n,height = 0; uint8_t *ptr;
|
||||
komodo_init();
|
||||
#ifdef KOMODO_ZCASH
|
||||
ptr = (uint8_t *)block->vtx[0].vin[0].scriptSig.data();
|
||||
#else
|
||||
@@ -392,6 +408,7 @@ int32_t komodo_block2height(CBlock *block)
|
||||
}
|
||||
//printf(" <- coinbase.%d ht.%d\n",(int32_t)block->vtx[0].vin[0].scriptSig.size(),height);
|
||||
}
|
||||
komodo_init(height);
|
||||
return(height);
|
||||
}
|
||||
|
||||
@@ -402,14 +419,14 @@ void komodo_block2pubkey33(uint8_t *pubkey33,CBlock& block)
|
||||
#else
|
||||
uint8_t *ptr = (uint8_t *)&block.vtx[0].vout[0].scriptPubKey[0];
|
||||
#endif
|
||||
komodo_init();
|
||||
komodo_init(0);
|
||||
memcpy(pubkey33,ptr+1,33);
|
||||
}
|
||||
|
||||
void komodo_index2pubkey33(uint8_t *pubkey33,CBlockIndex *pindex,int32_t height)
|
||||
{
|
||||
CBlock block;
|
||||
komodo_init();
|
||||
komodo_init(height);
|
||||
memset(pubkey33,0,33);
|
||||
if ( pindex != 0 )
|
||||
{
|
||||
|
||||
@@ -17,170 +17,349 @@
|
||||
|
||||
struct pax_transaction
|
||||
{
|
||||
struct queueitem DL;
|
||||
UT_hash_handle hh;
|
||||
uint256 txid;
|
||||
uint64_t komodoshis,fiatoshis;
|
||||
int32_t marked,height;
|
||||
uint16_t vout;
|
||||
char symbol[4]; uint8_t rmd160[20],shortflag;
|
||||
};
|
||||
char symbol[16],coinaddr[64]; uint8_t rmd160[20],shortflag;
|
||||
} *PAX;
|
||||
|
||||
void komodo_gateway_deposits(CMutableTransaction& txNew)
|
||||
uint64_t komodo_paxtotal()
|
||||
{
|
||||
struct pax_transaction *ptr; uint8_t *script,opret[10000],data[10000]; int32_t i,len=0,opretlen=0,numvouts=1;
|
||||
PENDING_KOMODO_TX = 0;
|
||||
while ( (ptr= (struct pax_transaction *)queue_dequeue(&DepositsQ)) != 0 )
|
||||
struct pax_transaction *pax,*tmp; uint64_t total = 0;
|
||||
/*pthread_mutex_lock(&komodo_mutex);
|
||||
tmp = 0;
|
||||
if ( PAX != 0 )
|
||||
{
|
||||
txNew.vout.resize(numvouts+1);
|
||||
txNew.vout[numvouts].nValue = ptr->fiatoshis;
|
||||
txNew.vout[numvouts].scriptPubKey.resize(25);
|
||||
script = (uint8_t *)&txNew.vout[numvouts].scriptPubKey[0];
|
||||
pax = (struct pax_transaction *)PAX->hh.next;
|
||||
while ( pax != 0 && pax != tmp && n++ < 1000000 )
|
||||
{
|
||||
printf("PAX.[%p %p] pax.%p marked.%d fiat %.8f KMD %.8f\n",PAX->hh.next,PAX->hh.prev,pax,pax->marked,dstr(pax->fiatoshis),dstr(pax->komodoshis));
|
||||
if ( pax->marked == 0 )
|
||||
{
|
||||
if ( komodo_is_issuer() != 0 )
|
||||
total += pax->fiatoshis;
|
||||
else total += pax->komodoshis;
|
||||
}
|
||||
tmp = pax;
|
||||
pax = (struct pax_transaction *)pax->hh.next;
|
||||
}
|
||||
}
|
||||
pthread_mutex_unlock(&komodo_mutex);
|
||||
if ( n >= 1000000 )
|
||||
printf("komodo_paxtotal n.%d iterations?\n",n);*/
|
||||
HASH_ITER(hh,PAX,pax,tmp)
|
||||
{
|
||||
if ( pax->marked == 0 )
|
||||
{
|
||||
if ( komodo_is_issuer() != 0 )
|
||||
total += pax->fiatoshis;
|
||||
else total += pax->komodoshis;
|
||||
}
|
||||
}
|
||||
return(total);
|
||||
}
|
||||
|
||||
struct pax_transaction *komodo_paxfind(struct pax_transaction *space,uint256 txid,uint16_t vout)
|
||||
{
|
||||
struct pax_transaction *pax;
|
||||
pthread_mutex_lock(&komodo_mutex);
|
||||
HASH_FIND(hh,PAX,&txid,sizeof(txid),pax);
|
||||
if ( pax != 0 )
|
||||
memcpy(space,pax,sizeof(*pax));
|
||||
pthread_mutex_unlock(&komodo_mutex);
|
||||
return(pax);
|
||||
}
|
||||
|
||||
struct pax_transaction *komodo_paxmark(int32_t height,struct pax_transaction *space,uint256 txid,uint16_t vout,int32_t mark)
|
||||
{
|
||||
struct pax_transaction *pax;
|
||||
pthread_mutex_lock(&komodo_mutex);
|
||||
HASH_FIND(hh,PAX,&txid,sizeof(txid),pax);
|
||||
if ( pax == 0 )
|
||||
{
|
||||
pax = (struct pax_transaction *)calloc(1,sizeof(*pax));
|
||||
pax->txid = txid;
|
||||
pax->vout = vout;
|
||||
HASH_ADD_KEYPTR(hh,PAX,&pax->txid,sizeof(pax->txid),pax);
|
||||
//printf("ht.%d create pax.%p mark.%d\n",height,pax,mark);
|
||||
}
|
||||
if ( pax != 0 )
|
||||
{
|
||||
pax->marked = mark;
|
||||
//int32_t i; for (i=0; i<32; i++)
|
||||
// printf("%02x",((uint8_t *)&txid)[i]);
|
||||
//printf(" paxmark.ht %d vout%d\n",mark,vout);
|
||||
memcpy(space,pax,sizeof(*pax));
|
||||
}
|
||||
pthread_mutex_unlock(&komodo_mutex);
|
||||
return(pax);
|
||||
}
|
||||
|
||||
void komodo_gateway_deposit(char *coinaddr,uint64_t value,int32_t shortflag,char *symbol,uint64_t fiatoshis,uint8_t *rmd160,uint256 txid,uint16_t vout,int32_t height) // assetchain context
|
||||
{
|
||||
struct pax_transaction *pax; int32_t addflag = 0;
|
||||
pthread_mutex_lock(&komodo_mutex);
|
||||
HASH_FIND(hh,PAX,&txid,sizeof(txid),pax);
|
||||
if ( pax == 0 )
|
||||
{
|
||||
pax = (struct pax_transaction *)calloc(1,sizeof(*pax));
|
||||
pax->txid = txid;
|
||||
pax->vout = vout;
|
||||
HASH_ADD_KEYPTR(hh,PAX,&pax->txid,sizeof(pax->txid),pax);
|
||||
//int32_t i; for (i=0; i<32; i++)
|
||||
// printf("%02x",((uint8_t *)&txid)[i]);
|
||||
//printf(" v.%d [%s] ht.%d create pax.%p\n",vout,ASSETCHAINS_SYMBOL,height,pax);
|
||||
}
|
||||
pthread_mutex_unlock(&komodo_mutex);
|
||||
if ( coinaddr != 0 )
|
||||
{
|
||||
strcpy(pax->coinaddr,coinaddr);
|
||||
pax->komodoshis = value;
|
||||
pax->shortflag = shortflag;
|
||||
strcpy(pax->symbol,symbol);
|
||||
pax->fiatoshis = fiatoshis;
|
||||
memcpy(pax->rmd160,rmd160,20);
|
||||
pax->height = height;
|
||||
if ( pax->marked == 0 )
|
||||
printf("[%s] %p ADD DEPOSIT %s %.8f -> %s TO PAX ht.%d total %.8f\n",ASSETCHAINS_SYMBOL,pax,symbol,dstr(fiatoshis),coinaddr,height,dstr(komodo_paxtotal()));
|
||||
else printf("%p MARKED.%d DEPOSIT %s %.8f -> %s TO PAX ht.%d\n",pax,pax->marked,symbol,dstr(fiatoshis),coinaddr,height);
|
||||
}
|
||||
else
|
||||
{
|
||||
pax->marked = height;
|
||||
printf("pax.%p MARK DEPOSIT ht.%d\n",pax,height);
|
||||
}
|
||||
}
|
||||
|
||||
int32_t komodo_issued_opreturn(uint8_t *shortflagp,char *base,uint256 *txids,uint16_t *vouts,uint8_t *opretbuf,int32_t opretlen)
|
||||
{
|
||||
int32_t i,n=0,j,len;
|
||||
if ( opretbuf[opretlen-5] == '-' )
|
||||
*shortflagp = 1;
|
||||
else *shortflagp = 0;
|
||||
for (i=0; i<4; i++)
|
||||
base[i] = opretbuf[opretlen-4+i];
|
||||
if ( (strcmp(base,"KMD") == 0 && ASSETCHAINS_SYMBOL[0] == 0) || strncmp(ASSETCHAINS_SYMBOL,base,strlen(base)) == 0 ) // shortflag
|
||||
{
|
||||
opretbuf++, opretlen--;
|
||||
for (n=len=0; n<opretlen/34; n++)
|
||||
{
|
||||
for (j=0; j<32; j++)
|
||||
{
|
||||
((uint8_t *)&txids[n])[j] = opretbuf[len++];
|
||||
//printf("%02x",((uint8_t *)&txids[n])[j]);
|
||||
}
|
||||
vouts[n] = opretbuf[len++];
|
||||
vouts[n] = (opretbuf[len++] << 8) | vouts[n];
|
||||
//printf(" issuedtxid v%d i.%d opretlen.%d\n",vouts[n],n,opretlen);
|
||||
}
|
||||
}
|
||||
return(n);
|
||||
}
|
||||
|
||||
void komodo_gateway_deposits(CMutableTransaction *txNew,int32_t shortflag,char *symbol)
|
||||
{
|
||||
struct pax_transaction *pax,*tmp; uint8_t *script,opcode,opret[10000],data[10000]; int32_t i,len=0,opretlen=0,numvouts=1;
|
||||
PENDING_KOMODO_TX = 0;
|
||||
if ( strcmp(symbol,"KMD") != 0 )
|
||||
opcode = 'I';
|
||||
else opcode = 'X';
|
||||
HASH_ITER(hh,PAX,pax,tmp)
|
||||
{
|
||||
if ( pax->marked != 0 )
|
||||
continue;
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
printf("pax.%p marked.%d %.8f -> %.8f\n",pax,pax->marked,dstr(pax->komodoshis),dstr(pax->fiatoshis));
|
||||
txNew->vout.resize(numvouts+1);
|
||||
txNew->vout[numvouts].nValue = pax->fiatoshis;
|
||||
txNew->vout[numvouts].scriptPubKey.resize(25);
|
||||
script = (uint8_t *)&txNew->vout[numvouts].scriptPubKey[0];
|
||||
*script++ = 0x76;
|
||||
*script++ = 0xa9;
|
||||
*script++ = 20;
|
||||
memcpy(script,ptr->rmd160,20), script += 20;
|
||||
memcpy(script,pax->rmd160,20), script += 20;
|
||||
*script++ = 0x88;
|
||||
*script++ = 0xac;
|
||||
for (i=0; i<32; i++)
|
||||
{
|
||||
printf("%02x",((uint8_t *)&ptr->txid)[i]);
|
||||
data[len++] = ((uint8_t *)&ptr->txid)[i];
|
||||
//printf("%02x",((uint8_t *)&pax->txid)[i]);
|
||||
data[len++] = ((uint8_t *)&pax->txid)[i];
|
||||
}
|
||||
data[len++] = ptr->vout & 0xff;
|
||||
data[len++] = (ptr->vout >> 8) & 0xff;
|
||||
printf(" vout.%u DEPOSIT %.8f\n",ptr->vout,(double)KOMODO_DEPOSIT/COIN);
|
||||
PENDING_KOMODO_TX += ptr->fiatoshis;
|
||||
numvouts++;
|
||||
queue_enqueue((char *)"PENDINGS",&PendingsQ,&ptr->DL);
|
||||
data[len++] = pax->vout & 0xff;
|
||||
data[len++] = (pax->vout >> 8) & 0xff;
|
||||
if ( strcmp(symbol,"KMD") != 0 )
|
||||
PENDING_KOMODO_TX += pax->fiatoshis;
|
||||
else PENDING_KOMODO_TX += pax->komodoshis;
|
||||
//printf(" vout.%u DEPOSIT %.8f <- paxdeposit.%s pending %.8f\n",pax->vout,(double)txNew->vout[numvouts].nValue/COIN,symbol,dstr(PENDING_KOMODO_TX));
|
||||
if ( numvouts++ >= 64 )
|
||||
break;
|
||||
}
|
||||
if ( numvouts > 1 )
|
||||
{
|
||||
opretlen = komodo_opreturnscript(opret,'I',data,len);
|
||||
txNew.vout.resize(numvouts+1);
|
||||
txNew.vout[numvouts].nValue = 0;
|
||||
txNew.vout[numvouts].scriptPubKey.resize(opretlen);
|
||||
script = (uint8_t *)&txNew.vout[numvouts].scriptPubKey[0];
|
||||
if ( shortflag != 0 )
|
||||
data[len++] = '-';
|
||||
for (i=0; symbol[i]!=0; i++)
|
||||
data[len++] = symbol[i];
|
||||
data[len++] = 0;
|
||||
opretlen = komodo_opreturnscript(opret,opcode,data,len);
|
||||
txNew->vout.resize(numvouts+1);
|
||||
txNew->vout[numvouts].nValue = 0;
|
||||
txNew->vout[numvouts].scriptPubKey.resize(opretlen);
|
||||
script = (uint8_t *)&txNew->vout[numvouts].scriptPubKey[0];
|
||||
memcpy(script,opret,opretlen);
|
||||
printf("total numvouts.%d %.8f opretlen.%d\n",numvouts,dstr(PENDING_KOMODO_TX),opretlen);
|
||||
}
|
||||
printf("total numvouts.%d %.8f\n",numvouts,dstr(PENDING_KOMODO_TX));
|
||||
}
|
||||
|
||||
int32_t komodo_check_deposit(const CBlock& block) // verify above block is valid pax pricing
|
||||
int32_t komodo_check_deposit(int32_t height,const CBlock& block) // verify above block is valid pax pricing
|
||||
{
|
||||
// reenable rpc auth
|
||||
return(0);
|
||||
}
|
||||
|
||||
void komodo_gateway_deposit(uint64_t value,int32_t shortflag,char *symbol,uint64_t fiatoshis,uint8_t *rmd160,uint256 txid,uint16_t vout) // assetchain context
|
||||
{
|
||||
struct pax_transaction *ptr;
|
||||
ptr = (struct pax_transaction *)calloc(1,sizeof(*ptr));
|
||||
ptr->komodoshis = value;
|
||||
ptr->fiatoshis = fiatoshis;
|
||||
memcpy(ptr->symbol,symbol,3);
|
||||
memcpy(ptr->rmd160,rmd160,20);
|
||||
ptr->shortflag = shortflag;
|
||||
ptr->txid = txid;
|
||||
ptr->vout = vout;
|
||||
KOMODO_DEPOSIT += fiatoshis;
|
||||
queue_enqueue((char *)"DEPOSITS",&DepositsQ,&ptr->DL);
|
||||
}
|
||||
|
||||
int32_t komodo_gateway_depositremove(uint256 txid,uint16_t vout) // assetchain context
|
||||
{
|
||||
int32_t iter,n=0; queue_t *Q; struct pax_transaction *ptr; struct queueitem *item;
|
||||
for (iter=0; iter<2; iter++)
|
||||
int32_t i,j,n,num,opretlen,offset=1,errs=0,matched=0; uint256 hash,txids[64]; uint8_t shortflag; char symbol[16],base[16]; uint16_t vouts[64]; uint8_t *script,opcode; struct pax_transaction *pax,space;
|
||||
n = block.vtx[0].vout.size();
|
||||
script = (uint8_t *)block.vtx[0].vout[n-1].scriptPubKey.data();
|
||||
if ( n <= 2 || script[0] != 0x6a )
|
||||
return(0);
|
||||
offset += komodo_scriptitemlen(&opretlen,&script[offset]);
|
||||
//printf("checkdeposit n.%d [%02x] [%c] %d vs %d\n",n,script[0],script[offset],script[offset],'I');
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
{
|
||||
Q = (iter == 0) ? &DepositsQ : &PendingsQ;
|
||||
portable_mutex_lock(&Q->mutex);
|
||||
if ( Q->list != 0 )
|
||||
opcode = 'X';
|
||||
strcpy(symbol,"KMD");
|
||||
}
|
||||
else
|
||||
{
|
||||
strcpy(symbol,ASSETCHAINS_SYMBOL);
|
||||
opcode = 'I';
|
||||
}
|
||||
if ( script[offset] == opcode && opretlen < block.vtx[0].vout[n-1].scriptPubKey.size() )
|
||||
{
|
||||
if ( (num= komodo_issued_opreturn(&shortflag,base,txids,vouts,&script[offset],opretlen)) > 0 )
|
||||
{
|
||||
item = &ptr->DL;
|
||||
DL_FOREACH(Q->list,item)
|
||||
for (i=1; i<n-1; i++)
|
||||
{
|
||||
ptr = (struct pax_transaction *)item;
|
||||
if ( memcmp(&ptr->txid,&txid,sizeof(txid)) == 0 && ptr->vout == vout )
|
||||
if ( (pax= komodo_paxfind(&space,txids[i-1],vouts[i-1])) != 0 )
|
||||
{
|
||||
if ( KOMODO_DEPOSIT >= ptr->fiatoshis )
|
||||
KOMODO_DEPOSIT -= ptr->fiatoshis;
|
||||
else KOMODO_DEPOSIT = 0;
|
||||
printf("DELETE %.8f DEPOSIT %s %.8f\n",dstr(ptr->komodoshis),ptr->symbol,dstr(ptr->fiatoshis));
|
||||
DL_DELETE(Q->list,&ptr->DL);
|
||||
n++;
|
||||
free(ptr);
|
||||
break;
|
||||
if ( ((opcode == 'I' && pax->fiatoshis == block.vtx[0].vout[i].nValue) || (opcode == 'X' && pax->komodoshis == block.vtx[0].vout[i].nValue)) )
|
||||
{
|
||||
if ( pax->marked != 0 )
|
||||
errs++;
|
||||
else matched++;
|
||||
//printf("errs.%d i.%d match %.8f == %.8f\n",errs,i,dstr(pax != 0 ? pax->fiatoshis:-1),dstr(block.vtx[0].vout[i].nValue));
|
||||
}
|
||||
else
|
||||
{
|
||||
hash = block.GetHash();
|
||||
//for (j=0; j<32; j++)
|
||||
// printf("%02x",((uint8_t *)&hash)[j]);
|
||||
//printf(" ht.%d blockhash couldnt find vout.[%d]\n",height,i);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//for (j=0; j<32; j++)
|
||||
// printf("%02x",((uint8_t *)&txids[i-1])[j]);
|
||||
//printf(" cant paxfind txid\n");
|
||||
}
|
||||
komodo_paxmark(height,&space,txids[i-1],vouts[i-1],height);
|
||||
}
|
||||
if ( matched != num )
|
||||
{
|
||||
//printf("matched.%d vs num.%d\n",matched,num);
|
||||
if ( height > 60000 )
|
||||
return(-1);
|
||||
}
|
||||
}
|
||||
portable_mutex_unlock(&Q->mutex);
|
||||
//printf("opretlen.%d num.%d\n",opretlen,num);
|
||||
}
|
||||
if ( queue_size(&DepositsQ) == 0 && queue_size(&PendingsQ) == 0 )
|
||||
KOMODO_DEPOSIT = PENDING_KOMODO_TX = 0;
|
||||
return(n);
|
||||
return(0);
|
||||
}
|
||||
|
||||
const char *komodo_opreturn(int32_t height,uint64_t value,uint8_t *opretbuf,int32_t opretlen,uint256 txid,uint16_t vout)
|
||||
{
|
||||
uint8_t rmd160[20],addrtype,shortflag,pubkey33[33]; int32_t i,j,len,tokomodo=0; char base[4],coinaddr[64],destaddr[64]; int64_t fiatoshis,checktoshis; const char *typestr = "unknown";
|
||||
#ifdef KOMODO_ISSUER
|
||||
tokomodo = 1;
|
||||
#endif
|
||||
if ( opretbuf[0] == ((tokomodo != 0) ? 'D' : 'W') )
|
||||
uint8_t rmd160[20],addrtype,shortflag,pubkey33[33]; int32_t i,j,n,len,tokomodo,kmdheight; char base[4],coinaddr[64],destaddr[64]; struct pax_transaction space; uint256 txids[64]; uint16_t vouts[64]; double diff; uint64_t seed; int64_t fiatoshis,checktoshis; const char *typestr = "unknown";
|
||||
tokomodo = (komodo_is_issuer() == 0);
|
||||
if ( 0 && ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
{
|
||||
if ( opretlen == 34 )
|
||||
for (i=0; i<opretlen; i++)
|
||||
printf("%02x",opretbuf[i]);
|
||||
printf(" opret[%c] else path tokomodo.%d ht.%d\n",opretbuf[0],tokomodo,height);
|
||||
}
|
||||
if ( opretbuf[0] == 'D' )
|
||||
{
|
||||
if ( opretlen == 38 ) // any KMD tx
|
||||
{
|
||||
iguana_rwnum(0,&opretbuf[34],sizeof(kmdheight),&kmdheight);
|
||||
memset(base,0,sizeof(base));
|
||||
PAX_pubkey(0,&opretbuf[1],&addrtype,rmd160,base,&shortflag,&fiatoshis);
|
||||
if ( fiatoshis < 0 )
|
||||
fiatoshis = -fiatoshis;
|
||||
bitcoin_address(coinaddr,addrtype,rmd160,20);
|
||||
checktoshis = PAX_fiatdest(tokomodo,destaddr,pubkey33,coinaddr,height,base,fiatoshis);
|
||||
for (i=0; i<opretlen; i++)
|
||||
printf("%02x",opretbuf[i]);
|
||||
printf(" DEPOSIT %.8f %c%s -> %s ",dstr(fiatoshis),shortflag!=0?'-':'+',base,coinaddr);
|
||||
for (i=0; i<32; i++)
|
||||
printf("%02x",((uint8_t *)&txid)[i]);
|
||||
printf(" <- txid.v%u ",vout);
|
||||
for (i=0; i<33; i++)
|
||||
printf("%02x",pubkey33[i]);
|
||||
printf(" checkpubkey check %.8f v %.8f dest.(%s)\n",dstr(checktoshis),dstr(value),destaddr);
|
||||
checktoshis = PAX_fiatdest(&seed,tokomodo,destaddr,pubkey33,coinaddr,kmdheight,base,fiatoshis);
|
||||
typestr = "deposit";
|
||||
#ifdef KOMODO_ISSUER
|
||||
if ( strncmp(KOMODO_SOURCE,base,strlen(base)) == 0 && value >= (9999*checktoshis)/10000 && shortflag == ASSETCHAINS_SHORTFLAG )
|
||||
printf("kmdheight.%d vs height.%d check %.8f vs %.8f tokomodo.%d %d seed.%llx\n",kmdheight,height,dstr(checktoshis),dstr(value),komodo_is_issuer(),strncmp(ASSETCHAINS_SYMBOL,base,strlen(base)) == 0,(long long)seed);
|
||||
diff = ((double)value / checktoshis) - 1.;
|
||||
if ( diff < 0. )
|
||||
diff = -diff;
|
||||
if ( kmdheight <= height )
|
||||
{
|
||||
komodo_gateway_deposit(value,shortflag,base,fiatoshis,rmd160,txid,vout);
|
||||
if ( tokomodo == 0 && strncmp(ASSETCHAINS_SYMBOL,base,strlen(base)) == 0 && shortflag == ASSETCHAINS_SHORTFLAG )
|
||||
{
|
||||
if ( shortflag == 0 )
|
||||
{
|
||||
for (i=0; i<32; i++)
|
||||
printf("%02x",((uint8_t *)&txid)[i]);
|
||||
printf(" <- txid.v%u ",vout);
|
||||
for (i=0; i<33; i++)
|
||||
printf("%02x",pubkey33[i]);
|
||||
printf(" checkpubkey check %.8f v %.8f dest.(%s) kmdheight.%d height.%d\n",dstr(checktoshis),dstr(value),destaddr,kmdheight,height);
|
||||
if ( value >= checktoshis || (seed == 0 && diff < .01) )
|
||||
{
|
||||
if ( komodo_paxfind(&space,txid,vout) == 0 )
|
||||
{
|
||||
komodo_gateway_deposit(coinaddr,value,shortflag,base,fiatoshis,rmd160,txid,vout,kmdheight);
|
||||
} else printf("duplicate deposit\n");
|
||||
}
|
||||
}
|
||||
else // short
|
||||
{
|
||||
for (i=0; i<opretlen; i++)
|
||||
printf("%02x",opretbuf[i]);
|
||||
printf(" opret[%c] tokomodo.%d value %.8f vs check %.8f\n",opretbuf[0],tokomodo,dstr(value),dstr(checktoshis));
|
||||
if ( value <= checktoshis || (seed == 0 && diff < .01) )
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#else
|
||||
if ( tokomodo != 0 && value <= (10000*checktoshis)/9999 )
|
||||
{
|
||||
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
else
|
||||
else if ( strncmp((char *)"KMD",(char *)&opretbuf[opretlen-4],3) != 0 )
|
||||
{
|
||||
for (i=0; i<opretlen; i++)
|
||||
printf("%02x",opretbuf[i]);
|
||||
printf(" komodo_opreturn[%c]: ht.%d %.8f opretlen.%d\n",opretbuf[0],height,dstr(value),opretlen);
|
||||
|
||||
if ( opretbuf[0] == 'I' )
|
||||
if ( tokomodo == 0 && opretbuf[0] == 'I' ) // assetchain coinbase
|
||||
{
|
||||
uint256 issuedtxid; uint16_t issuedvout;
|
||||
opretbuf++, opretlen--;
|
||||
for (i=len=0; i<opretlen/34; i++)
|
||||
if ( (n= komodo_issued_opreturn(&shortflag,base,txids,vouts,opretbuf,opretlen)) > 0 && shortflag == ASSETCHAINS_SHORTFLAG )
|
||||
{
|
||||
for (j=0; j<32; j++)
|
||||
for (i=0; i<n; i++)
|
||||
{
|
||||
((uint8_t *)&issuedtxid)[j] = opretbuf[len++];
|
||||
printf("%02x",((uint8_t *)&issuedtxid)[j]);
|
||||
//for (j=0; j<32; j++)
|
||||
// printf("%02x",((uint8_t *)&txids[i])[j]);
|
||||
if ( komodo_paxmark(height,&space,txids[i],vouts[i],height) == 0 )
|
||||
{
|
||||
komodo_gateway_deposit(0,0,0,0,0,0,txids[i],vouts[i],height);
|
||||
}
|
||||
else
|
||||
{
|
||||
//printf(" duplicate issuedtxid v%d i.%d of n.%d opretlen.%d\n",vouts[i],i,n,opretlen);
|
||||
}
|
||||
}
|
||||
issuedvout = opretbuf[len++];
|
||||
issuedvout = (opretbuf[len++] << 8) | vout;
|
||||
printf(" issuedtxid v%d i.%d opretlen.%d\n",issuedvout,i,opretlen);
|
||||
if ( komodo_gateway_depositremove(issuedtxid,issuedvout) == 0 )
|
||||
printf("error removing deposit\n");
|
||||
}
|
||||
}
|
||||
else if ( tokomodo != 0 && opretbuf[0] == 'X' )
|
||||
{
|
||||
// verify and update limits
|
||||
}
|
||||
}
|
||||
return(typestr);
|
||||
}
|
||||
@@ -190,16 +369,10 @@ void komodo_gateway_voutupdate(char *symbol,int32_t isspecial,int32_t height,int
|
||||
int32_t i,opretlen,offset = 0; uint256 zero,utxid; const char *typestr;
|
||||
typestr = "unknown";
|
||||
memcpy(&utxid,&txid,sizeof(utxid));
|
||||
if ( 0 )//txi != 0 || vout != 0 )
|
||||
{
|
||||
for (i=0; i<len; i++)
|
||||
printf("%02x",script[i]);
|
||||
printf(" <- %s VOUTUPDATE.%d txi.%d vout.%d %.8f scriptlen.%d OP_RETURN.%d (%s) len.%d\n",symbol,height,txi,vout,dstr(value),len,script[0] == 0x6a,typestr,opretlen);
|
||||
}
|
||||
if ( script[offset++] == 0x6a )
|
||||
{
|
||||
offset += komodo_scriptitemlen(&opretlen,&script[offset]);
|
||||
if ( isspecial != 0 && len >= offset+32*2+4 && strcmp((char *)&script[offset+32*2+4],"KMD") == 0 )
|
||||
if ( isspecial != 0 && len >= offset+32*2+4 && strcmp((char *)&script[offset+32*2+4],ASSETCHAINS_SYMBOL[0]==0?"KMD":ASSETCHAINS_SYMBOL) == 0 )
|
||||
typestr = "notarized";
|
||||
else if ( txi == 0 && vout == 1 && opretlen == 149 )
|
||||
{
|
||||
@@ -209,43 +382,48 @@ void komodo_gateway_voutupdate(char *symbol,int32_t isspecial,int32_t height,int
|
||||
}
|
||||
else komodo_stateupdate(height,0,0,0,utxid,0,0,0,0,0,value,&script[offset],opretlen,vout);
|
||||
}
|
||||
else if ( numvouts > 13 )
|
||||
else if ( numvouts >= KOMODO_MINRATIFY )
|
||||
typestr = "ratify";
|
||||
}
|
||||
|
||||
int32_t komodo_gateway_tx(char *symbol,int32_t height,int32_t txi,char *txidstr,uint32_t port)
|
||||
{
|
||||
char *retstr,params[256],*hexstr; uint8_t script[10000]; cJSON *json,*result,*vouts,*item,*sobj; int32_t vout,n,len,isspecial,retval = -1; uint64_t value; bits256 txid;
|
||||
char *retstr,params[256],*hexstr; uint8_t script[10000]; cJSON *oldpub,*newpub,*json,*result,*vouts,*item,*sobj; int32_t vout,n,len,isspecial,retval = -1; uint64_t value; bits256 txid;
|
||||
sprintf(params,"[\"%s\", 1]",txidstr);
|
||||
if ( (retstr= komodo_issuemethod((char *)"getrawtransaction",params,port)) != 0 )
|
||||
{
|
||||
if ( (json= cJSON_Parse(retstr)) != 0 )
|
||||
{
|
||||
if ( (result= jobj(json,(char *)"result")) != 0 && (vouts= jarray(&n,result,(char *)"vout")) != 0 )
|
||||
if ( (result= jobj(json,(char *)"result")) != 0 )
|
||||
{
|
||||
oldpub = jobj(result,(char *)"vpub_old");
|
||||
newpub = jobj(result,(char *)"vpub_new");
|
||||
retval = 0;
|
||||
isspecial = 0;
|
||||
txid = jbits256(result,(char *)"txid");
|
||||
for (vout=0; vout<n; vout++)
|
||||
if ( oldpub == 0 && newpub == 0 && (vouts= jarray(&n,result,(char *)"vout")) != 0 )
|
||||
{
|
||||
item = jitem(vouts,vout);
|
||||
value = SATOSHIDEN * jdouble(item,(char *)"value");
|
||||
if ( (sobj= jobj(item,(char *)"scriptPubKey")) != 0 )
|
||||
isspecial = 0;
|
||||
txid = jbits256(result,(char *)"txid");
|
||||
for (vout=0; vout<n; vout++)
|
||||
{
|
||||
if ( (hexstr= jstr(sobj,(char *)"hex")) != 0 )
|
||||
item = jitem(vouts,vout);
|
||||
value = SATOSHIDEN * jdouble(item,(char *)"value");
|
||||
if ( (sobj= jobj(item,(char *)"scriptPubKey")) != 0 )
|
||||
{
|
||||
len = (int32_t)strlen(hexstr) >> 1;
|
||||
if ( vout == 0 && ((memcmp(&hexstr[2],CRYPTO777_PUBSECPSTR,66) == 0 && len == 35) || (memcmp(&hexstr[6],CRYPTO777_RMD160STR,40) == 0 && len == 25)) )
|
||||
isspecial = 1;
|
||||
else if ( len <= sizeof(script) )
|
||||
if ( (hexstr= jstr(sobj,(char *)"hex")) != 0 )
|
||||
{
|
||||
decode_hex(script,len,hexstr);
|
||||
komodo_gateway_voutupdate(symbol,isspecial,height,txi,txid,vout,n,value,script,len);
|
||||
len = (int32_t)strlen(hexstr) >> 1;
|
||||
if ( vout == 0 && ((memcmp(&hexstr[2],CRYPTO777_PUBSECPSTR,66) == 0 && len == 35) || (memcmp(&hexstr[6],CRYPTO777_RMD160STR,40) == 0 && len == 25)) )
|
||||
isspecial = 1;
|
||||
else if ( len <= sizeof(script) )
|
||||
{
|
||||
decode_hex(script,len,hexstr);
|
||||
komodo_gateway_voutupdate(symbol,isspecial,height,txi,txid,vout,n,value,script,len);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} else printf("error getting txids.(%s) %p\n",retstr,result);
|
||||
free_json(json);
|
||||
}
|
||||
free(retstr);
|
||||
@@ -255,7 +433,7 @@ int32_t komodo_gateway_tx(char *symbol,int32_t height,int32_t txi,char *txidstr,
|
||||
|
||||
int32_t komodo_gateway_block(char *symbol,int32_t height,uint16_t port)
|
||||
{
|
||||
char *retstr,*retstr2,params[128],*txidstr; int32_t i,n,retval = -1; cJSON *json,*tx,*result,*result2;
|
||||
char *retstr,*retstr2,params[128],*txidstr; int32_t i,n,retval = -1; cJSON *json,*tx=0,*result=0,*result2;
|
||||
sprintf(params,"[%d]",height);
|
||||
if ( (retstr= komodo_issuemethod((char *)"getblockhash",params,port)) != 0 )
|
||||
{
|
||||
@@ -276,17 +454,17 @@ int32_t komodo_gateway_block(char *symbol,int32_t height,uint16_t port)
|
||||
break;
|
||||
if ( i == n )
|
||||
retval = 0;
|
||||
else printf("error i.%d vs n.%d\n",i,n);
|
||||
}
|
||||
else printf("komodo_gateway_block ht.%d error i.%d vs n.%d\n",height,i,n);
|
||||
} else printf("cant get result.%p or tx.%p\n",result,tx);
|
||||
free_json(json);
|
||||
}
|
||||
} else printf("cant parse2.(%s)\n",retstr2);
|
||||
free(retstr2);
|
||||
}
|
||||
} else printf("error getblock %s\n",params);
|
||||
} else printf("strlen.%ld (%s)\n",strlen(txidstr),txidstr);
|
||||
free_json(result);
|
||||
}
|
||||
} else printf("couldnt parse.(%s)\n",retstr);
|
||||
free(retstr);
|
||||
}
|
||||
} else printf("error from getblockhash %d\n",height);
|
||||
return(retval);
|
||||
}
|
||||
|
||||
@@ -295,25 +473,32 @@ void komodo_gateway_iteration(char *symbol)
|
||||
char *retstr; int32_t i,kmdheight; cJSON *infoobj,*result; uint256 zero; uint16_t port = 7771;
|
||||
if ( KMDHEIGHT <= 0 )
|
||||
KMDHEIGHT = 1;
|
||||
KOMODO_REALTIME = 0;
|
||||
if ( (retstr= komodo_issuemethod((char *)"getinfo",0,port)) != 0 )
|
||||
{
|
||||
if ( (infoobj= cJSON_Parse(retstr)) != 0 )
|
||||
{
|
||||
if ( (result= jobj(infoobj,(char *)"result")) != 0 && (kmdheight= jint(result,(char *)"blocks")) != 0 )
|
||||
{
|
||||
//printf("gateway KMDHEIGHT.%d kmdheight.%d\n",KMDHEIGHT,kmdheight);
|
||||
for (i=0; i<1000 && KMDHEIGHT<kmdheight; i++,KMDHEIGHT++)
|
||||
{
|
||||
//printf("KMDHEIGHT %d\n",KMDHEIGHT);
|
||||
if ( (KMDHEIGHT % 100) == 0 )
|
||||
if ( (KMDHEIGHT % 10) == 0 )
|
||||
{
|
||||
fprintf(stderr,"%s.%d ",symbol,KMDHEIGHT);
|
||||
if ( (KMDHEIGHT % 100) == 0 )
|
||||
fprintf(stderr,"%s.%d ",symbol,KMDHEIGHT);
|
||||
memset(&zero,0,sizeof(zero));
|
||||
komodo_stateupdate(KMDHEIGHT,0,0,0,zero,0,0,0,0,KMDHEIGHT,0,0,0,0);
|
||||
}
|
||||
if ( komodo_gateway_block(symbol,KMDHEIGHT,port) < 0 )
|
||||
{
|
||||
printf("error KMDHEIGHT %d\n",KMDHEIGHT);
|
||||
break;
|
||||
}
|
||||
usleep(10000);
|
||||
}
|
||||
if ( KMDHEIGHT >= kmdheight )
|
||||
KOMODO_REALTIME = (uint32_t)time(NULL);
|
||||
}
|
||||
free_json(infoobj);
|
||||
}
|
||||
@@ -321,20 +506,46 @@ void komodo_gateway_iteration(char *symbol)
|
||||
}
|
||||
else
|
||||
{
|
||||
//printf("error from %s\n",symbol);
|
||||
printf("error from %s\n",symbol);
|
||||
sleep(30);
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef KOMODO_ISSUER
|
||||
void komodo_gateway_issuer() // from "assetchain" connectblock()
|
||||
void komodo_iteration(char *symbol)
|
||||
{
|
||||
// check for redeems
|
||||
char *retstr,*base,*coinaddr,*txidstr,cmd[512]; uint64_t value,fiatoshis; cJSON *array,*item; int32_t i,n,vout,shortflag,height; uint256 txid; uint8_t rmd160[20],addrtype;
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
{
|
||||
//[{"prev_hash":"5d5c9a49489b558de9e84f991f996dedaae6b9d0f157f82b2fec64662476d5cf","prev_vout":2,"EUR":0.78329000,"fiat":"EUR","height":57930,"KMD":0.10000000,"address":"RDhEGYScNQYetCyG75Kf8Fg61UWPdwc1C5"}]
|
||||
sprintf(cmd,"{\"agent\":\"dpow\",\"method\":\"pending\",\"fiat\":\"%s\"}",symbol);
|
||||
if ( (retstr= issue_curl(cmd)) != 0 )
|
||||
{
|
||||
if ( (array= cJSON_Parse(retstr)) != 0 )
|
||||
{
|
||||
if ( (n= cJSON_GetArraySize(array)) > 0 )
|
||||
{
|
||||
for (i=0; i<n; i++)
|
||||
{
|
||||
item = jitem(array,i);
|
||||
coinaddr = jstr(item,(char *)"address");
|
||||
value = jdouble(item,(char *)"KMD") * COIN;
|
||||
shortflag = juint(item,(char *)"short");
|
||||
vout = jint(item,(char *)"prev_vout");
|
||||
height = jint(item,(char *)"height");
|
||||
base = jstr(item,(char *)"fiat");
|
||||
txidstr = jstr(item,(char *)"prev_hash");
|
||||
if ( coinaddr != 0 && base != 0 && value > 0 && height > 0 )
|
||||
{
|
||||
fiatoshis = jdouble(item,base) * COIN;
|
||||
decode_hex((uint8_t *)&txid,sizeof(txid),txidstr);
|
||||
bitcoin_addr2rmd160(&addrtype,rmd160,coinaddr);
|
||||
komodo_gateway_deposit(coinaddr,value,shortflag,base,fiatoshis,rmd160,txid,vout,height);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
printf("retstr.(%s)\n",retstr);
|
||||
free(retstr);
|
||||
}
|
||||
}
|
||||
}
|
||||
#else
|
||||
|
||||
void komodo_gateway_redeemer() // from "KMD" connectblock()
|
||||
{
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -29,6 +29,6 @@ uint64_t ASSETCHAINS_SUPPLY = 10;
|
||||
int32_t NOTARIZED_HEIGHT,Num_nutxos,KMDHEIGHT = 43000;
|
||||
uint256 NOTARIZED_HASH,NOTARIZED_DESTTXID;
|
||||
pthread_mutex_t komodo_mutex;
|
||||
uint32_t KOMODO_INITDONE;
|
||||
uint32_t KOMODO_INITDONE,KOMODO_REALTIME;
|
||||
char KMDUSERPASS[1024]; uint16_t BITCOIND_PORT = 7771;
|
||||
uint64_t KOMODO_DEPOSIT,PENDING_KOMODO_TX;
|
||||
uint64_t PENDING_KOMODO_TX;
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
* *
|
||||
******************************************************************************/
|
||||
|
||||
const char *Notaries[][2] =
|
||||
const char *Notaries_genesis[][2] =
|
||||
{
|
||||
{ "jl777_testA", "03b7621b44118017a16043f19b30cc8a4cfe068ac4e42417bae16ba460c80f3828" },
|
||||
{ "jl777_testB", "02ebfc784a4ba768aad88d44d1045d240d47b26e248cafaf1c5169a42d7a61d344" },
|
||||
@@ -60,18 +60,6 @@ struct knotary_entry { UT_hash_handle hh; uint8_t pubkey[33],notaryid; };
|
||||
struct knotaries_entry { int32_t height,numnotaries; struct knotary_entry *Notaries; } Pubkeys[10000];
|
||||
struct notarized_checkpoint { uint256 notarized_hash,notarized_desttxid; int32_t nHeight,notarized_height; } *NPOINTS; int32_t NUM_NPOINTS;
|
||||
|
||||
int32_t komodo_ratify_threshold(int32_t height,uint64_t signedmask)
|
||||
{
|
||||
int32_t numnotaries,i,wt = 0;
|
||||
numnotaries = Pubkeys[height / KOMODO_ELECTION_GAP].numnotaries;
|
||||
for (i=0; i<numnotaries; i++)
|
||||
if ( ((1LL << i) & signedmask) != 0 )
|
||||
wt++;
|
||||
if ( wt > (numnotaries >> 1) || (wt > 7 && (signedmask & 3) != 0) )
|
||||
return(1); // N/2+1 || N/3 + devsig
|
||||
else return(0);
|
||||
}
|
||||
|
||||
void komodo_nutxoadd(int32_t height,int32_t notaryid,uint256 txhash,uint64_t voutmask,int32_t numvouts)
|
||||
{
|
||||
struct nutxo_entry *np;
|
||||
@@ -84,7 +72,7 @@ void komodo_nutxoadd(int32_t height,int32_t notaryid,uint256 txhash,uint64_t vou
|
||||
np->voutmask = voutmask;
|
||||
np->notaryid = notaryid;
|
||||
HASH_ADD_KEYPTR(hh,NUTXOS,&np->txhash,sizeof(np->txhash),np);
|
||||
printf("Add NUTXO[%d] <- %s notaryid.%d t%u %s %llx\n",Num_nutxos,Notaries[notaryid][0],notaryid,komodo_txtime(txhash),txhash.ToString().c_str(),(long long)voutmask);
|
||||
//printf("Add NUTXO[%d] <- %s notaryid.%d t%u %s %llx\n",Num_nutxos,Notaries[notaryid][0],notaryid,komodo_txtime(txhash),txhash.ToString().c_str(),(long long)voutmask);
|
||||
Num_nutxos++;
|
||||
pthread_mutex_unlock(&komodo_mutex);
|
||||
}
|
||||
@@ -101,6 +89,44 @@ int32_t komodo_nutxofind(int32_t height,uint256 txhash,int32_t vout)
|
||||
return(-1);
|
||||
}
|
||||
|
||||
int32_t komodo_ratify_threshold(int32_t height,uint64_t signedmask)
|
||||
{
|
||||
int32_t htind,numnotaries,i,wt = 0;
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
return(2);
|
||||
if ( (htind= KOMODO_PUBKEYS_HEIGHT(height) / KOMODO_ELECTION_GAP) == 1 )
|
||||
htind = 0;
|
||||
numnotaries = Pubkeys[htind].numnotaries;
|
||||
for (i=0; i<numnotaries; i++)
|
||||
if ( ((1LL << i) & signedmask) != 0 )
|
||||
wt++;
|
||||
if ( wt > (numnotaries >> 1) || (wt > 7 && (signedmask & 3) != 0) )
|
||||
return(1);
|
||||
else return(0);
|
||||
}
|
||||
|
||||
int32_t komodo_notaries(uint8_t pubkeys[64][33],int32_t height)
|
||||
{
|
||||
int32_t i,htind,n; uint64_t mask = 0; struct knotary_entry *kp,*tmp;
|
||||
if ( (htind= KOMODO_PUBKEYS_HEIGHT(height) / KOMODO_ELECTION_GAP) == 1 )
|
||||
htind = 0;
|
||||
pthread_mutex_lock(&komodo_mutex);
|
||||
n = Pubkeys[htind].numnotaries;
|
||||
HASH_ITER(hh,Pubkeys[htind].Notaries,kp,tmp)
|
||||
{
|
||||
if ( kp->notaryid < n )
|
||||
{
|
||||
mask |= (1LL << kp->notaryid);
|
||||
memcpy(pubkeys[kp->notaryid],kp->pubkey,33);
|
||||
} else printf("illegal notaryid.%d vs n.%d\n",kp->notaryid,n);
|
||||
}
|
||||
pthread_mutex_unlock(&komodo_mutex);
|
||||
if ( mask == ((1LL << n)-1) )
|
||||
return(n);
|
||||
printf("error retrieving notaries ht.%d got mask.%llx for n.%d\n",height,(long long)mask,n);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
void komodo_notarysinit(int32_t height,uint8_t pubkeys[64][33],int32_t num)
|
||||
{
|
||||
int32_t k,i,htind; struct knotary_entry *kp; struct knotaries_entry N;
|
||||
@@ -120,8 +146,7 @@ void komodo_notarysinit(int32_t height,uint8_t pubkeys[64][33],int32_t num)
|
||||
}
|
||||
}
|
||||
N.numnotaries = num;
|
||||
htind = KOMODO_PUBKEYS_HEIGHT(height) / KOMODO_ELECTION_GAP;
|
||||
if ( htind == 1 )
|
||||
if ( (htind= KOMODO_PUBKEYS_HEIGHT(height) / KOMODO_ELECTION_GAP) == 1 )
|
||||
htind = 0;
|
||||
for (i=htind; i<sizeof(Pubkeys)/sizeof(*Pubkeys); i++)
|
||||
{
|
||||
@@ -134,16 +159,18 @@ void komodo_notarysinit(int32_t height,uint8_t pubkeys[64][33],int32_t num)
|
||||
int32_t komodo_chosennotary(int32_t *notaryidp,int32_t height,uint8_t *pubkey33)
|
||||
{
|
||||
// -1 if not notary, 0 if notary, 1 if special notary
|
||||
struct knotary_entry *kp; int32_t numnotaries,modval = -1;
|
||||
struct knotary_entry *kp; int32_t numnotaries,htind,modval = -1;
|
||||
*notaryidp = -1;
|
||||
if ( height < 0 || height/KOMODO_ELECTION_GAP >= sizeof(Pubkeys)/sizeof(*Pubkeys) )
|
||||
return(-1);
|
||||
if ( (htind= KOMODO_PUBKEYS_HEIGHT(height) / KOMODO_ELECTION_GAP) == 1 )
|
||||
htind = 0;
|
||||
pthread_mutex_lock(&komodo_mutex);
|
||||
HASH_FIND(hh,Pubkeys[height/KOMODO_ELECTION_GAP].Notaries,pubkey33,33,kp);
|
||||
HASH_FIND(hh,Pubkeys[htind].Notaries,pubkey33,33,kp);
|
||||
pthread_mutex_unlock(&komodo_mutex);
|
||||
if ( kp != 0 )
|
||||
{
|
||||
if ( (numnotaries= Pubkeys[height/KOMODO_ELECTION_GAP].numnotaries) > 0 )
|
||||
if ( (numnotaries= Pubkeys[htind].numnotaries) > 0 )
|
||||
{
|
||||
*notaryidp = kp->notaryid;
|
||||
modval = ((height % numnotaries) == kp->notaryid);
|
||||
@@ -195,25 +222,25 @@ int32_t komodo_notarizeddata(int32_t nHeight,uint256 *notarized_hashp,uint256 *n
|
||||
return(0);
|
||||
}
|
||||
|
||||
void komodo_init()
|
||||
void komodo_init(int32_t height)
|
||||
{
|
||||
static int didinit; uint256 zero; int32_t k,n; uint8_t pubkeys[64][33];
|
||||
if ( didinit == 0 )
|
||||
if ( height > didinit )
|
||||
{
|
||||
didinit = 1;
|
||||
iguana_initQ(&DepositsQ,(char *)"Deposits");
|
||||
iguana_initQ(&PendingsQ,(char *)"Pendings");
|
||||
pthread_mutex_init(&komodo_mutex,NULL);
|
||||
decode_hex(NOTARY_PUBKEY33,33,(char *)NOTARY_PUBKEY.c_str());
|
||||
n = (int32_t)(sizeof(Notaries)/sizeof(*Notaries));
|
||||
for (k=0; k<n; k++)
|
||||
if ( didinit == 0 )
|
||||
{
|
||||
if ( Notaries[k][0] == 0 || Notaries[k][1] == 0 || Notaries[k][0][0] == 0 || Notaries[k][1][0] == 0 )
|
||||
break;
|
||||
decode_hex(pubkeys[k],33,(char *)Notaries[k][1]);
|
||||
pthread_mutex_init(&komodo_mutex,NULL);
|
||||
decode_hex(NOTARY_PUBKEY33,33,(char *)NOTARY_PUBKEY.c_str());
|
||||
n = (int32_t)(sizeof(Notaries_genesis)/sizeof(*Notaries_genesis));
|
||||
for (k=0; k<n; k++)
|
||||
{
|
||||
if ( Notaries_genesis[k][0] == 0 || Notaries_genesis[k][1] == 0 || Notaries_genesis[k][0][0] == 0 || Notaries_genesis[k][1][0] == 0 )
|
||||
break;
|
||||
decode_hex(pubkeys[k],33,(char *)Notaries_genesis[k][1]);
|
||||
}
|
||||
komodo_notarysinit(0,pubkeys,k);
|
||||
memset(&zero,0,sizeof(zero));
|
||||
}
|
||||
komodo_notarysinit(0,pubkeys,k);
|
||||
memset(&zero,0,sizeof(zero));
|
||||
komodo_stateupdate(0,0,0,0,zero,0,0,0,0,0,0,0,0,0);
|
||||
}
|
||||
}
|
||||
|
||||
168
src/komodo_pax.h
168
src/komodo_pax.h
@@ -30,6 +30,72 @@ uint32_t MINDENOMS[] = { MIND, MIND, 100*MIND, MIND, MIND, MIND, MIND, MIND, //
|
||||
10*MIND,
|
||||
};
|
||||
|
||||
int32_t Peggy_inds[539] = {289, 404, 50, 490, 59, 208, 87, 508, 366, 288, 13, 38, 159, 440, 120, 480, 361, 104, 534, 195, 300, 362, 489, 108, 143, 220, 131, 244, 133, 473, 315, 439, 210, 456, 219, 352, 153, 444, 397, 491, 286, 479, 519, 384, 126, 369, 155, 427, 373, 360, 135, 297, 256, 506, 322, 425, 501, 251, 75, 18, 420, 537, 443, 438, 407, 145, 173, 78, 340, 240, 422, 160, 329, 32, 127, 128, 415, 495, 372, 522, 60, 238, 129, 364, 471, 140, 171, 215, 378, 292, 432, 526, 252, 389, 459, 350, 233, 408, 433, 51, 423, 19, 62, 115, 211, 22, 247, 197, 530, 7, 492, 5, 53, 318, 313, 283, 169, 464, 224, 282, 514, 385, 228, 175, 494, 237, 446, 105, 150, 338, 346, 510, 6, 348, 89, 63, 536, 442, 414, 209, 216, 227, 380, 72, 319, 259, 305, 334, 236, 103, 400, 176, 267, 355, 429, 134, 257, 527, 111, 287, 386, 15, 392, 535, 405, 23, 447, 399, 291, 112, 74, 36, 435, 434, 330, 520, 335, 201, 478, 17, 162, 483, 33, 130, 436, 395, 93, 298, 498, 511, 66, 487, 218, 65, 309, 419, 48, 214, 377, 409, 462, 139, 349, 4, 513, 497, 394, 170, 307, 241, 185, 454, 29, 367, 465, 194, 398, 301, 229, 212, 477, 303, 39, 524, 451, 116, 532, 30, 344, 85, 186, 202, 517, 531, 515, 230, 331, 466, 147, 426, 234, 304, 64, 100, 416, 336, 199, 383, 200, 166, 258, 95, 188, 246, 136, 90, 68, 45, 312, 354, 184, 314, 518, 326, 401, 269, 217, 512, 81, 88, 272, 14, 413, 328, 393, 198, 226, 381, 161, 474, 353, 337, 294, 295, 302, 505, 137, 207, 249, 46, 98, 27, 458, 482, 262, 253, 71, 25, 0, 40, 525, 122, 341, 107, 80, 165, 243, 168, 250, 375, 151, 503, 124, 52, 343, 371, 206, 178, 528, 232, 424, 163, 273, 191, 149, 493, 177, 144, 193, 388, 1, 412, 265, 457, 255, 475, 223, 41, 430, 76, 102, 132, 96, 97, 316, 472, 213, 263, 3, 317, 324, 274, 396, 486, 254, 205, 285, 101, 21, 279, 58, 467, 271, 92, 538, 516, 235, 332, 117, 500, 529, 113, 445, 390, 358, 79, 34, 488, 245, 83, 509, 203, 476, 496, 347, 280, 12, 84, 485, 323, 452, 10, 146, 391, 293, 86, 94, 523, 299, 91, 164, 363, 402, 110, 321, 181, 138, 192, 469, 351, 276, 308, 277, 428, 182, 260, 55, 152, 157, 382, 121, 507, 225, 61, 431, 31, 106, 327, 154, 16, 49, 499, 73, 70, 449, 460, 187, 24, 248, 311, 275, 158, 387, 125, 67, 284, 35, 463, 190, 179, 266, 376, 221, 42, 26, 290, 357, 268, 43, 167, 99, 374, 242, 156, 239, 403, 339, 183, 320, 180, 306, 379, 441, 20, 481, 141, 77, 484, 69, 410, 502, 172, 417, 118, 461, 261, 47, 333, 450, 296, 453, 368, 359, 437, 421, 264, 504, 281, 270, 114, 278, 56, 406, 448, 411, 521, 418, 470, 123, 455, 148, 356, 468, 109, 204, 533, 365, 8, 345, 174, 370, 28, 57, 11, 2, 231, 310, 196, 119, 82, 325, 44, 342, 37, 189, 142, 222, 9, 54, };
|
||||
|
||||
uint64_t peggy_smooth_coeffs[sizeof(Peggy_inds)/sizeof(*Peggy_inds)] = // numprimes.13
|
||||
{
|
||||
962714545, 962506087, 962158759, 961672710, 961048151, 960285354, 959384649, 958346426, 957171134, // x.8
|
||||
955859283, 954411438, 952828225, 951110328, 949258485, 947273493, 945156207, 942907532, 940528434, // x.17
|
||||
938019929, 935383089, 932619036, 929728945, 926714044, 923575608, 920314964, 916933485, 913432593, // x.26
|
||||
909813756, 906078486, 902228342, 898264923, 894189872, 890004874, 885711650, 881311964, 876807614, // x.35
|
||||
872200436, 867492300, 862685110, 857780804, 852781347, 847688737, 842505000, 837232189, 831872382, // x.44
|
||||
826427681, 820900212, 815292123, 809605581, 803842772, 798005901, 792097186, 786118864, 780073180, // x.53
|
||||
773962395, 767788778, 761554609, 755262175, 748913768, 742511686, 736058231, 729555707, 723006417, // x.62
|
||||
716412665, 709776755, 703100984, 696387648, 689639036, 682857428, 676045100, 669204315, 662337327, // x.71
|
||||
655446378, 648533696, 641601496, 634651978, 627687325, 620709702, 613721256, 606724115, 599720386, // x.80
|
||||
592712154, 585701482, 578690411, 571680955, 564675105, 557674825, 550682053, 543698699, 536726645, // x.89
|
||||
529767743, 522823816, 515896658, 508988029, 502099660, 495233249, 488390461, 481572928, 474782249, // x.98
|
||||
468019988, 461287675, 454586804, 447918836, 441285195, 434687268, 428126409, 421603932, 415121117, // x.107
|
||||
408679208, 402279408, 395922888, 389610779, 383344175, 377124134, 370951677, 364827785, 358753406, // x.116
|
||||
352729449, 346756785, 340836251, 334968645, 329154729, 323395230, 317690838, 312042206, 306449955, // x.125
|
||||
300914667, 295436891, 290017141, 284655897, 279353604, 274110676, 268927490, 263804394, 258741701, // x.134
|
||||
253739694, 248798623, 243918709, 239100140, 234343077, 229647649, 225013957, 220442073, 215932043, // x.143
|
||||
211483883, 207097585, 202773112, 198510404, 194309373, 190169909, 186091877, 182075118, 178119452, // x.152
|
||||
174224676, 170390565, 166616873, 162903335, 159249664, 155655556, 152120688, 148644718, 145227287, // x.161
|
||||
141868021, 138566528, 135322401, 132135218, 129004542, 125929924, 122910901, 119946997, 117037723, // x.170
|
||||
114182582, 111381062, 108632643, 105936795, 103292978, 100700645, 98159238, 95668194, 93226942, // x.179
|
||||
90834903, 88491495, 86196126, 83948203, 81747126, 79592292, 77483092, 75418916, 73399150, // x.188
|
||||
71423178, 69490383, 67600142, 65751837, 63944844, 62178541, 60452305, 58765515, 57117547, // x.197
|
||||
55507781, 53935597, 52400377, 50901505, 49438366, 48010349, 46616844, 45257246, 43930951, // x.206
|
||||
42637360, 41375878, 40145912, 38946876, 37778185, 36639262, 35529533, 34448428, 33395384, // x.215
|
||||
32369842, 31371249, 30399057, 29452725, 28531717, 27635503, 26763558, 25915365, 25090413, // x.224
|
||||
24288196, 23508216, 22749980, 22013003, 21296806, 20600917, 19924870, 19268206, 18630475, // x.233
|
||||
18011231, 17410035, 16826458, 16260073, 15710466, 15177224, 14659944, 14158231, 13671694, // x.242
|
||||
13199950, 12742625, 12299348, 11869759, 11453500, 11050225, 10659590, 10281262, 9914910, // x.251
|
||||
9560213, 9216856, 8884529, 8562931, 8251764, 7950739, 7659571, 7377984, 7105706, // x.260
|
||||
6842471, 6588020, 6342099, 6104460, 5874861, 5653066, 5438844, 5231969, 5032221, // x.269
|
||||
4839386, 4653254, 4473620, 4300287, 4133059, 3971747, 3816167, 3666139, 3521488, // x.278
|
||||
3382043, 3247640, 3118115, 2993313, 2873079, 2757266, 2645728, 2538325, 2434919, // x.287
|
||||
2335380, 2239575, 2147382, 2058677, 1973342, 1891262, 1812325, 1736424, 1663453, // x.296
|
||||
1593311, 1525898, 1461118, 1398879, 1339091, 1281666, 1226519, 1173569, 1122736, // x.305
|
||||
1073944, 1027117, 982185, 939076, 897725, 858065, 820033, 783568, 748612, // x.314
|
||||
715108, 682999, 652233, 622759, 594527, 567488, 541597, 516808, 493079, // x.323
|
||||
470368, 448635, 427841, 407948, 388921, 370725, 353326, 336692, 320792, // x.332
|
||||
305596, 291075, 277202, 263950, 251292, 239204, 227663, 216646, 206130, // x.341
|
||||
196094, 186517, 177381, 168667, 160356, 152430, 144874, 137671, 130806, // x.350
|
||||
124264, 118031, 112093, 106437, 101050, 95921, 91039, 86391, 81968, // x.359
|
||||
77759, 73755, 69945, 66322, 62877, 59602, 56488, 53528, 50716, // x.368
|
||||
48043, 45505, 43093, 40803, 38629, 36564, 34604, 32745, 30980, // x.377
|
||||
29305, 27717, 26211, 24782, 23428, 22144, 20927, 19774, 18681, // x.386
|
||||
17646, 16665, 15737, 14857, 14025, 13237, 12491, 11786, 11118, // x.395
|
||||
10487, 9890, 9325, 8791, 8287, 7810, 7359, 6933, 6531, // x.404
|
||||
6151, 5792, 5453, 5133, 4831, 4547, 4278, 4024, 3785, // x.413
|
||||
3560, 3347, 3147, 2958, 2779, 2612, 2454, 2305, 2164, // x.422
|
||||
2032, 1908, 1791, 1681, 1577, 1480, 1388, 1302, 1221, // x.431
|
||||
1145, 1073, 1006, 942, 883, 827, 775, 725, 679, // x.440
|
||||
636, 595, 557, 521, 487, 456, 426, 399, 373, // x.449
|
||||
348, 325, 304, 284, 265, 248, 231, 216, 202, // x.458
|
||||
188, 175, 164, 153, 142, 133, 124, 115, 107, // x.467
|
||||
100, 93, 87, 81, 75, 70, 65, 61, 56, // x.476
|
||||
53, 49, 45, 42, 39, 36, 34, 31, 29, // x.485
|
||||
27, 25, 23, 22, 20, 19, 17, 16, 15, // x.494
|
||||
14, 13, 12, 11, 10, 9, 9, 8, 7, // x.503
|
||||
7, 6, 6, 5, 5, 5, 4, 4, 4, // x.512
|
||||
3, 3, 3, 3, 2, 2, 2, 2, 2, // x.521
|
||||
2, 2, 1, 1, 1, 1, 1, 1, 1, // x.530
|
||||
1, 1, 1, 1, 1, 1, 0, 0, // isum 100000000000
|
||||
};
|
||||
|
||||
uint64_t komodo_paxvol(uint64_t volume,uint64_t price)
|
||||
{
|
||||
if ( volume < 10000000000 )
|
||||
@@ -234,8 +300,11 @@ void komodo_pvals(int32_t height,uint32_t *pvals,uint8_t numpvals)
|
||||
uint64_t komodo_paxcalc(uint32_t *pvals,int32_t baseid,int32_t relid,uint64_t basevolume)
|
||||
{
|
||||
uint32_t pvalb,pvalr,kmdbtc,btcusd; uint64_t usdvol,baseusd,usdkmd,baserel,ranked[32];
|
||||
if ( basevolume > 1000000*COIN )
|
||||
if ( basevolume > 10000*COIN )
|
||||
{
|
||||
printf("paxcalc overflow %.8f\n",dstr(basevolume));
|
||||
return(0);
|
||||
}
|
||||
if ( (pvalb= pvals[baseid]) != 0 )
|
||||
{
|
||||
if ( relid == MAX_CURRENCIES )
|
||||
@@ -248,28 +317,35 @@ uint64_t komodo_paxcalc(uint32_t *pvals,int32_t baseid,int32_t relid,uint64_t ba
|
||||
usdvol = komodo_paxvol(basevolume,baseusd) / MINDENOMS[baseid];
|
||||
usdkmd = ((uint64_t)btcusd * 1000000000) / kmdbtc;
|
||||
//printf("base -> USD %llu, BTC %llu KMDUSD %llu\n",(long long)baseusd,(long long)btcusd,(long long)kmdusd);
|
||||
printf("usdkmd.%llu basevolume.%llu baseusd.%llu paxvol.%llu usdvol.%llu\n",(long long)usdkmd,(long long)basevolume,(long long)baseusd,(long long)komodo_paxvol(basevolume,baseusd),(long long)usdvol);
|
||||
//printf("usdkmd.%llu basevolume.%llu baseusd.%llu paxvol.%llu usdvol.%llu -> %.8f\n",(long long)usdkmd,(long long)basevolume,(long long)baseusd,(long long)komodo_paxvol(basevolume,baseusd),(long long)usdvol,dstr(MINDENOMS[USD] * komodo_paxvol(usdvol,usdkmd)));
|
||||
return(MINDENOMS[USD] * komodo_paxvol(usdvol,usdkmd));
|
||||
}
|
||||
} //else printf("zero val in KMD conv %llu %llu %llu\n",(long long)pvals[USD],(long long)kmdbtc,(long long)btcusd);
|
||||
}
|
||||
else if ( baseid == relid )
|
||||
{
|
||||
if ( baseid != MAX_CURRENCIES )
|
||||
{
|
||||
pax_rank(ranked,pvals);
|
||||
return(10 * ranked[baseid]); // map to percentage
|
||||
}
|
||||
//printf("%s M1 percentage %.8f\n",CURRENCIES[baseid],dstr(10 * ranked[baseid]));
|
||||
return(10 * ranked[baseid]); // scaled percentage of M1 total
|
||||
} else return(basevolume);
|
||||
}
|
||||
else if ( (pvalr= pvals[relid]) != 0 )
|
||||
{
|
||||
baserel = ((uint64_t)pvalb * 1000000000) / pvalr;
|
||||
//printf("baserel.%lld %lld %lld %.8f %.8f\n",(long long)baserel,(long long)MINDENOMS[baseid],(long long)MINDENOMS[relid],dstr(MINDENOMS[baseid]/MINDENOMS[relid]),dstr(MINDENOMS[relid]/MINDENOMS[baseid]));
|
||||
if ( MINDENOMS[baseid] > MINDENOMS[relid] )
|
||||
basevolume /= (MINDENOMS[baseid] / MINDENOMS[relid]);
|
||||
else if ( MINDENOMS[baseid] < MINDENOMS[relid] )
|
||||
basevolume *= (MINDENOMS[relid] / MINDENOMS[baseid]);
|
||||
return(komodo_paxvol(basevolume,baserel));
|
||||
}
|
||||
}
|
||||
else printf("null pval for %s\n",CURRENCIES[relid]);
|
||||
} else printf("null pval for %s\n",CURRENCIES[baseid]);
|
||||
return(0);
|
||||
}
|
||||
|
||||
uint64_t komodo_paxprice(int32_t height,char *base,char *rel,uint64_t basevolume)
|
||||
uint64_t _komodo_paxprice(int32_t height,char *base,char *rel,uint64_t basevolume)
|
||||
{
|
||||
int32_t baseid=-1,relid=-1,i; uint32_t *ptr;
|
||||
if ( (baseid= komodo_baseid(base)) >= 0 && (relid= komodo_baseid(rel)) >= 0 )
|
||||
@@ -284,6 +360,79 @@ uint64_t komodo_paxprice(int32_t height,char *base,char *rel,uint64_t basevolume
|
||||
return(0);
|
||||
}
|
||||
|
||||
uint64_t komodo_paxprice(uint64_t *seedp,int32_t height,char *base,char *rel,uint64_t basevolume)
|
||||
{
|
||||
int32_t i,j,k,ind,zeroes,numvotes,wt,nonz; int64_t delta; uint64_t lastprice,seed,tolerance,den,densum,sum=0,votes[539];
|
||||
if ( basevolume > 10000*COIN )
|
||||
{
|
||||
printf("komodo_paxprice overflow %.8f\n",dstr(basevolume));
|
||||
return(0);
|
||||
}
|
||||
numvotes = (int32_t)(sizeof(Peggy_inds)/sizeof(*Peggy_inds));
|
||||
memset(votes,0,sizeof(votes));
|
||||
for (sum=i=zeroes=nonz=0; i<numvotes; i++)
|
||||
{
|
||||
if ( (votes[numvotes-1-i]= _komodo_paxprice(height-i,base,rel,100000)) == 0 )
|
||||
{
|
||||
zeroes++;
|
||||
//printf("null price height.%d\n",height-i);
|
||||
//return(0);
|
||||
} else sum += votes[i], nonz++;
|
||||
//printf("%.8f, ",dstr(votes[i]));
|
||||
}
|
||||
if ( nonz <= (numvotes >> 1) )
|
||||
return(0);
|
||||
sum /= nonz;
|
||||
lastprice = sum;
|
||||
for (i=0; i<numvotes; i++)
|
||||
{
|
||||
if ( votes[i] == 0 )
|
||||
votes[i] = lastprice;
|
||||
else lastprice = votes[i];
|
||||
}
|
||||
//printf("\n}; // numvotes.%d\n\n",numvotes);
|
||||
*seedp = seed = komodo_seed(height);
|
||||
tolerance = sum / 50;
|
||||
for (k=0; k<numvotes; k++)
|
||||
{
|
||||
ind = Peggy_inds[(k + seed) % numvotes];
|
||||
i = (int32_t)(ind % numvotes);
|
||||
wt = 0;
|
||||
if ( votes[i] != 0 )
|
||||
{
|
||||
for (j=0; j<numvotes; j++)
|
||||
{
|
||||
if ( votes[j] != 0 )
|
||||
{
|
||||
if ( (delta= (votes[i] - votes[j])) < 0 )
|
||||
delta = -delta;
|
||||
if ( delta <= tolerance )
|
||||
{
|
||||
wt++;
|
||||
if ( wt > (numvotes >> 1) )
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if ( wt > (numvotes >> 1) )
|
||||
{
|
||||
ind = i;
|
||||
for (densum=sum=j=0; j<numvotes; j++)
|
||||
{
|
||||
den = peggy_smooth_coeffs[j];
|
||||
densum += den;
|
||||
sum += (den * votes[(ind + j) % numvotes]);
|
||||
}
|
||||
sum /= densum;
|
||||
sum = (sum * basevolume) / 100000;
|
||||
printf("paxprice seed.%llx sum %.8f densum %.8f basevol %.8f height.%d\n",(long long)seed,dstr(sum),dstr(densum),dstr(basevolume),height);
|
||||
break;
|
||||
}
|
||||
}
|
||||
return(sum);
|
||||
}
|
||||
|
||||
int32_t komodo_paxprices(int32_t *heights,uint64_t *prices,int32_t max,char *base,char *rel)
|
||||
{
|
||||
int32_t baseid=-1,relid=-1,i,num = 0; uint32_t *ptr;
|
||||
@@ -311,7 +460,7 @@ void komodo_paxpricefeed(int32_t height,uint8_t *pricefeed,int32_t opretlen)
|
||||
//printf("komodo_paxpricefeed vout OP_RETURN.%d prices numpvals.%d opretlen.%d\n",height,numpvals,opretlen);
|
||||
}
|
||||
|
||||
uint64_t PAX_fiatdest(int32_t tokomodo,char *destaddr,uint8_t pubkey33[33],char *coinaddr,int32_t height,char *origbase,int64_t fiatoshis)
|
||||
uint64_t PAX_fiatdest(uint64_t *seedp,int32_t tokomodo,char *destaddr,uint8_t pubkey33[33],char *coinaddr,int32_t height,char *origbase,int64_t fiatoshis)
|
||||
{
|
||||
uint8_t shortflag = 0; char base[4]; int32_t i,baseid; uint8_t addrtype,rmd160[20]; int64_t komodoshis = 0;
|
||||
if ( (baseid= komodo_baseid(origbase)) < 0 || baseid == MAX_CURRENCIES )
|
||||
@@ -321,7 +470,8 @@ uint64_t PAX_fiatdest(int32_t tokomodo,char *destaddr,uint8_t pubkey33[33],char
|
||||
base[i] = 0;
|
||||
if ( fiatoshis < 0 )
|
||||
shortflag = 1, fiatoshis = -fiatoshis;
|
||||
komodoshis = komodo_paxprice(height,base,(char *)"KMD",(uint64_t)fiatoshis);
|
||||
komodoshis = komodo_paxprice(seedp,height,base,(char *)"KMD",(uint64_t)fiatoshis);
|
||||
//printf("PAX_fiatdest ht.%d price %s %.8f -> KMD %.8f\n",height,base,(double)fiatoshis/COIN,(double)komodoshis/COIN);
|
||||
if ( bitcoin_addr2rmd160(&addrtype,rmd160,coinaddr) == 20 )
|
||||
{
|
||||
PAX_pubkey(1,pubkey33,&addrtype,rmd160,base,&shortflag,tokomodo != 0 ? &komodoshis : &fiatoshis);
|
||||
|
||||
@@ -796,10 +796,17 @@ int32_t komodo_baseid(char *origbase)
|
||||
for (i=0; i<=MAX_CURRENCIES; i++)
|
||||
if ( strcmp(CURRENCIES[i],base) == 0 )
|
||||
return(i);
|
||||
printf("illegal base.(%s) %s\n",origbase,base);
|
||||
//printf("illegal base.(%s) %s\n",origbase,base);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
int32_t komodo_is_issuer()
|
||||
{
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 && komodo_baseid(ASSETCHAINS_SYMBOL) >= 0 )
|
||||
return(1);
|
||||
else return(0);
|
||||
}
|
||||
|
||||
int32_t _unhex(char c)
|
||||
{
|
||||
if ( c >= '0' && c <= '9' )
|
||||
@@ -1302,9 +1309,54 @@ void komodo_configfile(char *symbol,uint16_t port)
|
||||
} else printf("couldnt open.(%s)\n",fname);
|
||||
}
|
||||
|
||||
uint32_t komodo_assetmagic(char *symbol,uint64_t supply)
|
||||
{
|
||||
uint8_t buf[512]; int32_t len = 0;
|
||||
len = iguana_rwnum(1,&buf[len],sizeof(supply),(void *)&supply);
|
||||
strcpy((char *)&buf[len],symbol);
|
||||
len += strlen(symbol);
|
||||
return(calc_crc32(0,buf,len));
|
||||
}
|
||||
|
||||
int32_t komodo_shortflag(char *symbol)
|
||||
{
|
||||
int32_t i,shortflag = 0;
|
||||
if ( symbol[0] == '-' )
|
||||
{
|
||||
shortflag = 1;
|
||||
for (i=0; symbol[i+1]!=0; i++)
|
||||
symbol[i] = symbol[i+1];
|
||||
symbol[i] = 0;
|
||||
}
|
||||
return(shortflag);
|
||||
}
|
||||
|
||||
uint16_t komodo_assetport(uint32_t magic,int32_t shortflag)
|
||||
{
|
||||
return(8000 + shortflag*7777 + (magic % 7777));
|
||||
}
|
||||
|
||||
uint16_t komodo_port(char *symbol,uint64_t supply,uint32_t *magicp,int32_t *shortflagp)
|
||||
{
|
||||
*magicp = komodo_assetmagic(symbol,supply);
|
||||
*shortflagp = komodo_shortflag(symbol);
|
||||
return(komodo_assetport(*magicp,*shortflagp));
|
||||
}
|
||||
|
||||
void komodo_ports(uint16_t ports[MAX_CURRENCIES])
|
||||
{
|
||||
int32_t i,shortflag; uint32_t magic;
|
||||
for (i=0; i<MAX_CURRENCIES; i++)
|
||||
{
|
||||
ports[i] = komodo_port(CURRENCIES[i],10,&magic,&shortflag);
|
||||
printf("%u ",ports[i]);
|
||||
}
|
||||
printf("ports\n");
|
||||
}
|
||||
|
||||
void komodo_args()
|
||||
{
|
||||
std::string name; char *dirname; uint8_t buf[512]; int32_t i,len;
|
||||
std::string name; char *dirname; int32_t i,len;
|
||||
IS_KOMODO_NOTARY = GetBoolArg("-notary", false);
|
||||
NOTARY_PUBKEY = GetArg("-pubkey", "");
|
||||
if ( strlen(NOTARY_PUBKEY.c_str()) == 66 )
|
||||
@@ -1314,17 +1366,7 @@ void komodo_args()
|
||||
{
|
||||
ASSETCHAINS_SUPPLY = GetArg("-ac_supply",10);
|
||||
strncpy(ASSETCHAINS_SYMBOL,name.c_str(),sizeof(ASSETCHAINS_SYMBOL)-1);
|
||||
len = iguana_rwnum(1,&buf[len],sizeof(ASSETCHAINS_SUPPLY),(void *)&ASSETCHAINS_SUPPLY);
|
||||
strcpy((char *)&buf[len],ASSETCHAINS_SYMBOL);
|
||||
len += strlen(ASSETCHAINS_SYMBOL);
|
||||
ASSETCHAINS_MAGIC = calc_crc32(0,buf,len);
|
||||
ASSETCHAINS_PORT = GetArg("-ac_port",8000 + (ASSETCHAINS_MAGIC % 7777));
|
||||
if ( ASSETCHAINS_SYMBOL[0] == '-' )
|
||||
{
|
||||
ASSETCHAINS_SHORTFLAG = 1;
|
||||
for (i=0; ASSETCHAINS_SYMBOL[i+1]!=0; i++)
|
||||
ASSETCHAINS_SYMBOL[i] = ASSETCHAINS_SYMBOL[i+1];
|
||||
}
|
||||
ASSETCHAINS_PORT = komodo_port(ASSETCHAINS_SYMBOL,ASSETCHAINS_SUPPLY,&ASSETCHAINS_MAGIC,&ASSETCHAINS_SHORTFLAG);
|
||||
//fprintf(stderr,"after args: %c%s port.%u magic.%08x supply.%u\n",ASSETCHAINS_SHORTFLAG!=0?'-':'+',ASSETCHAINS_SYMBOL,ASSETCHAINS_PORT,ASSETCHAINS_MAGIC,(int32_t)ASSETCHAINS_SUPPLY);
|
||||
while ( (dirname= (char *)GetDataDir(false).string().c_str()) == 0 || dirname[0] == 0 )
|
||||
{
|
||||
@@ -1344,7 +1386,7 @@ void komodo_args()
|
||||
else
|
||||
{
|
||||
ASSETCHAINS_PORT = 8777;
|
||||
fprintf(stderr,"IS_KOMODO_NOTARY %d %s\n",IS_KOMODO_NOTARY,NOTARY_PUBKEY.c_str());
|
||||
//fprintf(stderr,"IS_KOMODO_NOTARY %d %s\n",IS_KOMODO_NOTARY,NOTARY_PUBKEY.c_str());
|
||||
}
|
||||
//fprintf(stderr,"%s chain params initialized\n",ASSETCHAINS_SYMBOL);
|
||||
}
|
||||
49
src/main.cpp
49
src/main.cpp
@@ -550,9 +550,8 @@ CBlockTreeDB *pblocktree = NULL;
|
||||
|
||||
// Komodo globals
|
||||
|
||||
#define KOMODO_TESTNET_EXPIRATION 60000
|
||||
//#define KOMODO_ENABLE_INTEREST enabling this is a hardfork
|
||||
#define KOMODO_SOURCE "KMD"
|
||||
#define KOMODO_TESTNET_EXPIRATION 100000
|
||||
#define KOMODO_ENABLE_INTEREST //enabling this is a hardfork
|
||||
#define KOMODO_PAX
|
||||
#define KOMODO_ZCASH
|
||||
#include "komodo.h"
|
||||
@@ -1470,16 +1469,31 @@ bool IsInitialBlockDownload()
|
||||
const CChainParams& chainParams = Params();
|
||||
LOCK(cs_main);
|
||||
if (fImporting || fReindex)
|
||||
{
|
||||
//fprintf(stderr,"fImporting %d || %d fReindex\n",(int32_t)fImporting,(int32_t)fReindex);
|
||||
return true;
|
||||
}
|
||||
if (fCheckpointsEnabled && chainActive.Height() < Checkpoints::GetTotalBlocksEstimate(chainParams.Checkpoints()))
|
||||
{
|
||||
//fprintf(stderr,"checkpoint -> initialdownload\n");
|
||||
return true;
|
||||
}
|
||||
static bool lockIBDState = false;
|
||||
if (lockIBDState)
|
||||
{
|
||||
//fprintf(stderr,"lockIBDState true %d < %d\n",chainActive.Height(),pindexBestHeader->nHeight - 10);
|
||||
return false;
|
||||
bool state = (chainActive.Height() < pindexBestHeader->nHeight - 24 * 6 ||
|
||||
pindexBestHeader->GetBlockTime() < GetTime() - chainParams.MaxTipAge());
|
||||
}
|
||||
bool state;
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
state = (chainActive.Height() < pindexBestHeader->nHeight - 24*6) ||
|
||||
pindexBestHeader->GetBlockTime() < (GetTime() - chainParams.MaxTipAge());
|
||||
else state = (chainActive.Height() < pindexBestHeader->nHeight - 100);
|
||||
if (!state)
|
||||
{
|
||||
//fprintf(stderr,"lockIBDState tru\n");
|
||||
lockIBDState = true;
|
||||
}
|
||||
return state;
|
||||
}
|
||||
|
||||
@@ -1621,8 +1635,8 @@ void static InvalidBlockFound(CBlockIndex *pindex, const CValidationState &state
|
||||
|
||||
void UpdateCoins(const CTransaction& tx, CValidationState &state, CCoinsViewCache &inputs, CTxUndo &txundo, int nHeight)
|
||||
{
|
||||
// mark inputs spent
|
||||
if (!tx.IsCoinBase()) {
|
||||
if (!tx.IsCoinBase()) // mark inputs spent
|
||||
{
|
||||
txundo.vprevout.reserve(tx.vin.size());
|
||||
BOOST_FOREACH(const CTxIn &txin, tx.vin) {
|
||||
CCoinsModifier coins = inputs.ModifyCoins(txin.prevout.hash);
|
||||
@@ -1641,16 +1655,12 @@ void UpdateCoins(const CTransaction& tx, CValidationState &state, CCoinsViewCach
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// spend nullifiers
|
||||
BOOST_FOREACH(const JSDescription &joinsplit, tx.vjoinsplit) {
|
||||
BOOST_FOREACH(const JSDescription &joinsplit, tx.vjoinsplit) { // spend nullifiers
|
||||
BOOST_FOREACH(const uint256 &nf, joinsplit.nullifiers) {
|
||||
inputs.SetNullifier(nf, true);
|
||||
}
|
||||
}
|
||||
|
||||
// add outputs
|
||||
inputs.ModifyCoins(tx.GetHash())->FromTx(tx, nHeight);
|
||||
inputs.ModifyCoins(tx.GetHash())->FromTx(tx, nHeight); // add outputs
|
||||
}
|
||||
|
||||
void UpdateCoins(const CTransaction& tx, CValidationState &state, CCoinsViewCache &inputs, int nHeight)
|
||||
@@ -2243,7 +2253,8 @@ bool ConnectBlock(const CBlock& block, CValidationState& state, CBlockIndex* pin
|
||||
LogPrint("bench", " - Connect %u transactions: %.2fms (%.3fms/tx, %.3fms/txin) [%.2fs]\n", (unsigned)block.vtx.size(), 0.001 * (nTime1 - nTimeStart), 0.001 * (nTime1 - nTimeStart) / block.vtx.size(), nInputs <= 1 ? 0 : 0.001 * (nTime1 - nTimeStart) / (nInputs-1), nTimeConnect * 0.000001);
|
||||
|
||||
CAmount blockReward = nFees + GetBlockSubsidy(pindex->nHeight, chainparams.GetConsensus());
|
||||
if (block.vtx[0].GetValueOut() > blockReward)
|
||||
if (block.vtx[0].vout[0].nValue > blockReward)
|
||||
//if (block.vtx[0].GetValueOut() > blockReward)
|
||||
return state.DoS(100,
|
||||
error("ConnectBlock(): coinbase pays too much (actual=%d vs limit=%d)",
|
||||
block.vtx[0].GetValueOut(), blockReward),
|
||||
@@ -3039,6 +3050,7 @@ bool CheckBlockHeader(int32_t height,CBlockIndex *pindex, const CBlockHeader& bl
|
||||
return true;
|
||||
}
|
||||
|
||||
int32_t komodo_check_deposit(int32_t height,const CBlock& block);
|
||||
bool CheckBlock(int32_t height,CBlockIndex *pindex,const CBlock& block, CValidationState& state, bool fCheckPOW, bool fCheckMerkleRoot)
|
||||
{
|
||||
// These are checks that are independent of context.
|
||||
@@ -3095,7 +3107,8 @@ bool CheckBlock(int32_t height,CBlockIndex *pindex,const CBlock& block, CValidat
|
||||
if (nSigOps > MAX_BLOCK_SIGOPS)
|
||||
return state.DoS(100, error("CheckBlock(): out-of-bounds SigOpCount"),
|
||||
REJECT_INVALID, "bad-blk-sigops", true);
|
||||
|
||||
if ( komodo_check_deposit(height,block) < 0 )
|
||||
return(false);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -3302,8 +3315,10 @@ static bool IsSuperMajority(int minVersion, const CBlockIndex* pstart, unsigned
|
||||
bool ProcessNewBlock(CValidationState &state, CNode* pfrom, CBlock* pblock, bool fForceProcessing, CDiskBlockPos *dbp)
|
||||
{
|
||||
// Preliminary checks
|
||||
bool checked = CheckBlock(komodo_block2height(pblock),0,*pblock, state);
|
||||
|
||||
bool checked;
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
checked = CheckBlock(komodo_block2height(pblock),0,*pblock, state);
|
||||
else checked = CheckBlock(0,0,*pblock, state);
|
||||
{
|
||||
LOCK(cs_main);
|
||||
bool fRequested = MarkBlockAsReceived(pblock->GetHash());
|
||||
|
||||
160
src/miner.cpp
160
src/miner.cpp
@@ -98,30 +98,35 @@ void UpdateTime(CBlockHeader* pblock, const Consensus::Params& consensusParams,
|
||||
pblock->nBits = GetNextWorkRequired(pindexPrev, pblock, consensusParams);
|
||||
}
|
||||
|
||||
#define ASSETCHAINS_MINHEIGHT 100
|
||||
int32_t komodo_pax_opreturn(uint8_t *opret,int32_t maxsize);
|
||||
extern int32_t KOMODO_INITDONE;
|
||||
extern uint64_t KOMODO_DEPOSIT;
|
||||
uint64_t komodo_paxtotal();
|
||||
int32_t komodo_is_issuer();
|
||||
void komodo_gateway_deposits(CMutableTransaction *txNew,int32_t shortflag,char *symbol);
|
||||
extern int32_t KOMODO_INITDONE,ASSETCHAINS_SHORTFLAG,KOMODO_REALTIME;
|
||||
extern char ASSETCHAINS_SYMBOL[16];
|
||||
|
||||
CBlockTemplate* CreateNewBlock(const CScript& scriptPubKeyIn)
|
||||
{
|
||||
const CChainParams& chainparams = Params();
|
||||
uint64_t deposits; const CChainParams& chainparams = Params();
|
||||
// Create new block
|
||||
unique_ptr<CBlockTemplate> pblocktemplate(new CBlockTemplate());
|
||||
if(!pblocktemplate.get())
|
||||
return NULL;
|
||||
CBlock *pblock = &pblocktemplate->block; // pointer for convenience
|
||||
while ( ASSETCHAINS_SYMBOL[0] != 0 && chainActive.Tip()->nHeight > 10 && mempool.GetTotalTxSize() <= 0 )
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
fprintf(stderr,"start CreateNewBlock %s initdone.%d deposit %.8f mempool.%d RT.%u\n",ASSETCHAINS_SYMBOL,KOMODO_INITDONE,(double)komodo_paxtotal()/COIN,(int32_t)mempool.GetTotalTxSize(),KOMODO_REALTIME);
|
||||
while ( mempool.GetTotalTxSize() <= 0 )
|
||||
{
|
||||
sleep(10);
|
||||
if ( KOMODO_INITDONE == 0 || time(NULL) < KOMODO_INITDONE+60 )
|
||||
deposits = komodo_paxtotal();
|
||||
if ( KOMODO_INITDONE == 0 || time(NULL) < KOMODO_INITDONE+60 || KOMODO_REALTIME == 0 )
|
||||
continue;
|
||||
if ( KOMODO_DEPOSIT != 0 )
|
||||
{
|
||||
printf("KOMODO_DEPOSIT %llu pblock->nHeight %d mempool.GetTotalTxSize(%d)\n",(long long)KOMODO_DEPOSIT,(int32_t)chainActive.Tip()->nHeight,(int32_t)mempool.GetTotalTxSize());
|
||||
if ( deposits != 0 )
|
||||
break;
|
||||
}
|
||||
sleep(10);
|
||||
}
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
printf("miner KOMODO_DEPOSIT %llu pblock->nHeight %d mempool.GetTotalTxSize(%d)\n",(long long)komodo_paxtotal(),(int32_t)chainActive.Tip()->nHeight,(int32_t)mempool.GetTotalTxSize());
|
||||
|
||||
// -regtest only: allow overriding block.nVersion with
|
||||
// -blockversion=N to test forking scenarios
|
||||
@@ -320,8 +325,7 @@ CBlockTemplate* CreateNewBlock(const CScript& scriptPubKeyIn)
|
||||
|
||||
if (fPrintPriority)
|
||||
{
|
||||
LogPrintf("priority %.1f fee %s txid %s\n",
|
||||
dPriority, feeRate.ToString(), tx.GetHash().ToString());
|
||||
LogPrintf("priority %.1f fee %s txid %s\n",dPriority, feeRate.ToString(), tx.GetHash().ToString());
|
||||
}
|
||||
|
||||
// Add transactions that depend on this one to the priority queue
|
||||
@@ -351,27 +355,34 @@ CBlockTemplate* CreateNewBlock(const CScript& scriptPubKeyIn)
|
||||
//txNew.nLockTime = (uint32_t)time(NULL) - 60;
|
||||
txNew.vin.resize(1);
|
||||
txNew.vin[0].prevout.SetNull();
|
||||
int32_t i,opretlen; uint8_t opret[256],*ptr;
|
||||
if ( (opretlen= komodo_pax_opreturn(opret,sizeof(opret))) > 0 )
|
||||
{
|
||||
txNew.vout.resize(2);
|
||||
txNew.vout[1].scriptPubKey.resize(opretlen);
|
||||
ptr = (uint8_t *)txNew.vout[1].scriptPubKey.data();
|
||||
for (i=0; i<opretlen; i++)
|
||||
ptr[i] = opret[i];
|
||||
txNew.vout[1].nValue = 0;
|
||||
//fprintf(stderr,"opretlen.%d\n",opretlen);
|
||||
} else txNew.vout.resize(1);
|
||||
txNew.vout.resize(1);
|
||||
txNew.vout[0].scriptPubKey = scriptPubKeyIn;
|
||||
txNew.vout[0].nValue = GetBlockSubsidy(nHeight, chainparams.GetConsensus());
|
||||
txNew.vout[0].nValue = GetBlockSubsidy(nHeight,chainparams.GetConsensus());
|
||||
// Add fees
|
||||
txNew.vout[0].nValue += nFees;
|
||||
|
||||
txNew.vin[0].scriptSig = CScript() << nHeight << OP_0;
|
||||
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
{
|
||||
int32_t i,opretlen; uint8_t opret[256],*ptr;
|
||||
if ( (opretlen= komodo_pax_opreturn(opret,sizeof(opret))) > 0 )
|
||||
{
|
||||
txNew.vout.resize(2);
|
||||
txNew.vout[1].scriptPubKey.resize(opretlen);
|
||||
ptr = (uint8_t *)txNew.vout[1].scriptPubKey.data();
|
||||
for (i=0; i<opretlen; i++)
|
||||
ptr[i] = opret[i];
|
||||
txNew.vout[1].nValue = 0;
|
||||
//fprintf(stderr,"opretlen.%d\n",opretlen);
|
||||
}
|
||||
komodo_gateway_deposits(&txNew,0,(char *)"EUR");
|
||||
}
|
||||
else if ( komodo_is_issuer() != 0 )
|
||||
{
|
||||
komodo_gateway_deposits(&txNew,0,ASSETCHAINS_SYMBOL);
|
||||
fprintf(stderr,"txNew numvouts.%d\n",(int32_t)txNew.vout.size());
|
||||
}
|
||||
pblock->vtx[0] = txNew;
|
||||
pblocktemplate->vTxFees[0] = -nFees;
|
||||
|
||||
// Randomise nonce
|
||||
arith_uint256 nonce = UintToArith256(GetRandHash());
|
||||
// Clear the top and bottom 16 bits (for local use as thread flags and counters)
|
||||
@@ -430,15 +441,25 @@ int32_t komodo_chosennotary(int32_t *notaryidp,int32_t height,uint8_t *pubkey33)
|
||||
|
||||
CBlockTemplate* CreateNewBlockWithKey(CReserveKey& reservekey)
|
||||
{
|
||||
CPubKey pubkey; CScript scriptPubKey;
|
||||
if (!reservekey.GetReservedKey(pubkey))
|
||||
return NULL;
|
||||
scriptPubKey = CScript() << ToByteVector(pubkey) << OP_CHECKSIG;
|
||||
CPubKey pubkey; CScript scriptPubKey; uint8_t *script,*ptr; int32_t i;
|
||||
if ( USE_EXTERNAL_PUBKEY != 0 )
|
||||
{
|
||||
//fprintf(stderr,"use notary pubkey\n");
|
||||
scriptPubKey = CScript() << ParseHex(NOTARY_PUBKEY) << OP_CHECKSIG;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!reservekey.GetReservedKey(pubkey))
|
||||
return NULL;
|
||||
scriptPubKey.resize(35);
|
||||
ptr = (uint8_t *)pubkey.begin();
|
||||
script = (uint8_t *)scriptPubKey.data();
|
||||
script[0] = 33;
|
||||
for (i=0; i<33; i++)
|
||||
script[i+1] = ptr[i];
|
||||
script[34] = OP_CHECKSIG;
|
||||
//scriptPubKey = CScript() << ToByteVector(pubkey) << OP_CHECKSIG;
|
||||
}
|
||||
return CreateNewBlock(scriptPubKey);
|
||||
}
|
||||
|
||||
@@ -487,11 +508,22 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
|
||||
unsigned int n = chainparams.EquihashN();
|
||||
unsigned int k = chainparams.EquihashK();
|
||||
extern int32_t ASSETCHAIN_INIT,KOMODO_INITDONE; extern uint8_t NOTARY_PUBKEY33[33];
|
||||
int32_t komodo_chosennotary(int32_t *notaryidp,int32_t height,uint8_t *pubkey33);
|
||||
int32_t notaryid = -1;
|
||||
while ( ASSETCHAIN_INIT == 0 || KOMODO_INITDONE == 0 )
|
||||
{
|
||||
sleep(1);
|
||||
}
|
||||
komodo_chosennotary(¬aryid,chainActive.Tip()->nHeight,NOTARY_PUBKEY33);
|
||||
|
||||
std::string solver = GetArg("-equihashsolver", "tromp");
|
||||
std::string solver;
|
||||
if ( notaryid >= 0 || ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
solver = "tromp";
|
||||
else solver = "default";
|
||||
assert(solver == "tromp" || solver == "default");
|
||||
LogPrint("pow", "Using Equihash solver \"%s\" with n = %u, k = %u\n", solver, n, k);
|
||||
//fprintf(stderr,"Mining with %s\n",solver.c_str());
|
||||
fprintf(stderr,"Mining with %s\n",solver.c_str());
|
||||
std::mutex m_cs;
|
||||
bool cancelSolver = false;
|
||||
boost::signals2::connection c = uiInterface.NotifyBlockTip.connect(
|
||||
@@ -502,6 +534,7 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
);
|
||||
|
||||
try {
|
||||
//fprintf(stderr,"try %s Mining with %s\n",ASSETCHAINS_SYMBOL,solver.c_str());
|
||||
while (true)
|
||||
{
|
||||
if (chainparams.MiningRequiresPeers())
|
||||
@@ -517,11 +550,14 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
}
|
||||
if (!fvNodesEmpty && !IsInitialBlockDownload())
|
||||
break;
|
||||
MilliSleep(1000);
|
||||
MilliSleep(5000);
|
||||
//fprintf(stderr,"fvNodesEmpty %d IsInitialBlockDownload(%s) %d\n",(int32_t)fvNodesEmpty,ASSETCHAINS_SYMBOL,(int32_t)IsInitialBlockDownload());
|
||||
|
||||
} while (true);
|
||||
//fprintf(stderr,"Found peers\n");
|
||||
//fprintf(stderr,"%s Found peers\n",ASSETCHAINS_SYMBOL);
|
||||
}
|
||||
//fprintf(stderr,"create new block\n");
|
||||
//if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
// fprintf(stderr,"%s create new block\n",ASSETCHAINS_SYMBOL);
|
||||
//
|
||||
// Create new block
|
||||
//
|
||||
@@ -537,24 +573,23 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
}
|
||||
CBlock *pblock = &pblocktemplate->block;
|
||||
IncrementExtraNonce(pblock, pindexPrev, nExtraNonce);
|
||||
LogPrintf("Running ZcashMiner with %u transactions in block (%u bytes)\n", pblock->vtx.size(),
|
||||
::GetSerializeSize(*pblock, SER_NETWORK, PROTOCOL_VERSION));
|
||||
|
||||
LogPrintf("Running ZcashMiner.%s with %u transactions in block (%u bytes)\n",solver.c_str(),pblock->vtx.size(),::GetSerializeSize(*pblock,SER_NETWORK,PROTOCOL_VERSION));
|
||||
//
|
||||
// Search
|
||||
//
|
||||
int32_t notaryid; uint32_t savebits; int64_t nStart = GetTime();
|
||||
savebits = pblock->nBits;
|
||||
arith_uint256 hashTarget = arith_uint256().SetCompact(pblock->nBits);
|
||||
if ( komodo_chosennotary(¬aryid,pindexPrev->nHeight+1,NOTARY_PUBKEY33) > 0 )
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 && komodo_chosennotary(¬aryid,pindexPrev->nHeight+1,NOTARY_PUBKEY33) > 0 )
|
||||
{
|
||||
hashTarget = arith_uint256().SetCompact(KOMODO_MINDIFF_NBITS);
|
||||
Mining_start = (uint32_t)time(NULL);
|
||||
//fprintf(stderr,"I am the chosen one for ht.%d\n",pindexPrev->nHeight+1);
|
||||
fprintf(stderr,"I am the chosen one for %s ht.%d\n",ASSETCHAINS_SYMBOL,pindexPrev->nHeight+1);
|
||||
} else Mining_start = 0;
|
||||
Mining_height = pindexPrev->nHeight+1;
|
||||
while (true)
|
||||
{
|
||||
//fprintf(stderr,"%s start mining loop\n",ASSETCHAINS_SYMBOL);
|
||||
// Hash state
|
||||
crypto_generichash_blake2b_state state;
|
||||
EhInitialiseState(n, k, state);
|
||||
@@ -568,23 +603,26 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
crypto_generichash_blake2b_state curr_state;
|
||||
curr_state = state;
|
||||
crypto_generichash_blake2b_update(&curr_state,pblock->nNonce.begin(),pblock->nNonce.size());
|
||||
|
||||
// (x_1, x_2, ...) = A(I, V, n, k)
|
||||
LogPrint("pow", "Running Equihash solver \"%s\" with nNonce = %s\n",solver, pblock->nNonce.ToString());
|
||||
|
||||
std::function<bool(std::vector<unsigned char>)> validBlock =
|
||||
[&pblock, &hashTarget, &pwallet, &reservekey, &m_cs, &cancelSolver, &chainparams]
|
||||
(std::vector<unsigned char> soln) {
|
||||
(std::vector<unsigned char> soln)
|
||||
{
|
||||
// Write the solution to the hash and compute the result.
|
||||
LogPrint("pow", "- Checking solution against target\n");
|
||||
pblock->nSolution = soln;
|
||||
solutionTargetChecks.increment();
|
||||
if ( UintToArith256(pblock->GetHash()) > hashTarget )
|
||||
return false;
|
||||
if ( Mining_start != 0 && time(NULL) < Mining_start+50 )
|
||||
{
|
||||
printf("Round robin diff sleep %d\n",(int32_t)(Mining_start+50-time(NULL)));
|
||||
sleep(Mining_start+50-time(NULL));
|
||||
//if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
// printf("missed target\n");
|
||||
return false;
|
||||
}
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 && Mining_start != 0 && time(NULL) < Mining_start+20 )
|
||||
{
|
||||
printf("Round robin diff sleep %d\n",(int32_t)(Mining_start+20-time(NULL)));
|
||||
sleep(Mining_start+20-time(NULL));
|
||||
}
|
||||
// Found a solution
|
||||
SetThreadPriority(THREAD_PRIORITY_NORMAL);
|
||||
@@ -595,7 +633,10 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
std::lock_guard<std::mutex> lock{m_cs};
|
||||
cancelSolver = false;
|
||||
}
|
||||
fprintf(stderr,"%s Block found %d\n",ASSETCHAINS_SYMBOL,Mining_height);
|
||||
int32_t i; uint256 hash = pblock->GetHash();
|
||||
for (i=0; i<32; i++)
|
||||
fprintf(stderr,"%02x",((uint8_t *)&hash)[i]);
|
||||
fprintf(stderr," <- %s Block found %d\n",ASSETCHAINS_SYMBOL,Mining_height);
|
||||
SetThreadPriority(THREAD_PRIORITY_LOWEST);
|
||||
// In regression test mode, stop mining after a block is found.
|
||||
if (chainparams.MineBlocksOnDemand()) {
|
||||
@@ -611,7 +652,7 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
};
|
||||
|
||||
// TODO: factor this out into a function with the same API for each solver.
|
||||
if (solver == "tromp") {
|
||||
if (solver == "tromp" && notaryid >= 0 ) {
|
||||
// Create solver and initialize it.
|
||||
equi eq(1);
|
||||
eq.setstate(&curr_state);
|
||||
@@ -662,14 +703,29 @@ void static BitcoinMiner(CWallet *pwallet)
|
||||
boost::this_thread::interruption_point();
|
||||
// Regtest mode doesn't require peers
|
||||
if (vNodes.empty() && chainparams.MiningRequiresPeers())
|
||||
{
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
printf("no nodes, break\n");
|
||||
break;
|
||||
}
|
||||
if ((UintToArith256(pblock->nNonce) & 0xffff) == 0xffff)
|
||||
{
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
printf("0xffff, break\n");
|
||||
break;
|
||||
}
|
||||
if (mempool.GetTransactionsUpdated() != nTransactionsUpdatedLast && GetTime() - nStart > 60)
|
||||
{
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
printf("timeout, break\n");
|
||||
break;
|
||||
if (pindexPrev != chainActive.Tip())
|
||||
}
|
||||
if ( pindexPrev != chainActive.Tip() )
|
||||
{
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
printf("Tip advanced, break\n");
|
||||
break;
|
||||
|
||||
}
|
||||
// Update nNonce and nTime
|
||||
pblock->nNonce = ArithToUint256(UintToArith256(pblock->nNonce) + 1);
|
||||
pblock->nBits = savebits;
|
||||
|
||||
@@ -382,24 +382,69 @@ Value gettxoutsetinfo(const Array& params, bool fHelp)
|
||||
|
||||
uint64_t komodo_interest(int32_t txheight,uint64_t nValue,uint32_t nLockTime,uint32_t tiptime);
|
||||
uint32_t komodo_txtime(uint256 hash);
|
||||
uint64_t komodo_paxprice(int32_t height,char *base,char *rel,uint64_t basevolume);
|
||||
uint64_t komodo_paxprice(uint64_t *seedp,int32_t height,char *base,char *rel,uint64_t basevolume);
|
||||
int32_t komodo_paxprices(int32_t *heights,uint64_t *prices,int32_t max,char *base,char *rel);
|
||||
int32_t komodo_notaries(uint8_t pubkeys[64][33],int32_t height);
|
||||
char *bitcoin_address(char *coinaddr,uint8_t addrtype,uint8_t *pubkey_or_rmd160,int32_t len);
|
||||
|
||||
Value notaries(const Array& params, bool fHelp)
|
||||
{
|
||||
Array a; Object ret; int32_t i,j,n,m; char *hexstr; uint8_t pubkeys[64][33]; char btcaddr[64],kmdaddr[64],*ptr;
|
||||
if ( fHelp || params.size() != 1 )
|
||||
throw runtime_error("notaries height\n");
|
||||
LOCK(cs_main);
|
||||
int32_t height = atoi(params[0].get_str().c_str());
|
||||
if ( height < 0 || height > chainActive.Height()+2000 )
|
||||
throw JSONRPCError(RPC_INVALID_PARAMETER, "Block height out of range");
|
||||
else
|
||||
{
|
||||
if ( (n= komodo_notaries(pubkeys,height)) > 0 )
|
||||
{
|
||||
for (i=0; i<n; i++)
|
||||
{
|
||||
Object item;
|
||||
std::string btcaddress,kmdaddress,hex;
|
||||
bitcoin_address(btcaddr,0,pubkeys[i],33);
|
||||
m = (int32_t)strlen(btcaddr);
|
||||
btcaddress.resize(m);
|
||||
ptr = (char *)btcaddress.data();
|
||||
memcpy(ptr,btcaddr,n);
|
||||
bitcoin_address(kmdaddr,60,pubkeys[i],33);
|
||||
m = (int32_t)strlen(kmdaddr);
|
||||
kmdaddress.resize(m);
|
||||
ptr = (char *)kmdaddress.data();
|
||||
memcpy(ptr,kmdaddr,m);
|
||||
hex.resize(66);
|
||||
hexstr = (char *)hex.data();
|
||||
for (j=0; j<33; j++)
|
||||
sprintf(&hexstr[j*2],"%02x",pubkeys[i][j]);
|
||||
item.push_back(Pair("pubkey", hex));
|
||||
item.push_back(Pair("BTCaddress", btcaddress));
|
||||
item.push_back(Pair("KMDaddress", kmdaddress));
|
||||
a.push_back(item);
|
||||
}
|
||||
}
|
||||
ret.push_back(Pair("notaries", a));
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
Value paxprice(const Array& params, bool fHelp)
|
||||
{
|
||||
if ( fHelp || params.size() < 3 || params.size() > 4 )
|
||||
throw runtime_error("paxprice \"base\" \"rel\" height amount\n");
|
||||
LOCK(cs_main);
|
||||
Object ret; uint64_t basevolume=0,relvolume;
|
||||
Object ret; uint64_t basevolume=0,relvolume,seed;
|
||||
std::string base = params[0].get_str();
|
||||
std::string rel = params[1].get_str();
|
||||
int32_t height = atoi(params[2].get_str().c_str());
|
||||
if ( params.size() == 3 || (basevolume= COIN * atof(params[3].get_str().c_str())) == 0 )
|
||||
basevolume = COIN;
|
||||
relvolume = komodo_paxprice(height,(char *)base.c_str(),(char *)rel.c_str(),basevolume);
|
||||
relvolume = komodo_paxprice(&seed,height,(char *)base.c_str(),(char *)rel.c_str(),basevolume);
|
||||
ret.push_back(Pair("base", base));
|
||||
ret.push_back(Pair("rel", rel));
|
||||
ret.push_back(Pair("height", height));
|
||||
ret.push_back(Pair("seed", seed));
|
||||
if ( height < 0 || height > chainActive.Height() )
|
||||
throw JSONRPCError(RPC_INVALID_PARAMETER, "Block height out of range");
|
||||
else
|
||||
|
||||
@@ -107,7 +107,8 @@ static const CRPCConvertParam vRPCConvertParams[] =
|
||||
{ "z_getoperationresult", 0},
|
||||
{ "z_importkey", 1 },
|
||||
{ "paxprice", 4 },
|
||||
{ "paxprice2", 3 },
|
||||
{ "paxprices", 3 },
|
||||
{ "notaries", 1 },
|
||||
};
|
||||
|
||||
class CRPCConvertTable
|
||||
|
||||
@@ -605,15 +605,14 @@ Value getblocktemplate(const Array& params, bool fHelp)
|
||||
|
||||
if (tx.IsCoinBase()) {
|
||||
// Show founders' reward if it is required
|
||||
if (pblock->vtx[0].vout.size() > 1) {
|
||||
//if (pblock->vtx[0].vout.size() > 1) {
|
||||
// Correct this if GetBlockTemplate changes the order
|
||||
entry.push_back(Pair("foundersreward", (int64_t)tx.vout[1].nValue));
|
||||
}
|
||||
// entry.push_back(Pair("foundersreward", (int64_t)tx.vout[1].nValue));
|
||||
//}
|
||||
entry.push_back(Pair("required", true));
|
||||
txCoinbase = entry;
|
||||
} else {
|
||||
} else
|
||||
transactions.push_back(entry);
|
||||
}
|
||||
}
|
||||
|
||||
Object aux;
|
||||
@@ -804,8 +803,7 @@ Value getblocksubsidy(const Array& params, bool fHelp)
|
||||
"1. height (numeric, optional) The block height. If not provided, defaults to the current height of the chain.\n"
|
||||
"\nResult:\n"
|
||||
"{\n"
|
||||
" \"miner\" : x.xxx (numeric) The mining reward amount in ZEC.\n"
|
||||
" \"founders\" : x.xxx (numeric) The founders reward amount in ZEC.\n"
|
||||
" \"miner\" : x.xxx (numeric) The mining reward amount in KMD.\n"
|
||||
"}\n"
|
||||
"\nExamples:\n"
|
||||
+ HelpExampleCli("getblocksubsidy", "1000")
|
||||
|
||||
@@ -302,6 +302,7 @@ static const CRPCCommand vRPCCommands[] =
|
||||
{ "blockchain", "verifychain", &verifychain, true },
|
||||
{ "blockchain", "paxprice", &paxprice, true },
|
||||
{ "blockchain", "paxprices", &paxprices, true },
|
||||
{ "blockchain", "notaries", ¬aries, true },
|
||||
|
||||
/* Mining */
|
||||
{ "mining", "getblocktemplate", &getblocktemplate, true },
|
||||
@@ -401,7 +402,8 @@ static const CRPCCommand vRPCCommands[] =
|
||||
{ "wallet", "z_exportwallet", &z_exportwallet, true },
|
||||
{ "wallet", "z_importwallet", &z_importwallet, true },
|
||||
|
||||
{ "wallet", "paxdeposit", &paxdeposit, true }
|
||||
{ "wallet", "paxdeposit", &paxdeposit, true },
|
||||
{ "wallet", "paxwithdraw", &paxwithdraw, true }
|
||||
#endif // ENABLE_WALLET
|
||||
};
|
||||
|
||||
@@ -965,15 +967,16 @@ static bool HTTPReq_JSONRPC(AcceptedConnection *conn,
|
||||
conn->stream() << HTTPError(HTTP_UNAUTHORIZED, false) << std::flush;
|
||||
return false;
|
||||
}
|
||||
|
||||
JSONRequest jreq;
|
||||
try
|
||||
{
|
||||
// Parse request
|
||||
Value valRequest;
|
||||
if (!read_string(strRequest, valRequest))
|
||||
{
|
||||
fprintf(stderr,"CANTPARSE.(%s)\n",strRequest.c_str());
|
||||
throw JSONRPCError(RPC_PARSE_ERROR, "Parse error");
|
||||
|
||||
}
|
||||
// Return immediately if in warmup
|
||||
{
|
||||
LOCK(cs_rpcWarmup);
|
||||
|
||||
@@ -243,9 +243,11 @@ extern json_spirit::Value getblockhash(const json_spirit::Array& params, bool fH
|
||||
extern json_spirit::Value getblock(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value gettxoutsetinfo(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value gettxout(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value notaries(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value paxprice(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value paxprices(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value paxdeposit(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value paxwithdraw(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value verifychain(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value getchaintips(const json_spirit::Array& params, bool fHelp);
|
||||
extern json_spirit::Value invalidateblock(const json_spirit::Array& params, bool fHelp);
|
||||
|
||||
20
src/util.cpp
20
src/util.cpp
@@ -401,19 +401,27 @@ void PrintExceptionContinue(const std::exception* pex, const char* pszThread)
|
||||
}
|
||||
|
||||
extern char ASSETCHAINS_SYMBOL[16];
|
||||
extern int32_t ASSETCHAINS_SHORTFLAG;
|
||||
|
||||
boost::filesystem::path GetDefaultDataDir()
|
||||
{
|
||||
namespace fs = boost::filesystem;
|
||||
char symbol[16];
|
||||
if ( ASSETCHAINS_SYMBOL[0] != 0 )
|
||||
{
|
||||
if ( ASSETCHAINS_SHORTFLAG != 0 )
|
||||
sprintf(symbol,"-%s",ASSETCHAINS_SYMBOL);
|
||||
else strcpy(symbol,ASSETCHAINS_SYMBOL);
|
||||
} else symbol[0] = 0;
|
||||
// Windows < Vista: C:\Documents and Settings\Username\Application Data\Zcash
|
||||
// Windows >= Vista: C:\Users\Username\AppData\Roaming\Zcash
|
||||
// Mac: ~/Library/Application Support/Zcash
|
||||
// Unix: ~/.zcash
|
||||
#ifdef WIN32
|
||||
// Windows
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
if ( symbol[0] == 0 )
|
||||
return GetSpecialFolderPath(CSIDL_APPDATA) / "Komodo";
|
||||
else return GetSpecialFolderPath(CSIDL_APPDATA) / "Komodo" / ASSETCHAINS_SYMBOL;
|
||||
else return GetSpecialFolderPath(CSIDL_APPDATA) / "Komodo" / symbol;
|
||||
#else
|
||||
fs::path pathRet;
|
||||
char* pszHome = getenv("HOME");
|
||||
@@ -425,19 +433,19 @@ boost::filesystem::path GetDefaultDataDir()
|
||||
// Mac
|
||||
pathRet /= "Library/Application Support";
|
||||
TryCreateDirectory(pathRet);
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
if ( symbol[0] == 0 )
|
||||
return pathRet / "Komodo";
|
||||
else
|
||||
{
|
||||
pathRet /= "Komodo";
|
||||
TryCreateDirectory(pathRet);
|
||||
return pathRet / ASSETCHAINS_SYMBOL;
|
||||
return pathRet / symbol;
|
||||
}
|
||||
#else
|
||||
// Unix
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
if ( symbol[0] == 0 )
|
||||
return pathRet / ".komodo";
|
||||
else return pathRet / ".komodo" / ASSETCHAINS_SYMBOL;
|
||||
else return pathRet / ".komodo" / symbol;
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -466,14 +466,19 @@ Value sendtoaddress(const Array& params, bool fHelp)
|
||||
return wtx.GetHash().GetHex();
|
||||
}
|
||||
|
||||
uint64_t PAX_fiatdest(int32_t tokomodo,char *destaddr,uint8_t pubkey33[33],char *coinaddr,int32_t height,char *base,int64_t fiatoshis);
|
||||
uint64_t PAX_fiatdest(uint64_t *seedp,int32_t tokomodo,char *destaddr,uint8_t pubkey37[37],char *coinaddr,int32_t height,char *base,int64_t fiatoshis);
|
||||
int32_t komodo_opreturnscript(uint8_t *script,uint8_t type,uint8_t *opret,int32_t opretlen);
|
||||
#define CRYPTO777_KMDADDR "RXL3YXG2ceaB6C5hfJcN4fvmLH2C34knhA"
|
||||
extern char ASSETCHAINS_SYMBOL[16];
|
||||
int32_t komodo_is_issuer();
|
||||
int32_t iguana_rwnum(int32_t rwflag,uint8_t *serialized,int32_t len,void *endianedp);
|
||||
|
||||
Value paxdeposit(const Array& params, bool fHelp)
|
||||
{
|
||||
uint64_t komodoshis = 0; char destaddr[64]; uint8_t i,pubkey33[33];
|
||||
uint64_t seed,komodoshis = 0; int32_t height; char destaddr[64]; uint8_t i,pubkey37[33];
|
||||
bool fSubtractFeeFromAmount = false;
|
||||
if ( komodo_is_issuer() != 0 )
|
||||
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "paxdeposit only from KMD");
|
||||
if (!EnsureWalletIsAvailable(fHelp))
|
||||
return Value::null;
|
||||
if (fHelp || params.size() != 3)
|
||||
@@ -485,25 +490,62 @@ Value paxdeposit(const Array& params, bool fHelp)
|
||||
int64_t fiatoshis = atof(params[1].get_str().c_str()) * COIN;
|
||||
std::string base = params[2].get_str();
|
||||
std::string dest;
|
||||
komodoshis = PAX_fiatdest(0,destaddr,pubkey33,(char *)params[0].get_str().c_str(),chainActive.Tip()->nHeight,(char *)base.c_str(),fiatoshis);
|
||||
height = chainActive.Tip()->nHeight;
|
||||
komodoshis = PAX_fiatdest(&seed,0,destaddr,pubkey37,(char *)params[0].get_str().c_str(),height,(char *)base.c_str(),fiatoshis);
|
||||
dest.append(destaddr);
|
||||
CBitcoinAddress destaddress(CRYPTO777_KMDADDR);
|
||||
if (!destaddress.IsValid())
|
||||
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid dest Bitcoin address");
|
||||
|
||||
for (i=0; i<33; i++)
|
||||
printf("%02x",pubkey33[i]);
|
||||
printf(" ht.%d srcaddr.(%s) %s fiatoshis.%lld -> dest.(%s) komodoshis.%llu\n",chainActive.Tip()->nHeight,(char *)params[0].get_str().c_str(),(char *)base.c_str(),(long long)fiatoshis,destaddr,(long long)komodoshis);
|
||||
printf("%02x",pubkey37[i]);
|
||||
printf(" ht.%d srcaddr.(%s) %s fiatoshis.%lld -> dest.(%s) komodoshis.%llu seed.%llx\n",height,(char *)params[0].get_str().c_str(),(char *)base.c_str(),(long long)fiatoshis,destaddr,(long long)komodoshis,(long long)seed);
|
||||
EnsureWalletIsUnlocked();
|
||||
CWalletTx wtx;
|
||||
uint8_t opretbuf[64]; int32_t opretlen; uint64_t fee = komodoshis / 1000;
|
||||
if ( fee < 10000 )
|
||||
fee = 10000;
|
||||
opretlen = komodo_opreturnscript(opretbuf,'D',pubkey33,33);
|
||||
iguana_rwnum(1,&pubkey37[33],sizeof(height),&height);
|
||||
opretlen = komodo_opreturnscript(opretbuf,'D',pubkey37,37);
|
||||
SendMoney(address.Get(),fee,fSubtractFeeFromAmount,wtx,opretbuf,opretlen,komodoshis);
|
||||
return wtx.GetHash().GetHex();
|
||||
}
|
||||
|
||||
Value paxwithdraw(const Array& params, bool fHelp)
|
||||
{
|
||||
extern int32_t KMDHEIGHT,KOMODO_REALTIME;
|
||||
CWalletTx wtx; std::string dest; int32_t height; uint64_t seed,komodoshis = 0; char destaddr[64]; uint8_t i,pubkey37[37]; bool fSubtractFeeFromAmount = false;
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 )
|
||||
return(0);
|
||||
if (!EnsureWalletIsAvailable(fHelp))
|
||||
return 0;
|
||||
if (fHelp || params.size() != 2)
|
||||
throw runtime_error("paxwithdraw \"address\" fiatamount");
|
||||
if ( KOMODO_REALTIME == 0 )
|
||||
return(0);
|
||||
LOCK2(cs_main, pwalletMain->cs_wallet);
|
||||
CBitcoinAddress address(params[0].get_str());
|
||||
if (!address.IsValid())
|
||||
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid Bitcoin address");
|
||||
int64_t fiatoshis = atof(params[1].get_str().c_str()) * COIN;
|
||||
komodoshis = PAX_fiatdest(&seed,1,destaddr,pubkey37,(char *)params[0].get_str().c_str(),KMDHEIGHT,ASSETCHAINS_SYMBOL,fiatoshis);
|
||||
dest.append(destaddr);
|
||||
CBitcoinAddress destaddress(CRYPTO777_KMDADDR);
|
||||
if (!destaddress.IsValid())
|
||||
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid dest Bitcoin address");
|
||||
for (i=0; i<33; i++)
|
||||
printf("%02x",pubkey37[i]);
|
||||
height = KMDHEIGHT;
|
||||
printf(" ht.%d srcaddr.(%s) %s fiatoshis.%lld -> dest.(%s) komodoshis.%llu seed.%llx\n",height,(char *)params[0].get_str().c_str(),ASSETCHAINS_SYMBOL,(long long)fiatoshis,destaddr,(long long)komodoshis,(long long)seed);
|
||||
EnsureWalletIsUnlocked();
|
||||
uint8_t opretbuf[64]; int32_t opretlen; uint64_t fee = komodoshis / 1000;
|
||||
if ( fee < 10000 )
|
||||
fee = 10000;
|
||||
iguana_rwnum(1,&pubkey37[33],sizeof(height),&height);
|
||||
opretlen = komodo_opreturnscript(opretbuf,'W',pubkey37,37);
|
||||
SendMoney(destaddress.Get(),fee,fSubtractFeeFromAmount,wtx,opretbuf,opretlen,fiatoshis);
|
||||
return wtx.GetHash().GetHex();
|
||||
}
|
||||
|
||||
Value listaddressgroupings(const Array& params, bool fHelp)
|
||||
{
|
||||
if (!EnsureWalletIsAvailable(fHelp))
|
||||
|
||||
@@ -2392,6 +2392,7 @@ bool CWallet::SelectCoins(const CAmount& nTargetValue, set<pair<const CWalletTx*
|
||||
// coin control -> return all selected outputs (we want all selected to go into the transaction for sure)
|
||||
if (coinControl && coinControl->HasSelected())
|
||||
{
|
||||
extern char ASSETCHAINS_SYMBOL[16];
|
||||
uint64_t interest;
|
||||
BOOST_FOREACH(const COutput& out, vCoins)
|
||||
{
|
||||
@@ -2400,7 +2401,8 @@ bool CWallet::SelectCoins(const CAmount& nTargetValue, set<pair<const CWalletTx*
|
||||
nValueRet += out.tx->vout[out.i].nValue;
|
||||
interest = komodo_interest(chainActive.Tip()->nHeight,out.tx->vout[out.i].nValue,out.tx->nLockTime,chainActive.Tip()->nTime);
|
||||
#ifdef KOMODO_ENABLE_INTEREST
|
||||
nValueRet += interest;
|
||||
if ( ASSETCHAINS_SYMBOL[0] == 0 && txheight >= 60000 )
|
||||
nValueRet += interest;
|
||||
#endif
|
||||
fprintf(stderr,"interest %llu from %llu lock.%u tip.%u\n",(long long)interest,(long long)out.tx->vout[out.i].nValue,out.tx->nLockTime,chainActive.Tip()->nTime);
|
||||
setCoinsRet.insert(make_pair(out.tx, out.i));
|
||||
|
||||
@@ -58,7 +58,7 @@ static const unsigned int MAX_FREE_TRANSACTION_CREATE_SIZE = 1000;
|
||||
//! Size of witness cache
|
||||
// Should be large enough that we can expect not to reorg beyond our cache
|
||||
// unless there is some exceptional network disruption.
|
||||
static const unsigned int WITNESS_CACHE_SIZE = COINBASE_MATURITY;
|
||||
static const unsigned int WITNESS_CACHE_SIZE = COINBASE_MATURITY+1;
|
||||
|
||||
class CAccountingEntry;
|
||||
class CBlockIndex;
|
||||
|
||||
Reference in New Issue
Block a user