summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorArun Banala <arun.banala@mongodb.com>2019-03-19 12:51:59 +0000
committerArun Banala <arun.banala@mongodb.com>2019-03-27 19:00:25 +0000
commit6b3f5310fd6b7acecf50ffdb073611e5c816b184 (patch)
treef1fa8d615a0e7b7b024b2992e4f78169f46a4acb /src
parent00e078174ea44ab2fc7bc9178822bce57c48851c (diff)
downloadmongo-6b3f5310fd6b7acecf50ffdb073611e5c816b184.tar.gz
SERVER-37848 Test $regex agg expressions with regex that meets and exceeds the capture limit
Diffstat (limited to 'src')
-rw-r--r--src/mongo/db/pipeline/expression.cpp11
1 files changed, 9 insertions, 2 deletions
diff --git a/src/mongo/db/pipeline/expression.cpp b/src/mongo/db/pipeline/expression.cpp
index e9794c06a70..cebc922084f 100644
--- a/src/mongo/db/pipeline/expression.cpp
+++ b/src/mongo/db/pipeline/expression.cpp
@@ -5775,8 +5775,9 @@ private:
// The first two-thirds of the vector is used to pass back captured substrings' start and
// limit indexes. The remaining third of the vector is used as workspace by pcre_exec()
// while matching capturing subpatterns, and is not available for passing back information.
- // TODO: Evaluate the upper bound for this array and fail the request if numCaptures are
- // higher than the limit (SERVER-37848).
+ // pcre_compile will error if there are too many capture groups in the pattern. As long as
+ // this memory is allocated after compile, the amount of memory allocated will not be too
+ // high.
_capturesBuffer = std::vector<int>((1 + _numCaptures) * 3);
}
@@ -5873,6 +5874,7 @@ Value ExpressionRegexFindAll::evaluate(const Document& root) const {
}
int startByteIndex = 0, startCodePointIndex = 0;
StringData input = regex.getInput();
+ size_t totalDocSize = 0;
// Using do...while loop because, when input is an empty string, we still want to see if there
// is a match.
@@ -5881,6 +5883,11 @@ Value ExpressionRegexFindAll::evaluate(const Document& root) const {
if (matchObj.getType() == BSONType::jstNULL) {
break;
}
+ totalDocSize += matchObj.getApproximateSize();
+ uassert(51151,
+ "The size of buffer to store $regexFindAll output exceeded the 64MB limit",
+ totalDocSize <= mongo::BufferMaxSize);
+
output.push_back(matchObj);
std::string matchStr = matchObj.getDocument().getField("match").getString();
if (matchStr.empty()) {