Date: Friday, January 19, 2007 @ 16:02:51
Author: marc
Path: /cvsroot/carob/carob
Modified: include/StringCodecs.hpp (1.25 -> 1.26) src/StringCodecs.cpp
(1.17 -> 1.18)
Implemented nomutex_en/decode() optimized methods for IconvCodec. CAROB-79
--------------------------+
include/StringCodecs.hpp | 9 +++++-
src/StringCodecs.cpp | 62 +++++++++++++++++++++++++++++++--------------
2 files changed, 52 insertions(+), 19 deletions(-)
Index: carob/include/StringCodecs.hpp
diff -u carob/include/StringCodecs.hpp:1.25 carob/include/StringCodecs.hpp:1.26
--- carob/include/StringCodecs.hpp:1.25 Fri Jan 19 15:34:58 2007
+++ carob/include/StringCodecs.hpp Fri Jan 19 16:02:51 2007
@@ -163,7 +163,7 @@
* Constructor.
* @param code The character code from/to the conversion will be.
*/
- IconvCodec(const std::string &code) throw (CodecException);
+ IconvCodec(const std::string &encodingName) throw (CodecException);
/**
* Destructor.
@@ -177,6 +177,8 @@
*/
std::string encode(const std::wstring&) const throw (CodecException);
+ std::string nomutex_encode(const std::wstring&) const throw (CodecException);
+
/**
* Decode from string to wstring.
* @param s the string.
@@ -184,6 +186,9 @@
*/
std::wstring decode(const std::string&) const throw (CodecException);
+ std::wstring nomutex_decode(const std::string&) const throw (CodecException);
+
+
private:
/**
* the conversion descriptors
@@ -191,6 +196,8 @@
iconv_t cd_from, cd_to;
/** iconv descriptors are stateful/not thread-safe */
mutable CriticalSection iconvDecodeCS, iconvEncodeCS;
+
+ std::wstring encodingName;
};
#endif // CAROB_USE_ICONV
Index: carob/src/StringCodecs.cpp
diff -u carob/src/StringCodecs.cpp:1.17 carob/src/StringCodecs.cpp:1.18
--- carob/src/StringCodecs.cpp:1.17 Fri Jan 19 12:35:36 2007
+++ carob/src/StringCodecs.cpp Fri Jan 19 16:02:51 2007
@@ -180,6 +180,9 @@
cd_to = iconv_open("WCHAR_T", code.c_str());
if (cd_to == (iconv_t) -1)
throw CodecException(L"Failed to open iconv decoder from " +
fromString(code));
+
+ encodingName = StaticCodecs::fromASCII(code);
+
}
IconvCodec::~IconvCodec()
@@ -194,9 +197,27 @@
}
}
+namespace {
+// reset the state
+size_t
+reset_iconv(iconv_t desc)
+{
+ return iconv_const_adapter(iconv, desc, 0, 0, 0, 0);
+}
+}
+
std::wstring
IconvCodec::decode(const std::string &s) const throw (CodecException)
{
+ // lock the iconv decode descriptor
+ LockScope ls(&iconvDecodeCS);
+
+ return nomutex_decode(s);
+}
+
+std::wstring
+IconvCodec::nomutex_decode(const std::string &s) const throw (CodecException)
+{
if (s.empty())
return std::wstring();
@@ -205,13 +226,7 @@
const char *inbuf = s.data();
size_t inbytesleft = s.length();
- // lock the iconv descriptor
- LockScope ls(&iconvDecodeCS);
- // reset the state
- if (iconv_const_adapter(iconv, cd_to, 0, 0, 0, 0) == (size_t) -1)
- throw CodecException(L"iconv reset failed.");
-
wchar_t convertbuf[CONVERTER_BUFFER_SIZE];
char *outbuf;
size_t outbytesleft;
@@ -229,11 +244,15 @@
case E2BIG:
break;
case EILSEQ:
- throw CodecException(L"An invalid multibyte sequence has been
encountered in the input.");
+ reset_iconv(cd_to);
+ throw CodecException(encodingName + L"-IconvCodec: an invalid
multibyte sequence"
+ L" has been encountered in the bytes to
decode");
break;
case EINVAL:
default:
- throw CodecException(L"An incomplete multibyte sequence has been
encountered in the input.");
+ reset_iconv(cd_to);
+ throw CodecException(encodingName + L"-IconvCodec: an incomplete
multibyte sequence"
+ L" has been encountered in the bytes to
decode");
break;
}
}
@@ -244,7 +263,17 @@
}
std::string
-IconvCodec::encode(const std::wstring &w) const throw (CodecException)
+IconvCodec::encode(const std::wstring &s) const throw (CodecException)
+{
+ // lock the iconv encode descriptor
+ LockScope ls(&iconvEncodeCS);
+
+ return nomutex_encode(s);
+}
+
+
+std::string
+IconvCodec::nomutex_encode(const std::wstring &w) const throw (CodecException)
{
if (w.empty())
return std::string();
@@ -258,13 +287,6 @@
char *outbuf;
size_t outbytesleft;
- // lock the iconv descriptor
- LockScope ls(&iconvEncodeCS);
-
- // reset the state
- if (iconv_const_adapter(iconv, cd_from, 0, 0, 0, 0) == (size_t) -1)
- throw CodecException(L"iconv reset failed.");
-
while (inbytesleft > 0)
{
outbuf = convertbuf;
@@ -278,11 +300,15 @@
case E2BIG:
break;
case EILSEQ:
- throw CodecException(L"An invalid multibyte sequence has been
encountered in the input.");
+ reset_iconv(cd_from);
+ throw CodecException(encodingName + L"An invalid multibyte sequence"
+ L" has been encountered in the wstring to
encode");
break;
case EINVAL:
default:
- throw CodecException(L"An incomplete multibyte sequence has been
encountered in the input.");
+ reset_iconv(cd_from);
+ throw CodecException(encodingName + L"An incomplete multibyte
sequence"
+ L" has been encountered in the wstring to
encode");
break;
}
}
_______________________________________________
Carob-commits mailing list
[email protected]
https://forge.continuent.org/mailman/listinfo/carob-commits