]> Git Repo - VerusCoin.git/blame - src/komodo_jumblr.h
Ensure export finalization edge case
[VerusCoin.git] / src / komodo_jumblr.h
CommitLineData
eeaaf554 1/******************************************************************************
713c2a94 2 * Copyright © 2014-2018 The SuperNET Developers. *
eeaaf554 3 * *
4 * See the AUTHORS, DEVELOPER-AGREEMENT and LICENSE files at *
5 * the top-level directory of this distribution for the individual copyright *
6 * holder information and the developer policies on copyright and licensing. *
7 * *
8 * Unless otherwise agreed in a custom licensing agreement, no part of the *
9 * SuperNET software, including this file may be copied, modified, propagated *
10 * or distributed except according to the terms contained in the LICENSE file *
11 * *
12 * Removal or modification of this copyright notice is prohibited. *
13 * *
14 ******************************************************************************/
15
16/*
17 z_exportkey "zaddr"
18 z_exportwallet "filename"
19 z_getoperationstatus (["operationid", ... ])
20 z_gettotalbalance ( minconf )
21 z_importkey "zkey" ( rescan )
22 z_importwallet "filename"
23 z_listaddresses
24 z_sendmany "fromaddress" [{"address":... ,"amount":..., "memo":"<hex>"},...] ( minconf ) ( fee )
25 */
26
9d365796 27#ifdef _WIN32
28#include <wincrypt.h>
29#endif
5416af1d 30#include "komodo_defs.h"
9d365796 31
eeaaf554 32#define JUMBLR_ADDR "RGhxXpXSSBTBm9EvNsXnTQczthMCxHX91t"
33#define JUMBLR_BTCADDR "18RmTJe9qMech8siuhYfMtHo8RtcN1obC6"
34#define JUMBLR_MAXSECRETADDRS 777
3db947b8 35#define JUMBLR_SYNCHRONIZED_BLOCKS 10
c89c562b 36#define JUMBLR_INCR 9.965
eeaaf554 37#define JUMBLR_FEE 0.001
38#define JUMBLR_TXFEE 0.01
9bbeff91 39#define SMALLVAL 0.000000000000001
eeaaf554 40
3f318aa4 41#define JUMBLR_ERROR_DUPLICATEDEPOSIT -1
42#define JUMBLR_ERROR_SECRETCANTBEDEPOSIT -2
43#define JUMBLR_ERROR_TOOMANYSECRETS -3
44165ded 44#define JUMBLR_ERROR_NOTINWALLET -4
3f318aa4 45
eeaaf554 46struct jumblr_item
47{
48 UT_hash_handle hh;
f3f124e1 49 int64_t amount,fee,txfee; // fee and txfee not really used (yet)
eeaaf554 50 uint32_t spent,pad;
f3f124e1 51 char opid[66],src[128],dest[128],status;
eeaaf554 52} *Jumblrs;
53
54char Jumblr_secretaddrs[JUMBLR_MAXSECRETADDRS][64],Jumblr_deposit[64];
55int32_t Jumblr_numsecretaddrs; // if 0 -> run silent mode
56
a8ec5e86 57char *jumblr_issuemethod(char *userpass,char *method,char *params,uint16_t port)
b487a8fe 58{
59 cJSON *retjson,*resjson = 0; char *retstr;
60 if ( (retstr= komodo_issuemethod(userpass,method,params,port)) != 0 )
61 {
62 if ( (retjson= cJSON_Parse(retstr)) != 0 )
63 {
eb416c9c 64 if ( jobj(retjson,(char *)"result") != 0 )
65 resjson = jduplicate(jobj(retjson,(char *)"result"));
66 else if ( jobj(retjson,(char *)"error") != 0 )
67 resjson = jduplicate(jobj(retjson,(char *)"error"));
b487a8fe 68 else
69 {
70 resjson = cJSON_CreateObject();
eb416c9c 71 jaddstr(resjson,(char *)"error",(char *)"cant parse return");
b487a8fe 72 }
73 free_json(retjson);
74 }
75 free(retstr);
76 }
77 if ( resjson != 0 )
78 return(jprint(resjson,1));
eb416c9c 79 else return(clonestr((char *)"{\"error\":\"unknown error\"}"));
b487a8fe 80}
81
19acd959 82char *jumblr_importaddress(char *address)
eeaaf554 83{
84 char params[1024];
85 sprintf(params,"[\"%s\", \"%s\", false]",address,address);
307d443c 86 return(jumblr_issuemethod(KMDUSERPASS,(char *)"importaddress",params,BITCOIND_RPCPORT));
eeaaf554 87}
88
44165ded 89char *jumblr_validateaddress(char *addr)
90{
91 char params[1024];
db53f4bf 92 sprintf(params,"[\"%s\"]",addr);
6ba30dbb 93 printf("validateaddress.%s\n",params);
307d443c 94 return(jumblr_issuemethod(KMDUSERPASS,(char *)"validateaddress",params,BITCOIND_RPCPORT));
44165ded 95}
96
eeaaf554 97int32_t Jumblr_secretaddrfind(char *searchaddr)
98{
99 int32_t i;
100 for (i=0; i<Jumblr_numsecretaddrs; i++)
101 {
102 if ( strcmp(searchaddr,Jumblr_secretaddrs[i]) == 0 )
103 return(i);
104 }
105 return(-1);
106}
107
108int32_t Jumblr_secretaddradd(char *secretaddr) // external
109{
110 int32_t ind;
3f318aa4 111 if ( secretaddr != 0 && secretaddr[0] != 0 )
eeaaf554 112 {
3f318aa4 113 if ( Jumblr_numsecretaddrs < JUMBLR_MAXSECRETADDRS )
eeaaf554 114 {
3f318aa4 115 if ( strcmp(Jumblr_deposit,secretaddr) != 0 )
116 {
117 if ( (ind= Jumblr_secretaddrfind(secretaddr)) < 0 )
118 {
c89c562b 119 ind = Jumblr_numsecretaddrs++;
120 safecopy(Jumblr_secretaddrs[ind],secretaddr,64);
121 }
122 return(ind);
3f318aa4 123 } else return(JUMBLR_ERROR_SECRETCANTBEDEPOSIT);
124 } else return(JUMBLR_ERROR_TOOMANYSECRETS);
125 }
126 else
127 {
128 memset(Jumblr_secretaddrs,0,sizeof(Jumblr_secretaddrs));
129 Jumblr_numsecretaddrs = 0;
eeaaf554 130 }
131 return(Jumblr_numsecretaddrs);
132}
133
b487a8fe 134int32_t Jumblr_depositaddradd(char *depositaddr) // external
eeaaf554 135{
44165ded 136 int32_t ind,retval = JUMBLR_ERROR_DUPLICATEDEPOSIT; char *retstr; cJSON *retjson,*ismine;
eeaaf554 137 if ( depositaddr == 0 )
19acd959 138 depositaddr = (char *)"";
9bbeff91 139 if ( (ind= Jumblr_secretaddrfind(depositaddr)) < 0 )
eeaaf554 140 {
44165ded 141 if ( (retstr= jumblr_validateaddress(depositaddr)) != 0 )
b487a8fe 142 {
143 if ( (retjson= cJSON_Parse(retstr)) != 0 )
144 {
d430a5e8 145 if ( (ismine= jobj(retjson,(char *)"ismine")) != 0 && cJSON_IsTrue(ismine) != 0 )
6ba30dbb 146 {
a8ec5e86 147 retval = 0;
6ba30dbb 148 safecopy(Jumblr_deposit,depositaddr,sizeof(Jumblr_deposit));
149 }
08952acd 150 else
151 {
152 retval = JUMBLR_ERROR_NOTINWALLET;
d430a5e8 153 printf("%s not in wallet: ismine.%p %d %s\n",depositaddr,ismine,cJSON_IsTrue(ismine),jprint(retjson,0));
08952acd 154 }
b487a8fe 155 free_json(retjson);
156 }
157 free(retstr);
158 }
159 }
160 return(retval);
eeaaf554 161}
162
9d365796 163#ifdef _WIN32
164void OS_randombytes(unsigned char *x,long xlen)
165{
166 HCRYPTPROV prov = 0;
167 CryptAcquireContextW(&prov, NULL, NULL,PROV_RSA_FULL, CRYPT_VERIFYCONTEXT | CRYPT_SILENT);
168 CryptGenRandom(prov, xlen, x);
169 CryptReleaseContext(prov, 0);
170}
171#endif
172
eeaaf554 173int32_t Jumblr_secretaddr(char *secretaddr)
174{
175 uint32_t r;
176 if ( Jumblr_numsecretaddrs > 0 )
177 {
19acd959 178 OS_randombytes((uint8_t *)&r,sizeof(r));
eeaaf554 179 r %= Jumblr_numsecretaddrs;
180 safecopy(secretaddr,Jumblr_secretaddrs[r],64);
181 }
182 return(r);
183}
184
185int32_t jumblr_addresstype(char *addr)
186{
aa3be97e 187 if ( addr[0] == '"' && addr[strlen(addr)-1] == '"' )
c8e62868 188 {
aa3be97e 189 addr[strlen(addr)-1] = 0;
190 addr++;
c8e62868 191 }
aa3be97e 192 if ( addr[0] == 'z' && addr[1] == 'c' && strlen(addr) >= 40 )
193 return('z');
eeaaf554 194 else if ( strlen(addr) < 40 )
195 return('t');
c8e62868 196 printf("strange.(%s)\n",addr);
197 return(-1);
eeaaf554 198}
199
200struct jumblr_item *jumblr_opidfind(char *opid)
201{
202 struct jumblr_item *ptr;
203 HASH_FIND(hh,Jumblrs,opid,(int32_t)strlen(opid),ptr);
204 return(ptr);
205}
206
207struct jumblr_item *jumblr_opidadd(char *opid)
208{
8ac54273 209 struct jumblr_item *ptr = 0;
210 if ( opid != 0 && (ptr= jumblr_opidfind(opid)) == 0 )
eeaaf554 211 {
19acd959 212 ptr = (struct jumblr_item *)calloc(1,sizeof(*ptr));
eeaaf554 213 safecopy(ptr->opid,opid,sizeof(ptr->opid));
214 HASH_ADD_KEYPTR(hh,Jumblrs,ptr->opid,(int32_t)strlen(ptr->opid),ptr);
215 if ( ptr != jumblr_opidfind(opid) )
216 printf("jumblr_opidadd.(%s) ERROR, couldnt find after add\n",opid);
217 }
218 return(ptr);
219}
220
eeaaf554 221char *jumblr_zgetnewaddress()
222{
223 char params[1024];
19acd959 224 sprintf(params,"[]");
307d443c 225 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_getnewaddress",params,BITCOIND_RPCPORT));
eeaaf554 226}
227
228char *jumblr_zlistoperationids()
229{
230 char params[1024];
19acd959 231 sprintf(params,"[]");
307d443c 232 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_listoperationids",params,BITCOIND_RPCPORT));
eeaaf554 233}
234
235char *jumblr_zgetoperationresult(char *opid)
236{
237 char params[1024];
238 sprintf(params,"[[\"%s\"]]",opid);
307d443c 239 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_getoperationresult",params,BITCOIND_RPCPORT));
eeaaf554 240}
241
242char *jumblr_zgetoperationstatus(char *opid)
243{
244 char params[1024];
245 sprintf(params,"[[\"%s\"]]",opid);
307d443c 246 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_getoperationstatus",params,BITCOIND_RPCPORT));
eeaaf554 247}
248
249char *jumblr_sendt_to_z(char *taddr,char *zaddr,double amount)
250{
c89c562b 251 char params[1024]; double fee = ((amount-3*JUMBLR_TXFEE) * JUMBLR_FEE) * 1.5;
eeaaf554 252 if ( jumblr_addresstype(zaddr) != 'z' || jumblr_addresstype(taddr) != 't' )
19acd959 253 return(clonestr((char *)"{\"error\":\"illegal address in t to z\"}"));
eeaaf554 254 sprintf(params,"[\"%s\", [{\"address\":\"%s\",\"amount\":%.8f}, {\"address\":\"%s\",\"amount\":%.8f}], 1, %.8f]",taddr,zaddr,amount-fee-JUMBLR_TXFEE,JUMBLR_ADDR,fee,JUMBLR_TXFEE);
61a0f96b 255 printf("t -> z: %s\n",params);
307d443c 256 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_sendmany",params,BITCOIND_RPCPORT));
eeaaf554 257}
258
259char *jumblr_sendz_to_z(char *zaddrS,char *zaddrD,double amount)
260{
261 char params[1024]; double fee = (amount-2*JUMBLR_TXFEE) * JUMBLR_FEE;
262 if ( jumblr_addresstype(zaddrS) != 'z' || jumblr_addresstype(zaddrD) != 'z' )
19acd959 263 return(clonestr((char *)"{\"error\":\"illegal address in z to z\"}"));
c89c562b 264 //sprintf(params,"[\"%s\", [{\"address\":\"%s\",\"amount\":%.8f}, {\"address\":\"%s\",\"amount\":%.8f}], 1, %.8f]",zaddrS,zaddrD,amount-fee-JUMBLR_TXFEE,JUMBLR_ADDR,fee,JUMBLR_TXFEE);
265 sprintf(params,"[\"%s\", [{\"address\":\"%s\",\"amount\":%.8f}], 1, %.8f]",zaddrS,zaddrD,amount-fee-JUMBLR_TXFEE,JUMBLR_TXFEE);
61a0f96b 266 printf("z -> z: %s\n",params);
307d443c 267 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_sendmany",params,BITCOIND_RPCPORT));
eeaaf554 268}
269
270char *jumblr_sendz_to_t(char *zaddr,char *taddr,double amount)
271{
c89c562b 272 char params[1024]; double fee = ((amount-JUMBLR_TXFEE) * JUMBLR_FEE) * 1.5;
eeaaf554 273 if ( jumblr_addresstype(zaddr) != 'z' || jumblr_addresstype(taddr) != 't' )
19acd959 274 return(clonestr((char *)"{\"error\":\"illegal address in z to t\"}"));
eeaaf554 275 sprintf(params,"[\"%s\", [{\"address\":\"%s\",\"amount\":%.8f}, {\"address\":\"%s\",\"amount\":%.8f}], 1, %.8f]",zaddr,taddr,amount-fee-JUMBLR_TXFEE,JUMBLR_ADDR,fee,JUMBLR_TXFEE);
61a0f96b 276 printf("z -> t: %s\n",params);
307d443c 277 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_sendmany",params,BITCOIND_RPCPORT));
eeaaf554 278}
279
007d1a86 280char *jumblr_zlistaddresses()
421d71a2 281{
282 char params[1024];
007d1a86 283 sprintf(params,"[]");
307d443c 284 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_listaddresses",params,BITCOIND_RPCPORT));
421d71a2 285}
286
eeaaf554 287char *jumblr_zlistreceivedbyaddress(char *addr)
288{
289 char params[1024];
290 sprintf(params,"[\"%s\", 1]",addr);
307d443c 291 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_listreceivedbyaddress",params,BITCOIND_RPCPORT));
eeaaf554 292}
293
294char *jumblr_getreceivedbyaddress(char *addr)
295{
296 char params[1024];
297 sprintf(params,"[\"%s\", 1]",addr);
307d443c 298 return(jumblr_issuemethod(KMDUSERPASS,(char *)"getreceivedbyaddress",params,BITCOIND_RPCPORT));
eeaaf554 299}
300
301char *jumblr_importprivkey(char *wifstr)
302{
303 char params[1024];
304 sprintf(params,"[\"%s\", \"\", false]",wifstr);
307d443c 305 return(jumblr_issuemethod(KMDUSERPASS,(char *)"importprivkey",params,BITCOIND_RPCPORT));
eeaaf554 306}
307
308char *jumblr_zgetbalance(char *addr)
309{
310 char params[1024];
311 sprintf(params,"[\"%s\", 1]",addr);
307d443c 312 return(jumblr_issuemethod(KMDUSERPASS,(char *)"z_getbalance",params,BITCOIND_RPCPORT));
eeaaf554 313}
314
315char *jumblr_listunspent(char *coinaddr)
316{
317 char params[1024];
318 sprintf(params,"[1, 99999999, [\"%s\"]]",coinaddr);
307d443c 319 return(jumblr_issuemethod(KMDUSERPASS,(char *)"listunspent",params,BITCOIND_RPCPORT));
eeaaf554 320}
321
bbd64789 322char *jumblr_gettransaction(char *txidstr)
323{
324 char params[1024];
325 sprintf(params,"[\"%s\", 1]",txidstr);
307d443c 326 return(jumblr_issuemethod(KMDUSERPASS,(char *)"getrawtransaction",params,BITCOIND_RPCPORT));
bbd64789 327}
328
329int32_t jumblr_numvins(bits256 txid)
330{
d506468b 331 char txidstr[65],params[1024],*retstr; cJSON *retjson,*vins; int32_t n,numvins = -1;
bbd64789 332 bits256_str(txidstr,txid);
333 if ( (retstr= jumblr_gettransaction(txidstr)) != 0 )
334 {
335 if ( (retjson= cJSON_Parse(retstr)) != 0 )
336 {
c4818fd4 337 if ( jobj(retjson,(char *)"vin") != 0 && ((vins= jarray(&n,retjson,(char *)"vin")) == 0 || n == 0) )
ad74c1a3 338 {
bbd64789 339 numvins = n;
c4818fd4 340 //printf("numvins.%d\n",n);
341 } //else printf("no vin.(%s)\n",retstr);
bbd64789 342 free_json(retjson);
343 }
344 free(retstr);
345 }
346 return(numvins);
347}
348
eeaaf554 349int64_t jumblr_receivedby(char *addr)
350{
351 char *retstr; int64_t total = 0;
352 if ( (retstr= jumblr_getreceivedbyaddress(addr)) != 0 )
353 {
354 total = atof(retstr) * SATOSHIDEN;
355 free(retstr);
356 }
357 return(total);
358}
359
360int64_t jumblr_balance(char *addr)
361{
78408e6b 362 char *retstr; double val; int64_t balance = 0; //cJSON *retjson; int32_t i,n;
90da8c91 363 /*if ( jumblr_addresstype(addr) == 't' )
eeaaf554 364 {
365 if ( (retstr= jumblr_listunspent(addr)) != 0 )
366 {
61a0f96b 367 //printf("jumblr.[%s].(%s)\n","KMD",retstr);
eeaaf554 368 if ( (retjson= cJSON_Parse(retstr)) != 0 )
369 {
d430a5e8 370 if ( (n= cJSON_GetArraySize(retjson)) > 0 && cJSON_IsArray(retjson) != 0 )
eeaaf554 371 for (i=0; i<n; i++)
19acd959 372 balance += SATOSHIDEN * jdouble(jitem(retjson,i),(char *)"amount");
eeaaf554 373 free_json(retjson);
374 }
375 free(retstr);
376 }
377 }
90da8c91 378 else*/ if ( (retstr= jumblr_zgetbalance(addr)) != 0 )
eeaaf554 379 {
380 if ( (val= atof(retstr)) > SMALLVAL )
381 balance = val * SATOSHIDEN;
382 free(retstr);
383 }
384 return(balance);
385}
386
387int32_t jumblr_itemset(struct jumblr_item *ptr,cJSON *item,char *status)
388{
389 cJSON *params,*amounts,*dest; char *from,*addr; int32_t i,n; int64_t amount;
390 /*"params" : {
391 "fromaddress" : "RDhEGYScNQYetCyG75Kf8Fg61UWPdwc1C5",
392 "amounts" : [
393 {
394 "address" : "zc9s3UdkDFTnnwHrMCr1vYy2WmkjhmTxXNiqC42s7BjeKBVUwk766TTSsrRPKfnX31Bbu8wbrTqnjDqskYGwx48FZMPHvft",
395 "amount" : 3.00000000
396 }
397 ],
398 "minconf" : 1,
399 "fee" : 0.00010000
400 }*/
19acd959 401 if ( (params= jobj(item,(char *)"params")) != 0 )
eeaaf554 402 {
403 //printf("params.(%s)\n",jprint(params,0));
19acd959 404 if ( (from= jstr(params,(char *)"fromaddress")) != 0 )
eeaaf554 405 {
406 safecopy(ptr->src,from,sizeof(ptr->src));
407 }
19acd959 408 if ( (amounts= jarray(&n,params,(char *)"amounts")) != 0 )
eeaaf554 409 {
410 for (i=0; i<n; i++)
411 {
412 dest = jitem(amounts,i);
413 //printf("%s ",jprint(dest,0));
19acd959 414 if ( (addr= jstr(dest,(char *)"address")) != 0 && (amount= jdouble(dest,(char *)"amount")*SATOSHIDEN) > 0 )
eeaaf554 415 {
416 if ( strcmp(addr,JUMBLR_ADDR) == 0 )
417 ptr->fee = amount;
418 else
419 {
420 ptr->amount = amount;
421 safecopy(ptr->dest,addr,sizeof(ptr->dest));
422 }
423 }
424 }
425 }
19acd959 426 ptr->txfee = jdouble(params,(char *)"fee") * SATOSHIDEN;
eeaaf554 427 }
428 return(1);
429}
430
431void jumblr_opidupdate(struct jumblr_item *ptr)
432{
433 char *retstr,*status; cJSON *retjson,*item;
434 if ( ptr->status == 0 )
435 {
436 if ( (retstr= jumblr_zgetoperationstatus(ptr->opid)) != 0 )
437 {
438 if ( (retjson= cJSON_Parse(retstr)) != 0 )
439 {
d430a5e8 440 if ( cJSON_GetArraySize(retjson) == 1 && cJSON_IsArray(retjson) != 0 )
eeaaf554 441 {
442 item = jitem(retjson,0);
443 //printf("%s\n",jprint(item,0));
19acd959 444 if ( (status= jstr(item,(char *)"status")) != 0 )
eeaaf554 445 {
19acd959 446 if ( strcmp(status,(char *)"success") == 0 )
eeaaf554 447 {
448 ptr->status = jumblr_itemset(ptr,item,status);
449 if ( (jumblr_addresstype(ptr->src) == 't' && jumblr_addresstype(ptr->src) == 'z' && strcmp(ptr->src,Jumblr_deposit) != 0) || (jumblr_addresstype(ptr->src) == 'z' && jumblr_addresstype(ptr->src) == 't' && Jumblr_secretaddrfind(ptr->dest) < 0) )
450 {
451 printf("a non-jumblr t->z pruned\n");
452 free(jumblr_zgetoperationresult(ptr->opid));
453 ptr->status = -1;
454 }
455
456 }
19acd959 457 else if ( strcmp(status,(char *)"failed") == 0 )
eeaaf554 458 {
459 printf("jumblr_opidupdate %s failed\n",ptr->opid);
460 free(jumblr_zgetoperationresult(ptr->opid));
461 ptr->status = -1;
462 }
463 }
464 }
465 free_json(retjson);
466 }
467 free(retstr);
468 }
469 }
470}
471
472void jumblr_prune(struct jumblr_item *ptr)
473{
474 struct jumblr_item *tmp; char oldsrc[128]; int32_t flag = 1;
eb23a642 475 if ( is_hexstr(ptr->opid,0) == 64 )
476 return;
eeaaf554 477 printf("jumblr_prune %s\n",ptr->opid);
478 strcpy(oldsrc,ptr->src);
479 free(jumblr_zgetoperationresult(ptr->opid));
480 while ( flag != 0 )
481 {
482 flag = 0;
483 HASH_ITER(hh,Jumblrs,ptr,tmp)
484 {
485 if ( strcmp(oldsrc,ptr->dest) == 0 )
486 {
eb23a642 487 if ( is_hexstr(ptr->opid,0) != 64 )
488 {
489 printf("jumblr_prune %s (%s -> %s) matched oldsrc\n",ptr->opid,ptr->src,ptr->dest);
490 free(jumblr_zgetoperationresult(ptr->opid));
491 strcpy(oldsrc,ptr->src);
492 flag = 1;
493 break;
494 }
eeaaf554 495 }
496 }
497 }
498}
499
d430a5e8
SS
500
501bits256 jbits256(cJSON *json,char *field);
502
503
421d71a2 504void jumblr_zaddrinit(char *zaddr)
505{
bbd64789 506 struct jumblr_item *ptr; char *retstr,*totalstr; cJSON *item,*array; double total; bits256 txid; char txidstr[65],t_z,z_z;
f3f124e1 507 if ( (totalstr= jumblr_zgetbalance(zaddr)) != 0 )
421d71a2 508 {
e5dfb297 509 if ( (total= atof(totalstr)) > SMALLVAL )
421d71a2 510 {
f3f124e1 511 if ( (retstr= jumblr_zlistreceivedbyaddress(zaddr)) != 0 )
512 {
513 if ( (array= cJSON_Parse(retstr)) != 0 )
514 {
afae290a 515 t_z = z_z = 0;
d430a5e8 516 if ( cJSON_GetArraySize(array) == 1 && cJSON_IsArray(array) != 0 )
f3f124e1 517 {
518 item = jitem(array,0);
b8623323 519 if ( (uint64_t)((total+0.0000000049) * SATOSHIDEN) == (uint64_t)((jdouble(item,(char *)"amount")+0.0000000049) * SATOSHIDEN) )
f3f124e1 520 {
bbd64789 521 txid = jbits256(item,(char *)"txid");
f3f124e1 522 bits256_str(txidstr,txid);
523 if ( (ptr= jumblr_opidadd(txidstr)) != 0 )
524 {
525 ptr->amount = (total * SATOSHIDEN);
526 ptr->status = 1;
527 strcpy(ptr->dest,zaddr);
231bcedc 528 if ( jumblr_addresstype(ptr->dest) != 'z' )
529 printf("error setting dest type to Z: %s\n",jprint(item,0));
f3f124e1 530 if ( jumblr_numvins(txid) == 0 )
531 {
532 z_z = 1;
231bcedc 533 strcpy(ptr->src,zaddr);
eb23a642 534 ptr->src[3] = '0';
535 ptr->src[4] = '0';
536 ptr->src[5] = '0';
f3f124e1 537 if ( jumblr_addresstype(ptr->src) != 'z' )
538 printf("error setting address type to Z: %s\n",jprint(item,0));
539 }
540 else
541 {
542 t_z = 1;
543 strcpy(ptr->src,"taddr");
544 if ( jumblr_addresstype(ptr->src) != 't' )
545 printf("error setting address type to T: %s\n",jprint(item,0));
546 }
547 printf("%s %s %.8f t_z.%d z_z.%d\n",zaddr,txidstr,total,t_z,z_z); // cant be z->t from spend
548 }
255e8e69 549 } else printf("mismatched %s %s total %.8f vs %.8f -> %lld\n",zaddr,totalstr,dstr(SATOSHIDEN * total),dstr(SATOSHIDEN * jdouble(item,(char *)"amount")),(long long)((uint64_t)(total * SATOSHIDEN) - (uint64_t)(jdouble(item,(char *)"amount") * SATOSHIDEN)));
f3f124e1 550 }
551 free_json(array);
552 }
553 free(retstr);
554 }
421d71a2 555 }
f3f124e1 556 free(totalstr);
421d71a2 557 }
558}
559
eeaaf554 560void jumblr_opidsupdate()
561{
562 char *retstr; cJSON *array; int32_t i,n; struct jumblr_item *ptr;
563 if ( (retstr= jumblr_zlistoperationids()) != 0 )
564 {
565 if ( (array= cJSON_Parse(retstr)) != 0 )
566 {
d430a5e8 567 if ( (n= cJSON_GetArraySize(array)) > 0 && cJSON_IsArray(array) != 0 )
eeaaf554 568 {
c89c562b 569 //printf("%s -> n%d\n",retstr,n);
eeaaf554 570 for (i=0; i<n; i++)
571 {
572 if ( (ptr= jumblr_opidadd(jstri(array,i))) != 0 )
573 {
574 if ( ptr->status == 0 )
575 jumblr_opidupdate(ptr);
576 //printf("%d: %s -> %s %.8f\n",ptr->status,ptr->src,ptr->dest,dstr(ptr->amount));
577 if ( jumblr_addresstype(ptr->src) == 'z' && jumblr_addresstype(ptr->dest) == 't' )
578 jumblr_prune(ptr);
579 }
580 }
581 }
582 free_json(array);
583 }
584 free(retstr);
585 }
586}
587
ae85ad79 588uint64_t jumblr_increment(uint8_t r,int32_t height,uint64_t total,uint64_t biggest,uint64_t medium, uint64_t smallest)
589{
590 int32_t i,n; uint64_t incrs[1000],remains = total;
591 height /= JUMBLR_SYNCHRONIZED_BLOCKS;
592 if ( (height % JUMBLR_SYNCHRONIZED_BLOCKS) == 0 || total >= 100*biggest )
593 {
594 if ( total >= biggest )
595 return(biggest);
596 else if ( total >= medium )
597 return(medium);
598 else if ( total >= smallest )
599 return(smallest);
600 else return(0);
601 }
602 else
603 {
604 n = 0;
605 while ( remains > smallest && n < sizeof(incrs)/sizeof(*incrs) )
606 {
607 if ( remains >= biggest )
608 incrs[n] = biggest;
609 else if ( remains >= medium )
610 incrs[n] = medium;
611 else if ( remains >= smallest )
612 incrs[n] = smallest;
613 else break;
614 remains -= incrs[n];
615 n++;
616 }
617 if ( n > 0 )
618 {
619 r %= n;
620 for (i=0; i<n; i++)
621 printf("%.8f ",dstr(incrs[i]));
88de65be 622 printf("n.%d incrs r.%d -> %.8f\n",n,r,dstr(incrs[r]));
ae85ad79 623 return(incrs[r]);
624 }
625 }
626 return(0);
627}
628
eeaaf554 629void jumblr_iteration()
630{
dca9da68 631 static int32_t lastheight; static uint32_t lasttime;
ae85ad79 632 char *zaddr,*addr,*retstr,secretaddr[64]; cJSON *array; int32_t i,iter,height,counter,chosen_one,n; uint64_t smallest,medium,biggest,amount=0,total=0; double fee; struct jumblr_item *ptr,*tmp; uint16_t r,s;
eea03b7b 633 if ( JUMBLR_PAUSE != 0 )
634 return;
421d71a2 635 if ( lasttime == 0 )
636 {
637 if ( (retstr= jumblr_zlistaddresses()) != 0 )
638 {
639 if ( (array= cJSON_Parse(retstr)) != 0 )
640 {
d430a5e8 641 if ( (n= cJSON_GetArraySize(array)) > 0 && cJSON_IsArray(array) != 0 )
421d71a2 642 {
643 for (i=0; i<n; i++)
644 jumblr_zaddrinit(jstri(array,i));
645 }
646 free_json(array);
647 }
648 free(retstr);
649 }
650 }
4b729ec5 651 height = (int32_t)chainActive.LastTip()->GetHeight();
a039c62d 652 if ( time(NULL) < lasttime+40 )
dca9da68 653 return;
654 lasttime = (uint32_t)time(NULL);
421d71a2 655 if ( lastheight == height )
656 return;
6a1b2452 657 lastheight = height;
a039c62d 658 if ( (height % JUMBLR_SYNCHRONIZED_BLOCKS) != JUMBLR_SYNCHRONIZED_BLOCKS-3 )
eeaaf554 659 return;
660 fee = JUMBLR_INCR * JUMBLR_FEE;
ae85ad79 661 smallest = SATOSHIDEN * ((JUMBLR_INCR + 3*fee) + 3*JUMBLR_TXFEE);
662 medium = SATOSHIDEN * ((JUMBLR_INCR + 3*fee)*10 + 3*JUMBLR_TXFEE);
663 biggest = SATOSHIDEN * ((JUMBLR_INCR + 3*fee)*777 + 3*JUMBLR_TXFEE);
fd9256e8 664 OS_randombytes((uint8_t *)&r,sizeof(r));
ae85ad79 665 s = (r % 3);
0a92b261 666 //printf("jumblr_iteration r.%u s.%u\n",r,s);
eeaaf554 667 switch ( s )
668 {
eb23a642 669 case 0: // t -> z
ae85ad79 670 default:
671 if ( Jumblr_deposit[0] != 0 && (total= jumblr_balance(Jumblr_deposit)) >= smallest )
eeaaf554 672 {
673 if ( (zaddr= jumblr_zgetnewaddress()) != 0 )
674 {
20082066 675 if ( zaddr[0] == '"' && zaddr[strlen(zaddr)-1] == '"' )
676 {
677 zaddr[strlen(zaddr)-1] = 0;
678 addr = zaddr+1;
679 } else addr = zaddr;
ae85ad79 680 amount = jumblr_increment(r/3,height,total,biggest,medium,smallest);
9d365796 681 /*
eeaaf554 682 amount = 0;
683 if ( (height % (JUMBLR_SYNCHRONIZED_BLOCKS*JUMBLR_SYNCHRONIZED_BLOCKS)) == 0 && total >= SATOSHIDEN * ((JUMBLR_INCR + 3*fee)*100 + 3*JUMBLR_TXFEE) )
ae85ad79 684 amount = SATOSHIDEN * ((JUMBLR_INCR + 3*fee)*100 + 3*JUMBLR_TXFEE);
eeaaf554 685 else if ( (r & 3) == 0 && total >= SATOSHIDEN * ((JUMBLR_INCR + 3*fee)*10 + 3*JUMBLR_TXFEE) )
686 amount = SATOSHIDEN * ((JUMBLR_INCR + 3*fee)*10 + 3*JUMBLR_TXFEE);
ae85ad79 687 else amount = SATOSHIDEN * ((JUMBLR_INCR + 3*fee) + 3*JUMBLR_TXFEE);*/
20082066 688 if ( amount > 0 && (retstr= jumblr_sendt_to_z(Jumblr_deposit,addr,dstr(amount))) != 0 )
eeaaf554 689 {
690 printf("sendt_to_z.(%s)\n",retstr);
691 free(retstr);
692 }
693 free(zaddr);
694 } else printf("no zaddr from jumblr_zgetnewaddress\n");
695 }
696 else if ( Jumblr_deposit[0] != 0 )
697 printf("%s total %.8f vs %.8f\n",Jumblr_deposit,dstr(total),(JUMBLR_INCR + 3*(fee+JUMBLR_TXFEE)));
698 break;
699 case 1: // z -> z
700 jumblr_opidsupdate();
701 chosen_one = -1;
702 for (iter=counter=0; iter<2; iter++)
703 {
704 counter = n = 0;
705 HASH_ITER(hh,Jumblrs,ptr,tmp)
706 {
1cacba6a 707 if ( ptr->spent == 0 && ptr->status > 0 && jumblr_addresstype(ptr->src) == 't' && jumblr_addresstype(ptr->dest) == 'z' )
eeaaf554 708 {
1cacba6a 709 if ( (total= jumblr_balance(ptr->dest)) >= (fee + JUMBLR_FEE)*SATOSHIDEN )
eeaaf554 710 {
711 if ( iter == 1 && counter == chosen_one )
712 {
713 if ( (zaddr= jumblr_zgetnewaddress()) != 0 )
714 {
dca9da68 715 if ( zaddr[0] == '"' && zaddr[strlen(zaddr)-1] == '"' )
716 {
717 zaddr[strlen(zaddr)-1] = 0;
718 addr = zaddr+1;
719 } else addr = zaddr;
720 if ( (retstr= jumblr_sendz_to_z(ptr->dest,addr,dstr(total))) != 0 )
eeaaf554 721 {
eb23a642 722 printf("n.%d counter.%d chosen_one.%d send z_to_z.(%s)\n",n,counter,chosen_one,retstr);
eeaaf554 723 free(retstr);
724 }
725 ptr->spent = (uint32_t)time(NULL);
726 free(zaddr);
727 break;
728 }
729 }
730 counter++;
731 }
732 }
733 n++;
734 }
735 if ( counter == 0 )
736 break;
737 if ( iter == 0 )
738 {
739 OS_randombytes((uint8_t *)&chosen_one,sizeof(chosen_one));
740 if ( chosen_one < 0 )
741 chosen_one = -chosen_one;
742 chosen_one %= counter;
743 printf("jumblr z->z chosen_one.%d of %d, from %d\n",chosen_one,counter,n);
744 }
745 }
746 break;
eb23a642 747 case 2: // z -> t
eeaaf554 748 if ( Jumblr_numsecretaddrs > 0 )
749 {
750 jumblr_opidsupdate();
751 chosen_one = -1;
752 for (iter=0; iter<2; iter++)
753 {
754 counter = n = 0;
755 HASH_ITER(hh,Jumblrs,ptr,tmp)
756 {
eb23a642 757 //printf("status.%d %c %c %.8f\n",ptr->status,jumblr_addresstype(ptr->src),jumblr_addresstype(ptr->dest),dstr(ptr->amount));
1cacba6a 758 if ( ptr->spent == 0 && ptr->status > 0 && jumblr_addresstype(ptr->src) == 'z' && jumblr_addresstype(ptr->dest) == 'z' )
eeaaf554 759 {
1cacba6a 760 if ( (total= jumblr_balance(ptr->dest)) >= (fee + JUMBLR_FEE)*SATOSHIDEN )
eeaaf554 761 {
3db947b8 762 if ( iter == 1 && counter == chosen_one )
eeaaf554 763 {
764 Jumblr_secretaddr(secretaddr);
765 if ( (retstr= jumblr_sendz_to_t(ptr->dest,secretaddr,dstr(total))) != 0 )
766 {
eb23a642 767 printf("%s send z_to_t.(%s)\n",secretaddr,retstr);
eeaaf554 768 free(retstr);
c89c562b 769 } else printf("null return from jumblr_sendz_to_t\n");
eeaaf554 770 ptr->spent = (uint32_t)time(NULL);
771 break;
772 }
773 counter++;
3db947b8 774 } //else printf("z->t spent.%u total %.8f error\n",ptr->spent,dstr(total));
eeaaf554 775 }
776 n++;
777 }
778 if ( counter == 0 )
779 break;
780 if ( iter == 0 )
781 {
782 OS_randombytes((uint8_t *)&chosen_one,sizeof(chosen_one));
783 if ( chosen_one < 0 )
784 chosen_one = -chosen_one;
785 chosen_one %= counter;
786 printf("jumblr z->t chosen_one.%d of %d, from %d\n",chosen_one,counter,n);
3db947b8 787 } //else printf("n.%d counter.%d chosen.%d\n",n,counter,chosen_one);
eeaaf554 788 }
789 }
790 break;
791 }
792}
This page took 0.312003 seconds and 4 git commands to generate.