mirror of
https://github.com/bitcoin/bitcoin.git
synced 2025-11-11 22:50:59 +01:00
rpc: Implement random-cookie based authentication
When no `-rpcpassword` is specified, use a special 'cookie' file for authentication. This file is generated with random content when the daemon starts, and deleted when it exits. Read access to this file controls who can access through RPC. By default this file is stored in the data directory but it be overriden with `-rpccookiefile`. This is similar to Tor CookieAuthentication: see https://www.torproject.org/docs/tor-manual.html.en Alternative to #6258. Like that pull, this allows running bitcoind without any manual configuration. However, daemons should ideally never write to their configuration files, so I prefer this solution.
This commit is contained in:
@@ -97,12 +97,6 @@ static bool AppInitRPC(int argc, char* argv[])
|
||||
|
||||
UniValue CallRPC(const string& strMethod, const UniValue& params)
|
||||
{
|
||||
if (mapArgs["-rpcuser"] == "" && mapArgs["-rpcpassword"] == "")
|
||||
throw runtime_error(strprintf(
|
||||
_("You must set rpcpassword=<password> in the configuration file:\n%s\n"
|
||||
"If the file does not exist, create it with owner-readable-only file permissions."),
|
||||
GetConfigFile().string().c_str()));
|
||||
|
||||
// Connect to localhost
|
||||
bool fUseSSL = GetBoolArg("-rpcssl", false);
|
||||
boost::asio::io_service io_service;
|
||||
@@ -116,10 +110,24 @@ UniValue CallRPC(const string& strMethod, const UniValue& params)
|
||||
if (!fConnected)
|
||||
throw CConnectionFailed("couldn't connect to server");
|
||||
|
||||
// Find credentials to use
|
||||
std::string strRPCUserColonPass;
|
||||
if (mapArgs["-rpcpassword"] == "") {
|
||||
// Try fall back to cookie-based authentication if no password is provided
|
||||
if (!GetAuthCookie(&strRPCUserColonPass)) {
|
||||
throw runtime_error(strprintf(
|
||||
_("You must set rpcpassword=<password> in the configuration file:\n%s\n"
|
||||
"If the file does not exist, create it with owner-readable-only file permissions."),
|
||||
GetConfigFile().string().c_str()));
|
||||
|
||||
}
|
||||
} else {
|
||||
strRPCUserColonPass = mapArgs["-rpcuser"] + ":" + mapArgs["-rpcpassword"];
|
||||
}
|
||||
|
||||
// HTTP basic authentication
|
||||
string strUserPass64 = EncodeBase64(mapArgs["-rpcuser"] + ":" + mapArgs["-rpcpassword"]);
|
||||
map<string, string> mapRequestHeaders;
|
||||
mapRequestHeaders["Authorization"] = string("Basic ") + strUserPass64;
|
||||
mapRequestHeaders["Authorization"] = string("Basic ") + EncodeBase64(strRPCUserColonPass);
|
||||
|
||||
// Send request
|
||||
string strRequest = JSONRPCRequest(strMethod, params, 1);
|
||||
|
||||
Reference in New Issue
Block a user