@@ -17,10 +17,11 @@
|
||||
|
||||
int64_t AddAssetInputs(struct CCcontract_info *cp,CMutableTransaction &mtx,CPubKey pk,uint256 assetid,int64_t total,int32_t maxinputs)
|
||||
{
|
||||
char coinaddr[64]; int64_t nValue,price,totalinputs = 0; uint256 txid,hashBlock; std::vector<uint8_t> origpubkey; CTransaction vintx; int32_t j,vout,n = 0;
|
||||
char coinaddr[64],destaddr[64]; int64_t nValue,price,totalinputs = 0; uint256 txid,hashBlock; std::vector<uint8_t> origpubkey; CTransaction vintx; int32_t j,vout,n = 0;
|
||||
std::vector<std::pair<CAddressUnspentKey, CAddressUnspentValue> > unspentOutputs;
|
||||
GetCCaddress(cp,coinaddr,pk);
|
||||
SetCCunspents(unspentOutputs,coinaddr);
|
||||
|
||||
for (std::vector<std::pair<CAddressUnspentKey, CAddressUnspentValue> >::const_iterator it=unspentOutputs.begin(); it!=unspentOutputs.end(); it++)
|
||||
{
|
||||
txid = it->first.txhash;
|
||||
@@ -32,6 +33,10 @@ int64_t AddAssetInputs(struct CCcontract_info *cp,CMutableTransaction &mtx,CPubK
|
||||
continue;
|
||||
if ( GetTransaction(txid,vintx,hashBlock,false) != 0 )
|
||||
{
|
||||
Getscriptaddress(destaddr,vintx.vout[vout].scriptPubKey);
|
||||
if ( strcmp(destaddr,coinaddr) != 0 && strcmp(destaddr,cp->unspendableCCaddr) != 0 && strcmp(destaddr,cp->unspendableaddr2) != 0 )
|
||||
continue;
|
||||
fprintf(stderr,"check %s %.8f\n",destaddr,(double)vintx.vout[vout].nValue/COIN);
|
||||
if ( (nValue= IsAssetvout(price,origpubkey,vintx,vout,assetid)) > 0 && myIsutxo_spentinmempool(txid,vout) == 0 )
|
||||
{
|
||||
if ( total != 0 && maxinputs != 0 )
|
||||
|
||||
@@ -67,12 +67,12 @@ struct CC_utxo
|
||||
struct CCcontract_info
|
||||
{
|
||||
uint256 prevtxid;
|
||||
char unspendableCCaddr[64],CChexstr[72],normaladdr[64],unspendableaddr2[64];
|
||||
uint8_t CCpriv[32],unspendablepriv2[32];
|
||||
CPubKey unspendablepk2;
|
||||
char unspendableCCaddr[64],CChexstr[72],normaladdr[64],unspendableaddr2[64],unspendableaddr3[64];
|
||||
uint8_t CCpriv[32],unspendablepriv2[32],unspendablepriv3[32];
|
||||
CPubKey unspendablepk2,unspendablepk3;
|
||||
bool (*validate)(struct CCcontract_info *cp,Eval* eval,const CTransaction &tx);
|
||||
bool (*ismyvin)(CScript const& scriptSig);
|
||||
uint8_t evalcode,evalcode2,didinit;
|
||||
uint8_t evalcode,evalcode2,evalcode3,didinit;
|
||||
};
|
||||
struct CCcontract_info *CCinit(struct CCcontract_info *cp,uint8_t evalcode);
|
||||
|
||||
@@ -126,6 +126,8 @@ CTxOut MakeCC1vout(uint8_t evalcode,CAmount nValue,CPubKey pk);
|
||||
CTxOut MakeCC1of2vout(uint8_t evalcode,CAmount nValue,CPubKey pk,CPubKey pk2);
|
||||
CC *MakeCCcond1(uint8_t evalcode,CPubKey pk);
|
||||
CC* GetCryptoCondition(CScript const& scriptSig);
|
||||
void CCaddr2set(struct CCcontract_info *cp,uint8_t evalcode,CPubKey pk,uint8_t *priv,char *coinaddr);
|
||||
void CCaddr3set(struct CCcontract_info *cp,uint8_t evalcode,CPubKey pk,uint8_t *priv,char *coinaddr);
|
||||
bool IsCCInput(CScript const& scriptSig);
|
||||
int32_t unstringbits(char *buf,uint64_t bits);
|
||||
uint64_t stringbits(char *str);
|
||||
|
||||
@@ -41,7 +41,7 @@ bool SignTx(CMutableTransaction &mtx,int32_t vini,int64_t utxovalue,const CScrip
|
||||
std::string FinalizeCCTx(uint64_t CCmask,struct CCcontract_info *cp,CMutableTransaction &mtx,CPubKey mypk,uint64_t txfee,CScript opret)
|
||||
{
|
||||
auto consensusBranchId = CurrentEpochBranchId(chainActive.Height() + 1, Params().GetConsensus());
|
||||
CTransaction vintx; std::string hex; uint256 hashBlock; uint64_t mask=0,nmask=0,vinimask=0; int64_t utxovalues[64],change,normalinputs=0,totaloutputs=0,normaloutputs=0,totalinputs=0; int32_t i,utxovout,n,err = 0; char myaddr[64],destaddr[64],unspendable[64]; uint8_t *privkey,myprivkey[32],unspendablepriv[32],*msg32 = 0; CC *mycond=0,*othercond=0,*othercond2=0,*cond; CPubKey unspendablepk;
|
||||
CTransaction vintx; std::string hex; uint256 hashBlock; uint64_t mask=0,nmask=0,vinimask=0; int64_t utxovalues[64],change,normalinputs=0,totaloutputs=0,normaloutputs=0,totalinputs=0; int32_t i,utxovout,n,err = 0; char myaddr[64],destaddr[64],unspendable[64]; uint8_t *privkey,myprivkey[32],unspendablepriv[32],*msg32 = 0; CC *mycond=0,*othercond=0,*othercond2=0,*othercond3=0,*cond; CPubKey unspendablepk;
|
||||
n = mtx.vout.size();
|
||||
for (i=0; i<n; i++)
|
||||
{
|
||||
@@ -127,6 +127,14 @@ std::string FinalizeCCTx(uint64_t CCmask,struct CCcontract_info *cp,CMutableTran
|
||||
othercond2 = MakeCCcond1(cp->evalcode2,cp->unspendablepk2);
|
||||
cond = othercond2;
|
||||
}
|
||||
else if ( strcmp(destaddr,cp->unspendableaddr3) == 0 )
|
||||
{
|
||||
//fprintf(stderr,"matched %s unspendable3!\n",cp->unspendableaddr3);
|
||||
privkey = cp->unspendablepriv3;
|
||||
if ( othercond3 == 0 )
|
||||
othercond3 = MakeCCcond1(cp->evalcode3,cp->unspendablepk3);
|
||||
cond = othercond3;
|
||||
}
|
||||
else
|
||||
{
|
||||
fprintf(stderr,"vini.%d has unknown CC address.(%s)\n",i,destaddr);
|
||||
@@ -155,6 +163,10 @@ std::string FinalizeCCTx(uint64_t CCmask,struct CCcontract_info *cp,CMutableTran
|
||||
cc_free(mycond);
|
||||
if ( othercond != 0 )
|
||||
cc_free(othercond);
|
||||
if ( othercond2 != 0 )
|
||||
cc_free(othercond2);
|
||||
if ( othercond3 != 0 )
|
||||
cc_free(othercond3);
|
||||
std::string strHex = EncodeHexTx(mtx);
|
||||
if ( strHex.size() > 0 )
|
||||
return(strHex);
|
||||
|
||||
@@ -169,6 +169,22 @@ CPubKey pubkey2pk(std::vector<uint8_t> pubkey)
|
||||
return(pk);
|
||||
}
|
||||
|
||||
void CCaddr2set(struct CCcontract_info *cp,uint8_t evalcode,CPubKey pk,uint8_t *priv,char *coinaddr)
|
||||
{
|
||||
cp->evalcode2 = evalcode;
|
||||
cp->unspendablepk2 = pk;
|
||||
memcpy(cp->unspendablepriv2,priv,32);
|
||||
strcpy(cp->unspendableaddr2,coinaddr);
|
||||
}
|
||||
|
||||
void CCaddr3set(struct CCcontract_info *cp,uint8_t evalcode,CPubKey pk,uint8_t *priv,char *coinaddr)
|
||||
{
|
||||
cp->evalcode3 = evalcode;
|
||||
cp->unspendablepk3 = pk;
|
||||
memcpy(cp->unspendablepriv3,priv,32);
|
||||
strcpy(cp->unspendableaddr3,coinaddr);
|
||||
}
|
||||
|
||||
bool Getscriptaddress(char *destaddr,const CScript &scriptPubKey)
|
||||
{
|
||||
CTxDestination address; txnouttype whichType;
|
||||
@@ -339,6 +355,8 @@ bool ProcessCC(struct CCcontract_info *cp,Eval* eval, std::vector<uint8_t> param
|
||||
//if ( txid == cp->prevtxid )
|
||||
// return(true);
|
||||
//fprintf(stderr,"process CC %02x\n",cp->evalcode);
|
||||
cp->evalcode2 = cp->evalcode3 = 0;
|
||||
cp->unspendableaddr2[0] = cp->unspendableaddr3[0] = 0;
|
||||
if ( paramsNull.size() != 0 ) // Don't expect params
|
||||
return eval->Invalid("Cannot have params");
|
||||
else if ( ctx.vout.size() == 0 )
|
||||
|
||||
@@ -19,7 +19,6 @@
|
||||
#include <memory.h>
|
||||
#include "cJSON.c"
|
||||
|
||||
|
||||
char hexbyte(int32_t c)
|
||||
{
|
||||
c &= 0xf;
|
||||
@@ -312,22 +311,25 @@ uint64_t get_btcusd()
|
||||
cJSON *get_komodocli(char **retstrp,char *acname,char *method,char *arg0,char *arg1,char *arg2)
|
||||
{
|
||||
long fsize; cJSON *retjson = 0; char cmdstr[32768],*jsonstr,*fname = "/tmp/komodocli";
|
||||
sprintf(cmdstr,"./komodo-cli -ac_name=%s %s %s %s %s > %s\n",acname,method,arg0,arg1,arg2,fname);
|
||||
if ( acname[0] != 0 )
|
||||
sprintf(cmdstr,"./komodo-cli -ac_name=%s %s %s %s %s > %s\n",acname,method,arg0,arg1,arg2,fname);
|
||||
else sprintf(cmdstr,"./komodo-cli %s %s %s %s > %s\n",method,arg0,arg1,arg2,fname);
|
||||
system(cmdstr);
|
||||
*retstrp = 0;
|
||||
if ( (jsonstr= filestr(&fsize,fname)) != 0 )
|
||||
{
|
||||
//fprintf(stderr,"%s -> jsonstr.(%s)\n",cmdstr,jsonstr);
|
||||
if ( (retjson= cJSON_Parse(jsonstr)) == 0 )
|
||||
if ( (jsonstr[0] != '{' && jsonstr[0] != '[') || (retjson= cJSON_Parse(jsonstr)) == 0 )
|
||||
*retstrp = jsonstr;
|
||||
else free(jsonstr);
|
||||
}
|
||||
return(retjson);
|
||||
}
|
||||
|
||||
void komodobroadcast(char *acname,cJSON *hexjson)
|
||||
bits256 komodobroadcast(char *acname,cJSON *hexjson)
|
||||
{
|
||||
char *hexstr,*retstr; cJSON *retjson;
|
||||
char *hexstr,*retstr,str[65]; cJSON *retjson; bits256 txid;
|
||||
memset(txid.bytes,0,sizeof(txid));
|
||||
if ( (hexstr= jstr(hexjson,"hex")) != 0 )
|
||||
{
|
||||
if ( (retjson= get_komodocli(&retstr,acname,"sendrawtransaction",hexstr,"","")) != 0 )
|
||||
@@ -337,10 +339,126 @@ void komodobroadcast(char *acname,cJSON *hexjson)
|
||||
}
|
||||
else if ( retstr != 0 )
|
||||
{
|
||||
fprintf(stderr,"txid.(%s)\n",retstr);
|
||||
if ( strlen(retstr) >= 64 )
|
||||
{
|
||||
retstr[64] = 0;
|
||||
decode_hex(txid.bytes,32,retstr);
|
||||
}
|
||||
fprintf(stderr,"txid.(%s)\n",bits256_str(str,txid));
|
||||
free(retstr);
|
||||
}
|
||||
}
|
||||
return(txid);
|
||||
}
|
||||
|
||||
int32_t get_KMDheight(char *acname)
|
||||
{
|
||||
cJSON *retjson; char *retstr; int32_t height=0;
|
||||
if ( (retjson= get_komodocli(&retstr,acname,"getinfo","","","")) != 0 )
|
||||
{
|
||||
height = jint(retjson,"blocks");
|
||||
//fprintf(stderr,"%s height.%d\n",acname[0]!=0?acname:"KMD",height);
|
||||
free_json(retjson);
|
||||
}
|
||||
else if ( retstr != 0 )
|
||||
{
|
||||
fprintf(stderr,"get_KMDheight.(%s) error.(%s)\n",acname,retstr);
|
||||
free(retstr);
|
||||
}
|
||||
return(height);
|
||||
}
|
||||
|
||||
bits256 get_KMDblockhash(int32_t height)
|
||||
{
|
||||
cJSON *retjson; char *retstr,heightstr[32]; bits256 hash;
|
||||
memset(hash.bytes,0,sizeof(hash));
|
||||
sprintf(heightstr,"%d",height);
|
||||
if ( (retjson= get_komodocli(&retstr,"","getblockhash",heightstr,"","")) != 0 )
|
||||
{
|
||||
fprintf(stderr,"unexpected blockhash json.(%s)\n",jprint(retjson,0));
|
||||
free_json(retjson);
|
||||
}
|
||||
else if ( retstr != 0 )
|
||||
{
|
||||
//fprintf(stderr,"get_KMDblockhash.(%s) %d\n",retstr,(int32_t)strlen(retstr));
|
||||
if ( strlen(retstr) >= 64 )
|
||||
{
|
||||
retstr[64] = 0;
|
||||
decode_hex(hash.bytes,32,retstr);
|
||||
}
|
||||
free(retstr);
|
||||
}
|
||||
return(hash);
|
||||
}
|
||||
|
||||
bits256 get_KMDmerkleroot(bits256 blockhash)
|
||||
{
|
||||
cJSON *retjson; char *retstr,str[65]; bits256 merkleroot;
|
||||
memset(merkleroot.bytes,0,sizeof(merkleroot));
|
||||
if ( (retjson= get_komodocli(&retstr,"","getblockheader",bits256_str(str,blockhash),"","")) != 0 )
|
||||
{
|
||||
merkleroot = jbits256(retjson,"merkleroot");
|
||||
//fprintf(stderr,"got merkleroot.(%s)\n",bits256_str(str,merkleroot));
|
||||
free_json(retjson);
|
||||
}
|
||||
else if ( retstr != 0 )
|
||||
{
|
||||
fprintf(stderr,"get_KMDmerkleroot error.(%s)\n",retstr);
|
||||
free(retstr);
|
||||
}
|
||||
return(merkleroot);
|
||||
}
|
||||
|
||||
int32_t get_KMDheader(bits256 *blockhashp,bits256 *merklerootp,int32_t prevheight)
|
||||
{
|
||||
int32_t height = 0; char str[65];
|
||||
if ( prevheight == 0 )
|
||||
height = get_KMDheight("") - 20;
|
||||
else height = prevheight + 1;
|
||||
if ( height > 0 )
|
||||
{
|
||||
*blockhashp = get_KMDblockhash(height);
|
||||
if ( bits256_nonz(*blockhashp) != 0 )
|
||||
{
|
||||
*merklerootp = get_KMDmerkleroot(*blockhashp);
|
||||
if ( bits256_nonz(*merklerootp) != 0 )
|
||||
return(height);
|
||||
}
|
||||
}
|
||||
memset(blockhashp,0,sizeof(*blockhashp));
|
||||
memset(merklerootp,0,sizeof(*merklerootp));
|
||||
return(0);
|
||||
}
|
||||
|
||||
int32_t get_oracledata(int32_t prevheight,char *hexstr,int32_t maxsize,char *format)
|
||||
{
|
||||
uint32_t i,height; uint64_t price; bits256 blockhash,merkleroot;
|
||||
hexstr[0] = 0;
|
||||
if ( format[0] == 'L' || format[0] == 'l' )
|
||||
{
|
||||
if ( (price= get_btcusd()) != 0 )
|
||||
{
|
||||
for (i=0; i<8; i++)
|
||||
sprintf(&hexstr[i*2],"%02x",(uint8_t)((price >> (i*8)) & 0xff));
|
||||
hexstr[16] = 0;
|
||||
return(16);
|
||||
}
|
||||
}
|
||||
else if ( strcmp(format,"Ihh") == 0 )
|
||||
{
|
||||
if ( (height= get_KMDheader(&blockhash,&merkleroot,prevheight)) > prevheight )
|
||||
{
|
||||
for (i=0; i<4; i++)
|
||||
sprintf(&hexstr[i*2],"%02x",(uint8_t)((height >> (i*8)) & 0xff));
|
||||
for (i=0; i<32; i++)
|
||||
sprintf(&hexstr[8 + (31-i)*2],"%02x",blockhash.bytes[i]);
|
||||
for (i=0; i<32; i++)
|
||||
sprintf(&hexstr[8 + 64 + (31-i)*2],"%02x",merkleroot.bytes[i]);
|
||||
hexstr[8 + 64*2] = 0;
|
||||
return(height);
|
||||
}
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -365,39 +483,60 @@ oraclesdata 17a841a919c284cea8a676f34e793da002e606f19a9258a3190bed12d5aaa3ff 034
|
||||
|
||||
*/
|
||||
|
||||
#define ORACLETXID "4895f631316a649e216153aee7a574bd281686265dc4e8d37597f72353facac3"
|
||||
#define MYPUBKEY "02ebc786cb83de8dc3922ab83c21f3f8a2f3216940c3bf9da43ce39e2a3a882c92"
|
||||
#define ACNAME "ORCL"
|
||||
//#define ORACLETXID "4895f631316a649e216153aee7a574bd281686265dc4e8d37597f72353facac3"
|
||||
//#define MYPUBKEY "02ebc786cb83de8dc3922ab83c21f3f8a2f3216940c3bf9da43ce39e2a3a882c92"
|
||||
//#define ACNAME "ORCL"
|
||||
|
||||
int32_t main(int32_t argc,char **argv)
|
||||
{
|
||||
cJSON *clijson,*clijson2,*regjson,*item; int32_t i,j,n; char *retstr,*retstr2,*pkstr,hexstr[64]; uint64_t price;
|
||||
printf("Powered by CoinDesk (%s) %.8f\n","https://www.coindesk.com/price/",dstr(get_btcusd()));
|
||||
cJSON *clijson,*clijson2,*regjson,*item; int32_t acheight,i,n,height,prevheight = 0; char *format,*acname,*oraclestr,*pkstr,*pubstr,*retstr,*retstr2,hexstr[4096]; uint64_t price; bits256 txid;
|
||||
if ( argc != 5 )
|
||||
{
|
||||
printf("usage: oraclefeed $ACNAME $ORACLETXID $MYPUBKEY $FORMAT\nPowered by CoinDesk (%s) %.8f\n","https://www.coindesk.com/price/",dstr(get_btcusd()));
|
||||
return(-1);
|
||||
}
|
||||
acname = argv[1];
|
||||
oraclestr = argv[2];
|
||||
pkstr = argv[3];
|
||||
format = argv[4];
|
||||
if ( strncmp(format,"Ihh",3) != 0 && format[0] != 'L' )
|
||||
{
|
||||
printf("only formats of L and Ihh are supported now\n");
|
||||
return(-1);
|
||||
}
|
||||
acheight = 0;
|
||||
while ( 1 )
|
||||
{
|
||||
retstr = 0;
|
||||
if ( (price= get_btcusd()) != 0 && (clijson= get_komodocli(&retstr,ACNAME,"oraclesinfo",ORACLETXID,"","")) != 0 )
|
||||
if ( acheight != (height= get_KMDheight(acname)) && (clijson= get_komodocli(&retstr,acname,"oraclesinfo",oraclestr,"","")) != 0 )
|
||||
{
|
||||
acheight = height;
|
||||
if ( (regjson= jarray(&n,clijson,"registered")) != 0 )
|
||||
{
|
||||
for (i=0; i<n; i++)
|
||||
{
|
||||
item = jitem(regjson,i);
|
||||
if ( (pkstr= jstr(item,"publisher")) != 0 && strcmp(pkstr,MYPUBKEY) == 0 )
|
||||
if ( (pubstr= jstr(item,"publisher")) != 0 && strcmp(pkstr,pubstr) == 0 )
|
||||
{
|
||||
for (j=0; j<8; j++)
|
||||
sprintf(&hexstr[j*2],"%02x",(uint8_t)((price >> (j*8)) & 0xff));
|
||||
hexstr[16] = 0;
|
||||
if ( (clijson2= get_komodocli(&retstr2,ACNAME,"oraclesdata",ORACLETXID,hexstr,"")) != 0 )
|
||||
if ( (height= get_oracledata(prevheight,hexstr,sizeof(hexstr),"Ihh")) != 0 )
|
||||
{
|
||||
//printf("data.(%s)\n",jprint(clijson2,0));
|
||||
komodobroadcast(ACNAME,clijson2);
|
||||
free_json(clijson2);
|
||||
}
|
||||
else if ( retstr2 != 0 )
|
||||
{
|
||||
printf("error parsing oraclesdata.(%s)\n",retstr2);
|
||||
free(retstr2);
|
||||
if ( (clijson2= get_komodocli(&retstr2,acname,"oraclesdata",oraclestr,hexstr,"")) != 0 )
|
||||
{
|
||||
//printf("data.(%s)\n",jprint(clijson2,0));
|
||||
txid = komodobroadcast(acname,clijson2);
|
||||
if ( bits256_nonz(txid) != 0 )
|
||||
{
|
||||
prevheight = height;
|
||||
acheight = get_KMDheight(acname);
|
||||
printf("ht.%d <- %s\n",height,hexstr);
|
||||
}
|
||||
free_json(clijson2);
|
||||
}
|
||||
else if ( retstr2 != 0 )
|
||||
{
|
||||
printf("error parsing oraclesdata.(%s)\n",retstr2);
|
||||
free(retstr2);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -410,7 +549,8 @@ int32_t main(int32_t argc,char **argv)
|
||||
printf("got json parse error.(%s)\n",retstr);
|
||||
free(retstr);
|
||||
}
|
||||
sleep(60);
|
||||
sleep(10);
|
||||
// best check is for txid to not be in mempool, ie confirmed
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
@@ -17,10 +17,8 @@
|
||||
|
||||
/*
|
||||
prevent duplicate bindtxid and cointxid via mempool scan
|
||||
baton from mempool for oracle
|
||||
|
||||
assets vin selector needs to filter by signable vins
|
||||
|
||||
loop on merkle oracle
|
||||
string oracles
|
||||
*/
|
||||
|
||||
@@ -464,8 +462,10 @@ uint256 GatewaysReverseScan(uint256 &txid,int32_t height,uint256 reforacletxid,u
|
||||
{
|
||||
CTransaction tx; uint256 hash,mhash,hashBlock,oracletxid; int64_t val; int32_t numvouts; int64_t merkleht; CPubKey pk; std::vector<uint8_t>data;
|
||||
txid = zeroid;
|
||||
char str[65]; fprintf(stderr,"reverse scan %s\n",uint256_str(str,batontxid));
|
||||
while ( GetTransaction(batontxid,tx,hashBlock,false) != 0 && (numvouts= tx.vout.size()) > 0 )
|
||||
{
|
||||
fprintf(stderr,"reverse scan %s\n",uint256_str(str,batontxid));
|
||||
if ( DecodeOraclesData(tx.vout[numvouts-1].scriptPubKey,oracletxid,hash,pk,data) == 'D' && oracletxid == reforacletxid )
|
||||
{
|
||||
if ( oracle_format(&hash,&merkleht,0,'I',(uint8_t *)data.data(),0,(int32_t)data.size()) == sizeof(int32_t) && merkleht == height )
|
||||
@@ -558,7 +558,7 @@ int64_t GatewaysDepositval(CTransaction tx)
|
||||
|
||||
std::string GatewaysDeposit(uint64_t txfee,uint256 bindtxid,int32_t height,std::string refcoin,uint256 cointxid,int32_t claimvout,std::string deposithex,std::vector<uint8_t>proof,CPubKey destpub,int64_t amount)
|
||||
{
|
||||
CMutableTransaction mtx; CTransaction bindtx; CPubKey mypk,gatewayspk; uint256 oracletxid,merkleroot,mhash,hashBlock,tokenid,txid; int64_t totalsupply; int32_t i,m,n,numvouts; uint8_t M,N,taddr,prefix,prefix2; std::string coin; struct CCcontract_info *cp,C; std::vector<CPubKey> pubkeys,publishers; std::vector<uint256>txids; char str[65],depositaddr[64],txidaddr[64];
|
||||
CMutableTransaction mtx; CTransaction bindtx; CPubKey mypk,gatewayspk; uint256 oracletxid,merkleroot,mhash,hashBlock,tokenid,txid; int64_t totalsupply; int32_t i,m,n,numvouts; uint8_t M,N,taddr,prefix,prefix2; std::string coin; struct CCcontract_info *cp,C; std::vector<CPubKey> pubkeys,publishers; std::vector<uint256>txids; char str[67],depositaddr[64],txidaddr[64];
|
||||
cp = CCinit(&C,EVAL_GATEWAYS);
|
||||
if ( txfee == 0 )
|
||||
txfee = 10000;
|
||||
@@ -575,15 +575,11 @@ std::string GatewaysDeposit(uint64_t txfee,uint256 bindtxid,int32_t height,std::
|
||||
fprintf(stderr,"invalid bindtxid %s coin.%s\n",uint256_str(str,bindtxid),coin.c_str());
|
||||
return("");
|
||||
}
|
||||
if ( GatewaysCointxidExists(cp,cointxid) != 0 )
|
||||
{
|
||||
fprintf(stderr,"cointxid.%s already exists\n",uint256_str(str,cointxid));
|
||||
return("");
|
||||
}
|
||||
n = (int32_t)pubkeys.size();
|
||||
merkleroot = zeroid;
|
||||
for (i=m=0; i<n; i++)
|
||||
{
|
||||
fprintf(stderr,"pubkeys[%d] %s\n",i,pubkey33_str(str,(uint8_t *)&pubkeys[i]));
|
||||
if ( (mhash= GatewaysReverseScan(txid,height,oracletxid,OraclesBatontxid(oracletxid,pubkeys[i]))) != zeroid )
|
||||
{
|
||||
if ( merkleroot == zeroid )
|
||||
@@ -594,13 +590,19 @@ std::string GatewaysDeposit(uint64_t txfee,uint256 bindtxid,int32_t height,std::
|
||||
txids.push_back(txid);
|
||||
}
|
||||
}
|
||||
fprintf(stderr,"m.%d of n.%d\n",m,n);
|
||||
if ( merkleroot == zeroid || m < n/2 )
|
||||
{
|
||||
uint256 tmp;
|
||||
decode_hex((uint8_t *)&tmp,32,(char *)"90aedc2f19200afc9aca2e351438d011ebae8264a58469bf225883045f61917f");
|
||||
merkleroot = revuint256(tmp);
|
||||
//uint256 tmp;
|
||||
//decode_hex((uint8_t *)&tmp,32,(char *)"90aedc2f19200afc9aca2e351438d011ebae8264a58469bf225883045f61917f");
|
||||
//merkleroot = revuint256(tmp);
|
||||
fprintf(stderr,"couldnt find merkleroot for ht.%d %s oracle.%s m.%d vs n.%d\n",height,coin.c_str(),uint256_str(str,oracletxid),m,n);
|
||||
//return("");
|
||||
return("");
|
||||
}
|
||||
if ( GatewaysCointxidExists(cp,cointxid) != 0 )
|
||||
{
|
||||
fprintf(stderr,"cointxid.%s already exists\n",uint256_str(str,cointxid));
|
||||
return("");
|
||||
}
|
||||
if ( GatewaysVerify(depositaddr,oracletxid,claimvout,coin,cointxid,deposithex,proof,merkleroot,destpub) != amount )
|
||||
{
|
||||
@@ -619,20 +621,18 @@ std::string GatewaysDeposit(uint64_t txfee,uint256 bindtxid,int32_t height,std::
|
||||
|
||||
std::string GatewaysClaim(uint64_t txfee,uint256 bindtxid,std::string refcoin,uint256 deposittxid,CPubKey destpub,int64_t amount)
|
||||
{
|
||||
CMutableTransaction mtx; CTransaction tx; CPubKey mypk,gatewayspk; struct CCcontract_info *cp,C,*assetscp,C2; uint8_t M,N,taddr,prefix,prefix2; std::string coin; std::vector<CPubKey> msigpubkeys; int64_t totalsupply,depositamount,inputs,CCchange=0; int32_t numvouts; uint256 hashBlock,assetid,oracletxid; char str[65],depositaddr[64];
|
||||
CMutableTransaction mtx; CTransaction tx; CPubKey mypk,gatewayspk; struct CCcontract_info *cp,C,*assetscp,C2; uint8_t M,N,taddr,prefix,prefix2,mypriv[32]; std::string coin; std::vector<CPubKey> msigpubkeys; int64_t totalsupply,depositamount,inputs,CCchange=0; int32_t numvouts; uint256 hashBlock,assetid,oracletxid; char str[65],depositaddr[64],coinaddr[64];
|
||||
cp = CCinit(&C,EVAL_GATEWAYS);
|
||||
assetscp = CCinit(&C2,EVAL_ASSETS);
|
||||
if ( txfee == 0 )
|
||||
txfee = 10000;
|
||||
mypk = pubkey2pk(Mypubkey());
|
||||
gatewayspk = GetUnspendable(cp,0);
|
||||
_GetCCaddress(cp->unspendableaddr2,EVAL_ASSETS,gatewayspk);
|
||||
memcpy(cp->unspendablepriv2,cp->CCpriv,32);
|
||||
assetscp->evalcode2 = cp->evalcode2 = EVAL_ASSETS;
|
||||
assetscp->unspendablepk2 = gatewayspk;
|
||||
cp->unspendablepk2 = gatewayspk;
|
||||
memcpy(assetscp->unspendablepriv2,cp->CCpriv,32);
|
||||
strcpy(assetscp->unspendableaddr2,cp->unspendableaddr2);
|
||||
_GetCCaddress(coinaddr,EVAL_ASSETS,gatewayspk);
|
||||
CCaddr2set(assetscp,EVAL_ASSETS,gatewayspk,cp->CCpriv,coinaddr);
|
||||
Myprivkey(mypriv);
|
||||
_GetCCaddress(coinaddr,EVAL_GATEWAYS,mypk);
|
||||
CCaddr3set(assetscp,EVAL_GATEWAYS,mypk,mypriv,coinaddr);
|
||||
if ( GetTransaction(bindtxid,tx,hashBlock,false) == 0 || (numvouts= tx.vout.size()) <= 0 )
|
||||
{
|
||||
fprintf(stderr,"cant find bindtxid %s\n",uint256_str(str,bindtxid));
|
||||
|
||||
@@ -276,6 +276,33 @@ uint256 OracleBatonUtxo(uint64_t txfee,struct CCcontract_info *cp,uint256 refora
|
||||
return(batontxid);
|
||||
}
|
||||
|
||||
uint256 OraclesBatontxid(uint256 reforacletxid,CPubKey refpk)
|
||||
{
|
||||
std::vector<std::pair<CAddressUnspentKey, CAddressUnspentValue> > unspentOutputs;
|
||||
CTransaction regtx; uint256 hash,txid,batontxid,oracletxid; CPubKey pk; int32_t numvouts,height,maxheight=0; int64_t datafee; char markeraddr[64],batonaddr[64]; std::vector <uint8_t> data; struct CCcontract_info *cp,C;
|
||||
batontxid = zeroid;
|
||||
cp = CCinit(&C,EVAL_ORACLES);
|
||||
CCtxidaddr(markeraddr,reforacletxid);
|
||||
SetCCunspents(unspentOutputs,markeraddr);
|
||||
char str[67]; fprintf(stderr,"markeraddr.(%s) %s\n",markeraddr,pubkey33_str(str,(uint8_t *)&refpk));
|
||||
for (std::vector<std::pair<CAddressUnspentKey, CAddressUnspentValue> >::const_iterator it=unspentOutputs.begin(); it!=unspentOutputs.end(); it++)
|
||||
{
|
||||
txid = it->first.txhash;
|
||||
fprintf(stderr,"check %s\n",uint256_str(str,txid));
|
||||
height = (int32_t)it->second.blockHeight;
|
||||
if ( myGetTransaction(txid,regtx,hash) != 0 )
|
||||
{
|
||||
if ( regtx.vout.size() > 0 && DecodeOraclesOpRet(regtx.vout[regtx.vout.size()-1].scriptPubKey,oracletxid,pk,datafee) == 'R' && oracletxid == reforacletxid && pk == refpk )
|
||||
{
|
||||
Getscriptaddress(batonaddr,regtx.vout[1].scriptPubKey);
|
||||
batontxid = OracleBatonUtxo(10000,cp,oracletxid,batonaddr,pk,data);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return(batontxid);
|
||||
}
|
||||
|
||||
int32_t oracle_format(uint256 *hashp,int64_t *valp,char *str,uint8_t fmt,uint8_t *data,int32_t offset,int32_t datalen)
|
||||
{
|
||||
char _str[65]; int32_t sflag = 0,i,val32,len = 0,slen = 0,dlen = 0; uint32_t uval32; uint16_t uval16; int16_t val16; int64_t val = 0; uint64_t uval = 0;
|
||||
@@ -477,33 +504,6 @@ int64_t OraclePrice(int32_t height,uint256 reforacletxid,char *markeraddr,char *
|
||||
return(0);
|
||||
}
|
||||
|
||||
uint256 OraclesBatontxid(uint256 reforacletxid,CPubKey refpk)
|
||||
{
|
||||
std::vector<std::pair<CAddressUnspentKey, CAddressUnspentValue> > unspentOutputs;
|
||||
CTransaction tx; uint256 hash,txid,rettxid,oracletxid; CPubKey pk; int32_t numvouts,maxheight=0; int64_t datafee,ht; char markeraddr[64]; std::vector <uint8_t> data; struct CCcontract_info *cp,C;
|
||||
rettxid = zeroid;
|
||||
cp = CCinit(&C,EVAL_ORACLES);
|
||||
CCtxidaddr(markeraddr,reforacletxid);
|
||||
SetCCunspents(unspentOutputs,markeraddr);
|
||||
for (std::vector<std::pair<CAddressUnspentKey, CAddressUnspentValue> >::const_iterator it=unspentOutputs.begin(); it!=unspentOutputs.end(); it++)
|
||||
{
|
||||
txid = it->first.txhash;
|
||||
//ht = (int32_t)it->second.blockHeight;
|
||||
if ( myGetTransaction(txid,tx,hash) != 0 && (numvouts= tx.vout.size()) > 0 )
|
||||
{
|
||||
if ( DecodeOraclesData(tx.vout[numvouts-1].scriptPubKey,oracletxid,hash,pk,data) == 'D' && oracletxid == reforacletxid && pk == refpk )
|
||||
{
|
||||
if ( oracle_format(&hash,&ht,0,'I',(uint8_t *)data.data(),0,(int32_t)data.size()) == sizeof(int32_t) && ht > maxheight )
|
||||
{
|
||||
maxheight = ht;
|
||||
rettxid = txid;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return(rettxid);
|
||||
}
|
||||
|
||||
int64_t IsOraclesvout(struct CCcontract_info *cp,const CTransaction& tx,int32_t v)
|
||||
{
|
||||
char destaddr[64];
|
||||
|
||||
@@ -107,6 +107,11 @@ static UniValue ValuePoolDesc(
|
||||
UniValue blockheaderToJSON(const CBlockIndex* blockindex)
|
||||
{
|
||||
UniValue result(UniValue::VOBJ);
|
||||
if ( blockindex == 0 )
|
||||
{
|
||||
result.push_back(Pair("error", "null blockhash"));
|
||||
return(result);
|
||||
}
|
||||
result.push_back(Pair("hash", blockindex->GetBlockHash().GetHex()));
|
||||
int confirmations = -1;
|
||||
// Only report confirmations if the block is on the main chain
|
||||
|
||||
Reference in New Issue
Block a user