|
|
@ -157,7 +157,7 @@ static const char *COMMA = ","; |
|
|
|
static const char SEPARATOR = '|'; |
|
|
|
static const char SEPARATOR = '|'; |
|
|
|
static const char GPUSEP = ','; |
|
|
|
static const char GPUSEP = ','; |
|
|
|
|
|
|
|
|
|
|
|
static const char *APIVERSION = "1.6"; |
|
|
|
static const char *APIVERSION = "1.7"; |
|
|
|
static const char *DEAD = "Dead"; |
|
|
|
static const char *DEAD = "Dead"; |
|
|
|
static const char *SICK = "Sick"; |
|
|
|
static const char *SICK = "Sick"; |
|
|
|
static const char *NOSTART = "NoStart"; |
|
|
|
static const char *NOSTART = "NoStart"; |
|
|
@ -483,6 +483,68 @@ extern struct device_api bitforce_api; |
|
|
|
extern struct device_api icarus_api; |
|
|
|
extern struct device_api icarus_api; |
|
|
|
#endif |
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// This is only called when expected to be needed (rarely)
|
|
|
|
|
|
|
|
// i.e. strings outside of the codes control (input from the user)
|
|
|
|
|
|
|
|
static char *escape_string(char *str, bool isjson) |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
char *buf, *ptr; |
|
|
|
|
|
|
|
int count; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
count = 0; |
|
|
|
|
|
|
|
for (ptr = str; *ptr; ptr++) { |
|
|
|
|
|
|
|
switch (*ptr) { |
|
|
|
|
|
|
|
case ',': |
|
|
|
|
|
|
|
case '|': |
|
|
|
|
|
|
|
case '=': |
|
|
|
|
|
|
|
if (!isjson) |
|
|
|
|
|
|
|
count++; |
|
|
|
|
|
|
|
break; |
|
|
|
|
|
|
|
case '"': |
|
|
|
|
|
|
|
if (isjson) |
|
|
|
|
|
|
|
count++; |
|
|
|
|
|
|
|
break; |
|
|
|
|
|
|
|
case '\\': |
|
|
|
|
|
|
|
count++; |
|
|
|
|
|
|
|
break; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (count == 0) |
|
|
|
|
|
|
|
return str; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
buf = malloc(strlen(str) + count + 1); |
|
|
|
|
|
|
|
if (unlikely(!buf)) |
|
|
|
|
|
|
|
quit(1, "Failed to malloc escape buf"); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
ptr = buf; |
|
|
|
|
|
|
|
while (*str) |
|
|
|
|
|
|
|
switch (*str) { |
|
|
|
|
|
|
|
case ',': |
|
|
|
|
|
|
|
case '|': |
|
|
|
|
|
|
|
case '=': |
|
|
|
|
|
|
|
if (!isjson) |
|
|
|
|
|
|
|
*(ptr++) = '\\'; |
|
|
|
|
|
|
|
*(ptr++) = *(str++); |
|
|
|
|
|
|
|
break; |
|
|
|
|
|
|
|
case '"': |
|
|
|
|
|
|
|
if (isjson) |
|
|
|
|
|
|
|
*(ptr++) = '\\'; |
|
|
|
|
|
|
|
*(ptr++) = *(str++); |
|
|
|
|
|
|
|
break; |
|
|
|
|
|
|
|
case '\\': |
|
|
|
|
|
|
|
*(ptr++) = '\\'; |
|
|
|
|
|
|
|
*(ptr++) = *(str++); |
|
|
|
|
|
|
|
break; |
|
|
|
|
|
|
|
default: |
|
|
|
|
|
|
|
*(ptr++) = *(str++); |
|
|
|
|
|
|
|
break; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*ptr = '\0'; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return buf; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
#if defined(USE_BITFORCE) || defined(USE_ICARUS) |
|
|
|
#if defined(USE_BITFORCE) || defined(USE_ICARUS) |
|
|
|
static int numpgas() |
|
|
|
static int numpgas() |
|
|
|
{ |
|
|
|
{ |
|
|
@ -1102,6 +1164,8 @@ static void poolstatus(__maybe_unused SOCKETTYPE c, __maybe_unused char *param, |
|
|
|
{ |
|
|
|
{ |
|
|
|
char buf[BUFSIZ]; |
|
|
|
char buf[BUFSIZ]; |
|
|
|
char *status, *lp; |
|
|
|
char *status, *lp; |
|
|
|
|
|
|
|
char *rpc_url; |
|
|
|
|
|
|
|
char *rpc_user; |
|
|
|
int i; |
|
|
|
int i; |
|
|
|
|
|
|
|
|
|
|
|
if (total_pools == 0) { |
|
|
|
if (total_pools == 0) { |
|
|
@ -1133,27 +1197,40 @@ static void poolstatus(__maybe_unused SOCKETTYPE c, __maybe_unused char *param, |
|
|
|
else |
|
|
|
else |
|
|
|
lp = (char *)NO; |
|
|
|
lp = (char *)NO; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
rpc_url = escape_string(pool->rpc_url, isjson); |
|
|
|
|
|
|
|
rpc_user = escape_string(pool->rpc_user, isjson); |
|
|
|
|
|
|
|
|
|
|
|
if (isjson) |
|
|
|
if (isjson) |
|
|
|
sprintf(buf, "%s{\"POOL\":%d,\"URL\":\"%s\",\"Status\":\"%s\",\"Priority\":%d,\"Long Poll\":\"%s\",\"Getworks\":%d,\"Accepted\":%d,\"Rejected\":%d,\"Discarded\":%d,\"Stale\":%d,\"Get Failures\":%d,\"Remote Failures\":%d}", |
|
|
|
sprintf(buf, "%s{\"POOL\":%d,\"URL\":\"%s\",\"Status\":\"%s\",\"Priority\":%d,\"Long Poll\":\"%s\",\"Getworks\":%d,\"Accepted\":%d,\"Rejected\":%d,\"Discarded\":%d,\"Stale\":%d,\"Get Failures\":%d,\"Remote Failures\":%d,\"User\":\"%s\"}", |
|
|
|
(i > 0) ? COMMA : "", |
|
|
|
(i > 0) ? COMMA : "", |
|
|
|
i, pool->rpc_url, status, pool->prio, lp, |
|
|
|
i, rpc_url, status, pool->prio, lp, |
|
|
|
pool->getwork_requested, |
|
|
|
pool->getwork_requested, |
|
|
|
pool->accepted, pool->rejected, |
|
|
|
pool->accepted, pool->rejected, |
|
|
|
pool->discarded_work, |
|
|
|
pool->discarded_work, |
|
|
|
pool->stale_shares, |
|
|
|
pool->stale_shares, |
|
|
|
pool->getfail_occasions, |
|
|
|
pool->getfail_occasions, |
|
|
|
pool->remotefail_occasions); |
|
|
|
pool->remotefail_occasions, |
|
|
|
|
|
|
|
rpc_user); |
|
|
|
else |
|
|
|
else |
|
|
|
sprintf(buf, "POOL=%d,URL=%s,Status=%s,Priority=%d,Long Poll=%s,Getworks=%d,Accepted=%d,Rejected=%d,Discarded=%d,Stale=%d,Get Failures=%d,Remote Failures=%d%c", |
|
|
|
sprintf(buf, "POOL=%d,URL=%s,Status=%s,Priority=%d,Long Poll=%s,Getworks=%d,Accepted=%d,Rejected=%d,Discarded=%d,Stale=%d,Get Failures=%d,Remote Failures=%d,User=%s%c", |
|
|
|
i, pool->rpc_url, status, pool->prio, lp, |
|
|
|
i, rpc_url, status, pool->prio, lp, |
|
|
|
pool->getwork_requested, |
|
|
|
pool->getwork_requested, |
|
|
|
pool->accepted, pool->rejected, |
|
|
|
pool->accepted, pool->rejected, |
|
|
|
pool->discarded_work, |
|
|
|
pool->discarded_work, |
|
|
|
pool->stale_shares, |
|
|
|
pool->stale_shares, |
|
|
|
pool->getfail_occasions, |
|
|
|
pool->getfail_occasions, |
|
|
|
pool->remotefail_occasions, SEPARATOR); |
|
|
|
pool->remotefail_occasions, |
|
|
|
|
|
|
|
rpc_user, SEPARATOR); |
|
|
|
|
|
|
|
|
|
|
|
strcat(io_buffer, buf); |
|
|
|
strcat(io_buffer, buf); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (rpc_url != pool->rpc_url) |
|
|
|
|
|
|
|
free(rpc_url); |
|
|
|
|
|
|
|
rpc_url = NULL; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (rpc_user != pool->rpc_user) |
|
|
|
|
|
|
|
free(rpc_user); |
|
|
|
|
|
|
|
rpc_user = NULL; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
if (isjson) |
|
|
|
if (isjson) |
|
|
@ -1443,6 +1520,7 @@ exitsama: |
|
|
|
static void addpool(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
static void addpool(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
{ |
|
|
|
{ |
|
|
|
char *url, *user, *pass; |
|
|
|
char *url, *user, *pass; |
|
|
|
|
|
|
|
char *ptr; |
|
|
|
|
|
|
|
|
|
|
|
if (param == NULL || *param == '\0') { |
|
|
|
if (param == NULL || *param == '\0') { |
|
|
|
strcpy(io_buffer, message(MSG_MISPDP, 0, NULL, isjson)); |
|
|
|
strcpy(io_buffer, message(MSG_MISPDP, 0, NULL, isjson)); |
|
|
@ -1450,7 +1528,11 @@ static void addpool(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
if (!pooldetails(param, &url, &user, &pass)) { |
|
|
|
if (!pooldetails(param, &url, &user, &pass)) { |
|
|
|
strcpy(io_buffer, message(MSG_INVPDP, 0, param, isjson)); |
|
|
|
ptr = escape_string(param, isjson); |
|
|
|
|
|
|
|
strcpy(io_buffer, message(MSG_INVPDP, 0, ptr, isjson)); |
|
|
|
|
|
|
|
if (ptr != param) |
|
|
|
|
|
|
|
free(ptr); |
|
|
|
|
|
|
|
ptr = NULL; |
|
|
|
return; |
|
|
|
return; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
@ -1459,7 +1541,11 @@ static void addpool(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
return; |
|
|
|
return; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
strcpy(io_buffer, message(MSG_ADDPOOL, 0, url, isjson)); |
|
|
|
ptr = escape_string(url, isjson); |
|
|
|
|
|
|
|
strcpy(io_buffer, message(MSG_ADDPOOL, 0, ptr, isjson)); |
|
|
|
|
|
|
|
if (ptr != url) |
|
|
|
|
|
|
|
free(ptr); |
|
|
|
|
|
|
|
ptr = NULL; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
static void enablepool(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
static void enablepool(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
@ -1792,6 +1878,7 @@ static void notify(__maybe_unused SOCKETTYPE c, __maybe_unused char *param, bool |
|
|
|
void dosave(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
void dosave(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
{ |
|
|
|
{ |
|
|
|
FILE *fcfg; |
|
|
|
FILE *fcfg; |
|
|
|
|
|
|
|
char *ptr; |
|
|
|
|
|
|
|
|
|
|
|
if (param == NULL || *param == '\0') { |
|
|
|
if (param == NULL || *param == '\0') { |
|
|
|
strcpy(io_buffer, message(MSG_MISFN, 0, NULL, isjson)); |
|
|
|
strcpy(io_buffer, message(MSG_MISFN, 0, NULL, isjson)); |
|
|
@ -1800,14 +1887,22 @@ void dosave(__maybe_unused SOCKETTYPE c, char *param, bool isjson) |
|
|
|
|
|
|
|
|
|
|
|
fcfg = fopen(param, "w"); |
|
|
|
fcfg = fopen(param, "w"); |
|
|
|
if (!fcfg) { |
|
|
|
if (!fcfg) { |
|
|
|
strcpy(io_buffer, message(MSG_BADFN, 0, param, isjson)); |
|
|
|
ptr = escape_string(param, isjson); |
|
|
|
|
|
|
|
strcpy(io_buffer, message(MSG_BADFN, 0, ptr, isjson)); |
|
|
|
|
|
|
|
if (ptr != param) |
|
|
|
|
|
|
|
free(ptr); |
|
|
|
|
|
|
|
ptr = NULL; |
|
|
|
return; |
|
|
|
return; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
write_config(fcfg); |
|
|
|
write_config(fcfg); |
|
|
|
fclose(fcfg); |
|
|
|
fclose(fcfg); |
|
|
|
|
|
|
|
|
|
|
|
strcpy(io_buffer, message(MSG_SAVED, 0, param, isjson)); |
|
|
|
ptr = escape_string(param, isjson); |
|
|
|
|
|
|
|
strcpy(io_buffer, message(MSG_SAVED, 0, ptr, isjson)); |
|
|
|
|
|
|
|
if (ptr != param) |
|
|
|
|
|
|
|
free(ptr); |
|
|
|
|
|
|
|
ptr = NULL; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
struct CMDS { |
|
|
|
struct CMDS { |
|
|
|