aboutsummaryrefslogtreecommitdiff
path: root/src/rpcprotocol.cpp
diff options
context:
space:
mode:
authorWladimir J. van der Laan <laanwj@gmail.com>2014-06-20 15:21:30 +0200
committerWladimir J. van der Laan <laanwj@gmail.com>2014-07-04 09:20:39 +0200
commit2ec5a3d212ac4b09e6c32d495f34ee3cdedc8c66 (patch)
tree0e6bc0e598836a18ccbea70fc58968226acd5c28 /src/rpcprotocol.cpp
parente81e2e8f7cdee307227f150a6a2408c01fcafbf2 (diff)
downloadbitcoin-2ec5a3d212ac4b09e6c32d495f34ee3cdedc8c66.tar.xz
rpc: Prevent easy memory exhaustion attack
Allocate memory for POST message data only as bytes come in, instead of all at once at the beginning. Fixes #4343.
Diffstat (limited to 'src/rpcprotocol.cpp')
-rw-r--r--src/rpcprotocol.cpp16
1 files changed, 14 insertions, 2 deletions
diff --git a/src/rpcprotocol.cpp b/src/rpcprotocol.cpp
index dd8692e802..9e18ca847e 100644
--- a/src/rpcprotocol.cpp
+++ b/src/rpcprotocol.cpp
@@ -25,6 +25,9 @@ using namespace boost;
using namespace boost::asio;
using namespace json_spirit;
+// Number of bytes to allocate and read at most at once in post data
+const size_t POST_READ_SIZE = 256 * 1024;
+
//
// HTTP protocol
//
@@ -204,8 +207,17 @@ int ReadHTTPMessage(std::basic_istream<char>& stream, map<string,
// Read message
if (nLen > 0)
{
- vector<char> vch(nLen);
- stream.read(&vch[0], nLen);
+ vector<char> vch;
+ size_t ptr = 0;
+ while (ptr < (size_t)nLen)
+ {
+ size_t bytes_to_read = std::min((size_t)nLen - ptr, POST_READ_SIZE);
+ vch.resize(ptr + bytes_to_read);
+ stream.read(&vch[ptr], bytes_to_read);
+ if (!stream) // Connection lost while reading
+ return HTTP_INTERNAL_SERVER_ERROR;
+ ptr += bytes_to_read;
+ }
strMessageRet = string(vch.begin(), vch.end());
}