diff options
author | Bernard Normier <bernard@zeroc.com> | 2016-10-20 21:03:44 -0400 |
---|---|---|
committer | Bernard Normier <bernard@zeroc.com> | 2016-10-20 21:03:44 -0400 |
commit | 3cb9c15995b828c52dba34d0a222f572d5bbc41b (patch) | |
tree | 87bad249c2ee04972be5f3c7635880cb0c556128 /cpp/src | |
parent | updating IceBT to BlueZ 5 (diff) | |
download | ice-3cb9c15995b828c52dba34d0a222f572d5bbc41b.tar.bz2 ice-3cb9c15995b828c52dba34d0a222f572d5bbc41b.tar.xz ice-3cb9c15995b828c52dba34d0a222f572d5bbc41b.zip |
Added support for non-ASCII characters and universal character names
to stringified identities and proxies.
This includes a new Ice.ToStringMode property.
Diffstat (limited to 'cpp/src')
44 files changed, 669 insertions, 379 deletions
diff --git a/cpp/src/Glacier2/Blobject.cpp b/cpp/src/Glacier2/Blobject.cpp index 4b822469c81..1f58da34ffb 100644 --- a/cpp/src/Glacier2/Blobject.cpp +++ b/cpp/src/Glacier2/Blobject.cpp @@ -261,7 +261,7 @@ Glacier2::Blobject::invoke(ObjectPrx& proxy, const AMD_Object_ice_invokePtr& amd } if(_reverseConnection) { - out << "\nidentity = " << identityToString(proxy->ice_getIdentity()); + out << "\nidentity = " << _instance->communicator()->identityToString(proxy->ice_getIdentity()); } else { @@ -310,7 +310,7 @@ Glacier2::Blobject::invoke(ObjectPrx& proxy, const AMD_Object_ice_invokePtr& amd out << "routing override"; if(_reverseConnection) { - out << "\nidentity = " << identityToString(proxy->ice_getIdentity()); + out << "\nidentity = " << _instance->communicator()->identityToString(proxy->ice_getIdentity()); } else { diff --git a/cpp/src/Glacier2/ClientBlobject.cpp b/cpp/src/Glacier2/ClientBlobject.cpp index f10c3d614b8..d7aef4ae401 100644 --- a/cpp/src/Glacier2/ClientBlobject.cpp +++ b/cpp/src/Glacier2/ClientBlobject.cpp @@ -120,7 +120,7 @@ Glacier2::ClientBlobject::ice_invoke_async(const Ice::AMD_Object_ice_invokePtr& { Trace out(_instance->logger(), "Glacier2"); out << "rejecting request: " << rejectedFilters << "\n"; - out << "identity: " << identityToString(current.id); + out << "identity: " << _instance->communicator()->identityToString(current.id); } ObjectNotExistException ex(__FILE__, __LINE__); diff --git a/cpp/src/Glacier2/FilterManager.cpp b/cpp/src/Glacier2/FilterManager.cpp index 95c52f9633a..7457367f0b9 100644 --- a/cpp/src/Glacier2/FilterManager.cpp +++ b/cpp/src/Glacier2/FilterManager.cpp @@ -34,7 +34,7 @@ stringToSeq(const string& str, vector<string>& seq) } static void -stringToSeq(const CommunicatorPtr& comm, const string& str, vector<Identity>& seq) +stringToSeq(const string& str, vector<Identity>& seq) { string const ws = " \t"; @@ -214,7 +214,7 @@ Glacier2::FilterManager::create(const InstancePtr& instance, const string& userI // IdentitySeq allowIdSeq; allow = props->getProperty("Glacier2.Filter.Identity.Accept"); - stringToSeq(instance->communicator(), allow, allowIdSeq); + stringToSeq(allow, allowIdSeq); Glacier2::IdentitySetIPtr identityFilter = new Glacier2::IdentitySetI(allowIdSeq); return new Glacier2::FilterManager(instance, categoryFilter, adapterIdFilter, identityFilter); diff --git a/cpp/src/Glacier2/Instance.h b/cpp/src/Glacier2/Instance.h index 65b0e70a848..ed1fd76f3ba 100644 --- a/cpp/src/Glacier2/Instance.h +++ b/cpp/src/Glacier2/Instance.h @@ -44,7 +44,7 @@ public: const Glacier2::Instrumentation::RouterObserverPtr& getObserver() const { return _observer; } void destroy(); - + private: friend class SessionRouterI; diff --git a/cpp/src/Glacier2/SessionRouterI.cpp b/cpp/src/Glacier2/SessionRouterI.cpp index 91b5e05db6f..9f774b79a8e 100644 --- a/cpp/src/Glacier2/SessionRouterI.cpp +++ b/cpp/src/Glacier2/SessionRouterI.cpp @@ -1150,7 +1150,7 @@ SessionRouterI::getRouterImpl(const ConnectionPtr& connection, const Ice::Identi { Trace out(_instance->logger(), "Glacier2"); out << "rejecting request. no session is associated with the connection.\n"; - out << "identity: " << identityToString(id); + out << "identity: " << _instance->communicator()->identityToString(id); } connection->close(true); throw ObjectNotExistException(__FILE__, __LINE__); diff --git a/cpp/src/Glacier2Lib/NullPermissionsVerifier.cpp b/cpp/src/Glacier2Lib/NullPermissionsVerifier.cpp index 31d33ad00a4..abc76a3b6e8 100644 --- a/cpp/src/Glacier2Lib/NullPermissionsVerifier.cpp +++ b/cpp/src/Glacier2Lib/NullPermissionsVerifier.cpp @@ -111,12 +111,12 @@ Init::checkPermissionVerifier(const string& val) // check if it's actually a stringified identity // (with typically missing " " because the category contains a space) - if(val == identityToString(_nullPVId)) + if(val == _communicator->identityToString(_nullPVId)) { createObjects(); return _adapter->createProxy(_nullPVId)->ice_toString(); // Return valid proxy to rewrite the property } - else if(val == identityToString(_nullSSLPVId)) + else if(val == _communicator->identityToString(_nullSSLPVId)) { createObjects(); return _adapter->createProxy(_nullSSLPVId)->ice_toString(); // Return valid proxy to rewrite the property diff --git a/cpp/src/Glacier2Lib/SessionHelper.cpp b/cpp/src/Glacier2Lib/SessionHelper.cpp index 34565f357e4..5a6c9354ae1 100644 --- a/cpp/src/Glacier2Lib/SessionHelper.cpp +++ b/cpp/src/Glacier2Lib/SessionHelper.cpp @@ -1215,7 +1215,9 @@ string Glacier2::SessionFactoryHelper::createProxyStr(const Ice::Identity& ident) { ostringstream os; - os << "\"" << Ice::identityToString(ident) << "\":" << _protocol << " -p " << getPortInternal() << " -h \"" << _routerHost << "\""; + os << "\"" << identityToString(ident, Ice::ICE_ENUM(ToStringMode, Unicode)) << "\":" << _protocol + << " -p " << getPortInternal() << " -h \"" << _routerHost << "\""; + if(_timeout > 0) { os << " -t " << _timeout; diff --git a/cpp/src/Ice/CommunicatorI.cpp b/cpp/src/Ice/CommunicatorI.cpp index 8a257ede66b..99c332f629e 100644 --- a/cpp/src/Ice/CommunicatorI.cpp +++ b/cpp/src/Ice/CommunicatorI.cpp @@ -89,7 +89,7 @@ Ice::CommunicatorI::stringToIdentity(const string& s) const string Ice::CommunicatorI::identityToString(const Identity& ident) const { - return Ice::identityToString(ident); + return Ice::identityToString(ident, _instance->toStringMode()); } ObjectAdapterPtr diff --git a/cpp/src/Ice/Exception.cpp b/cpp/src/Ice/Exception.cpp index 7e2fc340c9d..95136f5339a 100644 --- a/cpp/src/Ice/Exception.cpp +++ b/cpp/src/Ice/Exception.cpp @@ -14,6 +14,7 @@ #include <Ice/SlicedData.h> #include <Ice/OutputStream.h> #include <Ice/InputStream.h> +#include <Ice/Initialize.h> #include <IceUtil/StringUtil.h> #ifdef ICE_OS_WINRT # include <Ice/StringConverter.h> @@ -339,16 +340,7 @@ void Ice::IllegalIdentityException::ice_print(ostream& out) const { Exception::ice_print(out); - out << ":\nillegal identity: `"; - if(id.category.empty()) - { - out << IceUtilInternal::escapeString(id.name, "/"); - } - else - { - out << IceUtilInternal::escapeString(id.category, "/") << '/' << IceUtilInternal::escapeString(id.name, "/"); - } - out << "'"; + out << ":\nillegal identity: `" << identityToString(id, ICE_ENUM(ToStringMode, Unicode)) << "'"; } void @@ -362,16 +354,7 @@ Ice::IllegalServantException::ice_print(ostream& out) const static void printFailedRequestData(ostream& out, const RequestFailedException& ex) { - out << ":\nidentity: `"; - if(ex.id.category.empty()) - { - out << IceUtilInternal::escapeString(ex.id.name, "/"); - } - else - { - out << IceUtilInternal::escapeString(ex.id.category, "/") << '/' << IceUtilInternal::escapeString(ex.id.name, "/"); - } - out << "'"; + out << ":\nidentity: `" << identityToString(ex.id, ICE_ENUM(ToStringMode, Unicode)) << "'"; out << "\nfacet: " << ex.facet; out << "\noperation: " << ex.operation; } diff --git a/cpp/src/Ice/Incoming.cpp b/cpp/src/Ice/Incoming.cpp index 7b5e6741660..da4bb25cbc6 100644 --- a/cpp/src/Ice/Incoming.cpp +++ b/cpp/src/Ice/Incoming.cpp @@ -22,7 +22,7 @@ #include <Ice/Protocol.h> #include <Ice/ReplyStatus.h> #include <Ice/ResponseHandler.h> -#include <IceUtil/StringUtil.h> +#include <Ice/StringUtil.h> #include <typeinfo> using namespace std; @@ -222,9 +222,12 @@ IceInternal::IncomingBase::warning(const Exception& ex) const { Warning out(_os.instance()->initializationData().logger); + ToStringMode toStringMode = _os.instance()->toStringMode(); + out << "dispatch exception: " << ex; - out << "\nidentity: " << Ice::identityToString(_current.id); - out << "\nfacet: " << IceUtilInternal::escapeString(_current.facet, ""); + out << "\nidentity: " << identityToString(_current.id, toStringMode); + out << "\nfacet: "; + out << escapeString(_current.facet, "", toStringMode); out << "\noperation: " << _current.operation; if(_current.con) @@ -252,10 +255,11 @@ void IceInternal::IncomingBase::warning(const string& msg) const { Warning out(_os.instance()->initializationData().logger); + ToStringMode toStringMode = _os.instance()->toStringMode(); out << "dispatch exception: " << msg; - out << "\nidentity: " << Ice::identityToString(_current.id); - out << "\nfacet: " << IceUtilInternal::escapeString(_current.facet, ""); + out << "\nidentity: " << identityToString(_current.id, toStringMode); + out << "\nfacet: " << escapeString(_current.facet, "", toStringMode); out << "\noperation: " << _current.operation; if(_current.con) diff --git a/cpp/src/Ice/Initialize.cpp b/cpp/src/Ice/Initialize.cpp index 52f03678659..f1f92c3826d 100644 --- a/cpp/src/Ice/Initialize.cpp +++ b/cpp/src/Ice/Initialize.cpp @@ -16,7 +16,7 @@ #include <Ice/LoggerI.h> #include <Ice/Instance.h> #include <Ice/PluginManagerI.h> -#include <IceUtil/StringUtil.h> +#include <Ice/StringUtil.h> #include <IceUtil/Mutex.h> #include <IceUtil/MutexPtrLock.h> #include <Ice/StringConverter.h> @@ -357,15 +357,6 @@ IceInternal::getInstanceTimer(const CommunicatorPtr& communicator) Identity Ice::stringToIdentity(const string& s) { - // - // This method only accepts printable ascii. Since printable ascii is a subset - // of all narrow string encodings, it is not necessary to convert the string - // from the native string encoding. Any characters other than printable-ASCII - // will cause an IllegalArgumentException. Note that it can contain Unicode - // encoded in the escaped form which is the reason why we call fromUTF8 after - // unespcaping the printable ASCII string. - // - Identity ident; // @@ -376,7 +367,7 @@ Ice::stringToIdentity(const string& s) while((pos = s.find('/', pos)) != string::npos) { int escapes = 0; - while(static_cast<int>(pos)- escapes > 0 && s[pos - escapes - 1] == '\\') + while(static_cast<int>(pos) - escapes > 0 && s[pos - escapes - 1] == '\\') { escapes++; } @@ -396,7 +387,7 @@ Ice::stringToIdentity(const string& s) // Extra unescaped slash found. // IdentityParseException ex(__FILE__, __LINE__); - ex.str = "unescaped backslash in identity `" + s + "'"; + ex.str = "unescaped '/' in identity `" + s + "'"; throw ex; } } @@ -407,7 +398,7 @@ Ice::stringToIdentity(const string& s) { try { - ident.name = IceUtilInternal::unescapeString(s, 0, s.size()); + ident.name = unescapeString(s, 0, s.size()); } catch(const IceUtil::IllegalArgumentException& e) { @@ -420,7 +411,7 @@ Ice::stringToIdentity(const string& s) { try { - ident.category = IceUtilInternal::unescapeString(s, 0, slash); + ident.category = unescapeString(s, 0, slash); } catch(const IceUtil::IllegalArgumentException& e) { @@ -428,11 +419,12 @@ Ice::stringToIdentity(const string& s) ex.str = "invalid category in identity `" + s + "': " + e.reason(); throw ex; } + if(slash + 1 < s.size()) { try { - ident.name = IceUtilInternal::unescapeString(s, slash + 1, s.size()); + ident.name = unescapeString(s, slash + 1, s.size()); } catch(const IceUtil::IllegalArgumentException& e) { @@ -443,28 +435,18 @@ Ice::stringToIdentity(const string& s) } } - ident.name = UTF8ToNative(ident.name, getProcessStringConverter()); - ident.category = UTF8ToNative(ident.category, getProcessStringConverter()); - return ident; } string -Ice::identityToString(const Identity& ident) +Ice::identityToString(const Identity& ident, ToStringMode toStringMode) { - // - // This method returns the stringified identity. The returned string only - // contains printable ascii. It can contain UTF8 in the escaped form. - // - string name = nativeToUTF8(ident.name, getProcessStringConverter()); - string category = nativeToUTF8(ident.category, getProcessStringConverter()); - - if(category.empty()) + if(ident.category.empty()) { - return IceUtilInternal::escapeString(name, "/"); + return escapeString(ident.name, "/", toStringMode); } else { - return IceUtilInternal::escapeString(category, "/") + '/' + IceUtilInternal::escapeString(name, "/"); + return escapeString(ident.category, "/", toStringMode) + '/' + escapeString(ident.name, "/", toStringMode); } } diff --git a/cpp/src/Ice/Instance.cpp b/cpp/src/Ice/Instance.cpp index d99567e09f9..304036dec90 100644 --- a/cpp/src/Ice/Instance.cpp +++ b/cpp/src/Ice/Instance.cpp @@ -948,6 +948,7 @@ IceInternal::Instance::Instance(const CommunicatorPtr& communicator, const Initi _messageSizeMax(0), _batchAutoFlushSize(0), _collectObjects(false), + _toStringMode(ICE_ENUM(ToStringMode, Unicode)), _implicitContext(0), _stringConverter(Ice::getProcessStringConverter()), _wstringConverter(Ice::getProcessWstringConverter()), @@ -1189,6 +1190,21 @@ IceInternal::Instance::Instance(const CommunicatorPtr& communicator, const Initi const_cast<bool&>(_collectObjects) = _initData.properties->getPropertyAsInt("Ice.CollectObjects") > 0; + string toStringModeStr = _initData.properties->getPropertyWithDefault("Ice.ToStringMode", "Unicode"); + if(toStringModeStr == "ASCII") + { + const_cast<ToStringMode&>(_toStringMode) = ICE_ENUM(ToStringMode, ASCII); + } + else if(toStringModeStr == "Compat") + { + const_cast<ToStringMode&>(_toStringMode) = ICE_ENUM(ToStringMode, Compat); + } + else if(toStringModeStr != "Unicode") + { + throw InitializationException(__FILE__, __LINE__, "The value for Ice.ToStringMode must be Unicode, ASCII or Compat"); + } + + // // Client ACM enabled by default. Server ACM disabled by default. // diff --git a/cpp/src/Ice/Instance.h b/cpp/src/Ice/Instance.h index 22a39169c38..2e4fd503b16 100644 --- a/cpp/src/Ice/Instance.h +++ b/cpp/src/Ice/Instance.h @@ -110,6 +110,7 @@ public: size_t messageSizeMax() const { return _messageSizeMax; } size_t batchAutoFlushSize() const { return _batchAutoFlushSize; } bool collectObjects() const { return _collectObjects; } + Ice::ToStringMode toStringMode() const { return _toStringMode; } const ACMConfig& clientACM() const; const ACMConfig& serverACM() const; @@ -177,6 +178,7 @@ private: const size_t _messageSizeMax; // Immutable, not reset by destroy(). const size_t _batchAutoFlushSize; // Immutable, not reset by destroy(). const bool _collectObjects; // Immutable, not reset by destroy(). + const Ice::ToStringMode _toStringMode; // Immutable, not reset by destroy() ACMConfig _clientACM; ACMConfig _serverACM; RouterManagerPtr _routerManager; diff --git a/cpp/src/Ice/InstrumentationI.cpp b/cpp/src/Ice/InstrumentationI.cpp index 64ff4f91e07..0f816647a11 100644 --- a/cpp/src/Ice/InstrumentationI.cpp +++ b/cpp/src/Ice/InstrumentationI.cpp @@ -334,7 +334,7 @@ public: string getIdentity() const { - return identityToString(_current.id); + return _current.adapter->getCommunicator()->identityToString(_current.id); } private: @@ -443,7 +443,7 @@ public: catch(const Exception&) { // Either a fixed proxy or the communicator is destroyed. - os << identityToString(_proxy->ice_getIdentity()); + os << _proxy->ice_getCommunicator()->identityToString(_proxy->ice_getIdentity()); os << " [" << _operation << ']'; } } @@ -474,7 +474,7 @@ public: { if(_proxy) { - return identityToString(_proxy->ice_getIdentity()); + return _proxy->ice_getCommunicator()->identityToString(_proxy->ice_getIdentity()); } else { diff --git a/cpp/src/Ice/LocatorInfo.cpp b/cpp/src/Ice/LocatorInfo.cpp index 03264b5898c..74f65e2d808 100644 --- a/cpp/src/Ice/LocatorInfo.cpp +++ b/cpp/src/Ice/LocatorInfo.cpp @@ -785,12 +785,13 @@ IceInternal::LocatorInfo::getEndpointsException(const ReferencePtr& ref, const I Trace out(ref->getInstance()->initializationData().logger, ref->getInstance()->traceLevels()->locationCat); out << "object not found" << "\n"; - out << "object = " << Ice::identityToString(ref->getIdentity()); + out << "object = " << Ice::identityToString(ref->getIdentity(), + ref->getInstance()->toStringMode()); } NotRegisteredException ex(__FILE__, __LINE__); ex.kindOfObject = "object"; - ex.id = Ice::identityToString(ref->getIdentity()); + ex.id = Ice::identityToString(ref->getIdentity(), ref->getInstance()->toStringMode()); throw ex; } catch(const NotRegisteredException&) @@ -805,7 +806,8 @@ IceInternal::LocatorInfo::getEndpointsException(const ReferencePtr& ref, const I out << "couldn't contact the locator to retrieve adapter endpoints\n"; if(ref->getAdapterId().empty()) { - out << "object = " << Ice::identityToString(ref->getIdentity()) << "\n"; + out << "object = " << Ice::identityToString(ref->getIdentity(), ref->getInstance()->toStringMode()) + << "\n"; } else { @@ -840,7 +842,7 @@ IceInternal::LocatorInfo::getEndpointsTrace(const ReferencePtr& ref, if(ref->getAdapterId().empty()) { out << "object\n"; - out << "object = " << Ice::identityToString(ref->getIdentity()); + out << "object = " << Ice::identityToString(ref->getIdentity(), ref->getInstance()->toStringMode()); } else { @@ -863,7 +865,8 @@ IceInternal::LocatorInfo::trace(const string& msg, const ReferencePtr& ref, cons } else { - out << "object = " << Ice::identityToString(ref->getIdentity()) << '\n'; + out << "object = " << Ice::identityToString(ref->getIdentity(), ref->getInstance()->toStringMode()) + << '\n'; } const char* sep = endpoints.size() > 1 ? ":" : ""; @@ -901,7 +904,8 @@ IceInternal::LocatorInfo::getObjectRequest(const ReferencePtr& ref) if(ref->getInstance()->traceLevels()->location >= 1) { Trace out(ref->getInstance()->initializationData().logger, ref->getInstance()->traceLevels()->locationCat); - out << "searching for object by id\nobject = " << Ice::identityToString(ref->getIdentity()); + out << "searching for object by id\nobject = " << Ice::identityToString(ref->getIdentity(), + ref->getInstance()->toStringMode()); } map<Ice::Identity, RequestPtr>::const_iterator p = _objectRequests.find(ref->getIdentity()); diff --git a/cpp/src/Ice/ObjectAdapterI.cpp b/cpp/src/Ice/ObjectAdapterI.cpp index 18cc2dd87f0..0631186769d 100644 --- a/cpp/src/Ice/ObjectAdapterI.cpp +++ b/cpp/src/Ice/ObjectAdapterI.cpp @@ -682,7 +682,7 @@ Ice::ObjectAdapterI::getEndpoints() const EndpointSeq endpoints; transform(_incomingConnectionFactories.begin(), _incomingConnectionFactories.end(), - back_inserter(endpoints), + back_inserter(endpoints), #ifdef ICE_CPP11_MAPPING [](const IncomingConnectionFactoryPtr& factory) { @@ -1020,8 +1020,9 @@ Ice::ObjectAdapterI::initialize(const RouterPrxPtr& router) // if(_routerInfo->getAdapter()) { - throw AlreadyRegisteredException(__FILE__, __LINE__, "object adapter with router", - Ice::identityToString(router->ice_getIdentity())); + throw AlreadyRegisteredException(__FILE__, __LINE__, + "object adapter with router", + _communicator->identityToString(router->ice_getIdentity())); } // diff --git a/cpp/src/Ice/PropertyNames.cpp b/cpp/src/Ice/PropertyNames.cpp index c1a1cde9335..1bf95a2df3b 100644 --- a/cpp/src/Ice/PropertyNames.cpp +++ b/cpp/src/Ice/PropertyNames.cpp @@ -6,7 +6,7 @@ // ICE_LICENSE file included in this distribution. // // ********************************************************************** -// Generated by makeprops.py from file ../config/PropertyNames.xml, Wed Oct 5 19:04:47 2016 +// Generated by makeprops.py from file ../config/PropertyNames.xml, Tue Oct 18 11:38:00 2016 // IMPORTANT: Do not edit this file -- any edits made here will be lost! @@ -163,6 +163,7 @@ const IceInternal::Property IcePropsData[] = IceInternal::Property("Ice.ThreadPool.Server.ThreadIdleTime", false, 0), IceInternal::Property("Ice.ThreadPool.Server.ThreadPriority", false, 0), IceInternal::Property("Ice.ThreadPriority", false, 0), + IceInternal::Property("Ice.ToStringMode", false, 0), IceInternal::Property("Ice.Trace.Admin.Properties", false, 0), IceInternal::Property("Ice.Trace.Admin.Logger", false, 0), IceInternal::Property("Ice.Trace.Locator", false, 0), diff --git a/cpp/src/Ice/PropertyNames.h b/cpp/src/Ice/PropertyNames.h index 52e12f92225..e9c85a1e59f 100644 --- a/cpp/src/Ice/PropertyNames.h +++ b/cpp/src/Ice/PropertyNames.h @@ -6,7 +6,7 @@ // ICE_LICENSE file included in this distribution. // // ********************************************************************** -// Generated by makeprops.py from file ../config/PropertyNames.xml, Wed Oct 5 19:04:47 2016 +// Generated by makeprops.py from file ../config/PropertyNames.xml, Tue Oct 18 11:38:00 2016 // IMPORTANT: Do not edit this file -- any edits made here will be lost! diff --git a/cpp/src/Ice/Reference.cpp b/cpp/src/Ice/Reference.cpp index 86328e0880a..12296b9f04f 100644 --- a/cpp/src/Ice/Reference.cpp +++ b/cpp/src/Ice/Reference.cpp @@ -28,8 +28,8 @@ #include <Ice/ConnectionRequestHandler.h> #include <Ice/DefaultsAndOverrides.h> #include <Ice/Comparable.h> +#include <Ice/StringUtil.h> -#include <IceUtil/StringUtil.h> #include <IceUtil/Random.h> #include <IceUtil/MutexPtrLock.h> @@ -231,13 +231,18 @@ IceInternal::Reference::toString() const // ostringstream s; + ToStringMode toStringMode = _instance->toStringMode(); + const string separators = " :@"; + + string id = Ice::identityToString(_identity, toStringMode); + // // If the encoded identity string contains characters which // the reference parser uses as separators, then we enclose // the identity string in quotes. // - string id = Ice::identityToString(_identity); - if(id.find_first_of(" :@") != string::npos) + + if(id.find_first_of(separators) != string::npos) { s << '"' << id << '"'; } @@ -250,14 +255,13 @@ IceInternal::Reference::toString() const { s << " -f "; + string fs = escapeString(fs, "", toStringMode); // // If the encoded facet string contains characters which // the reference parser uses as separators, then we enclose // the facet string in quotes. // - string fs = nativeToUTF8(_facet, _instance->getStringConverter()); - fs = IceUtilInternal::escapeString(fs, ""); - if(fs.find_first_of(" :@") != string::npos) + if(fs.find_first_of(separators) != string::npos) { s << '"' << fs << '"'; } @@ -1224,8 +1228,7 @@ IceInternal::RoutableReference::toString() const // reference parser uses as separators, then we enclose the // adapter id string in quotes. // - string a = nativeToUTF8(_adapterId, getInstance()->getStringConverter()); - a = IceUtilInternal::escapeString(a, ""); + string a = escapeString(_adapterId, "", getInstance()->toStringMode()); if(a.find_first_of(" :@") != string::npos) { result.append("\""); diff --git a/cpp/src/Ice/ReferenceFactory.cpp b/cpp/src/Ice/ReferenceFactory.cpp index 3788324d81d..63b8df7effe 100644 --- a/cpp/src/Ice/ReferenceFactory.cpp +++ b/cpp/src/Ice/ReferenceFactory.cpp @@ -24,7 +24,7 @@ #include <Ice/Properties.h> #include <Ice/DefaultsAndOverrides.h> #include <Ice/PropertyNames.h> -#include <IceUtil/StringUtil.h> +#include <Ice/StringUtil.h> using namespace std; using namespace Ice; @@ -156,6 +156,7 @@ IceInternal::ReferenceFactory::create(const string& str, const string& propertyP // Parsing the identity may raise IdentityParseException. // Identity ident = Ice::stringToIdentity(idstr); + if(ident.name.empty()) { // @@ -279,7 +280,7 @@ IceInternal::ReferenceFactory::create(const string& str, const string& propertyP try { - facet = IceUtilInternal::unescapeString(argument, 0, argument.size()); + facet = unescapeString(argument, 0, argument.size()); } catch(const IceUtil::IllegalArgumentException& e) { @@ -288,7 +289,6 @@ IceInternal::ReferenceFactory::create(const string& str, const string& propertyP throw ex; } - facet = UTF8ToNative(facet, _instance->getStringConverter()); break; } @@ -554,7 +554,7 @@ IceInternal::ReferenceFactory::create(const string& str, const string& propertyP try { - adapter = IceUtilInternal::unescapeString(adapterstr, 0, adapterstr.size()); + adapter = unescapeString(adapterstr, 0, adapterstr.size()); } catch(const IceUtil::IllegalArgumentException& e) { @@ -569,8 +569,6 @@ IceInternal::ReferenceFactory::create(const string& str, const string& propertyP throw ex; } - adapter = UTF8ToNative(adapter, _instance->getStringConverter()); - return create(ident, facet, mode, secure, protocol, encoding, endpoints, adapter, propertyPrefix); break; } @@ -934,4 +932,3 @@ IceInternal::ReferenceFactory::create(const Identity& ident, invocationTimeout, ctx); } - diff --git a/cpp/src/Ice/ServantManager.cpp b/cpp/src/Ice/ServantManager.cpp index 3d1f51112ae..16c5da45d1f 100644 --- a/cpp/src/Ice/ServantManager.cpp +++ b/cpp/src/Ice/ServantManager.cpp @@ -12,7 +12,7 @@ #include <Ice/LocalException.h> #include <Ice/LoggerUtil.h> #include <Ice/Instance.h> -#include <IceUtil/StringUtil.h> +#include <Ice/StringUtil.h> using namespace std; using namespace Ice; @@ -44,11 +44,11 @@ IceInternal::ServantManager::addServant(const ObjectPtr& object, const Identity& { AlreadyRegisteredException ex(__FILE__, __LINE__); ex.kindOfObject = "servant"; - ex.id = Ice::identityToString(ident); + ToStringMode toStringMode = _instance->toStringMode(); + ex.id = Ice::identityToString(ident, toStringMode); if(!facet.empty()) { - string fs = nativeToUTF8(facet, _instance->getStringConverter()); - ex.id += " -f " + IceUtilInternal::escapeString(fs, ""); + ex.id += " -f " + escapeString(facet, "", toStringMode); } throw ex; } @@ -104,11 +104,11 @@ IceInternal::ServantManager::removeServant(const Identity& ident, const string& { NotRegisteredException ex(__FILE__, __LINE__); ex.kindOfObject = "servant"; - ex.id = Ice::identityToString(ident); + ToStringMode toStringMode = _instance->toStringMode(); + ex.id = Ice::identityToString(ident, toStringMode); if(!facet.empty()) { - string fs = nativeToUTF8(facet, _instance->getStringConverter()); - ex.id += " -f " + IceUtilInternal::escapeString(fs, ""); + ex.id += " -f " + escapeString(facet, "", toStringMode); } throw ex; } @@ -178,7 +178,7 @@ IceInternal::ServantManager::removeAllFacets(const Identity& ident) { NotRegisteredException ex(__FILE__, __LINE__); ex.kindOfObject = "servant"; - ex.id = Ice::identityToString(ident); + ex.id = Ice::identityToString(ident, _instance->toStringMode()); throw ex; } diff --git a/cpp/src/Ice/StringUtil.h b/cpp/src/Ice/StringUtil.h new file mode 100644 index 00000000000..70dab65bf88 --- /dev/null +++ b/cpp/src/Ice/StringUtil.h @@ -0,0 +1,35 @@ +// ********************************************************************** +// +// Copyright (c) 2003-2016 ZeroC, Inc. All rights reserved. +// +// This copy of Ice is licensed to you under the terms described in the +// ICE_LICENSE file included in this distribution. +// +// ********************************************************************** + +#ifndef ICE_STRING_UTIL_H +#define ICE_STRING_UTIL_H + +#include <Ice/Initialize.h> +#include <IceUtil/StringUtil.h> + +namespace IceInternal +{ + +// +// Adapter for ToStringMode +// +inline std::string +escapeString(const std::string& s, const std::string& special, Ice::ToStringMode mode) +{ + return IceUtilInternal::escapeString(s, special, static_cast<IceUtilInternal::ToStringMode>(mode)); +} + +// +// Provided for consistency with escapeString +// +using IceUtilInternal::unescapeString; + +} + +#endif diff --git a/cpp/src/Ice/TraceUtil.cpp b/cpp/src/Ice/TraceUtil.cpp index 5e92c6c05d5..db7c0041b45 100644 --- a/cpp/src/Ice/TraceUtil.cpp +++ b/cpp/src/Ice/TraceUtil.cpp @@ -9,7 +9,7 @@ #include <IceUtil/Mutex.h> #include <IceUtil/MutexPtrLock.h> -#include <IceUtil/StringUtil.h> +#include <Ice/StringUtil.h> #include <Ice/TraceUtil.h> #include <Ice/Instance.h> #include <Ice/Object.h> @@ -29,16 +29,22 @@ using namespace IceInternal; static void printIdentityFacetOperation(ostream& s, InputStream& stream) { + ToStringMode toStringMode = ICE_ENUM(ToStringMode, Unicode); + if(stream.instance()) + { + toStringMode = stream.instance()->toStringMode(); + } + Identity identity; stream.read(identity); - s << "\nidentity = " << Ice::identityToString(identity); + s << "\nidentity = " << Ice::identityToString(identity, toStringMode); vector<string> facet; stream.read(facet); s << "\nfacet = "; if(!facet.empty()) { - s << IceUtilInternal::escapeString(facet[0], ""); + s << escapeString(facet[0], "", toStringMode); } string operation; diff --git a/cpp/src/IceBox/Admin.cpp b/cpp/src/IceBox/Admin.cpp index bf7fa5d5a05..c7c76bac161 100644 --- a/cpp/src/IceBox/Admin.cpp +++ b/cpp/src/IceBox/Admin.cpp @@ -116,7 +116,7 @@ Client::run(int argc, char* argv[]) return EXIT_FAILURE; } - managerProxy = "\"" + identityToString(managerIdentity) + "\" :" + managerEndpoints; + managerProxy = "\"" + communicator()->identityToString(managerIdentity) + "\" :" + managerEndpoints; } else { @@ -127,7 +127,7 @@ Client::run(int argc, char* argv[]) return EXIT_FAILURE; } - managerProxy = "\"" + identityToString(managerIdentity) + "\" @" + managerAdapterId; + managerProxy = "\"" + communicator()->identityToString(managerIdentity) + "\" @" + managerAdapterId; } base = communicator()->stringToProxy(managerProxy); diff --git a/cpp/src/IceGrid/AdminI.cpp b/cpp/src/IceGrid/AdminI.cpp index 60af9f7b2df..21e190250e5 100644 --- a/cpp/src/IceGrid/AdminI.cpp +++ b/cpp/src/IceGrid/AdminI.cpp @@ -688,7 +688,7 @@ AdminI::updateObject(const Ice::ObjectPrx& proxy, const ::Ice::Current&) if(id.category == _database->getInstanceName()) { DeploymentException ex; - ex.reason = "updating object `" + identityToString(id) + "' is not allowed:\n"; + ex.reason = "updating object `" + _database->getCommunicator()->identityToString(id) + "' is not allowed:\n"; ex.reason += "objects with identity category `" + id.category + "' are managed by IceGrid"; throw ex; } @@ -709,7 +709,7 @@ AdminI::addObjectWithType(const Ice::ObjectPrx& proxy, const string& type, const if(id.category == _database->getInstanceName()) { DeploymentException ex; - ex.reason = "adding object `" + identityToString(id) + "' is not allowed:\n"; + ex.reason = "adding object `" + _database->getCommunicator()->identityToString(id) + "' is not allowed:\n"; ex.reason += "objects with identity category `" + id.category + "' are managed by IceGrid"; throw ex; } @@ -727,7 +727,7 @@ AdminI::removeObject(const Ice::Identity& id, const Ice::Current&) if(id.category == _database->getInstanceName()) { DeploymentException ex; - ex.reason = "removing object `" + identityToString(id) + "' is not allowed:\n"; + ex.reason = "removing object `" + _database->getCommunicator()->identityToString(id) + "' is not allowed:\n"; ex.reason += "objects with identity category `" + id.category + "' are managed by IceGrid"; throw ex; } diff --git a/cpp/src/IceGrid/AllocatableObjectCache.cpp b/cpp/src/IceGrid/AllocatableObjectCache.cpp index ae3294bb51c..3a9799e1eac 100644 --- a/cpp/src/IceGrid/AllocatableObjectCache.cpp +++ b/cpp/src/IceGrid/AllocatableObjectCache.cpp @@ -134,7 +134,7 @@ AllocatableObjectCache::add(const ObjectInfo& info, const AllocatablePtr& parent if(getImpl(id)) { Ice::Error out(_communicator->getLogger()); - out << "can't add duplicate allocatable object `" << identityToString(id) << "'"; + out << "can't add duplicate allocatable object `" << _communicator->identityToString(id) << "'"; return; } @@ -151,7 +151,7 @@ AllocatableObjectCache::add(const ObjectInfo& info, const AllocatablePtr& parent if(_traceLevels && _traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << "added allocatable object `" << identityToString(id) << "'"; + out << "added allocatable object `" << _communicator->identityToString(id) << "'"; } } @@ -177,7 +177,7 @@ AllocatableObjectCache::remove(const Ice::Identity& id) if(!entry) { Ice::Error out(_communicator->getLogger()); - out << "can't remove unknown object `" << identityToString(id) << "'"; + out << "can't remove unknown object `" << _communicator->identityToString(id) << "'"; } removeImpl(id); @@ -191,7 +191,7 @@ AllocatableObjectCache::remove(const Ice::Identity& id) if(_traceLevels && _traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << "removed allocatable object `" << identityToString(id) << "'"; + out << "removed allocatable object `" << _communicator->identityToString(id) << "'"; } } diff --git a/cpp/src/IceGrid/Database.cpp b/cpp/src/IceGrid/Database.cpp index 694d59c073d..5c9167b784d 100644 --- a/cpp/src/IceGrid/Database.cpp +++ b/cpp/src/IceGrid/Database.cpp @@ -1483,7 +1483,7 @@ Database::addObject(const ObjectInfo& info) if(_traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << "added object `" << identityToString(id) << "' (serial = `" << dbSerial << "')"; + out << "added object `" << _communicator->identityToString(id) << "' (serial = `" << dbSerial << "')"; } } _objectObserverTopic->waitForSyncedSubscribers(serial); @@ -1539,7 +1539,7 @@ Database::addOrUpdateObject(const ObjectInfo& info, Ice::Long dbSerial) if(_traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << (!update ? "added" : "updated") << " object `" << identityToString(id) << "' (serial = `" << dbSerial << "')"; + out << (!update ? "added" : "updated") << " object `" << _communicator->identityToString(id) << "' (serial = `" << dbSerial << "')"; } } _objectObserverTopic->waitForSyncedSubscribers(serial); @@ -1556,7 +1556,7 @@ Database::removeObject(const Ice::Identity& id, Ice::Long dbSerial) if(_objectCache.has(id)) { DeploymentException ex; - ex.reason = "removing object `" + identityToString(id) + "' is not allowed:\n"; + ex.reason = "removing object `" + _communicator->identityToString(id) + "' is not allowed:\n"; ex.reason += "the object was added with the application descriptor `"; ex.reason += _objectCache.get(id)->getApplication(); ex.reason += "'"; @@ -1590,7 +1590,7 @@ Database::removeObject(const Ice::Identity& id, Ice::Long dbSerial) if(_traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << "removed object `" << identityToString(id) << "' (serial = `" << dbSerial << "')"; + out << "removed object `" << _communicator->identityToString(id) << "' (serial = `" << dbSerial << "')"; } } _objectObserverTopic->waitForSyncedSubscribers(serial); @@ -1609,7 +1609,7 @@ Database::updateObject(const Ice::ObjectPrx& proxy) if(_objectCache.has(id)) { DeploymentException ex; - ex.reason = "updating object `" + identityToString(id) + "' is not allowed:\n"; + ex.reason = "updating object `" + _communicator->identityToString(id) + "' is not allowed:\n"; ex.reason += "the object was added with the application descriptor `"; ex.reason += _objectCache.get(id)->getApplication(); ex.reason += "'"; @@ -1644,7 +1644,7 @@ Database::updateObject(const Ice::ObjectPrx& proxy) if(_traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << "updated object `" << identityToString(id) << "' (serial = `" << dbSerial << "')"; + out << "updated object `" << _communicator->identityToString(id) << "' (serial = `" << dbSerial << "')"; } } _objectObserverTopic->waitForSyncedSubscribers(serial); @@ -1833,7 +1833,7 @@ Database::getAllObjectInfos(const string& expression) ObjectsMapROCursor cursor(_objects, txn); while(cursor.get(id, info, MDB_NEXT)) { - if(expression.empty() || IceUtilInternal::match(identityToString(id), expression, true)) + if(expression.empty() || IceUtilInternal::match(_communicator->identityToString(id), expression, true)) { infos.push_back(info); } @@ -2089,7 +2089,7 @@ Database::checkObjectForAddition(const Ice::Identity& objectId, if(found) { DeploymentException ex; - ex.reason = "object `" + identityToString(objectId) + "' is already registered"; + ex.reason = "object `" + _communicator->identityToString(objectId) + "' is already registered"; throw ex; } } @@ -2761,7 +2761,7 @@ Database::addObject(const IceDB::ReadWriteTxn& txn, const ObjectInfo& info, bool catch(const IceDB::KeyTooLongException& ex) { throw DeploymentException("object identity `" + - identityToString(info.proxy->ice_getIdentity()) + _communicator->identityToString(info.proxy->ice_getIdentity()) + "' is too long: " + ex.what()); } try diff --git a/cpp/src/IceGrid/DescriptorHelper.cpp b/cpp/src/IceGrid/DescriptorHelper.cpp index 7e1a531dbb5..3eef14ff351 100644 --- a/cpp/src/IceGrid/DescriptorHelper.cpp +++ b/cpp/src/IceGrid/DescriptorHelper.cpp @@ -650,11 +650,11 @@ Ice::Identity Resolver::operator()(const Ice::Identity& value, const string& name) const { assert(_communicator); - string str = asId(identityToString(value), name, false); + string str = asId(_communicator->identityToString(value), name, false); Ice::Identity id = Ice::stringToIdentity(str); if(id.name.empty()) { - exception("invalid object identity `" + identityToString(value) + "': name empty"); + exception("invalid object identity `" + _communicator->identityToString(value) + "': name empty"); } return id; } @@ -1387,7 +1387,7 @@ CommunicatorHelper::printObjectAdapter(const Ice::CommunicatorPtr& communicator, { out << nl << "well-known object"; out << sb; - out << nl << "identity = `" << identityToString(p->id) << "' "; + out << nl << "identity = `" << communicator->identityToString(p->id) << "' "; if(!p->type.empty()) { out << nl << "type = `" << p->type << "'"; @@ -1402,7 +1402,7 @@ CommunicatorHelper::printObjectAdapter(const Ice::CommunicatorPtr& communicator, { out << nl << "allocatable"; out << sb; - out << nl << "identity = `" << identityToString(p->id) << "' "; + out << nl << "identity = `" << communicator->identityToString(p->id) << "' "; if(!p->type.empty()) { out << nl << "type = `" << p->type << "'"; @@ -2825,7 +2825,7 @@ ApplicationHelper::ApplicationHelper(const Ice::CommunicatorPtr& communicator, { if(objectIds.count(*o) > 1) { - resolve.exception("duplicate object `" + identityToString(*o) + "'"); + resolve.exception("duplicate object `" + _communicator->identityToString(*o) + "'"); } } } diff --git a/cpp/src/IceGrid/ObjectCache.cpp b/cpp/src/IceGrid/ObjectCache.cpp index 9d7138e7050..cc76cc2d9b7 100644 --- a/cpp/src/IceGrid/ObjectCache.cpp +++ b/cpp/src/IceGrid/ObjectCache.cpp @@ -82,7 +82,7 @@ ObjectCache::add(const ObjectInfo& info, const string& application) if(getImpl(id)) { Ice::Error out(_communicator->getLogger()); - out << "can't add duplicate object `" << identityToString(id) << "'"; + out << "can't add duplicate object `" << _communicator->identityToString(id) << "'"; return; } @@ -99,7 +99,7 @@ ObjectCache::add(const ObjectInfo& info, const string& application) if(_traceLevels && _traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << "added object `" << identityToString(id) << "'"; + out << "added object `" << _communicator->identityToString(id) << "'"; } } @@ -123,7 +123,7 @@ ObjectCache::remove(const Ice::Identity& id) if(!entry) { Ice::Error out(_communicator->getLogger()); - out << "can't remove unknown object `" << identityToString(id) << "'"; + out << "can't remove unknown object `" << _communicator->identityToString(id) << "'"; return; } removeImpl(id); @@ -138,7 +138,7 @@ ObjectCache::remove(const Ice::Identity& id) if(_traceLevels && _traceLevels->object > 0) { Ice::Trace out(_traceLevels->logger, _traceLevels->objectCat); - out << "removed object `" << identityToString(id) << "'"; + out << "removed object `" << _communicator->identityToString(id) << "'"; } } @@ -167,7 +167,7 @@ ObjectCache::getAll(const string& expression) ObjectInfoSeq infos; for(map<Ice::Identity, ObjectEntryPtr>::const_iterator p = _entries.begin(); p != _entries.end(); ++p) { - if(expression.empty() || IceUtilInternal::match(identityToString(p->first), expression, true)) + if(expression.empty() || IceUtilInternal::match(_communicator->identityToString(p->first), expression, true)) { infos.push_back(p->second->getObjectInfo()); } diff --git a/cpp/src/IceGrid/Parser.cpp b/cpp/src/IceGrid/Parser.cpp index 30f80de48c7..7a88d5247a6 100644 --- a/cpp/src/IceGrid/Parser.cpp +++ b/cpp/src/IceGrid/Parser.cpp @@ -2100,7 +2100,7 @@ Parser::removeObject(const list<string>& args) try { - _admin->removeObject(stringToIdentity((*(args.begin())))); + _admin->removeObject(Ice::stringToIdentity((*(args.begin())))); } catch(const Ice::Exception& ex) { @@ -2148,7 +2148,7 @@ Parser::describeObject(const list<string>& args) string arg = *(args.begin()); if(arg.find('*') == string::npos) { - ObjectInfo info = _admin->getObjectInfo(stringToIdentity(arg)); + ObjectInfo info = _admin->getObjectInfo(Ice::stringToIdentity(arg)); cout << "proxy = `" << _communicator->proxyToString(info.proxy) << "'" << endl; cout << "type = `" << info.type << "'" << endl; return; @@ -2198,7 +2198,7 @@ Parser::listObject(const list<string>& args) for(ObjectInfoSeq::const_iterator p = objects.begin(); p != objects.end(); ++p) { - cout << identityToString(p->proxy->ice_getIdentity()) << endl; + cout << _communicator->identityToString(p->proxy->ice_getIdentity()) << endl; } } catch(const Ice::Exception& ex) @@ -2957,11 +2957,11 @@ Parser::exception(const Ice::Exception& ex) } catch(const ObjectNotRegisteredException& ex) { - error("couldn't find object `" + identityToString(ex.id) + "'"); + error("couldn't find object `" + _communicator->identityToString(ex.id) + "'"); } catch(const ObjectExistsException& ex) { - error("object `" + identityToString(ex.id) + "' already exists"); + error("object `" + _communicator->identityToString(ex.id) + "' already exists"); } catch(const DeploymentException& ex) { diff --git a/cpp/src/IceGrid/ReplicaSessionManager.cpp b/cpp/src/IceGrid/ReplicaSessionManager.cpp index 77c324aea27..9895963a1c5 100644 --- a/cpp/src/IceGrid/ReplicaSessionManager.cpp +++ b/cpp/src/IceGrid/ReplicaSessionManager.cpp @@ -177,7 +177,7 @@ public: { ostringstream os; os << ex << ":\n"; - os << "id: " << identityToString(info.proxy->ice_getIdentity()); + os << "id: " << _database->getCommunicator()->identityToString(info.proxy->ice_getIdentity()); failure = os.str(); } receivedUpdate(ObjectObserverTopicName, serial, failure); @@ -196,7 +196,7 @@ public: { ostringstream os; os << ex << ":\n"; - os << "id: " << identityToString(info.proxy->ice_getIdentity()); + os << "id: " << _database->getCommunicator()->identityToString(info.proxy->ice_getIdentity()); failure = os.str(); } catch(const DeploymentException& ex) diff --git a/cpp/src/IceGrid/Util.cpp b/cpp/src/IceGrid/Util.cpp index 8c0d04cd911..c56e30717c0 100644 --- a/cpp/src/IceGrid/Util.cpp +++ b/cpp/src/IceGrid/Util.cpp @@ -207,7 +207,7 @@ IceGrid::toObjectInfo(const Ice::CommunicatorPtr& communicator, const ObjectDesc ObjectInfo info; info.type = obj.type; ostringstream proxyStr; - proxyStr << "\"" << identityToString(obj.id) << "\""; + proxyStr << "\"" << communicator->identityToString(obj.id) << "\""; if(!obj.proxyOptions.empty()) { proxyStr << ' ' << obj.proxyOptions; @@ -220,7 +220,7 @@ IceGrid::toObjectInfo(const Ice::CommunicatorPtr& communicator, const ObjectDesc catch(const Ice::ProxyParseException&) { ostringstream fallbackProxyStr; - fallbackProxyStr << "\"" << identityToString(obj.id) << "\"" << " @ \"" << adapterId << "\""; + fallbackProxyStr << "\"" << communicator->identityToString(obj.id) << "\"" << " @ \"" << adapterId << "\""; info.proxy = communicator->stringToProxy(fallbackProxyStr.str()); } return info; diff --git a/cpp/src/IcePatch2Lib/Util.cpp b/cpp/src/IcePatch2Lib/Util.cpp index 88798feaba5..63fc5087eeb 100644 --- a/cpp/src/IcePatch2Lib/Util.cpp +++ b/cpp/src/IcePatch2Lib/Util.cpp @@ -81,7 +81,7 @@ bool IcePatch2Internal::writeFileInfo(FILE* fp, const LargeFileInfo& info) { int rc = fprintf(fp, "%s\t%s\t" ICE_INT64_FORMAT "\t%d\n", - IceUtilInternal::escapeString(info.path, "").c_str(), + escapeString(info.path, "", IceUtilInternal::Compat).c_str(), bytesToString(info.checksum).c_str(), info.size, static_cast<int>(info.executable)); diff --git a/cpp/src/IceStorm/IceStormDB.cpp b/cpp/src/IceStorm/IceStormDB.cpp index 9a3c81022e3..b3a927c719e 100644 --- a/cpp/src/IceStorm/IceStormDB.cpp +++ b/cpp/src/IceStorm/IceStormDB.cpp @@ -231,8 +231,8 @@ Client::run(int argc, char* argv[]) { if(debug) { - cout << " KEY = TOPIC(" << identityToString(q->first.topic) - << ") ID(" << identityToString(q->first.id) << ")" <<endl; + cout << " KEY = TOPIC(" << communicator()->identityToString(q->first.topic) + << ") ID(" << communicator()->identityToString(q->first.id) << ")" <<endl; } subscriberMap.put(txn, q->first, q->second); } @@ -286,8 +286,8 @@ Client::run(int argc, char* argv[]) { if(debug) { - cout << " KEY = TOPIC(" << identityToString(key.topic) - << ") ID(" << identityToString(key.id) << ")" <<endl; + cout << " KEY = TOPIC(" << communicator()->identityToString(key.topic) + << ") ID(" << communicator()->identityToString(key.id) << ")" <<endl; } data.subscribers.insert(std::make_pair(key, record)); } diff --git a/cpp/src/IceStorm/InstrumentationI.cpp b/cpp/src/IceStorm/InstrumentationI.cpp index ad3495429c9..017a5196fd3 100644 --- a/cpp/src/IceStorm/InstrumentationI.cpp +++ b/cpp/src/IceStorm/InstrumentationI.cpp @@ -174,7 +174,7 @@ public: } catch(const ::Ice::FixedProxyException&) { - _id = identityToString(_proxy->ice_getIdentity()); + _id = _proxy->ice_getCommunicator()->identityToString(_proxy->ice_getIdentity()); } } return _id; @@ -206,7 +206,7 @@ public: string getIdentity() const { - return identityToString(_proxy->ice_getIdentity()); + return _proxy->ice_getCommunicator()->identityToString(_proxy->ice_getIdentity()); } private: diff --git a/cpp/src/IceStorm/Parser.cpp b/cpp/src/IceStorm/Parser.cpp index 6f802b11569..ca0c0c5ae7b 100644 --- a/cpp/src/IceStorm/Parser.cpp +++ b/cpp/src/IceStorm/Parser.cpp @@ -364,7 +364,7 @@ Parser::subscribers(const list<string>& args) IdentitySeq subscribers = topic->getSubscribers(); for(IdentitySeq::const_iterator j = subscribers.begin(); j != subscribers.end(); ++j) { - cout << "\t" << identityToString(*j) << endl; + cout << "\t" << _communicator->identityToString(*j) << endl; } } } @@ -379,7 +379,7 @@ Parser::current(const list<string>& args) { if(args.empty()) { - cout << identityToString(_defaultManager->ice_getIdentity()) << endl; + cout << _communicator->identityToString(_defaultManager->ice_getIdentity()) << endl; return; } else if(args.size() > 1) @@ -618,7 +618,7 @@ Parser::parse(const std::string& commands, bool debug) TopicManagerPrx Parser::findManagerById(const string& full, string& arg) const { - Ice::Identity id = stringToIdentity(full); + Ice::Identity id = Ice::stringToIdentity(full); arg = id.name; if(id.category.empty()) { diff --git a/cpp/src/IceStorm/Subscriber.cpp b/cpp/src/IceStorm/Subscriber.cpp index 529461f0f03..5c1740ad612 100644 --- a/cpp/src/IceStorm/Subscriber.cpp +++ b/cpp/src/IceStorm/Subscriber.cpp @@ -546,7 +546,7 @@ Subscriber::create( Ice::Identity perId; perId.category = instance->instanceName(); perId.name = "topic." + rec.topicName + ".publish." + - identityToString(rec.obj->ice_getIdentity()); + instance->communicator()->identityToString(rec.obj->ice_getIdentity()); Ice::ObjectPrx proxy = instance->publishAdapter()->add(per, perId); TraceLevelsPtr traceLevels = instance->traceLevels(); SubscriberPtr subscriber; @@ -829,7 +829,7 @@ Subscriber::error(bool dec, const Ice::Exception& e) if(_currentRetry == 0) { Ice::Warning warn(traceLevels->logger); - warn << traceLevels->subscriberCat << ":" << identityToString(_rec.id); + warn << traceLevels->subscriberCat << ":" << _instance->communicator()->identityToString(_rec.id); if(traceLevels->subscriber > 1) { warn << " endpoints: " << IceStormInternal::describeEndpoints(_rec.obj); @@ -842,7 +842,7 @@ Subscriber::error(bool dec, const Ice::Exception& e) if(traceLevels->subscriber > 0) { Ice::Trace out(traceLevels->logger, traceLevels->subscriberCat); - out << identityToString(_rec.id); + out << _instance->communicator()->identityToString(_rec.id); if(traceLevels->subscriber > 1) { out << " endpoints: " << IceStormInternal::describeEndpoints(_rec.obj); @@ -870,7 +870,7 @@ Subscriber::error(bool dec, const Ice::Exception& e) if(traceLevels->subscriber > 0) { Ice::Trace out(traceLevels->logger, traceLevels->subscriberCat); - out << identityToString(_rec.id); + out << _instance->communicator()->identityToString(_rec.id); if(traceLevels->subscriber > 1) { out << " endpoints: " << IceStormInternal::describeEndpoints(_rec.obj); diff --git a/cpp/src/IceStorm/TopicI.cpp b/cpp/src/IceStorm/TopicI.cpp index 3a9c3d65a79..acea59e5c15 100644 --- a/cpp/src/IceStorm/TopicI.cpp +++ b/cpp/src/IceStorm/TopicI.cpp @@ -399,7 +399,7 @@ TopicImpl::TopicImpl( if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << " recreate " << identityToString(id); + out << _name << " recreate " << _instance->communicator()->identityToString(id); if(traceLevels->topic > 1) { out << " endpoints: " << IceStormInternal::describeEndpoints(p->obj); @@ -418,7 +418,7 @@ TopicImpl::TopicImpl( catch(const Ice::Exception& ex) { Ice::Warning out(traceLevels->logger); - out << _name << " recreate " << identityToString(id); + out << _name << " recreate " << _instance->communicator()->identityToString(id); if(traceLevels->topic > 1) { out << " endpoints: " << IceStormInternal::describeEndpoints(p->obj); @@ -491,7 +491,7 @@ trace(Ice::Trace& out, const PersistentInstancePtr& instance, const vector<Subsc { out << ","; } - out << identityToString((*p)->id()); + out << instance->communicator()->identityToString((*p)->id()); } out << "]"; } @@ -516,7 +516,7 @@ TopicImpl::subscribeAndGetPublisher(const QoS& qos, const Ice::ObjectPrx& obj) if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": subscribeAndGetPublisher: " << identityToString(id); + out << _name << ": subscribeAndGetPublisher: " << _instance->communicator()->identityToString(id); if(traceLevels->topic > 1) { @@ -600,7 +600,7 @@ TopicImpl::unsubscribe(const Ice::ObjectPrx& subscriber) if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": unsubscribe: " << identityToString(id); + out << _name << ": unsubscribe: " << _instance->communicator()->identityToString(id); if(traceLevels->topic > 1) { @@ -637,7 +637,7 @@ TopicImpl::link(const TopicPrx& topic, Ice::Int cost) if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": link " << identityToString(topic->ice_getIdentity()) + out << _name << ": link " << _instance->communicator()->identityToString(topic->ice_getIdentity()) << " cost " << cost; } @@ -722,7 +722,7 @@ TopicImpl::unlink(const TopicPrx& topic) if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << " unlink " << identityToString(id); + out << _name << " unlink " << _instance->communicator()->identityToString(id); } Ice::IdentitySeq ids; @@ -746,7 +746,7 @@ TopicImpl::reap(const Ice::IdentitySeq& ids) { out << ","; } - out << identityToString(*p); + out << _instance->communicator()->identityToString(*p); } } @@ -1045,7 +1045,7 @@ TopicImpl::observerAddSubscriber(const LogUpdate& llu, const SubscriberRecord& r if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": add replica observer: " << identityToString(record.id); + out << _name << ": add replica observer: " << _instance->communicator()->identityToString(record.id); if(traceLevels->topic > 1) { @@ -1072,7 +1072,7 @@ TopicImpl::observerAddSubscriber(const LogUpdate& llu, const SubscriberRecord& r if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << identityToString(record.id) << ": already subscribed"; + out << _instance->communicator()->identityToString(record.id) << ": already subscribed"; } return; } @@ -1116,7 +1116,7 @@ TopicImpl::observerRemoveSubscriber(const LogUpdate& llu, const Ice::IdentitySeq { out << ","; } - out << identityToString(*id); + out << _instance->communicator()->identityToString(*id); } out << " llu: " << llu.generation << "/" << llu.iteration; } diff --git a/cpp/src/IceStorm/TopicManagerI.cpp b/cpp/src/IceStorm/TopicManagerI.cpp index 15696d70abc..5c4ad1c6cbc 100644 --- a/cpp/src/IceStorm/TopicManagerI.cpp +++ b/cpp/src/IceStorm/TopicManagerI.cpp @@ -421,14 +421,14 @@ TopicManagerImpl::observerInit(const LogUpdate& llu, const TopicContentSeq& cont out << "init"; for(TopicContentSeq::const_iterator p = content.begin(); p != content.end(); ++p) { - out << " topic: " << identityToString(p->id) << " subscribers: "; + out << " topic: " << _instance->communicator()->identityToString(p->id) << " subscribers: "; for(SubscriberRecordSeq::const_iterator q = p->records.begin(); q != p->records.end(); ++q) { if(q != p->records.begin()) { out << ","; } - out << identityToString(q->id); + out << _instance->communicator()->identityToString(q->id); if(traceLevels->topicMgr > 1) { out << " endpoints: " << IceStormInternal::describeEndpoints(q->obj); @@ -803,7 +803,7 @@ TopicManagerImpl::installTopic(const string& name, const Ice::Identity& id, bool if(create) { out << "creating new topic \"" << name << "\". id: " - << identityToString(id) + << _instance->communicator()->identityToString(id) << " subscribers: "; for(SubscriberRecordSeq::const_iterator q = subscribers.begin(); q != subscribers.end(); ++q) { @@ -813,7 +813,7 @@ TopicManagerImpl::installTopic(const string& name, const Ice::Identity& id, bool } if(traceLevels->topicMgr > 1) { - out << identityToString(q->id) + out << _instance->communicator()->identityToString(q->id) << " endpoints: " << IceStormInternal::describeEndpoints(q->obj); } } @@ -821,7 +821,7 @@ TopicManagerImpl::installTopic(const string& name, const Ice::Identity& id, bool else { out << "loading topic \"" << name << "\" from database. id: " - << identityToString(id) + << _instance->communicator()->identityToString(id) << " subscribers: "; for(SubscriberRecordSeq::const_iterator q = subscribers.begin(); q != subscribers.end(); ++q) { @@ -831,7 +831,7 @@ TopicManagerImpl::installTopic(const string& name, const Ice::Identity& id, bool } if(traceLevels->topicMgr > 1) { - out << identityToString(q->id) + out << _instance->communicator()->identityToString(q->id) << " endpoints: " << IceStormInternal::describeEndpoints(q->obj); } } diff --git a/cpp/src/IceStorm/TransientTopicI.cpp b/cpp/src/IceStorm/TransientTopicI.cpp index f11688d1a10..062db7014fb 100644 --- a/cpp/src/IceStorm/TransientTopicI.cpp +++ b/cpp/src/IceStorm/TransientTopicI.cpp @@ -178,7 +178,7 @@ TransientTopicImpl::subscribe(const QoS& origQoS, const Ice::ObjectPrx& obj, con if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": subscribe: " << identityToString(id); + out << _name << ": subscribe: " << _instance->communicator()->identityToString(id); if(traceLevels->topic > 1) { @@ -280,7 +280,7 @@ TransientTopicImpl::subscribeAndGetPublisher(const QoS& qos, const Ice::ObjectPr if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": subscribeAndGetPublisher: " << identityToString(id); + out << _name << ": subscribeAndGetPublisher: " << _instance->communicator()->identityToString(id); if(traceLevels->topic > 1) { @@ -338,7 +338,7 @@ TransientTopicImpl::unsubscribe(const Ice::ObjectPrx& subscriber, const Ice::Cur if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": unsubscribe: " << identityToString(id); + out << _name << ": unsubscribe: " << _instance->communicator()->identityToString(id); if(traceLevels->topic > 1) { out << " endpoints: " << IceStormInternal::describeEndpoints(subscriber); @@ -374,7 +374,7 @@ TransientTopicImpl::link(const TopicPrx& topic, Ice::Int cost, const Ice::Curren if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << ": link " << identityToString(topic->ice_getIdentity()) + out << _name << ": link " << _instance->communicator()->identityToString(topic->ice_getIdentity()) << " cost " << cost; } @@ -434,7 +434,7 @@ TransientTopicImpl::unlink(const TopicPrx& topic, const Ice::Current&) if(traceLevels->topic > 0) { Ice::Trace out(traceLevels->logger, traceLevels->topicCat); - out << _name << " unlink " << identityToString(id); + out << _name << " unlink " << _instance->communicator()->identityToString(id); } // Remove the subscriber from the subscribers list. Note diff --git a/cpp/src/IceStorm/TransientTopicManagerI.cpp b/cpp/src/IceStorm/TransientTopicManagerI.cpp index 5bd8449fd66..8c45a471f19 100644 --- a/cpp/src/IceStorm/TransientTopicManagerI.cpp +++ b/cpp/src/IceStorm/TransientTopicManagerI.cpp @@ -55,7 +55,7 @@ TransientTopicManagerImpl::create(const string& name, const Ice::Current&) { Ice::Trace out(traceLevels->logger, traceLevels->topicMgrCat); out << "creating new topic \"" << name << "\". id: " - << identityToString(id); + << _instance->communicator()->identityToString(id); } // diff --git a/cpp/src/IceUtil/StringUtil.cpp b/cpp/src/IceUtil/StringUtil.cpp index ec33cf8c587..0e7d9162d6c 100644 --- a/cpp/src/IceUtil/StringUtil.cpp +++ b/cpp/src/IceUtil/StringUtil.cpp @@ -35,96 +35,89 @@ toOctalString(unsigned int n) return string(s, charPos, (32 - charPos)); } +char +toHexDigit(Byte b) +{ + assert(b < 16); + if(b < 10) + { + return '0' + b; + } + else + { + return 'a' - 10 + b; + } +} + + +unsigned int +addContinuationByte(string::iterator& p, string::iterator end, unsigned int codePoint) +{ + if(p == end) + { + throw IllegalArgumentException(__FILE__, __LINE__, "UTF-8 sequence too short"); + } + + Byte b = static_cast<Byte>(*p++); + + if((b >> 6) != 2) + { + throw IllegalArgumentException(__FILE__, __LINE__, "Invalid UTF-8 sequence"); + } + return (codePoint << 6) + (b & 0x3F); +} + // -// Write the byte b as an escape sequence if it isn't a printable ASCII -// character and append the escape sequence to s. Additional characters -// that should be escaped can be passed in special. If b is any of these -// characters, b is preceded by a backslash in s. +// Appends a 2 to 4 bytes UTF-8 sequence as a universal character name // void -encodeChar(string::value_type b, string& s, const string& special) +appendUniversalName(char c, string::iterator& p, string::iterator end, string& result) { - switch(b) + unsigned int codePoint; + + Byte b = static_cast<Byte>(c); + if((b >> 5) == 0x06) { - case '\\': - { - s.append("\\\\"); - break; - } - - case '\'': - { - s.append("\\'"); - break; - } - - case '"': - { - s.append("\\\""); - break; - } - - case '\b': - { - s.append("\\b"); - break; - } - - case '\f': - { - s.append("\\f"); - break; - } - - case '\n': - { - s.append("\\n"); - break; - } - - case '\r': - { - s.append("\\r"); - break; - } - - case '\t': + // 2 bytes + codePoint = (b & 0x1F); + codePoint = addContinuationByte(p, end, codePoint); + } + else if((b >> 4) == 0x0E) + { + // 3 bytes + codePoint = (b & 0x0F); + codePoint = addContinuationByte(p, end, codePoint); + codePoint = addContinuationByte(p, end, codePoint); + } + else if((b >> 3) == 0x1E) + { + // 4 bytes + codePoint = (b & 0x07); + codePoint = addContinuationByte(p, end, codePoint); + codePoint = addContinuationByte(p, end, codePoint); + codePoint = addContinuationByte(p, end, codePoint); + } + else + { + ostringstream ostr; + ostr << "Invalid first byte 0x" << hex << static_cast<unsigned short>(b) << " in UTF-8 sequence" << endl; + throw IllegalArgumentException(__FILE__, __LINE__, ostr.str()); + } + + if(codePoint > 0xFFFF) + { + result.append("\\U"); + for(int j = 7; j >= 0; j--) { - s.append("\\t"); - break; + result.push_back(toHexDigit(static_cast<Byte>((codePoint >> (j * 4)) & 0x0F))); } - - default: + } + else + { + result.append("\\u"); + for(int j = 3; j >= 0; j--) { - unsigned char i = static_cast<unsigned char>(b); - if(!(i >= 32 && i <= 126)) - { - s.push_back('\\'); - string octal = toOctalString(i); - // - // Add leading zeroes so that we avoid problems during - // decoding. For example, consider the escaped string - // \0013 (i.e., a character with value 1 followed by the - // character '3'). If the leading zeroes were omitted, the - // result would be incorrectly interpreted as a single - // character with value 11. - // - for(string::size_type j = octal.size(); j < 3; j++) - { - s.push_back('0'); - } - s.append(octal); - } - else if(special.find(b) != string::npos) - { - s.push_back('\\'); - s.push_back(b); - } - else - { - s.push_back(b); - } - break; + result.push_back(toHexDigit(static_cast<Byte>((codePoint >> (j * 4)) & 0x0F))); } } } @@ -132,27 +125,153 @@ encodeChar(string::value_type b, string& s, const string& special) } // -// Add escape sequences (such as "\n", or "\007") to make a string -// readable in ASCII. Any characters that appear in special are -// prefixed with a backslash in the returned string. +// Add escape sequences. Any characters that appear in special are prefixed with a backslash in the returned string. // string -IceUtilInternal::escapeString(const string& s, const string& special) +IceUtilInternal::escapeString(const string& s, const string& special, ToStringMode toStringMode) { for(string::size_type i = 0; i < special.size(); ++i) { if(static_cast<unsigned char>(special[i]) < 32 || static_cast<unsigned char>(special[i]) > 126) { - throw IllegalArgumentException(__FILE__, __LINE__, "special characters must be in ASCII range 32-126"); + throw IllegalArgumentException(__FILE__, __LINE__, "Special characters must be in ASCII range 32-126"); } } - + + // + // First convert to UTF-8 + // + string u8s = nativeToUTF8(s, getProcessStringConverter()); + + string::iterator p = u8s.begin(); + string result; - for(string::size_type i = 0; i < s.size(); ++i) + + while(p != u8s.end()) { - encodeChar(s[i], result, special); + char c = *p++; + + switch(c) + { + case '\\': + { + result.append("\\\\"); + break; + } + + case '\'': + { + result.append("\\'"); + break; + } + + case '"': + { + result.append("\\\""); + break; + } + + case '\b': + { + result.append("\\b"); + break; + } + + case '\f': + { + result.append("\\f"); + break; + } + + case '\n': + { + result.append("\\n"); + break; + } + + case '\r': + { + result.append("\\r"); + break; + } + + case '\t': + { + result.append("\\t"); + break; + } + + default: + { + if(special.find(c) != string::npos) + { + result.push_back('\\'); + result.push_back(c); + } + else + { + unsigned char i = static_cast<unsigned char>(c); + + if(i < 32 || i > 126) + { + if(toStringMode == ICE_ENUM(ToStringMode, Compat)) + { + // append octal string + + result.push_back('\\'); + string octal = toOctalString(i); + // + // Add leading zeroes so that we avoid problems during + // decoding. For example, consider the escaped string + // \0013 (i.e., a character with value 1 followed by the + // character '3'). If the leading zeroes were omitted, the + // result would be incorrectly interpreted as a single + // character with value 11. + // + for(string::size_type j = octal.size(); j < 3; j++) + { + result.push_back('0'); + } + result.append(octal); + } + else if(i < 32 || i == 127) + { + // append \u00nn + result.append("\\u00"); + result.push_back(toHexDigit(i >> 4)); + result.push_back(toHexDigit(i & 0x0F)); + } + else if(toStringMode == ICE_ENUM(ToStringMode, ASCII)) + { + // append \unnnn or \Unnnnnnnn after reading more UTF-8 bytes + appendUniversalName(c, p, u8s.end(), result); + } + else + { + // keep as is + result.push_back(c); + } + } + else + { + // printable ASCII character + result.push_back(c); + } + } + break; + } + } } - + + if(toStringMode == ICE_ENUM(ToStringMode, Unicode)) + { + // + // Convert back to Native + // + result = UTF8ToNative(result, getProcessStringConverter()); + } + // else it's a pure ASCII string + return result; } @@ -163,7 +282,7 @@ char checkChar(const string& s, string::size_type pos) { unsigned char c = static_cast<unsigned char>(s[pos]); - if(!(c >= 32 && c <= 126)) + if(c < 32 || c == 127) { ostringstream ostr; if(pos > 0) @@ -174,29 +293,74 @@ checkChar(const string& s, string::size_type pos) { ostr << "first character"; } - ostr << " is not a printable ASCII character (ordinal " << static_cast<int>(c) << ")"; + ostr << " has invalid ordinal value " << static_cast<int>(c); throw IllegalArgumentException(__FILE__, __LINE__, ostr.str()); } return c; } // -// Decode the character or escape sequence starting at start and return it. +// Append codePoint as a UTF-8 sequence +// +void +appendUTF8(unsigned int codePoint, bool inBMP, string& result) +{ + if(inBMP && codePoint >= 0xD800 && codePoint <= 0xDFFF) + { + throw IllegalArgumentException(__FILE__, __LINE__, + "A non-BMP character cannot be encoded with \\unnnn, use \\Unnnnnnnn instead"); + } + + if(codePoint <= 0x7F) + { + // ASCII + result.push_back(static_cast<char>(codePoint)); + } + else if(codePoint <= 0x7FF) + { + // 2 bytes + result.push_back(static_cast<char>((codePoint >> 6) | 0xC0)); + result.push_back(static_cast<char>((codePoint & 0x3F) | 0x80)); + } + else if(codePoint <= 0xFFFF) + { + // 3 bytes + result.push_back(static_cast<char>((codePoint >> 12) | 0xE0)); + result.push_back(static_cast<char>(((codePoint >> 6) & 0x3F) | 0x80)); + result.push_back(static_cast<char>((codePoint & 0x3F) | 0x80)); + } + else if(codePoint <= 0x10FFFF) + { + // 4 bytes + result.push_back(static_cast<char>((codePoint >> 18) | 0xF0)); + result.push_back(static_cast<char>(((codePoint >> 12) & 0x3F) | 0x80)); + result.push_back(static_cast<char>(((codePoint >> 6) & 0x3F) | 0x80)); + result.push_back(static_cast<char>((codePoint & 0x3F) | 0x80)); + } + else + { + throw IllegalArgumentException(__FILE__, __LINE__, "Invalid universal character name"); + } +} + +// +// Decode the character or escape sequence starting at start and appends it to result; // end marks the one-past-the-end position of the substring to be scanned. // nextStart is set to the index of the first character following the decoded // character or escape sequence. // -char -decodeChar(const string& s, string::size_type start, string::size_type end, string::size_type& nextStart) +bool +decodeChar(const string& s, string::size_type start, string::size_type end, string::size_type& nextStart, + string& result) { assert(start < end); assert(end <= s.size()); - char c; + bool pureASCII = true; if(s[start] != '\\') { - c = checkChar(s, start++); + result.push_back(checkChar(s, start++)); } else { @@ -204,43 +368,90 @@ decodeChar(const string& s, string::size_type start, string::size_type end, stri { throw IllegalArgumentException(__FILE__, __LINE__, "trailing backslash"); } - switch(s[++start]) + + char c = s[++start]; + + switch(c) { - case '\\': - case '\'': - case '"': + case '\\': + case '\'': + case '"': + { + ++start; + result.push_back(c); + break; + } + case 'b': { - c = s[start++]; + ++start; + result.push_back('\b'); break; } - case 'b': + case 'f': { ++start; - c = '\b'; + result.push_back('\f'); break; } - case 'f': + case 'n': { ++start; - c = '\f'; + result.push_back('\n'); break; } - case 'n': + case 'r': { ++start; - c = '\n'; + result.push_back('\r'); break; } - case 'r': + case 't': { ++start; - c = '\r'; + result.push_back('\t'); break; } - case 't': + case 'u': + case 'U': { + unsigned int codePoint = 0; + bool inBMP = (c == 'u'); + int size = inBMP ? 4 : 8; ++start; - c = '\t'; + while(size > 0 && start < end) + { + c = s[start++]; + int charVal = 0; + if(c >= '0' && c <= '9') + { + charVal = c - '0'; + } + else if(c >= 'a' && c <= 'f') + { + charVal = 10 + (c - 'a'); + } + else if(c >= 'A' && c <= 'F') + { + charVal = 10 + (c - 'A'); + } + else + { + break; // while + } + codePoint = codePoint * 16 + static_cast<unsigned int>(charVal); + --size; + } + if(size > 0) + { + throw IllegalArgumentException(__FILE__, __LINE__, + "Invalid universal character name: too few hex digits"); + } + + appendUTF8(codePoint, inBMP, result); + if(codePoint > 127) + { + pureASCII = false; + } break; } case '0': @@ -269,31 +480,26 @@ decodeChar(const string& s, string::size_type start, string::size_type end, stri ostr << "octal value \\" << oct << val << dec << " (" << val << ") is out of range"; throw IllegalArgumentException(__FILE__, __LINE__, ostr.str()); } - c = static_cast<char>(val); + result.push_back(static_cast<char>(val)); + if(val > 127) + { + pureASCII = false; + } break; } default: { - c = checkChar(s, start++); + if(static_cast<unsigned char>(c) > 127) + { + pureASCII = false; + } + result.push_back(checkChar(s, start++)); break; } } } nextStart = start; - return c; -} - -// -// Remove escape sequences from s and append the result to sb. -// Return true if successful, false otherwise. -// -void -decodeString(const string& s, string::size_type start, string::size_type end, string& sb) -{ - while(start < end) - { - sb.push_back(decodeChar(s, start, end, start)); - } + return pureASCII; } } @@ -306,11 +512,61 @@ IceUtilInternal::unescapeString(const string& s, string::size_type start, string { assert(start <= end && end <= s.size()); - string result; - result.reserve(end - start); - result.clear(); - decodeString(s, start, end, result); - return result; + // Optimization for strings without escapes + string::size_type p = s.find('\\', start); + if(p == string::npos || p >= end) + { + p = start; + while(p < end) + { + checkChar(s, p++); + } + return s.substr(start, end); + } + else + { + StringConverterPtr stringConverter = getProcessStringConverter(); + + const string* inputStringPtr = &s; + string u8s; + + if(stringConverter) + { + bool inputIsPureASCII = true; + string::size_type i = start; + while(i < end && inputIsPureASCII) + { + inputIsPureASCII = static_cast<unsigned char>(s[i++]) <= 127; + } + + if(!inputIsPureASCII) + { + u8s = nativeToUTF8(s.substr(start, end), stringConverter); + inputStringPtr = &u8s; + start = 0; + end = u8s.size(); + } + } + + bool resultIsPureASCII = true; + string result; + result.reserve(end - start); + while(start < end) + { + if(decodeChar(*inputStringPtr, start, end, start, result)) + { + resultIsPureASCII = false; + } + } + + if(stringConverter && !resultIsPureASCII) + { + // Need to convert from UTF-8 to Native + result = UTF8ToNative(result, stringConverter); + } + + return result; + } } bool @@ -328,7 +584,7 @@ IceUtilInternal::splitString(const string& str, const string& delim, vector<stri quoteChar = str[pos++]; continue; // Skip the quote } - else if(quoteChar == '\0' && str[pos] == '\\' && pos + 1 < length && + else if(quoteChar == '\0' && str[pos] == '\\' && pos + 1 < length && (str[pos + 1] == '\'' || str[pos + 1] == '"')) { ++pos; @@ -356,7 +612,7 @@ IceUtilInternal::splitString(const string& str, const string& delim, vector<stri continue; } } - + if(pos < length) { elt += str[pos++]; @@ -437,7 +693,7 @@ IceUtilInternal::checkQuote(const string& s, string::size_type start) // // Match `s' against the pattern `pat'. A * in the pattern acts // as a wildcard: it matches any non-empty sequence of characters. -// We match by hand here because it's portable across platforms +// We match by hand here because it's portable across platforms // (whereas regex() isn't). Only one * per pattern is supported. // bool @@ -500,7 +756,7 @@ IceUtilInternal::errorToString(int error, LPCVOID source) wstring lpMsgBuf(256, wchar_t()); DWORD stored = 0; - + while(stored == 0) { stored = FormatMessageW( @@ -531,7 +787,7 @@ IceUtilInternal::errorToString(int error, LPCVOID source) else { break; - } + } } } @@ -539,7 +795,7 @@ IceUtilInternal::errorToString(int error, LPCVOID source) #else LPWSTR msg = 0; - + DWORD stored = FormatMessageW( FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | @@ -552,7 +808,7 @@ IceUtilInternal::errorToString(int error, LPCVOID source) 0, NULL); #endif - + if(stored > 0) { assert(msg && wcslen(msg) > 0); @@ -576,159 +832,159 @@ IceUtilInternal::errorToString(int error, LPCVOID source) return os.str(); } } - + switch(error) { case WSAEINTR: return "WSAEINTR"; - + case WSAEBADF: return "WSAEBADF"; - + case WSAEACCES: return "WSAEACCES"; - + case WSAEFAULT: return "WSAEFAULT"; - + case WSAEINVAL: return "WSAEINVAL"; - + case WSAEMFILE: return "WSAEMFILE"; - + case WSAEWOULDBLOCK: return "WSAEWOULDBLOCK"; - + case WSAEINPROGRESS: return "WSAEINPROGRESS"; - + case WSAEALREADY: return "WSAEALREADY"; - + case WSAENOTSOCK: return "WSAENOTSOCK"; - + case WSAEDESTADDRREQ: return "WSAEDESTADDRREQ"; - + case WSAEMSGSIZE: return "WSAEMSGSIZE"; - + case WSAEPROTOTYPE: return "WSAEPROTOTYPE"; - + case WSAENOPROTOOPT: return "WSAENOPROTOOPT"; - + case WSAEPROTONOSUPPORT: return "WSAEPROTONOSUPPORT"; - + case WSAESOCKTNOSUPPORT: return "WSAESOCKTNOSUPPORT"; - + case WSAEOPNOTSUPP: return "WSAEOPNOTSUPP"; - + case WSAEPFNOSUPPORT: return "WSAEPFNOSUPPORT"; - + case WSAEAFNOSUPPORT: return "WSAEAFNOSUPPORT"; - + case WSAEADDRINUSE: return "WSAEADDRINUSE"; - + case WSAEADDRNOTAVAIL: return "WSAEADDRNOTAVAIL"; - + case WSAENETDOWN: return "WSAENETDOWN"; - + case WSAENETUNREACH: return "WSAENETUNREACH"; - + case WSAENETRESET: return "WSAENETRESET"; - + case WSAECONNABORTED: return "WSAECONNABORTED"; - + case WSAECONNRESET: return "WSAECONNRESET"; - + case WSAENOBUFS: return "WSAENOBUFS"; - + case WSAEISCONN: return "WSAEISCONN"; - + case WSAENOTCONN: return "WSAENOTCONN"; - + case WSAESHUTDOWN: return "WSAESHUTDOWN"; - + case WSAETOOMANYREFS: return "WSAETOOMANYREFS"; - + case WSAETIMEDOUT: return "WSAETIMEDOUT"; - + case WSAECONNREFUSED: return "WSAECONNREFUSED"; - + case WSAELOOP: return "WSAELOOP"; - + case WSAENAMETOOLONG: return "WSAENAMETOOLONG"; - + case WSAEHOSTDOWN: return "WSAEHOSTDOWN"; - + case WSAEHOSTUNREACH: return "WSAEHOSTUNREACH"; - + case WSAENOTEMPTY: return "WSAENOTEMPTY"; - + case WSAEPROCLIM: return "WSAEPROCLIM"; - + case WSAEUSERS: return "WSAEUSERS"; - + case WSAEDQUOT: return "WSAEDQUOT"; - + case WSAESTALE: return "WSAESTALE"; - + case WSAEREMOTE: return "WSAEREMOTE"; - + case WSAEDISCON: return "WSAEDISCON"; - + case WSASYSNOTREADY: return "WSASYSNOTREADY"; - + case WSAVERNOTSUPPORTED: return "WSAVERNOTSUPPORTED"; - + case WSANOTINITIALISED: return "WSANOTINITIALISED"; - + case WSAHOST_NOT_FOUND: return "WSAHOST_NOT_FOUND"; - + case WSATRY_AGAIN: return "WSATRY_AGAIN"; - + case WSANO_RECOVERY: return "WSANO_RECOVERY"; - + case WSANO_DATA: return "WSANO_DATA"; diff --git a/cpp/src/Slice/Preprocessor.cpp b/cpp/src/Slice/Preprocessor.cpp index c8e49029f25..57d5ed5f78f 100644 --- a/cpp/src/Slice/Preprocessor.cpp +++ b/cpp/src/Slice/Preprocessor.cpp @@ -83,11 +83,9 @@ Slice::Preprocessor::addQuotes(const string& arg) { // // Add quotes around the given argument to ensure that arguments - // with spaces will be preserved as a single argument. We also - // escape the "\" character to ensure that we don't end up with a - // \" at the end of the string. + // with spaces will be preserved as a single argument // - return "\"" + IceUtilInternal::escapeString(arg, "\\") + "\""; + return "\"" + escapeString(arg, "", IceUtilInternal::Unicode) + "\""; } string diff --git a/cpp/src/icegriddb/IceGridDB.cpp b/cpp/src/icegriddb/IceGridDB.cpp index 42b61f1ab92..8426d773d63 100644 --- a/cpp/src/icegriddb/IceGridDB.cpp +++ b/cpp/src/icegriddb/IceGridDB.cpp @@ -372,7 +372,7 @@ Client::run(int argc, char* argv[]) { if(debug) { - cout << " NAME = " << identityToString(p->proxy->ice_getIdentity()) << endl; + cout << " NAME = " << communicator()->identityToString(p->proxy->ice_getIdentity()) << endl; } objs.put(txn, p->proxy->ice_getIdentity(), *p); } @@ -390,7 +390,7 @@ Client::run(int argc, char* argv[]) { if(debug) { - cout << " NAME = " << identityToString(p->proxy->ice_getIdentity()) << endl; + cout << " NAME = " << communicator()->identityToString(p->proxy->ice_getIdentity()) << endl; } internalObjs.put(txn, p->proxy->ice_getIdentity(), *p); } @@ -483,7 +483,7 @@ Client::run(int argc, char* argv[]) { if(debug) { - cout << " IDENTITY = " << identityToString(id) << endl; + cout << " IDENTITY = " << communicator()->identityToString(id) << endl; } data.objects.push_back(object); } @@ -503,7 +503,7 @@ Client::run(int argc, char* argv[]) { if(debug) { - cout << " IDENTITY = " << identityToString(id) << endl; + cout << " IDENTITY = " << communicator()->identityToString(id) << endl; } data.internalObjects.push_back(object); } |