aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorWladimir J. van der Laan <laanwj@gmail.com>2014-08-07 10:39:19 +0200
committerWladimir J. van der Laan <laanwj@gmail.com>2014-08-07 10:50:37 +0200
commit0b588168ab24c1db93fd568cc136380b59fc5809 (patch)
tree8e1fbb72c7d1a7774706671eef0baf08f11de9e4 /src
parent8833acc4c979877993f87c8fdc8a6d14cd072ba2 (diff)
parent733177ebd3ecf3a03c2acb6b244c8b3d1b4a3981 (diff)
Merge pull request #4640
733177e Remove size limit in RPC client, keep it in server (Wladimir J. van der Laan) e17151a Avoid a copy in RPC output (Wladimir J. van der Laan)
Diffstat (limited to 'src')
-rw-r--r--src/bitcoin-cli.cpp2
-rw-r--r--src/rpcprotocol.cpp27
-rw-r--r--src/rpcprotocol.h4
-rw-r--r--src/rpcserver.cpp4
4 files changed, 23 insertions, 14 deletions
diff --git a/src/bitcoin-cli.cpp b/src/bitcoin-cli.cpp
index 3b991f9276..0609adcab3 100644
--- a/src/bitcoin-cli.cpp
+++ b/src/bitcoin-cli.cpp
@@ -126,7 +126,7 @@ Object CallRPC(const string& strMethod, const Array& params)
// Receive HTTP reply message headers and body
map<string, string> mapHeaders;
string strReply;
- ReadHTTPMessage(stream, mapHeaders, strReply, nProto);
+ ReadHTTPMessage(stream, mapHeaders, strReply, nProto, std::numeric_limits<size_t>::max());
if (nStatus == HTTP_UNAUTHORIZED)
throw runtime_error("incorrect rpcuser or rpcpassword (authorization failed)");
diff --git a/src/rpcprotocol.cpp b/src/rpcprotocol.cpp
index 9e18ca847e..643208b3b6 100644
--- a/src/rpcprotocol.cpp
+++ b/src/rpcprotocol.cpp
@@ -93,8 +93,7 @@ string HTTPError(int nStatus, bool keepalive, bool headersOnly)
headersOnly, "text/plain");
}
-string HTTPReply(int nStatus, const string& strMsg, bool keepalive,
- bool headersOnly, const char *contentType)
+string HTTPReplyHeader(int nStatus, bool keepalive, size_t contentLength, const char *contentType)
{
return strprintf(
"HTTP/1.1 %d %s\r\n"
@@ -103,17 +102,25 @@ string HTTPReply(int nStatus, const string& strMsg, bool keepalive,
"Content-Length: %u\r\n"
"Content-Type: %s\r\n"
"Server: bitcoin-json-rpc/%s\r\n"
- "\r\n"
- "%s",
+ "\r\n",
nStatus,
httpStatusDescription(nStatus),
rfc1123Time(),
keepalive ? "keep-alive" : "close",
- (headersOnly ? 0 : strMsg.size()),
+ contentLength,
contentType,
- FormatFullVersion(),
- (headersOnly ? "" : strMsg.c_str())
- );
+ FormatFullVersion());
+}
+
+string HTTPReply(int nStatus, const string& strMsg, bool keepalive,
+ bool headersOnly, const char *contentType)
+{
+ if (headersOnly)
+ {
+ return HTTPReplyHeader(nStatus, keepalive, 0, contentType);
+ } else {
+ return HTTPReplyHeader(nStatus, keepalive, strMsg.size(), contentType) + strMsg;
+ }
}
bool ReadHTTPRequestLine(std::basic_istream<char>& stream, int &proto,
@@ -194,14 +201,14 @@ int ReadHTTPHeaders(std::basic_istream<char>& stream, map<string, string>& mapHe
int ReadHTTPMessage(std::basic_istream<char>& stream, map<string,
string>& mapHeadersRet, string& strMessageRet,
- int nProto)
+ int nProto, size_t max_size)
{
mapHeadersRet.clear();
strMessageRet = "";
// Read header
int nLen = ReadHTTPHeaders(stream, mapHeadersRet);
- if (nLen < 0 || nLen > (int)MAX_SIZE)
+ if (nLen < 0 || (size_t)nLen > max_size)
return HTTP_INTERNAL_SERVER_ERROR;
// Read message
diff --git a/src/rpcprotocol.h b/src/rpcprotocol.h
index 5627077bfb..8f05c08482 100644
--- a/src/rpcprotocol.h
+++ b/src/rpcprotocol.h
@@ -143,6 +143,8 @@ private:
std::string HTTPPost(const std::string& strMsg, const std::map<std::string,std::string>& mapRequestHeaders);
std::string HTTPError(int nStatus, bool keepalive,
bool headerOnly = false);
+std::string HTTPReplyHeader(int nStatus, bool keepalive, size_t contentLength,
+ const char *contentType = "application/json");
std::string HTTPReply(int nStatus, const std::string& strMsg, bool keepalive,
bool headerOnly = false,
const char *contentType = "application/json");
@@ -151,7 +153,7 @@ bool ReadHTTPRequestLine(std::basic_istream<char>& stream, int &proto,
int ReadHTTPStatus(std::basic_istream<char>& stream, int &proto);
int ReadHTTPHeaders(std::basic_istream<char>& stream, std::map<std::string, std::string>& mapHeadersRet);
int ReadHTTPMessage(std::basic_istream<char>& stream, std::map<std::string, std::string>& mapHeadersRet,
- std::string& strMessageRet, int nProto);
+ std::string& strMessageRet, int nProto, size_t max_size);
std::string JSONRPCRequest(const std::string& strMethod, const json_spirit::Array& params, const json_spirit::Value& id);
json_spirit::Object JSONRPCReplyObj(const json_spirit::Value& result, const json_spirit::Value& error, const json_spirit::Value& id);
std::string JSONRPCReply(const json_spirit::Value& result, const json_spirit::Value& error, const json_spirit::Value& id);
diff --git a/src/rpcserver.cpp b/src/rpcserver.cpp
index 716a7fba6a..e7ed73310c 100644
--- a/src/rpcserver.cpp
+++ b/src/rpcserver.cpp
@@ -862,7 +862,7 @@ static bool HTTPReq_JSONRPC(AcceptedConnection *conn,
else
throw JSONRPCError(RPC_PARSE_ERROR, "Top-level object parse error");
- conn->stream() << HTTPReply(HTTP_OK, strReply, fRun) << std::flush;
+ conn->stream() << HTTPReplyHeader(HTTP_OK, fRun, strReply.size()) << strReply << std::flush;
}
catch (Object& objError)
{
@@ -891,7 +891,7 @@ void ServiceConnection(AcceptedConnection *conn)
break;
// Read HTTP message headers and body
- ReadHTTPMessage(conn->stream(), mapHeaders, strRequest, nProto);
+ ReadHTTPMessage(conn->stream(), mapHeaders, strRequest, nProto, MAX_SIZE);
// HTTP Keep-Alive is false; close connection immediately
if (mapHeaders["connection"] == "close")