forked from Ocean/datum_gateway
Add support for rpccookiefile alternative to rpcuser/rpcpassword
This commit is contained in:
commit
14993bbd91
@ -43,6 +43,7 @@
|
||||
#include <jansson.h>
|
||||
|
||||
#include "datum_conf.h"
|
||||
#include "datum_jsonrpc.h"
|
||||
#include "datum_utils.h"
|
||||
#include "datum_sockets.h"
|
||||
|
||||
@ -52,10 +53,12 @@ const char *datum_conf_var_type_text[] = { "N/A", "boolean", "integer", "string"
|
||||
|
||||
const T_DATUM_CONFIG_ITEM datum_config_options[] = {
|
||||
// Bitcoind configs
|
||||
{ .var_type = DATUM_CONF_STRING, .category = "bitcoind", .name = "rpccookiefile", .description = "Path to file to read RPC cookie from, for communication with local bitcoind.",
|
||||
.required = false, .ptr = datum_config.bitcoind_rpccookiefile, .default_string[0] = "", .max_string_len = sizeof(datum_config.bitcoind_rpccookiefile) },
|
||||
{ .var_type = DATUM_CONF_STRING, .category = "bitcoind", .name = "rpcuser", .description = "RPC username for communication with local bitcoind.",
|
||||
.required = true, .ptr = datum_config.bitcoind_rpcuser, .max_string_len = sizeof(datum_config.bitcoind_rpcuser) },
|
||||
.required = false, .ptr = datum_config.bitcoind_rpcuser, .default_string[0] = "", .max_string_len = sizeof(datum_config.bitcoind_rpcuser) },
|
||||
{ .var_type = DATUM_CONF_STRING, .category = "bitcoind", .name = "rpcpassword", .description = "RPC password for communication with local bitcoind.",
|
||||
.required = true, .ptr = datum_config.bitcoind_rpcpassword, .max_string_len = sizeof(datum_config.bitcoind_rpcpassword) },
|
||||
.required = false, .ptr = datum_config.bitcoind_rpcpassword, .default_string[0] = "", .max_string_len = sizeof(datum_config.bitcoind_rpcpassword) },
|
||||
{ .var_type = DATUM_CONF_STRING, .category = "bitcoind", .name = "rpcurl", .description = "RPC URL for communication with local bitcoind. (GBT Template Source)",
|
||||
.required = true, .ptr = datum_config.bitcoind_rpcurl, .max_string_len = sizeof(datum_config.bitcoind_rpcurl) },
|
||||
{ .var_type = DATUM_CONF_INT, .category = "bitcoind", .name = "work_update_seconds", .description = "How many seconds between normal work updates? (5-120, 40 suggested)",
|
||||
@ -269,6 +272,11 @@ int datum_config_parse_value(const T_DATUM_CONFIG_ITEM *c, json_t *item) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
static void datum_config_opt_missing_error(const T_DATUM_CONFIG_ITEM * const opt) {
|
||||
DLOG_ERROR("Required configuration option (%s.%s) not found in config file:", opt->category, opt->name);
|
||||
DLOG_ERROR("--- Config description: \"%s\"", opt->description);
|
||||
}
|
||||
|
||||
int datum_read_config(const char *conffile) {
|
||||
json_t *config = NULL;
|
||||
json_t *cat, *item;
|
||||
@ -293,8 +301,7 @@ int datum_read_config(const char *conffile) {
|
||||
}
|
||||
if ((!item) || json_is_null(item)) {
|
||||
if (datum_config_options[i].required) {
|
||||
DLOG_ERROR("Required configuration option (%s.%s) not found in config file:", datum_config_options[i].category, datum_config_options[i].name);
|
||||
DLOG_ERROR("--- Config description: \"%s\"", datum_config_options[i].description);
|
||||
datum_config_opt_missing_error(&datum_config_options[i]);
|
||||
return 0;
|
||||
} else {
|
||||
datum_config_set_default(&datum_config_options[i]);
|
||||
@ -336,6 +343,24 @@ int datum_read_config(const char *conffile) {
|
||||
datum_config.bitcoind_work_update_seconds = 120;
|
||||
}
|
||||
|
||||
if (datum_config.bitcoind_rpcuser[0]) {
|
||||
if (!datum_config.bitcoind_rpcpassword[0]) {
|
||||
datum_config_opt_missing_error(datum_config_get_option_info2("bitcoind", "rpcpassword"));
|
||||
return 0;
|
||||
}
|
||||
sprintf(datum_config.bitcoind_rpcuserpass, "%s:%s", datum_config.bitcoind_rpcuser, datum_config.bitcoind_rpcpassword);
|
||||
} else if (datum_config.bitcoind_rpccookiefile[0]) {
|
||||
update_rpc_cookie(&datum_config);
|
||||
} else {
|
||||
const T_DATUM_CONFIG_ITEM *opt;
|
||||
DLOG_ERROR("Either bitcoind.rpcuser (and bitcoind.rpcpassword) or bitcoind.rpccookiefile is required.");
|
||||
opt = datum_config_get_option_info2("bitcoind", "rpcuser");
|
||||
DLOG_ERROR("--- Config description for %s.%s: \"%s\"", opt->category, opt->name, opt->description);
|
||||
opt = datum_config_get_option_info2("bitcoind", "rpccookiefile");
|
||||
DLOG_ERROR("--- Config description for %s.%s: \"%s\"", opt->category, opt->name, opt->description);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (datum_config.stratum_v1_max_threads > MAX_THREADS) {
|
||||
DLOG_FATAL("Maximum threads must be less than %d.", MAX_THREADS);
|
||||
return 0;
|
||||
|
@ -71,6 +71,7 @@ const T_DATUM_CONFIG_ITEM *datum_config_get_option_info2(const char *category, c
|
||||
// Globally accessable config options
|
||||
typedef struct {
|
||||
char bitcoind_rpcuserpass[256];
|
||||
char bitcoind_rpccookiefile[1024];
|
||||
char bitcoind_rpcuser[128];
|
||||
char bitcoind_rpcpassword[128];
|
||||
char bitcoind_rpcurl[256];
|
||||
|
@ -33,6 +33,7 @@
|
||||
*
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
@ -138,7 +139,7 @@ err_out:
|
||||
return NULL;
|
||||
}
|
||||
|
||||
json_t *json_rpc_call_full(CURL *curl, const char *url, const char *userpass, const char *rpc_req, const char *extra_header) {
|
||||
json_t *json_rpc_call_full(CURL *curl, const char *url, const char *userpass, const char *rpc_req, const char *extra_header, long * const http_resp_code_out) {
|
||||
json_t *val, *err_val, *res_val;
|
||||
CURLcode rc;
|
||||
struct data_buffer all_data = { };
|
||||
@ -186,6 +187,7 @@ json_t *json_rpc_call_full(CURL *curl, const char *url, const char *userpass, co
|
||||
|
||||
rc = curl_easy_perform(curl);
|
||||
if (rc) {
|
||||
if (http_resp_code_out) curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, http_resp_code_out);
|
||||
DLOG_DEBUG("json_rpc_call: HTTP request failed: %s", curl_err_str);
|
||||
DLOG_DEBUG("json_rpc_call: Request was: %s",rpc_req);
|
||||
goto err_out;
|
||||
@ -231,9 +233,31 @@ err_out:
|
||||
}
|
||||
|
||||
json_t *json_rpc_call(CURL *curl, const char *url, const char *userpass, const char *rpc_req) {
|
||||
return json_rpc_call_full(curl, url, userpass, rpc_req, NULL);
|
||||
return json_rpc_call_full(curl, url, userpass, rpc_req, NULL, NULL);
|
||||
}
|
||||
|
||||
bool update_rpc_cookie(global_config_t * const cfg) {
|
||||
assert(!cfg->bitcoind_rpcuser[0]);
|
||||
FILE * const F = fopen(cfg->bitcoind_rpccookiefile, "r");
|
||||
if (!F) {
|
||||
DLOG_ERROR("Cannot %s cookie file %s", "open", datum_config.bitcoind_rpccookiefile);
|
||||
return false;
|
||||
}
|
||||
if (!(fgets(cfg->bitcoind_rpcuserpass, sizeof(cfg->bitcoind_rpcuserpass), F) && cfg->bitcoind_rpcuserpass[0])) {
|
||||
DLOG_ERROR("Cannot %s cookie file %s", "read", datum_config.bitcoind_rpccookiefile);
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
json_t *bitcoind_json_rpc_call(CURL * const curl, global_config_t * const cfg, const char * const rpc_req) {
|
||||
return json_rpc_call(curl, cfg->bitcoind_rpcurl, datum_config.bitcoind_rpcuserpass, rpc_req);
|
||||
long http_resp_code = -1;
|
||||
json_t *j = json_rpc_call_full(curl, cfg->bitcoind_rpcurl, cfg->bitcoind_rpcuserpass, rpc_req, NULL, &http_resp_code);
|
||||
if (j) return j;
|
||||
if (cfg->bitcoind_rpcuser[0]) return NULL;
|
||||
if (http_resp_code != 401) return NULL;
|
||||
|
||||
// Authentication failure using cookie; reload cookie file and try again
|
||||
if (!update_rpc_cookie(cfg)) return NULL;
|
||||
return json_rpc_call(curl, cfg->bitcoind_rpcurl, cfg->bitcoind_rpcuserpass, rpc_req);
|
||||
}
|
||||
|
@ -65,6 +65,7 @@ struct upload_buffer {
|
||||
|
||||
json_t *json_rpc_call(CURL *curl, const char *url, const char *userpass, const char *rpc_req);
|
||||
char *basic_http_call(CURL *curl, const char *url);
|
||||
bool update_rpc_cookie(global_config_t *cfg);
|
||||
json_t *bitcoind_json_rpc_call(CURL *curl, global_config_t *cfg, const char *rpc_req);
|
||||
|
||||
#endif
|
||||
|
Loading…
Reference in New Issue
Block a user