summaryrefslogtreecommitdiff
path: root/cpp/src/Ice/InputStream.cpp
diff options
context:
space:
mode:
authorBenoit Foucher <benoit@zeroc.com>2016-09-07 18:09:21 +0200
committerBenoit Foucher <benoit@zeroc.com>2016-09-07 18:09:21 +0200
commit6c2e83d4c5418efa07af0af6d8c1aed1625c74a6 (patch)
treee874c3a845b1d50a1ad6acc084b49eb4354fcdee /cpp/src/Ice/InputStream.cpp
parentICE-7316 - JavaScript test/Ice/enum hang (diff)
downloadice-6c2e83d4c5418efa07af0af6d8c1aed1625c74a6.tar.bz2
ice-6c2e83d4c5418efa07af0af6d8c1aed1625c74a6.tar.xz
ice-6c2e83d4c5418efa07af0af6d8c1aed1625c74a6.zip
Fixed ICE-7279 - Fixed input stream to use zero-copy for string reads if there's no string converter
Diffstat (limited to 'cpp/src/Ice/InputStream.cpp')
-rw-r--r--cpp/src/Ice/InputStream.cpp63
1 files changed, 38 insertions, 25 deletions
diff --git a/cpp/src/Ice/InputStream.cpp b/cpp/src/Ice/InputStream.cpp
index 7563f412ae4..132012b07b2 100644
--- a/cpp/src/Ice/InputStream.cpp
+++ b/cpp/src/Ice/InputStream.cpp
@@ -1130,11 +1130,8 @@ Ice::InputStream::read(std::string& v, bool convert)
{
throwUnmarshalOutOfBoundsException(__FILE__, __LINE__);
}
- if(convert)
- {
- readConverted(v, sz);
- }
- else
+
+ if(!convert || !readConverted(v, sz))
{
string(reinterpret_cast<const char*>(&*i), reinterpret_cast<const char*>(&*i) + sz).swap(v);
}
@@ -1167,22 +1164,29 @@ Ice::InputStream::read(const char*& vdata, size_t& vsize, bool convert)
else
{
string converted;
- readConverted(converted, sz);
- if(converted.size() <= static_cast<size_t>(sz))
+ if(readConverted(converted, sz))
{
- //
- // Write converted string directly into buffer
- //
- std::memcpy(i, converted.data(), converted.size());
- vdata = reinterpret_cast<const char*>(&*i);
- vsize = converted.size();
+ if(converted.size() <= static_cast<size_t>(sz))
+ {
+ //
+ // Write converted string directly into buffer
+ //
+ std::memcpy(i, converted.data(), converted.size());
+ vdata = reinterpret_cast<const char*>(&*i);
+ vsize = converted.size();
+ }
+ else
+ {
+ auto holder = new string(std::move(converted));
+ _deleters.push_back([holder] { delete holder; });
+ vdata = holder->data();
+ vsize = holder->size();
+ }
}
else
{
- auto holder = new string(std::move(converted));
- _deleters.push_back([holder] { delete holder; });
- vdata = holder->data();
- vsize = holder->size();
+ vdata = reinterpret_cast<const char*>(&*i);
+ vsize = static_cast<size_t>(sz);
}
i += sz;
}
@@ -1229,10 +1233,17 @@ Ice::InputStream::read(const char*& vdata, size_t& vsize, string& holder)
throwUnmarshalOutOfBoundsException(__FILE__, __LINE__);
}
- readConverted(holder, sz);
+ if(readConverted(holder, sz))
+ {
+ vdata = holder.data();
+ vsize = holder.size();
+ }
+ else
+ {
+ vdata = reinterpret_cast<const char*>(&*i);
+ vsize = static_cast<size_t>(sz);
+ }
i += sz;
- vdata = holder.data();
- vsize = holder.size();
}
else
{
@@ -1243,13 +1254,18 @@ Ice::InputStream::read(const char*& vdata, size_t& vsize, string& holder)
}
#endif
-void
+bool
Ice::InputStream::readConverted(string& v, int sz)
{
try
{
bool converted = false;
+ //
+ // NOTE: When using an _instance, we get a const& on the string reference to
+ // not have to increment unecessarily its reference count.
+ //
+
if(_instance)
{
const StringConverterPtr& stringConverter = _instance->getStringConverter();
@@ -1269,10 +1285,7 @@ Ice::InputStream::readConverted(string& v, int sz)
}
}
- if(!converted)
- {
- string(reinterpret_cast<const char*>(&*i), reinterpret_cast<const char*>(&*i) + sz).swap(v);
- }
+ return converted;
}
catch(const IllegalConversionException& ex)
{