Browse Source

Merge pull request #423 from jl777/spvdex

improved bot
etomic
jl777 8 years ago
committed by GitHub
parent
commit
9ff43582fc
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
  1. 16
      iguana/dexscripts.win32/1-client.cmd
  2. 7
      iguana/dexscripts.win32/2-getuserpass.cmd
  3. 4
      iguana/dexscripts.win32/balance.cmd
  4. BIN
      iguana/dexscripts.win32/curl.exe
  5. 4
      iguana/dexscripts.win32/enable.cmd
  6. 4
      iguana/dexscripts.win32/getcoin.cmd
  7. 4
      iguana/dexscripts.win32/getutxos.cmd
  8. 24
      iguana/dexscripts.win32/how_to_use.md
  9. BIN
      iguana/dexscripts.win32/images/userpass.png
  10. BIN
      iguana/dexscripts.win32/images/userpass_usage.png
  11. 4
      iguana/dexscripts.win32/inventory.cmd
  12. 4
      iguana/dexscripts.win32/listunspent.cmd
  13. 4
      iguana/dexscripts.win32/orderbook.cmd
  14. 1
      iguana/dexscripts.win32/passphrase
  15. 4
      iguana/dexscripts.win32/portfolio.cmd
  16. 5
      iguana/dexscripts.win32/snapshot.cmd
  17. 0
      iguana/dexscripts.win32/userpass
  18. 24
      iguana/exchanges/LP_RTmetrics.c
  19. 1
      iguana/exchanges/LP_include.h
  20. 14
      iguana/exchanges/LP_nativeDEX.c
  21. 3
      iguana/exchanges/LP_socket.c
  22. 39
      iguana/exchanges/LP_tradebots.c

16
iguana/dexscripts.win32/1-client.cmd

@ -0,0 +1,16 @@
@echo off
set USERHOME=%APPDATA:\=\\%
rem [!] Coins config now taked from coins.json file, no need to put in environment variable
rem ---------------------------------------------------------------------------------------
rem set COINS=[{\"coin\":\"REVS\",\"active\":1,\"asset\":\"REVS\",\"rpcport\":10196}]
rem marketmaker "{\"gui\":\"nogui\",\"client\":1, \"userhome\":\"%USERHOME%\", \"passphrase\":\"mypassphrase\", \"coins\":%COINS%}"
set COINS=\"\"
set /p PASSPHRASE=<passphrase
rem , \"canbind\":1
rem marketmaker "{\"gui\":\"nogui\",\"client\":1, \"userhome\":\"%USERHOME%\", \"passphrase\":\"%PASSPHRASE%\"}" 1> marketmaker.log 2>&1
marketmaker "{\"gui\":\"nogui\",\"client\":1, \"userhome\":\"%USERHOME%\", \"passphrase\":\"%PASSPHRASE%\"}"

7
iguana/dexscripts.win32/2-getuserpass.cmd

@ -0,0 +1,7 @@
@echo off
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":null,\"method\":\"enable\",\"coin\":\" \"}" -s > userpass.json
for /f "tokens=2 delims=:," %%a in (' find "userpass" "userpass.json" ') do (
echo UserPass: %%~a
echo %%~a > userpass
)
del userpass.json

4
iguana/dexscripts.win32/balance.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"balance\",\"coin\":\"KMD\",\"address\":\"RSpP2Nffy379SwF1cAkooNg6vwPHpakCpC\"}"

BIN
iguana/dexscripts.win32/curl.exe

Binary file not shown.

4
iguana/dexscripts.win32/enable.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"enable\",\"coin\":\"REVS\"}"

4
iguana/dexscripts.win32/getcoin.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"getcoin\",\"coin\":\"KMD\"}"

4
iguana/dexscripts.win32/getutxos.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"getutxos\",\"coin\":\"KMD\"}"

24
iguana/dexscripts.win32/how_to_use.md

@ -0,0 +1,24 @@
## DexScripts for Windows. How to use? ##
**1.** Before start you should put scripts and following binaries into one folder:
- curl.exe (required for all scripts)
- marketmaker.exe
- libcurl.dll (required to run marketmaker)
- nanomsg.dll (required to run marketmaker)
**2.** Don't forget to put `coins.json` file into a same folder. This file is available it this repo.
**3.** Type your passphrase into passphrase file in this folder (you should create file with name `passphrase` and without extension) and run `1-client.cmd`. This will run marketmaker. Next step is to obtain userpass needed for other scripts, you can simply copy and paste it from marketmaker output on startup into userpass file.
![](./images/userpass.png)
Or run `2-getuserpass.cmd` to fill userpass file automatically.** NB!** To get userpass you shouldn't run any scripts between 1-client.cmd and 2-getuserpass.cmd launching.
Sample output of correct `2-getuserpass.cmd` usage is:
![](./images/userpass_usage.png)
You should see your userpass on screen, and after it will automatically copied in userpass file. It's important to all other scripts to have this password in userpass file. If output of `2-getuserpass.cmd` is not same as showed on screen above - wait some seconds and run `2-getuserpass.cmd` again. Also make sure that you have allowed marketmaker to accept incoming connections in your Windows Firewall (first time launched system should automatically asked for it).
**4.** For using other scripts please refer to barterDEX API. Or **barterDEX API Summary by Category** document by *shossain*.

BIN
iguana/dexscripts.win32/images/userpass.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB

BIN
iguana/dexscripts.win32/images/userpass_usage.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

4
iguana/dexscripts.win32/inventory.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"inventory\",\"coin\":\"KMD\"}"

4
iguana/dexscripts.win32/listunspent.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"listunspent\",\"coin\":\"KMD\",\"address\":\"RSpP2Nffy379SwF1cAkooNg6vwPHpakCpC\"}"

4
iguana/dexscripts.win32/orderbook.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"orderbook\",\"base\":\"KMD\",\"rel\":\"REVS\"}"

1
iguana/dexscripts.win32/passphrase

@ -0,0 +1 @@
your_very_strong_secret_passphrase

4
iguana/dexscripts.win32/portfolio.cmd

@ -0,0 +1,4 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"portfolio\"}"

5
iguana/dexscripts.win32/snapshot.cmd

@ -0,0 +1,5 @@
@echo off
set /p TMPUSERPASS=<userpass
set USERPASS=%TMPUSERPASS: =%
curl --url "http://127.0.0.1:7783" --data "{\"userpass\":\"%USERPASS%\",\"method\":\"snapshot\",\"coin\":\"KMD\",\"height\":%1}"

0
iguana/dexscripts.win32/userpass

24
iguana/exchanges/LP_RTmetrics.c

@ -184,24 +184,28 @@ double _LP_RTmetric_calc(struct LP_metricinfo *mp,double bestprice,double maxpri
metric = origmetric;
if ( mp->numutxos == 0 || relvolume == 0. || mp->maxvol == 0. || mp->balance == 0. )
{
printf("skip i.%d as no info\n",mp->ind);
//printf("skip i.%d as no info\n",mp->ind);
return(metric * 100.);
}
if ( relvolume < mp->minvol )
{
metric *= (mp->minvol / relvolume);
//printf("relvolume < minvol %.8f\n",(mp->minvol / relvolume));
}
else if ( relvolume > mp->maxvol )
{
metric *= (relvolume / mp->maxvol);
//printf("relvolume > minvol %.8f\n",(relvolume / mp->maxvol));
}
if ( relvolume < mp->balance/LP_MINVOL )
{
metric *= (mp->balance / relvolume);
//printf("relvolume < balance %.8f\n",(mp->balance / relvolume));
}
else if ( relvolume > mp->balance/mp->numutxos )
{
metric *= (relvolume / (mp->balance/mp->numutxos));
//printf("relvolume < ave %.8f\n",(relvolume / (mp->balance/mp->numutxos)));
}
if ( mp->age > LP_ORDERBOOK_DURATION*0.8 )
metric *= 2;
@ -229,6 +233,19 @@ void LP_RTmetric_calc(struct LP_metricinfo *sortbuf,int32_t ind,cJSON *item,doub
sortbuf[ind].metric = _LP_RTmetric_calc(&sortbuf[ind],bestprice,maxprice,relvolume);
}
int _increasing_metrics(const void *a,const void *b)
{
#define ptr_a ((struct LP_metricinfo *)a)
#define ptr_b ((struct LP_metricinfo *)b)
if ( ptr_b->metric > ptr_a->metric )
return(-1);
else if ( ptr_b->metric < ptr_a->metric )
return(1);
return(0);
#undef ptr_a
#undef ptr_b
}
cJSON *LP_RTmetrics_sort(char *base,char *rel,cJSON *rawasks,int32_t numasks,double maxprice,double relvolume)
{
cJSON *array=rawasks,*item; int32_t i,num,groupi; double price,prevdepth,bestprice; struct LP_metricinfo *sortbuf;
@ -255,12 +272,13 @@ cJSON *LP_RTmetrics_sort(char *base,char *rel,cJSON *rawasks,int32_t numasks,dou
item = jitem(rawasks,i);
LP_RTmetric_calc(sortbuf,i,item,bestprice,maxprice,relvolume,prevdepth);
prevdepth = jdouble(item,"depth");
//printf("%.8f ",sortbuf[i].metric);
}
revsortds(&sortbuf[0].metric,groupi+1,sizeof(*sortbuf));
qsort(&sortbuf[0].metric,groupi+1,sizeof(*sortbuf),_increasing_metrics);
array = cJSON_CreateArray();
for (i=0; i<=groupi; i++)
{
printf("(%d -> %d %.3f) ",i,sortbuf[i].ind,sortbuf[i].metric);
printf("(%d <- %d %.3f) ",i,sortbuf[i].ind,sortbuf[i].metric);
item = jitem(rawasks,sortbuf[i].ind);
jaddi(array,jduplicate(item));
}

1
iguana/exchanges/LP_include.h

@ -40,6 +40,7 @@ void emscripten_usleep(int32_t x); // returns immediate, no sense for sleeping
#define LP_HTTP_TIMEOUT 3 // 1 is too small due to edge cases of time(NULL)
#define LP_AUTOTRADE_TIMEOUT 15
#define ELECTRUM_TIMEOUT 10
#define LP_ELECTRUM_KEEPALIVE 60
#define LP_ELECTRUM_MAXERRORS 777
#define LP_MEMPOOL_TIMEINCR 10

14
iguana/exchanges/LP_nativeDEX.c

@ -18,8 +18,6 @@
// LP_nativeDEX.c
// marketmaker
//
// electrum keepalive
// merge bots + portfoliot
// verify portfolio, interest to KMD withdraw
// dPoW security -> 4: KMD notarized, 5: BTC notarized, after next notary elections
// bigendian architectures need to use little endian for sighash calcs
@ -494,7 +492,7 @@ int32_t LP_utxos_sync(struct LP_peerinfo *peer)
void LP_coinsloop(void *_coins)
{
struct LP_address *ap=0,*atmp; struct LP_address_utxo *up,*tmp; struct iguana_info *coin,*ctmp; char str[65]; struct electrum_info *ep,*backupep=0; bits256 zero; int32_t oldht,j,nonz; char *coins = _coins;
struct LP_address *ap=0,*atmp; cJSON *retjson; struct LP_address_utxo *up,*tmp; struct iguana_info *coin,*ctmp; char str[65]; struct electrum_info *ep,*backupep=0; bits256 zero; int32_t oldht,j,nonz; char *coins = _coins;
while ( 1 )
{
nonz = 0;
@ -548,6 +546,16 @@ void LP_coinsloop(void *_coins)
}
}
}
while ( ep != 0 )
{
if ( time(NULL) > ep->keepalive+LP_ELECTRUM_KEEPALIVE )
{
//printf("%s electrum.%p needs a keepalive: lag.%d\n",ep->symbol,ep,(int32_t)(time(NULL) - ep->keepalive));
if ( (retjson= electrum_donation(ep->symbol,ep,&retjson)) != 0 )
free_json(retjson);
}
ep = ep->prev;
}
continue;
}
if ( coin->firstrefht == 0 )

3
iguana/exchanges/LP_socket.c

@ -245,7 +245,7 @@ struct electrum_info
struct electrum_info *prev;
int32_t bufsize,sock,*heightp,numerrors;
struct iguana_info *coin;
uint32_t stratumid,lasttime,pending,*heighttimep;
uint32_t stratumid,lasttime,keepalive,pending,*heighttimep;
char ipaddr[64],symbol[16];
uint16_t port;
uint8_t buf[];
@ -931,6 +931,7 @@ void LP_dedicatedloop(void *arg)
ep->sock = -1;
break;
}
ep->keepalive = (uint32_t)time(NULL);
if ( sitem->expiration != 0 )
sitem->expiration += (uint32_t)time(NULL);
else sitem->expiration = (uint32_t)time(NULL) + ELECTRUM_TIMEOUT;

39
iguana/exchanges/LP_tradebots.c

@ -259,7 +259,7 @@ struct LP_tradebot_trade *LP_tradebot_pending(struct LP_tradebot *bot,cJSON *pen
void LP_tradebot_timeslice(void *ctx,struct LP_tradebot *bot)
{
double remaining; uint32_t tradeid; bits256 destpubkey; char *retstr,*liststr; cJSON *retjson,*retjson2,*pending;
double remaining; int32_t i,maxiters = 10; uint32_t tradeid; bits256 destpubkey; char *retstr,*liststr; cJSON *retjson,*retjson2,*pending;
memset(destpubkey.bytes,0,sizeof(destpubkey));
if ( bot->dead == 0 && bot->pause == 0 && bot->numtrades < sizeof(bot->trades)/sizeof(*bot->trades) )
{
@ -272,21 +272,28 @@ void LP_tradebot_timeslice(void *ctx,struct LP_tradebot *bot)
remaining = bot->totalrelvolume - (bot->relsum + bot->pendrelsum);
printf("try autobuy %s/%s remaining %.8f maxprice %.8f\n",bot->base,bot->rel,remaining,bot->maxprice);
tradeid = rand();
if ( (retstr= LP_autobuy(ctx,LP_myipaddr,LP_mypubsock,bot->base,bot->rel,bot->maxprice,remaining,0,0,G.gui,0,destpubkey,tradeid)) != 0 )
for (i=1; i<=maxiters; i++)
{
if ( (retjson2= cJSON_Parse(retstr)) != 0 )
if ( (retstr= LP_autobuy(ctx,LP_myipaddr,LP_mypubsock,bot->base,bot->rel,bot->maxprice,remaining/i,0,0,G.gui,0,destpubkey,tradeid)) != 0 )
{
if ( (pending= jobj(retjson2,"pending")) != 0 && juint(pending,"tradeid") == tradeid )
if ( (retjson2= cJSON_Parse(retstr)) != 0 )
{
bot->trades[bot->numtrades++] = LP_tradebot_pending(bot,pending,tradeid);
if ( bot->relsum >= 0.99*bot->totalrelvolume-SMALLVAL || bot->basesum >= 0.99*bot->totalbasevolume-SMALLVAL )
bot->dead = (uint32_t)time(NULL);
else if ( (bot->pendrelsum+bot->relsum) >= 0.99*bot->totalrelvolume-SMALLVAL || (bot->basesum+bot->pendbasesum) >= 0.99*bot->totalbasevolume-SMALLVAL )
bot->pause = (uint32_t)time(NULL);
} else printf("didnt get any trade pending %s %s\n\n",bot->name,retstr);
free_json(retjson2);
} else printf("%s\n",retstr);
free(retstr);
if ( (pending= jobj(retjson2,"pending")) != 0 && juint(pending,"tradeid") == tradeid )
{
bot->trades[bot->numtrades++] = LP_tradebot_pending(bot,pending,tradeid);
if ( bot->relsum >= 0.99*bot->totalrelvolume-SMALLVAL || bot->basesum >= 0.99*bot->totalbasevolume-SMALLVAL )
bot->dead = (uint32_t)time(NULL);
else if ( (bot->pendrelsum+bot->relsum) >= 0.99*bot->totalrelvolume-SMALLVAL || (bot->basesum+bot->pendbasesum) >= 0.99*bot->totalbasevolume-SMALLVAL )
bot->pause = (uint32_t)time(NULL);
printf("issued bot trade.%u\n",tradeid);
free_json(retjson2);
free(retstr);
break;
} else printf("iter.%d/%d %.8f didnt get any trade pending %s %s\n\n",i,maxiters,remaining/i,bot->name,retstr);
free_json(retjson2);
} else printf("iter.%d/%d %.8f %s\n",i,maxiters,remaining/i,retstr);
free(retstr);
}
}
}
free_json(retjson);
@ -312,7 +319,7 @@ void LP_tradebot_finished(uint32_t tradeid,uint32_t requestid,uint32_t quoteid)
bot->pendbasesum -= tp->basevol, bot->basesum += tp->basevol;
bot->pendrelsum -= tp->relvol, bot->relsum += tp->relvol;
bot->numpending--, bot->completed++;
printf("bot.%u detected completion tradeid.%u aliceid.%llx r.%u q.%u\n",bot->id,tp->tradeid,(long long)tp->aliceid,tp->requestid,tp->quoteid);
printf("bot.%u detected completion tradeid.%u aliceid.%llx r.%u q.%u, numpending.%d completed.%d\n",bot->id,tp->tradeid,(long long)tp->aliceid,tp->requestid,tp->quoteid,bot->numpending,bot->completed);
tp->finished = (uint32_t)time(NULL);
break;
}
@ -364,7 +371,7 @@ char *LP_tradebot_list(void *ctx,int32_t pubsock,cJSON *argjson)
char *LP_tradebot_buy(int32_t dispdir,char *base,char *rel,double maxprice,double relvolume)
{
struct LP_tradebot *bot; double shortfall; int32_t i,n; cJSON *array,*item,*retjson; uint64_t txfees,balance=0,abalance=0; struct iguana_info *basecoin,*relcoin;
struct LP_tradebot *bot; char *retstr; double shortfall; int32_t i,n; cJSON *array,*item,*retjson; uint64_t txfees,balance=0,abalance=0; struct iguana_info *basecoin,*relcoin;
basecoin = LP_coinfind(base);
relcoin = LP_coinfind(rel);
if ( basecoin == 0 || relcoin == 0 || basecoin->inactive != 0 || relcoin->inactive != 0 )
@ -381,6 +388,8 @@ char *LP_tradebot_buy(int32_t dispdir,char *base,char *rel,double maxprice,doubl
}
free_json(array);
}
if ( (retstr= LP_orderbook(base,rel,0)) != 0 )
free(retstr);
txfees = 10 * relcoin->txfee;
printf("%s inventory balance %.8f, relvolume %.8f + txfees %.8f\n",rel,dstr(abalance),relvolume,dstr(txfees));
if ( dstr(abalance) < relvolume + dstr(txfees) )

Loading…
Cancel
Save