summaryrefslogtreecommitdiff
path: root/cpp/src/Ice/InputStream.cpp
diff options
context:
space:
mode:
authorBenoit Foucher <benoit@zeroc.com>2017-03-23 15:29:25 +0100
committerBenoit Foucher <benoit@zeroc.com>2017-03-23 15:29:25 +0100
commit1597a75419cd8049252cfbca6fce6ae95ef8b2c7 (patch)
tree2b2c858df1dbe68c1d576cae06c4713fd2ad5c40 /cpp/src/Ice/InputStream.cpp
parentUse Ice\None with PHP namespace mapping (diff)
downloadice-1597a75419cd8049252cfbca6fce6ae95ef8b2c7.tar.bz2
ice-1597a75419cd8049252cfbca6fce6ae95ef8b2c7.tar.xz
ice-1597a75419cd8049252cfbca6fce6ae95ef8b2c7.zip
Fix for ICE-7125 - Added support for Ice.ClassGraphDepthMax
Diffstat (limited to 'cpp/src/Ice/InputStream.cpp')
-rw-r--r--cpp/src/Ice/InputStream.cpp52
1 files changed, 50 insertions, 2 deletions
diff --git a/cpp/src/Ice/InputStream.cpp b/cpp/src/Ice/InputStream.cpp
index e10bc107df9..61f71c7b5ba 100644
--- a/cpp/src/Ice/InputStream.cpp
+++ b/cpp/src/Ice/InputStream.cpp
@@ -167,6 +167,7 @@ Ice::InputStream::initialize(Instance* instance, const EncodingVersion& encoding
_collectObjects = _instance->collectObjects();
#endif
_traceSlicing = _instance->traceLevels()->slicing > 0;
+ _classGraphDepthMax = _instance->classGraphDepthMax();
}
void
@@ -179,6 +180,7 @@ Ice::InputStream::initialize(const EncodingVersion& encoding)
_collectObjects = false;
#endif
_traceSlicing = false;
+ _classGraphDepthMax = 0x7fffffff;
_closure = 0;
_sliceValues = true;
_startSeq = -1;
@@ -241,6 +243,19 @@ Ice::InputStream::setTraceSlicing(bool b)
_traceSlicing = b;
}
+void
+Ice::InputStream::setClassGraphDepthMax(size_t classGraphDepthMax)
+{
+ if(classGraphDepthMax < 1)
+ {
+ _classGraphDepthMax = 0x7fffffff;
+ }
+ else
+ {
+ _classGraphDepthMax = classGraphDepthMax;
+ }
+}
+
void*
Ice::InputStream::getClosure() const
{
@@ -266,6 +281,7 @@ Ice::InputStream::swap(InputStream& other)
std::swap(_collectObjects, other._collectObjects);
#endif
std::swap(_traceSlicing, other._traceSlicing);
+ std::swap(_classGraphDepthMax, other._classGraphDepthMax);
std::swap(_closure, other._closure);
std::swap(_sliceValues, other._sliceValues);
@@ -1740,11 +1756,11 @@ Ice::InputStream::initEncaps()
ValueFactoryManagerPtr vfm = valueFactoryManager();
if(_currentEncaps->encoding == Encoding_1_0)
{
- _currentEncaps->decoder = new EncapsDecoder10(this, _currentEncaps, _sliceValues, vfm);
+ _currentEncaps->decoder = new EncapsDecoder10(this, _currentEncaps, _sliceValues, _classGraphDepthMax, vfm);
}
else
{
- _currentEncaps->decoder = new EncapsDecoder11(this, _currentEncaps, _sliceValues, vfm);
+ _currentEncaps->decoder = new EncapsDecoder11(this, _currentEncaps, _sliceValues, _classGraphDepthMax, vfm);
}
}
}
@@ -1884,6 +1900,7 @@ Ice::InputStream::EncapsDecoder::addPatchEntry(Int index, PatchFunc patchFunc, v
PatchEntry e;
e.patchFunc = patchFunc;
e.patchAddr = patchAddr;
+ e.classGraphDepth = _classGraphDepth;
q->second.push_back(e);
}
@@ -2233,6 +2250,30 @@ Ice::InputStream::EncapsDecoder10::readInstance()
}
//
+ // Compute the biggest class graph depth of this object. To compute this,
+ // we get the class graph depth of each ancestor from the patch map and
+ // keep the biggest one.
+ //
+ _classGraphDepth = 0;
+ PatchMap::iterator patchPos = _patchMap.find(index);
+ if(patchPos != _patchMap.end())
+ {
+ assert(patchPos->second.size() > 0);
+ for(PatchList::iterator k = patchPos->second.begin(); k != patchPos->second.end(); ++k)
+ {
+ if(k->classGraphDepth > _classGraphDepth)
+ {
+ _classGraphDepth = k->classGraphDepth;
+ }
+ }
+ }
+
+ if(++_classGraphDepth > _classGraphDepthMax)
+ {
+ throw MarshalException(__FILE__, __LINE__, "maximum class graph depth reached");
+ }
+
+ //
// Unmarshal the instance and add it to the map of unmarshaled instances.
//
unmarshal(index, v);
@@ -2668,11 +2709,18 @@ Ice::InputStream::EncapsDecoder11::readInstance(Int index, PatchFunc patchFunc,
startSlice(); // Read next Slice header for next iteration.
}
+ if(++_classGraphDepth > _classGraphDepthMax)
+ {
+ throw MarshalException(__FILE__, __LINE__, "maximum class graph depth reached");
+ }
+
//
// Unmarshal the object.
//
unmarshal(index, v);
+ --_classGraphDepth;
+
if(!_current && !_patchMap.empty())
{
//