Browse Source

Submit remotely found blocks locally at the master pool in addition to sending their details to ckdb.

master
Con Kolivas 8 years ago
parent
commit
c8af7e3a91
  1. 71
      src/stratifier.c

71
src/stratifier.c

@ -136,6 +136,8 @@ struct workbase {
ckpool_t *ckp; ckpool_t *ckp;
bool proxy; /* This workbase is proxied work */ bool proxy; /* This workbase is proxied work */
bool incomplete; /* This is a remote workinfo without all the txn data */
}; };
typedef struct workbase workbase_t; typedef struct workbase workbase_t;
@ -1579,9 +1581,16 @@ static void add_node_base(ckpool_t *ckp, json_t *val, bool trusted)
json_intcpy(&wb->txns, val, "transactions"); json_intcpy(&wb->txns, val, "transactions");
if (!ckp->proxy) { if (!ckp->proxy) {
/* This is a workbase from a trusted remote */ /* This is a workbase from a trusted remote */
json_intcpy(&wb->txns, val, "txns");
json_strdup(&wb->txn_hashes, val, "txn_hashes"); json_strdup(&wb->txn_hashes, val, "txn_hashes");
wb->merkle_array = json_object_dup(val, "merklehash"); wb->merkle_array = json_object_dup(val, "merklehash");
json_intcpy(&wb->merkles, val, "merkles"); json_intcpy(&wb->merkles, val, "merkles");
txnhashes = json_object_get(val, "txn_hashes");
if (!rebuild_txns(ckp, sdata, wb, txnhashes)) {
LOGWARNING("Unable to rebuild transactions to create workinfo from remote, will be unable to submit block locally");
wb->incomplete = true;
wb->txns = 0;
}
} else if (wb->txns) { } else if (wb->txns) {
int i; int i;
@ -1788,6 +1797,7 @@ process_block(ckpool_t *ckp, const workbase_t *wb, const char *coinbase, const i
strcat(gbt_block, hexcoinbase); strcat(gbt_block, hexcoinbase);
if (wb->txns) if (wb->txns)
realloc_strcat(&gbt_block, wb->txn_data); realloc_strcat(&gbt_block, wb->txn_data);
generator_submitblock(ckp, gbt_block); generator_submitblock(ckp, gbt_block);
free(gbt_block); free(gbt_block);
} }
@ -1831,7 +1841,7 @@ static void submit_node_block(ckpool_t *ckp, sdata_t *sdata, json_t *val)
goto out; goto out;
} }
LOGWARNING("Possible upstream block solve diff %f !", diff); LOGWARNING("Possible upstream block solve diff %lf !", diff);
ts_realtime(&ts_now); ts_realtime(&ts_now);
sprintf(cdfield, "%lu,%lu", ts_now.tv_sec, ts_now.tv_nsec); sprintf(cdfield, "%lu,%lu", ts_now.tv_sec, ts_now.tv_nsec);
@ -5508,7 +5518,7 @@ test_blocksolve(const stratum_instance_t *client, const workbase_t *wb, const uc
if (diff < sdata->current_workbase->network_diff * 0.999) if (diff < sdata->current_workbase->network_diff * 0.999)
return; return;
LOGWARNING("Possible %sblock solve diff %f !", stale ? "stale share " : "", diff); LOGWARNING("Possible %sblock solve diff %lf !", stale ? "stale share " : "", diff);
/* Can't submit a block in proxy mode without the transactions */ /* Can't submit a block in proxy mode without the transactions */
if (!ckp->node && wb->proxy) if (!ckp->node && wb->proxy)
return; return;
@ -5517,11 +5527,10 @@ test_blocksolve(const stratum_instance_t *client, const workbase_t *wb, const uc
sprintf(cdfield, "%lu,%lu", ts_now.tv_sec, ts_now.tv_nsec); sprintf(cdfield, "%lu,%lu", ts_now.tv_sec, ts_now.tv_nsec);
process_block(ckp, wb, coinbase, cblen, data, hash, swap32, blockhash); process_block(ckp, wb, coinbase, cblen, data, hash, swap32, blockhash);
send_node_block(sdata, client->enonce1, nonce, nonce2, ntime32, wb->id, send_node_block(sdata, client->enonce1, nonce, nonce2, ntime32, wb->id,
diff, client->id); diff, client->id);
JSON_CPACK(val, "{si,ss,ss,sI,ss,ss,sI,ss,ss,ss,sI,ss,ss,ss,ss}", JSON_CPACK(val, "{si,ss,ss,sI,ss,ss,sI,ss,ss,ss,sI,sf,ss,ss,ss,ss}",
"height", wb->height, "height", wb->height,
"blockhash", blockhash, "blockhash", blockhash,
"confirmed", "n", "confirmed", "n",
@ -5533,12 +5542,12 @@ test_blocksolve(const stratum_instance_t *client, const workbase_t *wb, const uc
"nonce2", nonce2, "nonce2", nonce2,
"nonce", nonce, "nonce", nonce,
"reward", wb->coinbasevalue, "reward", wb->coinbasevalue,
"diff", diff,
"createdate", cdfield, "createdate", cdfield,
"createby", "code", "createby", "code",
"createcode", __func__, "createcode", __func__,
"createinet", ckp->serverurl[client->server]); "createinet", ckp->serverurl[client->server]);
val_copy = json_deep_copy(val); val_copy = json_deep_copy(val);
json_set_double(val_copy, "diff", diff);
block_ckmsg = ckalloc(sizeof(ckmsg_t)); block_ckmsg = ckalloc(sizeof(ckmsg_t));
block_ckmsg->data = val_copy; block_ckmsg->data = val_copy;
@ -5547,7 +5556,16 @@ test_blocksolve(const stratum_instance_t *client, const workbase_t *wb, const uc
mutex_unlock(&sdata->block_lock); mutex_unlock(&sdata->block_lock);
if (ckp->remote) { if (ckp->remote) {
char *buf;
json_set_string(val, "name", ckp->name); json_set_string(val, "name", ckp->name);
json_set_int(val, "cblen", cblen);
buf = bin2hex(coinbase, cblen);
json_set_string(val, "coinbasehex", buf);
free(buf);
buf = bin2hex(data, 80);
json_set_string(val, "swaphex", buf);
free(buf);
upstream_json_msgtype(ckp, val, SM_BLOCK); upstream_json_msgtype(ckp, val, SM_BLOCK);
} else } else
ckdbq_add(ckp, ID_BLOCK, val); ckdbq_add(ckp, ID_BLOCK, val);
@ -6644,18 +6662,57 @@ static void parse_remote_blocksubmit(ckpool_t *ckp, json_t *val, const char *buf
free(gbt_block); free(gbt_block);
} }
/* Attempt to submit a remote block locally by recreating it from its workinfo
* in addition to sending it to ckdb */
static void parse_remote_block(ckpool_t *ckp, sdata_t *sdata, json_t *val, const char *buf) static void parse_remote_block(ckpool_t *ckp, sdata_t *sdata, json_t *val, const char *buf)
{ {
json_t *workername_val = json_object_get(val, "workername"), json_t *workername_val = json_object_get(val, "workername"),
*name_val = json_object_get(val, "name"); *name_val = json_object_get(val, "name");
const char *workername, *name; const char *workername, *name, *coinbasehex, *swaphex, *cnfrm;
workbase_t *wb = NULL;
double diff = 0; double diff = 0;
int height = 0; int height = 0;
int64_t id = 0;
char *msg; char *msg;
int cblen;
name = json_string_value(name_val); name = json_string_value(name_val);
if (!name_val || !name) if (!name_val || !name)
goto out_add; goto out_add;
/* If this is the confirm block message don't try to resubmit it */
cnfrm = json_string_value(json_object_get(val, "confirmed"));
if (cnfrm && cnfrm[0] == '1')
goto out_add;
json_get_int64(&id, val, "workinfoid");
coinbasehex = json_string_value(json_object_get(val, "coinbasehex"));
swaphex = json_string_value(json_object_get(val, "swaphex"));
json_get_int(&cblen, val, "cblen");
json_get_double(&diff, val, "diff");
if (likely(id && coinbasehex && swaphex && cblen)) {
ck_rlock(&sdata->workbase_lock);
HASH_FIND_I64(sdata->remote_workbases, &id, wb);
if (wb && wb->incomplete)
wb = NULL;
ck_runlock(&sdata->workbase_lock);
}
if (unlikely(!wb))
LOGWARNING("Inadequate data locally to attempt submit of remote block");
else {
uchar swap[80], hash[32], hash1[32], swap32[32];
char *coinbase = alloca(cblen);
char blockhash[68];
LOGWARNING("Possible remote block solve diff %lf !", diff);
hex2bin(coinbase, coinbasehex, cblen);
hex2bin(swap, swaphex, 80);
sha256(swap, 80, hash1);
sha256(hash1, 32, hash);
process_block(ckp, wb, coinbase, cblen, swap, hash, swap32, blockhash);
}
workername = json_string_value(workername_val); workername = json_string_value(workername_val);
if (unlikely(!workername_val || !workername)) { if (unlikely(!workername_val || !workername)) {
LOGWARNING("Failed to get workername from remote message %s", buf); LOGWARNING("Failed to get workername from remote message %s", buf);
@ -6663,8 +6720,6 @@ static void parse_remote_block(ckpool_t *ckp, sdata_t *sdata, json_t *val, const
} }
if (unlikely(!json_get_int(&height, val, "height"))) if (unlikely(!json_get_int(&height, val, "height")))
LOGWARNING("Failed to get height from remote message %s", buf); LOGWARNING("Failed to get height from remote message %s", buf);
if (unlikely(!json_get_double(&diff, val, "diff")))
LOGWARNING("Failed to get diff from remote message %s", buf);
ASPRINTF(&msg, "Block %d solved by %s @ %s!", height, workername, name); ASPRINTF(&msg, "Block %d solved by %s @ %s!", height, workername, name);
LOGWARNING("%s", msg); LOGWARNING("%s", msg);
stratum_broadcast_message(sdata, msg); stratum_broadcast_message(sdata, msg);

Loading…
Cancel
Save