diff --git a/basilisk/basilisk.c b/basilisk/basilisk.c index fe63fb3c0..010022402 100755 --- a/basilisk/basilisk.c +++ b/basilisk/basilisk.c @@ -141,7 +141,9 @@ struct basilisk_item *basilisk_itemcreate(struct supernet_info *myinfo,char *CMD ptr->numrequired = 1; strcpy(ptr->CMD,CMD); safecopy(ptr->symbol,symbol,sizeof(ptr->symbol)); + ptr->duration = timeoutmillis; ptr->expiration = OS_milliseconds() + timeoutmillis; + //printf("itemcreate.%p %s %f timeout.%d\n",ptr,CMD,OS_milliseconds(),timeoutmillis); return(ptr); } @@ -335,7 +337,7 @@ void basilisk_sendback(struct supernet_info *myinfo,char *origCMD,char *symbol,c struct basilisk_item *basilisk_issueremote(struct supernet_info *myinfo,struct iguana_peer *addr,int32_t *numsentp,char *CMD,char *symbol,int32_t blockflag,cJSON *valsobj,int32_t fanout,int32_t numrequired,uint32_t basilisktag,int32_t timeoutmillis,void *deprecated_dontuse,char *retstr,int32_t encryptflag,int32_t delaymillis,uint32_t nBits) { - struct basilisk_item *pending; uint8_t *allocptr,*data,space[4096]; int32_t datalen; cJSON *retarray; + struct basilisk_item *pending; uint8_t *allocptr,*data,space[4096]; int32_t datalen; pending = basilisk_itemcreate(myinfo,CMD,symbol,basilisktag,numrequired,valsobj,timeoutmillis,0); pending->nBits = nBits; *numsentp = 0; @@ -356,31 +358,23 @@ struct basilisk_item *basilisk_issueremote(struct supernet_info *myinfo,struct i HASH_ADD(hh,myinfo->basilisks.issued,basilisktag,sizeof(basilisktag),pending); portable_mutex_unlock(&myinfo->basilisk_mutex); if ( pending->expiration <= OS_milliseconds() ) - pending->expiration = OS_milliseconds() + BASILISK_TIMEOUT; - strcpy(pending->symbol,"BTCD"); + pending->expiration = OS_milliseconds() + pending->duration; + strcpy(pending->symbol,"NOTARY"); strcpy(pending->CMD,CMD); + //printf("block for %f\n",pending->expiration - OS_milliseconds()); while ( OS_milliseconds() < pending->expiration ) { portable_mutex_lock(&myinfo->basilisk_mutex); - if ( pending->numresults >= pending->numrequired )//|| (retstr= pending->retstr) != 0 ) + if ( pending->numresults >= pending->numrequired ) { portable_mutex_unlock(&myinfo->basilisk_mutex); - //printf("<<<<<<<<<<<<< numresults.%d vs numrequired.%d\n",pending->numresults,pending->numrequired); + //printf("%p <<<<<<<<<<<<< numresults.%d vs numrequired.%d\n",pending,pending->numresults,pending->numrequired); break; } portable_mutex_unlock(&myinfo->basilisk_mutex); usleep(10000); } - portable_mutex_lock(&myinfo->basilisk_mutex); - if ( (retarray= pending->retarray) != 0 ) - { - pending->retstr = jprint(retarray,0); - //printf("num.%d:%d required.%d RETSTR.(%s)\n",pending->numresults,cJSON_GetArraySize(pending->retarray),pending->numrequired,pending->retstr); - pending->retarray = 0; - free_json(retarray); - } - portable_mutex_unlock(&myinfo->basilisk_mutex); - } else free(pending), pending = 0; //ptr->finished = (uint32_t)time(NULL); + } if ( allocptr != 0 ) free(allocptr); } @@ -401,15 +395,15 @@ struct basilisk_item *basilisk_requestservice(struct supernet_info *myinfo,struc if ( (timeoutmillis= jint(valsobj,"timeout")) == 0 ) timeoutmillis = BASILISK_TIMEOUT; minfanout = sqrt(myinfo->NOTARY.NUMRELAYS)+1; - if ( minfanout < 5 ) - minfanout = 5; + if ( minfanout < 8 ) + minfanout = 8; if ( jobj(valsobj,"fanout") == 0 ) fanout = minfanout; else fanout = jint(valsobj,"fanout"); if ( fanout < minfanout ) fanout = minfanout; if ( (numrequired= jint(valsobj,"numrequired")) <= 0 ) - numrequired = MIN(fanout,sqrt(myinfo->NOTARY.NUMRELAYS)+1); + numrequired = MIN(fanout/2,sqrt(myinfo->NOTARY.NUMRELAYS)+1); if ( (symbol= jstr(valsobj,"coin")) != 0 || (symbol= jstr(valsobj,"symbol")) != 0 ) { if ( (virt= iguana_coinfind(symbol)) != 0 ) @@ -420,7 +414,7 @@ struct basilisk_item *basilisk_requestservice(struct supernet_info *myinfo,struc } } if ( symbol == 0 ) - symbol = "BTCD"; + symbol = "NOTARY"; encryptflag = jint(valsobj,"encrypt"); delaymillis = jint(valsobj,"delay"); ptr = basilisk_issueremote(myinfo,addr,&numsent,CMD,symbol,blockflag,valsobj,fanout,numrequired,0,timeoutmillis,0,0,encryptflag,delaymillis,nBits); @@ -429,7 +423,7 @@ struct basilisk_item *basilisk_requestservice(struct supernet_info *myinfo,struc char *basilisk_standardservice(char *CMD,struct supernet_info *myinfo,void *_addr,bits256 hash,cJSON *valsobj,char *hexstr,int32_t blockflag) // client side { - uint32_t nBits = 0; uint8_t space[4096],*allocptr=0,*data = 0; struct basilisk_item *ptr; int32_t datalen = 0; cJSON *retjson; char *retstr=0; + uint32_t nBits = 0; uint8_t space[4096],*allocptr=0,*data = 0; struct basilisk_item *ptr; int32_t i,datalen = 0; cJSON *retjson; char *retstr=0; if ( myinfo->IAMNOTARY != 0 && myinfo->NOTARY.RELAYID >= 0 && (strcmp(CMD,"INF") != 0 && basilisk_notarycmd(CMD) == 0) ) return(clonestr("{\"error\":\"unsupported special relay command\"}")); data = get_dataptr(BASILISK_HDROFFSET,&allocptr,&datalen,space,sizeof(space),hexstr); @@ -439,22 +433,32 @@ char *basilisk_standardservice(char *CMD,struct supernet_info *myinfo,void *_add free(allocptr); if ( ptr != 0 ) { - if ( ptr->retstr != 0 ) - retstr = ptr->retstr, ptr->retstr = 0; + if ( (retstr= ptr->retstr) != 0 ) + ptr->retstr = 0; else { - retjson = cJSON_CreateObject(); - if ( ptr->numsent > 0 ) + if ( ptr->numresults > 0 ) { - //queue_enqueue("submitQ",&myinfo->basilisks.submitQ,&ptr->DL,0); - jaddstr(retjson,"result","success"); - jaddnum(retjson,"numsent",ptr->numsent); - } else jaddstr(retjson,"error","didnt find any nodes to send to"); + retjson = cJSON_CreateArray(); + for (i=0; inumresults; i++) + jaddi(retjson,ptr->results[i]), ptr->results[i] = 0; + //printf("numresults.%d (%p)\n",ptr->numresults,ptr); + } + else + { + retjson = cJSON_CreateObject(); + if ( ptr->numsent > 0 ) + { + //queue_enqueue("submitQ",&myinfo->basilisks.submitQ,&ptr->DL,0); + jaddstr(retjson,"result","error"); + jaddnum(retjson,"packetsize",ptr->numsent); + } else jaddstr(retjson,"error","didnt find any nodes to send to"); + } retstr = jprint(retjson,1); } - ptr->finished = (uint32_t)time(NULL); + ptr->finished = OS_milliseconds() + 10000; } - if ( 0 && strcmp("RID",CMD) != 0 && strcmp("BAL",CMD) != 0 && strcmp("MSG",CMD) != 0 ) + if ( 0 && strcmp("MSG",CMD) == 0 ) printf("%s.(%s) -> (%s)\n",CMD,jprint(valsobj,0),retstr!=0?retstr:""); return(retstr); } @@ -588,25 +592,22 @@ void basilisk_result(struct supernet_info *myinfo,char *remoteaddr,uint32_t basi { portable_mutex_lock(&myinfo->basilisk_mutex); HASH_FIND(hh,myinfo->basilisks.issued,&basilisktag,sizeof(basilisktag),pending); - //printf("HASH_FIND.%p\n",pending); + portable_mutex_unlock(&myinfo->basilisk_mutex); if ( pending != 0 && retstr != 0 ) { if ( (item= cJSON_Parse(retstr)) != 0 ) { - if ( pending->retarray == 0 ) - pending->retarray = cJSON_CreateArray(); if ( jobj(item,"myip") == 0 ) jaddstr(item,"myip",remoteaddr); - jaddi(pending->retarray,item); - if ( jobj(item,"error") == 0 ) + if ( pending->numresults < sizeof(pending->results)/sizeof(*pending->results) ) { - //printf("numresults.%d:%d\n",pending->numresults,cJSON_GetArraySize(pending->retarray)); - pending->numresults++; + //printf("%p.(RESULT).%d\n",pending,pending->numresults); + pending->results[pending->numresults++] = item; } } else printf("couldnt parse.(%s)\n",retstr); } //else printf("couldnt find issued.%u\n",basilisktag); - portable_mutex_unlock(&myinfo->basilisk_mutex); } + free(retstr); } } @@ -635,7 +636,6 @@ void basilisk_msgprocess(struct supernet_info *myinfo,void *_addr,uint32_t sende { (void *)"VOT", &basilisk_respond_VOT }, // VOTE handler for something //{ (void *)"PIN", &basilisk_respond_PIN }, - // encrypted data for jumblr { (void *)"HOP", &basilisk_respond_forward }, // message forwarding { (void *)"BOX", &basilisk_respond_mailbox }, // create/send/check mailbox pubkey @@ -748,9 +748,10 @@ void basilisk_msgprocess(struct supernet_info *myinfo,void *_addr,uint32_t sende { if ( (coin != 0 && coin->FULLNODE != 0) || myinfo->NOTARY.RELAYID >= 0 ) // iguana node { + //printf("\n call %s from_basilisk.%d (%s)\n",addr->ipaddr,from_basilisk,type); if ( (retstr= (*basilisk_services[i][1])(myinfo,type,addr,remoteaddr,basilisktag,valsobj,data,datalen,hash,from_basilisk)) != 0 ) { - //printf("from_basilisk.%d ret.(%s)\n",from_basilisk,retstr); + //printf("%s from_basilisk.%d ret.(%s)\n",addr->ipaddr,from_basilisk,retstr); //if ( from_basilisk != 0 || strcmp(CMD,"GET") == 0 ) basilisk_sendback(myinfo,CMD,symbol,remoteaddr,basilisktag,retstr); if ( retstr != 0 ) @@ -767,9 +768,52 @@ void basilisk_msgprocess(struct supernet_info *myinfo,void *_addr,uint32_t sende myinfo->basilisk_busy = 0; } -void basilisk_p2p(void *_myinfo,void *_addr,char *senderip,uint8_t *data,int32_t datalen,char *type,int32_t encrypted) +int32_t basilisk_p2pQ_process(struct supernet_info *myinfo,int32_t maxiters) +{ + struct basilisk_p2pitem *ptr; char senderip[64]; uint32_t n=0,basilisktag,len; + while ( n < maxiters && (ptr= queue_dequeue(&myinfo->p2pQ,0)) != 0 ) + { + len = 0; + expand_ipbits(senderip,ptr->ipbits); + if ( ptr->type[0] == 'P' && ptr->type[1] == 'I' && ptr->type[2] == 'N' ) + { + if ( myinfo->NOTARY.RELAYID >= 0 ) + { + basilisk_ping_process(myinfo,ptr->addr,ptr->ipbits,ptr->data,ptr->datalen); + } + } + else + { + len += iguana_rwnum(0,ptr->data,sizeof(basilisktag),&basilisktag); + if ( 0 && myinfo->IAMLP == 0 ) + printf("RELAYID.%d ->received.%d basilisk_p2p.(%s) from %s tag.%u\n",myinfo->NOTARY.RELAYID,ptr->datalen,ptr->type,senderip,basilisktag); + basilisk_msgprocess(myinfo,ptr->addr,ptr->ipbits,ptr->type,basilisktag,&ptr->data[len],ptr->datalen - len); + if ( 0 && myinfo->IAMLP == 0 ) + printf("processed.%s from %s\n",ptr->type,senderip); + } + free(ptr); + n++; + } + return(n); +} + +struct basilisk_p2pitem *basilisk_p2pitem_create(struct iguana_info *coin,struct iguana_peer *addr,char *type,uint32_t ipbits,uint8_t *data,int32_t datalen) { - uint32_t ipbits,basilisktag; int32_t msglen,len=0; void *ptr = 0; uint8_t space[4096]; bits256 senderpub; struct supernet_info *myinfo = _myinfo; + struct basilisk_p2pitem *ptr; + ptr = calloc(1,sizeof(*ptr) + datalen); + ptr->coin = coin; + ptr->addr = addr; + ptr->ipbits = ipbits; + ptr->datalen = datalen; + safecopy(ptr->type,type,sizeof(ptr->type)); + memcpy(ptr->data,data,datalen); + return(ptr); +} + +void basilisk_p2p(struct supernet_info *myinfo,struct iguana_info *coin,struct iguana_peer *addr,char *senderip,uint8_t *data,int32_t datalen,char *type,int32_t encrypted) +{ + uint32_t ipbits; int32_t msglen; void *ptr = 0; uint8_t space[4096]; bits256 senderpub; + ipbits = (uint32_t)calc_ipbits(senderip); if ( encrypted != 0 ) { printf("encrypted p2p\n"); @@ -779,34 +823,25 @@ void basilisk_p2p(void *_myinfo,void *_addr,char *senderip,uint8_t *data,int32_t printf("basilisk_p2p decrytion error\n"); return; } else datalen = msglen; + if ( ptr != 0 ) + free(ptr); } if ( senderip != 0 && senderip[0] != 0 && strcmp(senderip,"127.0.0.1") != 0 ) ipbits = (uint32_t)calc_ipbits(senderip); else ipbits = myinfo->myaddr.myipbits; - if ( type[0] == 'P' && type[1] == 'I' && type[2] == 'N' ) - { - if ( strcmp(type,"PIN") == 0 && myinfo->NOTARY.RELAYID >= 0 ) - { - basilisk_ping_process(myinfo,_addr,ipbits,data,datalen); - } - } - else - { - len += iguana_rwnum(0,data,sizeof(basilisktag),&basilisktag); - //int32_t i; for (i=0; iNOTARY.RELAYID >= 0 ) - printf("RELAYID.%d ->received.%d basilisk_p2p.(%s) from %s tag.%u\n",myinfo->NOTARY.RELAYID,datalen,type,senderip!=0?senderip:"?",basilisktag); - basilisk_msgprocess(myinfo,_addr,ipbits,type,basilisktag,&data[len],datalen - len); - } - if ( ptr != 0 ) - free(ptr); + ptr = basilisk_p2pitem_create(coin,addr,type,ipbits,data,datalen); + queue_enqueue("p2pQ",&myinfo->p2pQ,ptr,0); } void basilisk_requests_poll(struct supernet_info *myinfo) { - char *retstr; uint8_t data[8192]; cJSON *outerarray,*retjson; int32_t datalen,i,n; struct basilisk_request issueR; double hwm = 0.; + static uint32_t lastpoll; + char *retstr; uint8_t data[32768]; cJSON *outerarray,*retjson; int32_t datalen,i,n; struct basilisk_request issueR; double hwm = 0.; + if ( time(NULL) < lastpoll+3 ) + return; + lastpoll = (uint32_t)time(NULL); memset(&issueR,0,sizeof(issueR)); + //printf("Call incoming\n"); if ( (retstr= InstantDEX_incoming(myinfo,0,0,0,0)) != 0 ) { //printf("poll.(%s)\n",retstr); @@ -845,73 +880,72 @@ void basilisk_requests_poll(struct supernet_info *myinfo) } } -void basilisks_loop(void *arg) +int32_t basilisk_issued_purge(struct supernet_info *myinfo,int32_t timepad) { - struct iguana_info *virt,*tmpcoin,*notary; struct basilisk_message *msg,*tmpmsg; struct basilisk_item *tmp,*pending; uint32_t now; int32_t iter,maxmillis,flag=0; struct supernet_info *myinfo = arg; - iter = 0; - while ( 1 ) + struct basilisk_item *tmp,*pending; cJSON *item; int32_t i,n = 0; double startmilli = OS_milliseconds(); + portable_mutex_lock(&myinfo->basilisk_mutex); + HASH_ITER(hh,myinfo->basilisks.issued,pending,tmp) { - portable_mutex_lock(&myinfo->basilisk_mutex); - HASH_ITER(hh,myinfo->basilisks.issued,pending,tmp) + if ( pending != 0 && ((pending->finished > 0 && startmilli > pending->finished) || startmilli > pending->expiration+timepad) ) { - if ( pending != 0 && (pending->finished != 0 || OS_milliseconds() > pending->expiration+600000) ) - { - //printf("enable free for HASH_DELETE.(%p)\n",pending); - HASH_DELETE(hh,myinfo->basilisks.issued,pending); - memset(pending,0,sizeof(*pending)); - free(pending); - } + HASH_DELETE(hh,myinfo->basilisks.issued,pending); + //printf("%f > %f (%d) clear pending.%p numresults.%d %p\n",startmilli,pending->expiration+timepad,timepad,pending,pending->numresults,pending->retstr); + for (i=0; inumresults; i++) + if ( (item= pending->results[i]) != 0 ) + free_json(item); + if ( pending->retstr != 0 ) + free(pending->retstr); + memset(pending,0,sizeof(*pending)); + free(pending); + n++; } - notary = iguana_coinfind("NOTARY"); - now = (uint32_t)time(NULL); - portable_mutex_unlock(&myinfo->basilisk_mutex); - if ( myinfo->NOTARY.RELAYID >= 0 ) + } + portable_mutex_unlock(&myinfo->basilisk_mutex); + return(n); +} + +void basilisk_iteration(struct supernet_info *myinfo) +{ + struct iguana_info *notary; uint32_t now; + now = (uint32_t)time(NULL); + notary = iguana_coinfind("NOTARY"); + if ( myinfo->NOTARY.RELAYID >= 0 ) + { + basilisk_ping_send(myinfo,notary); + /*if ( notary != 0 ) { - if ( notary != 0 ) + struct iguana_info *virt,*tmpcoin; int32_t maxmillis; + maxmillis = (1000 / (myinfo->allcoins_numvirts + 1)) + 1; + HASH_ITER(hh,myinfo->allcoins,virt,tmpcoin) { - maxmillis = (1000 / (myinfo->allcoins_numvirts + 1)) + 1; - //portable_mutex_lock(&myinfo->allcoins_mutex); - HASH_ITER(hh,myinfo->allcoins,virt,tmpcoin) - { - if ( virt->started != 0 && virt->active != 0 && virt->virtualchain != 0 ) - { - gecko_iteration(myinfo,notary,virt,maxmillis), flag++; - } - } - //portable_mutex_unlock(&myinfo->allcoins_mutex); - basilisk_ping_send(myinfo,notary); + if ( virt->started != 0 && virt->active != 0 && virt->virtualchain != 0 ) + gecko_iteration(myinfo,notary,virt,maxmillis), flag++; } - } // else printf("not notary %p %d\n",notary,myinfo->NOTARY.RELAYID); - else if ( myinfo->expiration != 0 ) - { - /*HASH_ITER(hh,myinfo->allcoins,coin,tmpcoin) - { - if ( strcmp(coin->symbol,"NOTARY") != 0 && (myinfo->Cunspents == 0 || time(NULL) > coin->lastunspentsupdate+60) ) - { - //printf(">>>>>>>>>>>>> update %s\n",coin->symbol); - basilisk_unspents_update(myinfo,coin); - coin->lastunspentsupdate = now; - //printf(">>>>>>>>>>>>> update %s finished\n",coin->symbol); - } - }*/ - if ( myinfo->IAMLP != 0 || myinfo->DEXactive > now ) - basilisk_requests_poll(myinfo); - } - portable_mutex_lock(&myinfo->messagemutex); - HASH_ITER(hh,myinfo->messagetable,msg,tmpmsg) - { - if ( now > msg->expiration ) - { - printf("delete expired message.%p QUEUEITEMS.%d\n",msg,QUEUEITEMS); - HASH_DELETE(hh,myinfo->messagetable,msg); - QUEUEITEMS--; - free(msg); - } //else printf("remains.%d\n",msg->expiration - now); - } - portable_mutex_unlock(&myinfo->messagemutex); + }*/ + } + /*else + { + if ( myinfo->expiration != 0 && (myinfo->IAMLP != 0 || myinfo->DEXactive > now) ) + basilisk_requests_poll(myinfo); + }*/ +} + +void basilisks_loop(void *arg) +{ + struct supernet_info *myinfo = arg; int32_t iter; double startmilli,endmilli; + iter = 0; + while ( 1 ) + { + startmilli = OS_milliseconds(); + basilisk_issued_purge(myinfo,600000); + basilisk_iteration(myinfo); + basilisk_p2pQ_process(myinfo,777); if ( myinfo->NOTARY.RELAYID >= 0 ) - usleep(500000); - else usleep(3000000); + endmilli = startmilli + 500; + else endmilli = startmilli + 2000; + while ( OS_milliseconds() < endmilli ) + usleep(10000); + iter++; } } @@ -945,9 +979,9 @@ HASH_ARRAY_STRING(basilisk,balances,hash,vals,hexstr) if ( jobj(vals,"history") == 0 ) jaddnum(vals,"history",3); if ( jobj(vals,"fanout") == 0 ) - jaddnum(vals,"fanout",MAX(5,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); + jaddnum(vals,"fanout",MAX(8,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); if ( jobj(vals,"numrequired") == 0 ) - jaddnum(vals,"numrequired",juint(vals,"fanout")); + jaddnum(vals,"numrequired",MIN(juint(vals,"fanout")/2,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS))); if ( jobj(vals,"addresses") == 0 ) { jadd(vals,"addresses",iguana_getaddressesbyaccount(myinfo,coin,"*")); @@ -956,7 +990,7 @@ HASH_ARRAY_STRING(basilisk,balances,hash,vals,hexstr) if ( (basilisktag= juint(vals,"basilisktag")) == 0 ) basilisktag = rand(); if ( (timeoutmillis= juint(vals,"timeout")) <= 0 ) - timeoutmillis = 3000; + timeoutmillis = BASILISK_TIMEOUT; if ( coin != 0 ) { if ( coin->FULLNODE != 0 || coin->VALIDATENODE != 0 ) @@ -964,7 +998,7 @@ HASH_ARRAY_STRING(basilisk,balances,hash,vals,hexstr) if ( (ptr= basilisk_bitcoinbalances(&Lptr,myinfo,coin,remoteaddr,basilisktag,timeoutmillis,vals)) != 0 ) { retstr = ptr->retstr, ptr->retstr = 0; - ptr->finished = (uint32_t)time(NULL); + ptr->finished = OS_milliseconds() + 10000; return(retstr); } return(clonestr("{\"error\":\"no result\"}")); diff --git a/basilisk/basilisk.h b/basilisk/basilisk.h index 2f3183160..54a2a4dcc 100755 --- a/basilisk/basilisk.h +++ b/basilisk/basilisk.h @@ -20,7 +20,7 @@ #include "../iguana/iguana777.h" -#define BASILISK_TIMEOUT 5000 +#define BASILISK_TIMEOUT 3000 #define BASILISK_MINFANOUT 8 #define BASILISK_MAXFANOUT 64 #define BASILISK_DEFAULTDIFF 0x1effffff @@ -76,8 +76,8 @@ struct basilisk_value { bits256 txid; int64_t value; int32_t height; int16_t vou struct basilisk_item { struct queueitem DL; UT_hash_handle hh; - double expiration; cJSON *retarray; - uint32_t submit,finished,basilisktag,numresults,numsent,numrequired,nBits; + double expiration,finished; cJSON *results[64]; + uint32_t submit,basilisktag,numresults,numsent,numrequired,nBits,duration; char symbol[32],CMD[4],remoteaddr[64],*retstr; }; @@ -102,7 +102,7 @@ void basilisk_msgprocess(struct supernet_info *myinfo,void *addr,uint32_t sender int32_t basilisk_sendcmd(struct supernet_info *myinfo,char *destipaddr,char *type,uint32_t *basilisktagp,int32_t encryptflag,int32_t delaymillis,uint8_t *data,int32_t datalen,int32_t fanout,uint32_t nBits); // data must be offset by sizeof(iguana_msghdr)+sizeof(basilisktag) void basilisks_init(struct supernet_info *myinfo); -void basilisk_p2p(void *myinfo,void *_addr,char *ipaddr,uint8_t *data,int32_t datalen,char *type,int32_t encrypted); +void basilisk_p2p(struct supernet_info *myinfo,struct iguana_info *coin,struct iguana_peer *addr,char *senderip,uint8_t *data,int32_t datalen,char *type,int32_t encrypted); uint8_t *basilisk_jsondata(int32_t extraoffset,uint8_t **ptrp,uint8_t *space,int32_t spacesize,int32_t *datalenp,char *symbol,cJSON *sendjson,uint32_t basilisktag); uint8_t *SuperNET_ciphercalc(void **ptrp,int32_t *cipherlenp,bits256 *privkeyp,bits256 *destpubkeyp,uint8_t *data,int32_t datalen,uint8_t *space2,int32_t space2size); diff --git a/basilisk/basilisk_CMD.c b/basilisk/basilisk_CMD.c index 5a25b9a4b..97010ac4d 100755 --- a/basilisk/basilisk_CMD.c +++ b/basilisk/basilisk_CMD.c @@ -206,7 +206,7 @@ char *basilisk_respond_VPNmessage(struct supernet_info *myinfo,char *CMD,void *a if ( coin != 0 && (ptr= basilisk_bitcoinrawtx(&Lptr,myinfo,coin,remoteaddr,basilisktag,timeoutmillis,valsobj)) != 0 ) { retstr = ptr->retstr; - ptr->finished = (uint32_t)time(NULL); + ptr->finished = OS_milliseconds() + 10000; } else retstr = clonestr("{\"error\":\"no coin specified or error bitcoinrawtx\"}"); return(retstr); }*/ @@ -220,7 +220,7 @@ char *basilisk_respond_value(struct supernet_info *myinfo,char *CMD,void *addr,c if ( coin != 0 && (ptr= basilisk_bitcoinvalue(&Lptr,myinfo,coin,remoteaddr,basilisktag,timeoutmillis,valsobj)) != 0 ) { retstr = ptr->retstr; - ptr->finished = (uint32_t)time(NULL); + ptr->finished = OS_milliseconds() + 10000; } else retstr = clonestr("{\"error\":\"no coin specified or error bitcoin value\"}"); return(retstr); } @@ -234,7 +234,7 @@ char *basilisk_respond_balances(struct supernet_info *myinfo,char *CMD,void *add if ( coin != 0 && (ptr= basilisk_bitcoinbalances(&Lptr,myinfo,coin,remoteaddr,basilisktag,timeoutmillis,valsobj)) != 0 ) { retstr = ptr->retstr; - ptr->finished = (uint32_t)time(NULL); + ptr->finished = OS_milliseconds() + 10000; } else retstr = clonestr("{\"error\":\"no coin specified or error bitcoin balances\"}"); return(retstr); } @@ -243,13 +243,13 @@ char *basilisk_respond_getinfo(struct supernet_info *myinfo,char *CMD,void *addr { char *symbol,*retstr=0; struct basilisk_item Lptr,*ptr; int32_t timeoutmillis; struct iguana_info *coin = 0; if ( (timeoutmillis= jint(valsobj,"timeout")) <= 0 ) - timeoutmillis = 1000; + timeoutmillis = 5000; if ( (symbol= jstr(valsobj,"coin")) != 0 || (symbol= jstr(valsobj,"symbol")) != 0 ) coin = iguana_coinfind(symbol); if ( coin != 0 && (ptr= basilisk_getinfo(&Lptr,myinfo,coin,remoteaddr,basilisktag,timeoutmillis,valsobj)) != 0 ) { retstr = ptr->retstr; - ptr->finished = (uint32_t)time(NULL); + ptr->finished = OS_milliseconds() + 10000; } else retstr = clonestr("{\"error\":\"no coin specified or error bitcoin getinfo\"}"); return(retstr); } diff --git a/basilisk/basilisk_DEX.c b/basilisk/basilisk_DEX.c index 6bdf8dc44..47e2596bc 100755 --- a/basilisk/basilisk_DEX.c +++ b/basilisk/basilisk_DEX.c @@ -420,6 +420,7 @@ STRING_ARG(InstantDEX,available,source) { if ( (unspents= iguana_listunspents(myinfo,coin,0,0,0,remoteaddr)) != 0 ) { + //printf("available.(%s)\n",jprint(unspents,0)); if ( (n= cJSON_GetArraySize(unspents)) > 0 ) { for (i=0; iDEXactive = (uint32_t)time(NULL) + 3*BASILISK_TIMEOUT; jadd64bits(vals,"minamount",jdouble(vals,"minprice") * jdouble(vals,"amount") * SATOSHIDEN); if ( jobj(vals,"srchash") == 0 ) - jaddbits256(vals,"srchash",myinfo->myaddr.pubkey); + jaddbits256(vals,"srchash",myinfo->myaddr.persistent); if ( jobj(vals,"desthash") == 0 ) jaddbits256(vals,"desthash",hash); jadd64bits(vals,"satoshis",jdouble(vals,"amount") * SATOSHIDEN); @@ -494,10 +495,10 @@ INT_ARG(InstantDEX,automatched,requestid) int32_t InstantDEX_incoming_func(struct supernet_info *myinfo,void *ptr,uint8_t *data,int32_t datalen) { - int32_t i; - for (i=0; iDEXpoll) + 2*drift; @@ -520,7 +521,7 @@ INT_ARG(InstantDEX,incoming,requestid) retjson = cJSON_CreateObject(); DEX_channel = 'D' + ((uint32_t)'E' << 8) + ((uint32_t)'X' << 16); msgid = (uint32_t)time(NULL) + drift; - if ( (retarray= basilisk_channelget(myinfo,zero,myinfo->myaddr.persistent,DEX_channel,msgid,width)) != 0 ) + if ( (retarray= basilisk_channelget(myinfo,zero,myinfo->myaddr.persistent,DEX_channel,msgid,width)) != 0 ) { //printf("GOT.(%s)\n",jprint(retarray,0)); if ( (retval= basilisk_process_retarray(myinfo,0,InstantDEX_process_channelget,data,sizeof(data),DEX_channel,msgid,retarray,InstantDEX_incoming_func)) > 0 ) diff --git a/basilisk/basilisk_MSG.c b/basilisk/basilisk_MSG.c index 3e3907c26..f6c448b25 100755 --- a/basilisk/basilisk_MSG.c +++ b/basilisk/basilisk_MSG.c @@ -15,39 +15,24 @@ // included from basilisk.c -char *basilisk_respond_addmessage(struct supernet_info *myinfo,uint8_t *key,int32_t keylen,uint8_t *data,int32_t datalen,int32_t sendping,uint32_t duration) +int32_t basilisk_messagekeyread(uint8_t *key,uint32_t *channelp,uint32_t *msgidp,bits256 *srchashp,bits256 *desthashp) { - struct basilisk_message *msg; int32_t i; bits256 desthash; - HASH_FIND(hh,myinfo->messagetable,key,keylen,msg); - if ( msg == 0 && keylen == BASILISK_KEYSIZE ) - { - msg = calloc(1,sizeof(*msg) + datalen); - if ( duration == 0 ) - duration = BASILISK_MSGDURATION; - else if ( duration > INSTANTDEX_LOCKTIME*2 ) - duration = INSTANTDEX_LOCKTIME*2; - memcpy(desthash.bytes,&key[BASILISK_KEYSIZE - sizeof(desthash)],sizeof(desthash)); - if ( bits256_nonz(desthash) == 0 ) - msg->broadcast = 1; - msg->duration = duration; - msg->expiration = (uint32_t)time(NULL) + duration; - msg->keylen = keylen; - memcpy(msg->key,key,keylen); - msg->datalen = datalen; - memcpy(msg->data,data,datalen); - portable_mutex_lock(&myinfo->messagemutex); - HASH_ADD_KEYPTR(hh,myinfo->messagetable,msg->key,msg->keylen,msg); - for (i=0; iexpiration); - QUEUEITEMS++; - portable_mutex_unlock(&myinfo->messagemutex); - if ( sendping != 0 ) - { - queue_enqueue("basilisk_message",&myinfo->msgQ,&msg->DL,0); - return(clonestr("{\"result\":\"message added to hashtable\"}")); - } else return(0); - } else return(0); + int32_t keylen = 0; + keylen += iguana_rwnum(0,&key[keylen],sizeof(uint32_t),channelp); + keylen += iguana_rwnum(0,&key[keylen],sizeof(uint32_t),msgidp); + keylen += iguana_rwbignum(0,&key[keylen],sizeof(*srchashp),srchashp->bytes); + keylen += iguana_rwbignum(0,&key[keylen],sizeof(*desthashp),desthashp->bytes); + return(keylen); +} + +int32_t basilisk_messagekey(uint8_t *key,uint32_t channel,uint32_t msgid,bits256 srchash,bits256 desthash) +{ + int32_t keylen = 0; + keylen += iguana_rwnum(1,&key[keylen],sizeof(uint32_t),&channel); + keylen += iguana_rwnum(1,&key[keylen],sizeof(uint32_t),&msgid); + keylen += iguana_rwbignum(1,&key[keylen],sizeof(srchash),srchash.bytes); + keylen += iguana_rwbignum(1,&key[keylen],sizeof(desthash),desthash.bytes); + return(keylen); } cJSON *basilisk_msgjson(struct basilisk_message *msg,uint8_t *key,int32_t keylen) @@ -70,56 +55,15 @@ cJSON *basilisk_msgjson(struct basilisk_message *msg,uint8_t *key,int32_t keylen return(msgjson); } -cJSON *basilisk_respond_getmessage(struct supernet_info *myinfo,uint8_t *key,int32_t keylen) +cJSON *_basilisk_respond_getmessage(struct supernet_info *myinfo,uint8_t *key,int32_t keylen) { cJSON *msgjson = 0; struct basilisk_message *msg; - portable_mutex_lock(&myinfo->messagemutex); HASH_FIND(hh,myinfo->messagetable,key,keylen,msg); if ( msg != 0 && msg->broadcast == 0 ) msgjson = basilisk_msgjson(msg,key,keylen); - portable_mutex_unlock(&myinfo->messagemutex); return(msgjson); } -// respond to incoming OUT, MSG - -int32_t basilisk_messagekeyread(uint8_t *key,uint32_t *channelp,uint32_t *msgidp,bits256 *srchashp,bits256 *desthashp) -{ - int32_t keylen = 0; - keylen += iguana_rwnum(0,&key[keylen],sizeof(uint32_t),channelp); - keylen += iguana_rwnum(0,&key[keylen],sizeof(uint32_t),msgidp); - keylen += iguana_rwbignum(0,&key[keylen],sizeof(*srchashp),srchashp->bytes); - keylen += iguana_rwbignum(0,&key[keylen],sizeof(*desthashp),desthashp->bytes); - return(keylen); -} - -int32_t basilisk_messagekey(uint8_t *key,uint32_t channel,uint32_t msgid,bits256 srchash,bits256 desthash) -{ - int32_t keylen = 0; - keylen += iguana_rwnum(1,&key[keylen],sizeof(uint32_t),&channel); - keylen += iguana_rwnum(1,&key[keylen],sizeof(uint32_t),&msgid); - keylen += iguana_rwbignum(1,&key[keylen],sizeof(srchash),srchash.bytes); - keylen += iguana_rwbignum(1,&key[keylen],sizeof(desthash),desthash.bytes); - return(keylen); -} - -char *basilisk_respond_OUT(struct supernet_info *myinfo,char *CMD,void *addr,char *remoteaddr,uint32_t basilisktag,cJSON *valsobj,uint8_t *data,int32_t datalen,bits256 hash,int32_t from_basilisk) -{ - int32_t keylen,duration; uint8_t key[BASILISK_KEYSIZE]; bits256 senderhash; char *retstr; - senderhash = jbits256(valsobj,"srchash"); - duration = juint(valsobj,"duration"); - keylen = basilisk_messagekey(key,juint(valsobj,"channel"),juint(valsobj,"msgid"),senderhash,hash); - retstr = basilisk_respond_addmessage(myinfo,key,keylen,data,datalen,1,duration); - if ( bits256_nonz(hash) == 0 ) - { - if ( duration > BASILISK_MSGDURATION ) - duration = BASILISK_MSGDURATION; - } - // printf("OUT keylen.%d datalen.%d\n",keylen,datalen); - char str[65]; printf("add message.[%d] channel.%u msgid.%x %s\n",datalen,juint(valsobj,"channel"),juint(valsobj,"msgid"),bits256_str(str,hash)); - return(retstr); -} - int32_t basilisk_msgcmp(struct basilisk_message *msg,int32_t width,uint32_t channel,uint32_t msgid,bits256 srchash,bits256 desthash) { uint32_t keychannel,keymsgid; bits256 keysrc,keydest; @@ -141,67 +85,159 @@ int32_t basilisk_msgcmp(struct basilisk_message *msg,int32_t width,uint32_t chan char *basilisk_iterate_MSG(struct supernet_info *myinfo,uint32_t channel,uint32_t msgid,bits256 srchash,bits256 desthash,int32_t origwidth) { - struct basilisk_message *msg,*tmpmsg; uint8_t key[BASILISK_KEYSIZE]; int32_t i,keylen,width; cJSON *item,*retjson,*array; bits256 zero; + uint8_t key[BASILISK_KEYSIZE]; int32_t i,keylen,width; cJSON *msgjson,*item,*retjson,*array; bits256 zero; struct basilisk_message *msg,*tmpmsg; uint32_t now = (uint32_t)time(NULL); memset(zero.bytes,0,sizeof(zero)); - array = cJSON_CreateArray(); if ( (width= origwidth) > 3600 ) width = 3600; else if ( width < 1 ) width = 1; + char str[65],str2[65]; printf("MSGiterate (%s) -> (%s)\n",bits256_str(str,srchash),bits256_str(str2,desthash)); + array = cJSON_CreateArray(); portable_mutex_lock(&myinfo->messagemutex); - HASH_ITER(hh,myinfo->messagetable,msg,tmpmsg) + if ( bits256_nonz(srchash) == 0 ) { - if ( msg->broadcast != 0 && basilisk_msgcmp(msg,origwidth,channel,msgid,zero,zero) == 0 ) - jaddi(array,basilisk_msgjson(msg,msg->key,msg->keylen)); + HASH_ITER(hh,myinfo->messagetable,msg,tmpmsg) + { + if ( basilisk_msgcmp(msg,origwidth,channel,msgid,zero,zero) == 0 ) + { + if ( (msgjson= basilisk_msgjson(msg,msg->key,msg->keylen)) != 0 ) + jaddi(array,msgjson); + } + if ( now > msg->expiration ) + { + printf("delete expired message.%p QUEUEITEMS.%d\n",msg,QUEUEITEMS); + HASH_DELETE(hh,myinfo->messagetable,msg); + QUEUEITEMS--; + free(msg); + } + } } - portable_mutex_unlock(&myinfo->messagemutex); - //printf("iterate_MSG width.%d channel.%d msgid.%d src.%llx -> %llx\n",origwidth,channel,msgid,(long long)srchash.txid,(long long)desthash.txid); + //printf("iterate_MSG allflag.%d width.%d channel.%d msgid.%d src.%llx -> %llx\n",allflag,origwidth,channel,msgid,(long long)srchash.txid,(long long)desthash.txid); for (i=0; i 0 ) { if ( bits256_nonz(srchash) != 0 ) { keylen = basilisk_messagekey(key,channel,msgid,zero,desthash); - if ( (item= basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) + if ( (item= _basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) jaddi(array,item);//, printf("gotmsg1.(%s)\n",jprint(item,0)); + //keylen = basilisk_messagekey(key,channel,msgid,desthash,zero); + //if ( (item= _basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) + // jaddi(array,item);//, printf("gotmsg1.(%s)\n",jprint(item,0)); } if ( bits256_nonz(desthash) != 0 ) { keylen = basilisk_messagekey(key,channel,msgid,srchash,zero); - if ( (item= basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) + if ( (item= _basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) jaddi(array,item);//, printf("gotmsg2.(%s)\n",jprint(item,0)); + //keylen = basilisk_messagekey(key,channel,msgid,zero,srchash); + //if ( (item= _basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) + // jaddi(array,item);//, printf("gotmsg2.(%s)\n",jprint(item,0)); } if ( bits256_nonz(srchash) != 0 && bits256_nonz(desthash) != 0 ) { keylen = basilisk_messagekey(key,channel,msgid,zero,zero); - if ( (item= basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) + if ( (item= _basilisk_respond_getmessage(myinfo,key,keylen)) != 0 ) jaddi(array,item);//, printf("gotmsg3.(%s)\n",jprint(item,0)); } } msgid--; } + portable_mutex_unlock(&myinfo->messagemutex); if ( cJSON_GetArraySize(array) > 0 ) { retjson = cJSON_CreateObject(); jaddstr(retjson,"result","success"); jadd(retjson,"messages",array); - //printf("MESSAGES.(%s)\n",jprint(array,0)); + printf("MESSAGES.(%s)\n",jprint(array,0)); return(jprint(retjson,1)); - } else return(clonestr("{\"error\":\"no messages\"}")); + } + printf("no matching messages\n"); + return(clonestr("{\"error\":\"no messages\"}")); +} + +char *basilisk_respond_addmessage(struct supernet_info *myinfo,uint8_t *key,int32_t keylen,uint8_t *data,int32_t datalen,int32_t sendping,uint32_t duration) +{ + struct basilisk_message *msg; int32_t i; bits256 desthash; + if ( keylen != BASILISK_KEYSIZE ) + { + printf("basilisk_respond_addmessage keylen.%d != %d\n",keylen,BASILISK_KEYSIZE); + return(0); + } + if ( duration == 0 ) + duration = BASILISK_MSGDURATION; + else if ( duration > INSTANTDEX_LOCKTIME*2 ) + duration = INSTANTDEX_LOCKTIME*2; + portable_mutex_lock(&myinfo->messagemutex); + HASH_FIND(hh,myinfo->messagetable,key,keylen,msg); + if ( msg == 0 )//|| msg->datalen != datalen ) + { + if ( msg != 0 ) + { + printf("overwrite delete of msg.[%d]\n",msg->datalen); + HASH_DELETE(hh,myinfo->messagetable,msg); + QUEUEITEMS--; + free(msg); + } + msg = calloc(1,sizeof(*msg) + datalen); + msg->keylen = keylen; + memcpy(msg->key,key,keylen); + msg->datalen = datalen; + memcpy(msg->data,data,datalen); + memcpy(desthash.bytes,&key[BASILISK_KEYSIZE - sizeof(desthash)],sizeof(desthash)); + if ( bits256_nonz(desthash) == 0 ) + msg->broadcast = 1; + msg->duration = duration; + msg->expiration = (uint32_t)time(NULL) + duration; + HASH_ADD_KEYPTR(hh,myinfo->messagetable,msg->key,msg->keylen,msg); + QUEUEITEMS++; + for (i=0; iexpiration,msg,msg->hh.next,msg->hh.prev); + if ( sendping != 0 ) + queue_enqueue("basilisk_message",&myinfo->msgQ,&msg->DL,0); + } //else memcpy(msg->data,data,datalen); + portable_mutex_unlock(&myinfo->messagemutex); + return(clonestr("{\"result\":\"message added to hashtable\"}")); +} + +// respond to incoming OUT, MSG + +char *basilisk_respond_OUT(struct supernet_info *myinfo,char *CMD,void *addr,char *remoteaddr,uint32_t basilisktag,cJSON *valsobj,uint8_t *data,int32_t datalen,bits256 hash,int32_t from_basilisk) +{ + int32_t keylen,duration; uint8_t key[BASILISK_KEYSIZE]; bits256 desthash,senderhash; char *retstr; + senderhash = jbits256(valsobj,"srchash"); + desthash = jbits256(valsobj,"desthash"); + duration = juint(valsobj,"duration"); + keylen = basilisk_messagekey(key,juint(valsobj,"channel"),juint(valsobj,"msgid"),senderhash,desthash); + if ( bits256_nonz(hash) == 0 ) + { + if ( duration > BASILISK_MSGDURATION ) + duration = BASILISK_MSGDURATION; + } + //char str[65]; printf("add message.[%d] channel.%u msgid.%x %s\n",datalen,juint(valsobj,"channel"),juint(valsobj,"msgid"),bits256_str(str,hash)); + retstr = basilisk_respond_addmessage(myinfo,key,keylen,data,datalen,1,duration); + // printf("OUT keylen.%d datalen.%d\n",keylen,datalen); + return(retstr); } char *basilisk_respond_MSG(struct supernet_info *myinfo,char *CMD,void *addr,char *remoteaddr,uint32_t basilisktag,cJSON *valsobj,uint8_t *data,int32_t datalen,bits256 hash,int32_t from_basilisk) { - int32_t width; uint32_t msgid,channel; + int32_t width; uint32_t msgid,channel; char *retstr; width = juint(valsobj,"width"); msgid = juint(valsobj,"msgid"); channel = juint(valsobj,"channel"); - //char str[65],str2[65]; printf("%s -> %s channel.%u msgid.%x width.%d\n",bits256_str(str,jbits256(valsobj,"sender")),bits256_str(str2,hash),juint(valsobj,"channel"),msgid,width); - return(basilisk_iterate_MSG(myinfo,channel,msgid,jbits256(valsobj,"srchash"),hash,width)); + //char str[65],str2[65]; printf("%s -> %s channel.%u msgid.%x width.%d\n",bits256_str(str,jbits256(valsobj,"sender")),bits256_str(str2,jbits256(valsobj,"desthash")),juint(valsobj,"channel"),msgid,width); + retstr = basilisk_iterate_MSG(myinfo,channel,msgid,jbits256(valsobj,"srchash"),jbits256(valsobj,"desthash"),width); + //printf("iterate_MSG.(%s)\n",retstr); + return(retstr); } #include "../includes/iguana_apidefs.h" @@ -209,9 +245,12 @@ char *basilisk_respond_MSG(struct supernet_info *myinfo,char *CMD,void *addr,cha HASH_ARRAY_STRING(basilisk,getmessage,hash,vals,hexstr) { - uint32_t msgid,width,channel; - jaddbits256(vals,"srchash",hash); - jaddbits256(vals,"desthash",myinfo->myaddr.persistent); + uint32_t msgid,width,channel; char *retstr; + if ( bits256_cmp(GENESIS_PUBKEY,jbits256(vals,"srchash")) == 0 ) + jaddbits256(vals,"srchash",hash); + if ( bits256_cmp(GENESIS_PUBKEY,jbits256(vals,"desthash")) == 0 ) + jaddbits256(vals,"desthash",myinfo->myaddr.persistent); + //char str[65]; printf("getmessage for (%s)\n",bits256_str(str,jbits256(vals,"desthash"))); if ( (msgid= juint(vals,"msgid")) == 0 ) { msgid = (uint32_t)time(NULL); @@ -222,8 +261,9 @@ HASH_ARRAY_STRING(basilisk,getmessage,hash,vals,hexstr) { channel = juint(vals,"channel"); width = juint(vals,"width"); - return(basilisk_iterate_MSG(myinfo,channel,msgid,myinfo->myaddr.persistent,myinfo->myaddr.persistent,width)); - } else return(basilisk_standardservice("MSG",myinfo,0,myinfo->myaddr.persistent,vals,hexstr,1)); + retstr = basilisk_iterate_MSG(myinfo,channel,msgid,jbits256(vals,"srchash"),jbits256(vals,"desthash"),width); + return(retstr); + } else return(basilisk_standardservice("MSG",myinfo,0,jbits256(vals,"desthash"),vals,hexstr,1)); } HASH_ARRAY_STRING(basilisk,sendmessage,hash,vals,hexstr) @@ -231,7 +271,7 @@ HASH_ARRAY_STRING(basilisk,sendmessage,hash,vals,hexstr) int32_t keylen,datalen; uint8_t key[BASILISK_KEYSIZE],space[16384],*data,*ptr = 0; char *retstr=0; if ( myinfo->IAMNOTARY != 0 && myinfo->NOTARY.RELAYID >= 0 ) { - keylen = basilisk_messagekey(key,juint(vals,"channel"),juint(vals,"msgid"),jbits256(vals,"srchash"),hash); + keylen = basilisk_messagekey(key,juint(vals,"channel"),juint(vals,"msgid"),jbits256(vals,"srchash"),jbits256(vals,"desthash")); if ( (data= get_dataptr(BASILISK_HDROFFSET,&ptr,&datalen,space,sizeof(space),hexstr)) != 0 ) { retstr = basilisk_respond_addmessage(myinfo,key,keylen,data,datalen,0,juint(vals,"duration")); @@ -242,8 +282,8 @@ HASH_ARRAY_STRING(basilisk,sendmessage,hash,vals,hexstr) free(retstr); } if ( vals != 0 && juint(vals,"fanout") == 0 ) - jaddnum(vals,"fanout",MAX(5,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+2)); - return(basilisk_standardservice("OUT",myinfo,0,hash,vals,hexstr,0)); + jaddnum(vals,"fanout",MAX(8,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+2)); + return(basilisk_standardservice("OUT",myinfo,0,jbits256(vals,"desthash"),vals,hexstr,0)); } #include "../includes/iguana_apiundefs.h" @@ -256,12 +296,12 @@ int32_t basilisk_channelsend(struct supernet_info *myinfo,bits256 srchash,bits25 jaddnum(valsobj,"channel",channel); if ( msgid == 0 ) msgid = (uint32_t)time(NULL); - jaddnum(valsobj,"fanout",MAX(5,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+2)); + jaddnum(valsobj,"fanout",MAX(8,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+2)); jaddnum(valsobj,"msgid",msgid); jaddnum(valsobj,"duration",duration); jaddbits256(valsobj,"srchash",srchash); jaddbits256(valsobj,"desthash",desthash); - char str[65]; printf("sendmessage.[%d] channel.%u msgid.%x -> %s numrelays.%d:%d\n",datalen,channel,msgid,bits256_str(str,desthash),myinfo->NOTARY.NUMRELAYS,juint(valsobj,"fanout")); + //char str[65]; printf("sendmessage.[%d] channel.%u msgid.%x -> %s numrelays.%d:%d\n",datalen,channel,msgid,bits256_str(str,desthash),myinfo->NOTARY.NUMRELAYS,juint(valsobj,"fanout")); if ( (retstr= basilisk_sendmessage(myinfo,0,0,0,desthash,valsobj,hexstr)) != 0 ) free(retstr); free_json(valsobj); @@ -289,7 +329,7 @@ int32_t basilisk_message_returned(uint8_t *key,uint8_t *data,int32_t maxlen,cJSO decode_hex(data,datalen,hexstr); //printf("decoded hexstr.[%d]\n",datalen); retval = datalen; - } else printf("datalen.%d < maxlen.%d\n",datalen,maxlen); + } else printf("datalen.%d >= maxlen.%d\n",datalen,maxlen); } } } //else printf("no hexstr.%p or datalen.%d (%s)\n",hexstr,datalen,jprint(json,0)); @@ -305,14 +345,14 @@ cJSON *basilisk_channelget(struct supernet_info *myinfo,bits256 srchash,bits256 msgid = (uint32_t)time(NULL); jaddnum(valsobj,"msgid",msgid); jaddnum(valsobj,"width",width); - jaddnum(valsobj,"timeout",2500); - jaddnum(valsobj,"fanout",MAX(5,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); + jaddnum(valsobj,"timeout",BASILISK_TIMEOUT); + jaddnum(valsobj,"fanout",MAX(8,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); jaddnum(valsobj,"numrequired",1); jaddbits256(valsobj,"srchash",srchash); jaddbits256(valsobj,"desthash",desthash); if ( (retstr= basilisk_getmessage(myinfo,0,0,0,desthash,valsobj,0)) != 0 ) { - printf("channel.%u msgid.%u gotmessage.(%d)\n",channel,msgid,(int32_t)strlen(retstr)); + //printf("channel.%u msgid.%u gotmessage.(%d)\n",channel,msgid,(int32_t)strlen(retstr)); if ( (retarray= cJSON_Parse(retstr)) != 0 ) { if ( is_cJSON_Array(retarray) == 0 ) diff --git a/basilisk/basilisk_bitcoin.c b/basilisk/basilisk_bitcoin.c index dea04fc92..acf5e5c0a 100755 --- a/basilisk/basilisk_bitcoin.c +++ b/basilisk/basilisk_bitcoin.c @@ -842,7 +842,7 @@ HASH_ARRAY_STRING(basilisk,value,hash,vals,hexstr) if ( coin->FULLNODE != 0 && (ptr= basilisk_bitcoinvalue(&Lptr,myinfo,coin,remoteaddr,basilisktag,timeoutmillis,vals)) != 0 ) { retstr = ptr->retstr, ptr->retstr = 0; - ptr->finished = (uint32_t)time(NULL); + ptr->finished = OS_milliseconds() + 10000; return(retstr); } } @@ -862,7 +862,7 @@ HASH_ARRAY_STRING(basilisk,rawtx,hash,vals,hexstr) if ( jobj(vals,"numrequired") == 0 ) jaddnum(vals,"numrequired",MIN(3,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); if ( jobj(vals,"fanout") == 0 ) - jaddnum(vals,"fanout",MIN(3,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); + jaddnum(vals,"fanout",MAX(3,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); if ( coin != 0 ) { //if ( juint(vals,"burn") == 0 ) diff --git a/basilisk/basilisk_ping.c b/basilisk/basilisk_ping.c index 191cf36fe..de8cbec95 100755 --- a/basilisk/basilisk_ping.c +++ b/basilisk/basilisk_ping.c @@ -152,7 +152,7 @@ int32_t basilisk_ping_genMSG(struct supernet_info *myinfo,uint8_t *data,int32_t datalen += iguana_rwnum(1,&data[datalen],sizeof(msg->duration),&msg->duration); if ( maxlen > datalen+msg->datalen ) { - //printf("SEND keylen.%d msglen.%d\n",msg->keylen,msg->datalen); + printf("SEND keylen.%d msglen.%d\n",msg->keylen,msg->datalen); memcpy(&data[datalen],msg->data,msg->datalen), datalen += msg->datalen; } else @@ -263,7 +263,7 @@ int32_t basilisk_ping_gen(struct supernet_info *myinfo,uint8_t *data,int32_t max datalen += basilisk_ping_genMSG(myinfo,&data[datalen],maxlen - datalen); //for (i=0; i>>>>>>>>> Q.%d\n",datalen,myinfo->RELAYID,QUEUEITEMS); + //printf("output ping datalen.%d relay.%d >>>>>>>>>> Q.%d\n",datalen,myinfo->NOTARY.RELAYID,QUEUEITEMS); return(datalen); } diff --git a/basilisk/basilisk_tradebot.c b/basilisk/basilisk_tradebot.c index bc62e5858..16e1499d1 100755 --- a/basilisk/basilisk_tradebot.c +++ b/basilisk/basilisk_tradebot.c @@ -236,7 +236,7 @@ double basilisk_request_listprocess(struct supernet_info *myinfo,struct basilisk double basilisk_process_results(struct supernet_info *myinfo,struct basilisk_request *issueR,cJSON *retjson,double hwm) { - cJSON *array,*item; uint8_t *hexdata,*allocptr,hexspace[8192]; char *hexstr; int32_t i,hexlen,n,m,nonz; struct basilisk_request tmpR,R,refR,list[BASILISK_MAXRELAYS]; double metric=0.; + cJSON *array,*item; uint8_t *hexdata,*allocptr,hexspace[32768]; char *hexstr; int32_t i,hexlen,n,m,nonz; struct basilisk_request tmpR,R,refR,list[BASILISK_MAXRELAYS]; double metric=0.; memset(&refR,0,sizeof(refR)); //printf("process.(%s)\n",jprint(retjson,0)); if ( (array= jarray(&n,retjson,"messages")) != 0 ) @@ -250,8 +250,9 @@ double basilisk_process_results(struct supernet_info *myinfo,struct basilisk_req { if ( (hexdata= get_dataptr(0,&allocptr,&hexlen,hexspace,sizeof(hexspace),hexstr)) != 0 ) { + memset(&R,0,sizeof(R)); basilisk_rwDEXquote(0,hexdata,&R); - printf("[%d].(%s)\n",i,jprint(basilisk_requestjson(&R),1)); + //printf("[%d].(%s)\n",i,jprint(basilisk_requestjson(&R),1)); } } else basilisk_parsejson(&R,item); if ( nonz != 0 ) diff --git a/iguana/iguana777.c b/iguana/iguana777.c index db10b4bc6..626c8774e 100755 --- a/iguana/iguana777.c +++ b/iguana/iguana777.c @@ -742,6 +742,7 @@ void iguana_helper(void *arg) for (i=0; ibundles[i] == 0 || coin->bundles[i]->utxofinish <= 1 ) break; + retval = 1; if ( bp->utxofinish == 0 || (retval= iguana_spendvectors(myinfo,coin,bp,&bp->ramchain,0,bp->n,1,0)) >= 0 ) { if ( retval > 0 ) @@ -853,6 +854,11 @@ void iguana_coinloop(void *arg) { if ( (coin= coins[i]) != 0 ) { + if ( strcmp(coin->symbol,"NOTARY") == 0 ) + { + if ( myinfo->expiration != 0 && (myinfo->IAMLP != 0 || myinfo->DEXactive > now) ) + basilisk_requests_poll(myinfo); + } if ( n > 1 && coin->RTheight > 0 && (rand() % 10) != 0 ) continue; if ( coin->peers == 0 ) diff --git a/iguana/iguana777.h b/iguana/iguana777.h index ee45bc7d1..dd8d3bd95 100755 --- a/iguana/iguana777.h +++ b/iguana/iguana777.h @@ -86,7 +86,7 @@ struct supernet_info portable_mutex_t bu_mutex,allcoins_mutex,gecko_mutex,basilisk_mutex,DEX_mutex,DEX_reqmutex,DEX_swapmutex; struct queueitem *DEX_quotes; cJSON *Cunspents,*Cspends; struct basilisk_swap *swaps[256]; int32_t numswaps; - struct basilisk_message *messagetable; portable_mutex_t messagemutex; queue_t msgQ; + struct basilisk_message *messagetable; portable_mutex_t messagemutex; queue_t msgQ,p2pQ; void *ctx; uint8_t *pingbuf; struct delayedPoW_info dPoW; diff --git a/iguana/iguana_msg.c b/iguana/iguana_msg.c index 81be7eb1c..536343946 100755 --- a/iguana/iguana_msg.c +++ b/iguana/iguana_msg.c @@ -940,7 +940,7 @@ int32_t iguana_msgparser(struct supernet_info *myinfo,struct iguana_info *coin,s } else ipaddr = 0; len = recvlen; //printf("GOT.(%s) len.%d from %s\n",H->command,recvlen,addr->ipaddr); - basilisk_p2p(myinfo,addr,ipaddr,data,recvlen,&H->command[strlen("SuperNET")],H->command[6] == 'e' && H->command[7] == 't'); + basilisk_p2p(myinfo,coin,addr,ipaddr,data,recvlen,&H->command[strlen("SuperNET")],H->command[6] == 'e' && H->command[7] == 't'); return(0); } if ( addr != 0 ) diff --git a/iguana/iguana_payments.c b/iguana/iguana_payments.c index 032ce2e87..052c31d96 100755 --- a/iguana/iguana_payments.c +++ b/iguana/iguana_payments.c @@ -1288,24 +1288,29 @@ ARRAY_OBJ_INT(bitcoinrpc,createrawtransaction,vins,vouts,locktime) cJSON *iguana_listunspents(struct supernet_info *myinfo,struct iguana_info *coin,cJSON *array,int32_t minconf,int32_t maxconf,char *remoteaddr) { + cJSON *retjson; int32_t flag = 0; + if ( array == 0 ) + { + array = iguana_getaddressesbyaccount(myinfo,coin,"*"); + flag = 1; + } if ( minconf == 0 ) minconf = 1; if ( maxconf == 0 ) maxconf = (1 << 30); - return(iguana_RTlistunspent(myinfo,coin,array,minconf,maxconf,remoteaddr,0)); + retjson = iguana_RTlistunspent(myinfo,coin,array,minconf,maxconf,remoteaddr,0); + if ( array != 0 && flag != 0 ) + free_json(array); + return(retjson); } TWOINTS_AND_ARRAY(bitcoinrpc,listunspent,minconf,maxconf,array) { //int32_t numrmds,numunspents=0; uint8_t *rmdarray; cJSON *retjson = cJSON_CreateArray(); - cJSON *argarray,*retjson; + cJSON *retjson; if ( remoteaddr != 0 ) return(clonestr("{\"error\":\"no remote\"}")); - if ( (argarray= array) == 0 || cJSON_GetArraySize(array) == 0 ) - argarray = iguana_getaddressesbyaccount(myinfo,coin,"*"); - retjson = iguana_listunspents(myinfo,coin,argarray,minconf,maxconf,remoteaddr); - if ( argarray != array ) - free_json(argarray); + retjson = iguana_listunspents(myinfo,coin,array,minconf,maxconf,remoteaddr); return(jprint(retjson,1)); } diff --git a/iguana/iguana_peers.c b/iguana/iguana_peers.c index 9efdb8d82..6323e0d74 100755 --- a/iguana/iguana_peers.c +++ b/iguana/iguana_peers.c @@ -413,6 +413,9 @@ int32_t iguana_socket(int32_t bindflag,char *hostname,uint16_t port) closesocket(sock); return(-1); } + timeout.tv_sec = 10000000; + timeout.tv_usec = 0; + setsockopt(sock,SOL_SOCKET,SO_RCVTIMEO,(void *)&timeout,sizeof(timeout)); } else { @@ -448,9 +451,9 @@ int32_t iguana_socket(int32_t bindflag,char *hostname,uint16_t port) } } #ifdef __APPLE__ - timeout.tv_sec = 0; - timeout.tv_usec = 30000; - setsockopt(sock,SOL_SOCKET,SO_RCVTIMEO,(void *)&timeout,sizeof(timeout)); + //timeout.tv_sec = 0; + //timeout.tv_usec = 30000; + //setsockopt(sock,SOL_SOCKET,SO_RCVTIMEO,(void *)&timeout,sizeof(timeout)); timeout.tv_sec = 0; timeout.tv_usec = 10000; setsockopt(sock,SOL_SOCKET,SO_SNDTIMEO,(void *)&timeout,sizeof(timeout)); @@ -584,7 +587,7 @@ int32_t iguana_recv(char *ipaddr,int32_t usock,uint8_t *recvbuf,int32_t len) remains -= recvlen; //int32_t i; for (i=0; iXoffset); *prevhashp = prev_hash = X[ind]; - if ( (unspentind= iguana_unspentindfind(myinfo,coin,&RTspent,0,0,0,0,&height,prev_hash,prev_vout,spent_hdrsi-1,0)) != 0 ) - //if ( (firstvout= iguana_txidfastfind(coin,&height,prev_hash,spent_hdrsi-1)) >= 0 ) + if ( (unspentind= iguana_unspentindfind(myinfo,coin,&RTspent,0,0,0,0,&height,prev_hash,prev_vout,spent_hdrsi-1,0)) > 0 ) + //if ( (firstvout= iguana_txidfastfind(coin,&height,prev_hash,spent_hdrsi-1)) > 0 ) { /*duration = (OS_milliseconds() - startmillis); if ( ((uint64_t)coin->txidfind_num % 100) == 1 ) diff --git a/iguana/iguana_txidfind.c b/iguana/iguana_txidfind.c index 5255dee9a..d8cec460f 100755 --- a/iguana/iguana_txidfind.c +++ b/iguana/iguana_txidfind.c @@ -362,13 +362,13 @@ int32_t iguana_txidfastfind(struct iguana_info *coin,int32_t *heightp,bits256 tx if ( val >= tablesize ) val = 0; if ( (i= hashtable[val]) == 0 ) - return(-1); + return(0); else { if ( i > num ) { printf("illegal val.%d vs num.%d tablesize.%d fastfind.%02x\n",i,num,tablesize,txid.bytes[31]); - return(-1); + return(0); } else { @@ -381,7 +381,7 @@ int32_t iguana_txidfastfind(struct iguana_info *coin,int32_t *heightp,bits256 tx if ( *heightp >= (lasthdrsi+1)*coin->chain->bundlesize ) { printf("txidfastfind: unexpected height.%d with lasthdrsi.%d\n",*heightp,lasthdrsi); - return(-1); + return(0); } return(firstvout); } @@ -403,7 +403,7 @@ int32_t iguana_txidfastfind(struct iguana_info *coin,int32_t *heightp,bits256 tx } } } - return(-1); + return(0); } int32_t iguana_fastfindadd(struct iguana_info *coin,bits256 txid,int32_t height,uint32_t firstvout) diff --git a/iguana/iguana_unspents.c b/iguana/iguana_unspents.c index a32a44a22..f04c965d1 100755 --- a/iguana/iguana_unspents.c +++ b/iguana/iguana_unspents.c @@ -73,7 +73,7 @@ int32_t iguana_unspentindfind(struct supernet_info *myinfo,struct iguana_info *c *spentamountp = 0; if ( coinaddr != 0 ) coinaddr[0] = 0; - if ( coin->fastfind != 0 && (firstvout= iguana_txidfastfind(coin,heightp,txid,lasthdrsi)) >= 0 ) + if ( coin->fastfind != 0 && (firstvout= iguana_txidfastfind(coin,heightp,txid,lasthdrsi)) > 0 ) unspentind = (firstvout + vout); else if ( (tp= iguana_txidfind(coin,heightp,&TX,txid,lasthdrsi)) != 0 ) unspentind = (tp->firstvout + vout); @@ -1039,8 +1039,8 @@ cJSON *iguana_RTlistunspent(struct supernet_info *myinfo,struct iguana_info *coi jaddstr(vals,"coin",coin->symbol); jaddnum(vals,"history",1); jaddnum(vals,"firstheight",0); - jaddnum(vals,"fanout",MAX(5,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); - jaddnum(vals,"numrequired",MAX(5,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); + jaddnum(vals,"fanout",MAX(8,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); + jaddnum(vals,"numrequired",MIN(4,(int32_t)sqrt(myinfo->NOTARY.NUMRELAYS)+1)); jadd(vals,"addresses",jduplicate(argarray)); if ( (retstr= basilisk_standardservice("BAL",myinfo,0,hash,vals,"",1)) != 0 ) { diff --git a/iguana/iguana_wallet.c b/iguana/iguana_wallet.c index 18884b54f..625b494cb 100755 --- a/iguana/iguana_wallet.c +++ b/iguana/iguana_wallet.c @@ -1146,7 +1146,7 @@ ZERO_ARGS(bitcoinrpc,getinfo) else { valsobj = cJSON_CreateObject(); - ptr = basilisk_getinfo(&Lptr,myinfo,coin,remoteaddr,0,3000,valsobj); + ptr = basilisk_getinfo(&Lptr,myinfo,coin,remoteaddr,0,5000,valsobj); free_json(valsobj); if ( ptr != 0 && ptr->retstr != 0 ) { @@ -1196,12 +1196,12 @@ ZERO_ARGS(bitcoinrpc,getinfo) } else { - free(ptr->retstr); + ptr->finished = OS_milliseconds(); return(jprint(array,1)); } free_json(array); } - free(ptr->retstr); + ptr->finished = OS_milliseconds(); if ( getinfoobj != 0 ) return(jprint(getinfoobj,1)); } diff --git a/iguana/pnacl/Release/iguana.nmf b/iguana/pnacl/Release/iguana.nmf new file mode 100644 index 000000000..9d37ed227 --- /dev/null +++ b/iguana/pnacl/Release/iguana.nmf @@ -0,0 +1,12 @@ +{ + "program": { + "portable": { + "pnacl-translate": { + "url": "iguana.pexe" + }, + "pnacl-debug": { + "url": "iguana_unstripped.bc" + } + } + } +} diff --git a/includes/iguana_funcs.h b/includes/iguana_funcs.h index 1369ea1d6..b3d76e79f 100755 --- a/includes/iguana_funcs.h +++ b/includes/iguana_funcs.h @@ -565,6 +565,7 @@ int32_t iguana_opreturn(struct supernet_info *myinfo,int32_t ordered,struct igua int32_t iguana_scriptdata(struct iguana_info *coin,uint8_t *scriptspace,long fileptr[2],char *fname,uint64_t scriptpos,int32_t scriptlen); struct iguana_peer *basilisk_ensurerelay(struct supernet_info *myinfo,struct iguana_info *notaries,uint32_t ipbits); int32_t iguana_datachain_scan(struct supernet_info *myinfo,struct iguana_info *coin,uint8_t rmd160[20]); +void basilisk_requests_poll(struct supernet_info *myinfo); void iguana_RTreset(struct iguana_info *coin); void iguana_RTpurge(struct iguana_info *coin,int32_t lastheight); diff --git a/includes/iguana_structs.h b/includes/iguana_structs.h index f1550d962..39d5016ad 100755 --- a/includes/iguana_structs.h +++ b/includes/iguana_structs.h @@ -545,6 +545,14 @@ struct _gfshare_ctx uint8_t sharenrs[255],buffer[]; }; +struct basilisk_p2pitem +{ + struct queueitem DL; + struct iguana_info *coin; struct iguana_peer *addr; + uint32_t ipbits,datalen; char type[4]; + uint8_t data[]; +}; + struct basilisk_request { uint32_t requestid,timestamp,quoteid,quotetime; // 0 to 15