From: <ale...@us...> - 2011-08-02 11:54:36
|
Revision: 53367 http://firebird.svn.sourceforge.net/firebird/?rev=53367&view=rev Author: alexpeshkoff Date: 2011-08-02 11:54:30 +0000 (Tue, 02 Aug 2011) Log Message: ----------- Enabled use of any available on the target system ICU version for non-collation calls Modified Paths: -------------- firebird/trunk/builds/posix/darwin.defaults firebird/trunk/builds/posix/make.defaults firebird/trunk/builds/posix/prefix.aix_powerpc firebird/trunk/builds/posix/prefix.aix_powerpc_xlc firebird/trunk/builds/posix/prefix.hpux_aCC firebird/trunk/builds/posix/prefix.mingw firebird/trunk/src/common/unicode_util.cpp firebird/trunk/src/common/unicode_util.h firebird/trunk/src/intl/cs_icu.cpp firebird/trunk/src/intl/cv_icu.cpp Modified: firebird/trunk/builds/posix/darwin.defaults =================================================================== --- firebird/trunk/builds/posix/darwin.defaults 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/builds/posix/darwin.defaults 2011-08-02 11:54:30 UTC (rev 53367) @@ -27,7 +27,7 @@ LIB_LINK_RPATH:=-install_name /Library/Frameworks/Firebird.framework/Versions/A/Libraries/ LIB_EMBED_LINK_OPTIONS:=-install_name /Library/Frameworks/Firebird.framework/Versions/A/Firebird LIB_CLIENT_LINK_OPTIONS:=-install_name /Library/Frameworks/Firebird.framework/Versions/A/Firebird -FBEMBED_LINK:=-F../gen/firebird -framework Firebird -L$(LIB) -lfbembed $(ICU_LIBS) +FBEMBED_LINK:=-F../gen/firebird -framework Firebird -L$(LIB) -lfbembed PLATFORM_PATH=os/darwin PLATFORM_FALLBACK=os/posix Modified: firebird/trunk/builds/posix/make.defaults =================================================================== --- firebird/trunk/builds/posix/make.defaults 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/builds/posix/make.defaults 2011-08-02 11:54:30 UTC (rev 53367) @@ -162,7 +162,6 @@ STATICEXE_LINK:= @CXX@ $(GLOB_OPTIONS) LINK_LIBS = @LIBS@ -ICU_LIBS = -licuuc STATICLINK_LIBS = @LIBS@ SO_LINK_LIBS = @LIBS@ @@ -301,11 +300,11 @@ LINK_INTL = $(LIB_LINK) $(LINK_FBINTL_SYMBOLS) $(LIB_LINK_OPTIONS) $(UNDEF_FLAGS)\ $(call LIB_LINK_SONAME,libintl.$(SHRLIB_EXT).1) $(call LIB_LINK_RPATH,lib) -LINK_INTL_LIBS = -L$(LIB) $(ICU_LIBS) $(SO_LINK_LIBS) $(FIREBIRD_LIBRARY_LINK) +LINK_INTL_LIBS = -L$(LIB) $(SO_LINK_LIBS) $(FIREBIRD_LIBRARY_LINK) LINK_TRACE = $(LIB_LINK) $(LINK_PLUGIN_SYMBOLS) $(LIB_LINK_OPTIONS) $(UNDEF_FLAGS)\ $(call LIB_LINK_SONAME,$(LIB_PREFIX)fbtrace.$(SHRLIB_EXT).0) $(call LIB_LINK_RPATH,lib) -LINK_TRACE_LIBS = -L$(LIB) $(SO_LINK_LIBS) $(ICU_LIBS) +LINK_TRACE_LIBS = -L$(LIB) $(SO_LINK_LIBS) LINK_FIREBIRD = $(LIB_LINK) $(LINK_FIREBIRD_SYMBOLS) $(LIB_LINK_OPTIONS) $(LIB_FIREBIRD_OPTIONS) $(UNDEF_FLAGS)\ $(call LIB_LINK_SONAME,$(LibrarySoName)) $(call LIB_LINK_RPATH,lib) @@ -313,7 +312,7 @@ LINK_ENGINE = $(LIB_LINK) $(LINK_PLUGIN_SYMBOLS) $(LIB_LINK_OPTIONS) $(LIB_FIREBIRD_OPTIONS) $(UNDEF_FLAGS)\ $(call LIB_LINK_SONAME,$(EngineSoName)) $(call LIB_LINK_RPATH,lib) -LINK_ENGINE_LIBS = $(LINK_FIREBIRD_LIBS) $(FIREBIRD_LIBRARY_LINK) $(ICU_LIBS) +LINK_ENGINE_LIBS = $(LINK_FIREBIRD_LIBS) $(FIREBIRD_LIBRARY_LINK) LINK_UDRENG = $(LIB_LINK) $(LINK_UDRENG_SYMBOLS) $(LIB_LINK_OPTIONS) $(call LIB_LINK_RPATH,lib) $(UNDEF_FLAGS) LINK_UDRENG_LIBS = -L$(LIB) $(SO_LINK_LIBS) Modified: firebird/trunk/builds/posix/prefix.aix_powerpc =================================================================== --- firebird/trunk/builds/posix/prefix.aix_powerpc 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/builds/posix/prefix.aix_powerpc 2011-08-02 11:54:30 UTC (rev 53367) @@ -51,10 +51,6 @@ # Additional -blibpath options are not additive! All paths must be provided as a colon separated list. LIB_PATH_OPTS= -Wl,-blibpath:@FB_LIBDIR@:@FB_INTLDIR@:/usr/local/lib:/usr/lib:/lib:$(GCC_RUNTIME) -ifeq ($(STD_ICU),true) - ICU_LIBS= -L/usr/local/lib -licuuc -endif - # non-firebird libraries have .a extension SHRLIB_FOREIGN_EXT=a Modified: firebird/trunk/builds/posix/prefix.aix_powerpc_xlc =================================================================== --- firebird/trunk/builds/posix/prefix.aix_powerpc_xlc 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/builds/posix/prefix.aix_powerpc_xlc 2011-08-02 11:54:30 UTC (rev 53367) @@ -57,10 +57,6 @@ # Additional -blibpath options are not additive! All paths must be provided as a colon separated list. LIB_PATH_OPTS= -blibpath:@FB_LIBDIR@:@FB_INTLDIR@:/usr/local/lib:/usr/lib:/lib -ifeq ($(STD_ICU),true) - ICU_LIBS= -L/usr/local/lib -licuuc -endif - # non-firebird libraries have .a extension SHRLIB_FOREIGN_EXT=a Modified: firebird/trunk/builds/posix/prefix.hpux_aCC =================================================================== --- firebird/trunk/builds/posix/prefix.hpux_aCC 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/builds/posix/prefix.hpux_aCC 2011-08-02 11:54:30 UTC (rev 53367) @@ -81,11 +81,8 @@ # link options for HP-UX linker, /usr/bin/ld LINK_OPTS= $(LDFLAGS) $(THR_FLAGS) $(UNDEF_FLAGS) $(LIB_PATH_OPTS) -AA +e -Wl,+concatrpath -LINK_LIBS+= $(ICU_LIBS) LIB_LINK_OPTIONS= $(LDFLAGS) $(THR_FLAGS) -b +e -Wl,+concatrpath -LINK_UDF_LIBS+=$(ICU_LIBS) - # From original HPUX prefix file LIB_LINK_RPATH= -Wl,+b,$(1) LIB_LINK_SONAME= -Wl,+h,$(1) Modified: firebird/trunk/builds/posix/prefix.mingw =================================================================== --- firebird/trunk/builds/posix/prefix.mingw 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/builds/posix/prefix.mingw 2011-08-02 11:54:30 UTC (rev 53367) @@ -66,4 +66,4 @@ LINK_UDF_LIBS = # Special options for trace plugin link -LINK_TRACE_LIBS = -L$(LIB) $(SO_LINK_LIBS) $(ICU_LIBS) +LINK_TRACE_LIBS = -L$(LIB) $(SO_LINK_LIBS) Modified: firebird/trunk/src/common/unicode_util.cpp =================================================================== --- firebird/trunk/src/common/unicode_util.cpp 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/src/common/unicode_util.cpp 2011-08-02 11:54:30 UTC (rev 53367) @@ -37,46 +37,45 @@ #include "../common/classes/init.h" #include "../common/classes/objects_array.h" #include "../common/classes/rwlock.h" +#include "../common/StatusHolder.h" #include <unicode/ustring.h> #include <unicode/utrans.h> #include <unicode/uchar.h> -#include <unicode/ucnv.h> #include <unicode/ucol.h> using namespace Firebird; +namespace { +#if defined(WIN_NT) +const char* const inTemplate = "icuin%d%d.dll"; +const char* const ucTemplate = "icuuc%d%d.dll"; +#elif defined(DARWIN) +const char* const inTemplate = "/Library/Frameworks/Firebird.framework/Versions/A/Libraries/libicui18n.dylib"; +const char* const ucTemplate = "/Library/Frameworks/Firebird.framework/versions/A/Libraries/libicuuc.dylib"; +#elif defined(HPUX) +const char* const inTemplate = "libicui18n.sl.%d%d"; +const char* const ucTemplate = "libicuuc.sl.%d%d"; +#else +const char* const inTemplate = "libicui18n.so.%d%d"; +const char* const ucTemplate = "libicuuc.so.%d%d"; +#endif -namespace Jrd { - - -const char* const UnicodeUtil::DEFAULT_ICU_VERSION = - STRINGIZE(U_ICU_VERSION_MAJOR_NUM)"."STRINGIZE(U_ICU_VERSION_MINOR_NUM); - - -// encapsulate ICU collations libraries -struct UnicodeUtil::ICU +// encapsulate ICU library +struct BaseICU { private: - ICU(const ICU&); // not implemented - ICU& operator =(const ICU&); // not implemented + BaseICU(const BaseICU&); // not implemented + BaseICU& operator =(const BaseICU&); // not implemented public: - ICU(int aMajorVersion, int aMinorVersion) + BaseICU(int aMajorVersion, int aMinorVersion) : majorVersion(aMajorVersion), - minorVersion(aMinorVersion), - inModule(NULL), - ucModule(NULL) + minorVersion(aMinorVersion) { } - ~ICU() - { - delete ucModule; - delete inModule; - } - template <typename T> void getEntryPoint(const char* name, ModuleLoader::Module* module, T& ptr) { string symbol; @@ -97,11 +96,39 @@ int majorVersion; int minorVersion; + + void (U_EXPORT2 *uInit)(UErrorCode* status); +}; +} + +namespace Jrd { + + +const char* const UnicodeUtil::DEFAULT_ICU_VERSION = + STRINGIZE(U_ICU_VERSION_MAJOR_NUM)"."STRINGIZE(U_ICU_VERSION_MINOR_NUM); + + +// encapsulate ICU collations libraries +struct UnicodeUtil::ICU : public BaseICU +{ +public: + ICU(int aMajorVersion, int aMinorVersion) + : BaseICU(aMajorVersion, aMinorVersion), + inModule(NULL), + ucModule(NULL) + { + } + + ~ICU() + { + delete ucModule; + delete inModule; + } + ModuleLoader::Module* inModule; ModuleLoader::Module* ucModule; UVersionInfo collVersion; - void (U_EXPORT2 *uInit)(UErrorCode* status); void (U_EXPORT2 *uVersionToString)(UVersionInfo versionArray, char* versionString); int32_t (U_EXPORT2 *ulocCountAvailable)(); @@ -143,6 +170,77 @@ }; +// encapsulate ICU conversion library +struct ImplementConversionICU : public UnicodeUtil::ConversionICU, BaseICU +{ +public: + ImplementConversionICU(int aMajorVersion, int aMinorVersion) + : BaseICU(aMajorVersion, aMinorVersion), + module(NULL) + { + PathName filename; + filename.printf(ucTemplate, aMajorVersion, aMinorVersion); + + module = ModuleLoader::fixAndLoadModule(filename); + if (!module) + { + //(Arg::Gds(isc_random) << "Missing library" << + // Arg::Gds(isc_random) << filename).raise(); + // Instead raise 'empty' exception in order to ignore "Missing library" later + LongJump::raise(); + } + + try + { + getEntryPoint("u_init", module, uInit); + } + catch (const status_exception&) + { } + + getEntryPoint("ucnv_open", module, ucnv_open); + getEntryPoint("ucnv_close", module, ucnv_close); + getEntryPoint("ucnv_fromUChars", module, ucnv_fromUChars); + getEntryPoint("u_tolower", module, u_tolower); + getEntryPoint("u_toupper", module, u_toupper); + getEntryPoint("u_strCompare", module, u_strCompare); + getEntryPoint("u_countChar32", module, u_countChar32); + getEntryPoint("utf8_nextCharSafeBody", module, utf8_nextCharSafeBody); + + getEntryPoint("UCNV_FROM_U_CALLBACK_STOP", module, UCNV_FROM_U_CALLBACK_STOP); + getEntryPoint("UCNV_TO_U_CALLBACK_STOP", module, UCNV_TO_U_CALLBACK_STOP); + getEntryPoint("ucnv_fromUnicode", module, ucnv_fromUnicode); + getEntryPoint("ucnv_toUnicode", module, ucnv_toUnicode); + getEntryPoint("ucnv_getInvalidChars", module, ucnv_getInvalidChars); + getEntryPoint("ucnv_getMaxCharSize", module, ucnv_getMaxCharSize); + getEntryPoint("ucnv_getMinCharSize", module, ucnv_getMinCharSize); + getEntryPoint("ucnv_setFromUCallBack", module, ucnv_setFromUCallBack); + getEntryPoint("ucnv_setToUCallBack", module, ucnv_setToUCallBack); + + if (uInit) + { + UErrorCode status = U_ZERO_ERROR; + uInit(&status); + if (status != U_ZERO_ERROR) + { + string diag; + diag.printf("u_init() error %d", status); + (Arg::Gds(isc_random) << diag).raise(); + } + } + } + + ~ImplementConversionICU() + { + delete module; + } + + ModuleLoader::Module* module; +}; + +static ImplementConversionICU* convIcu = 0; +static GlobalPtr<Mutex> convIcuMutex; + + // cache ICU module instances to not load and unload many times class UnicodeUtil::ICUModules { @@ -224,15 +322,16 @@ return INTL_BAD_KEY_LENGTH; UErrorCode status = U_ZERO_ERROR; - UConverter* conv = ucnv_open("BOCU-1", &status); + ConversionICU& cIcu(getConversionICU()); + UConverter* conv = cIcu.ucnv_open("BOCU-1", &status); fb_assert(U_SUCCESS(status)); - const int32_t len = ucnv_fromUChars(conv, reinterpret_cast<char*>(dst), dstLen, + const int32_t len = cIcu.ucnv_fromUChars(conv, reinterpret_cast<char*>(dst), dstLen, // safe cast - alignment not changed reinterpret_cast<const UChar*>(src), srcLen / sizeof(*src), &status); fb_assert(U_SUCCESS(status)); - ucnv_close(conv); + cIcu.ucnv_close(conv); return len; } @@ -278,6 +377,7 @@ dstLen /= sizeof(*dst); ULONG n = 0; + ConversionICU& cIcu(getConversionICU()); for (ULONG i = 0; i < srcLen;) { @@ -285,7 +385,7 @@ U16_NEXT(src, i, srcLen, c); if (!exceptions) - c = u_tolower(c); + c = cIcu.u_tolower(c); else { const ULONG* p = exceptions; @@ -293,7 +393,7 @@ ++p; if (*p == 0) - c = u_tolower(c); + c = cIcu.u_tolower(c); } bool error; @@ -344,6 +444,7 @@ dstLen /= sizeof(*dst); ULONG n = 0; + ConversionICU& cIcu(getConversionICU()); for (ULONG i = 0; i < srcLen;) { @@ -351,7 +452,7 @@ U16_NEXT(src, i, srcLen, c); if (!exceptions) - c = u_toupper(c); + c = cIcu.u_toupper(c); else { const ULONG* p = exceptions; @@ -359,7 +460,7 @@ ++p; if (*p == 0) - c = u_toupper(c); + c = cIcu.u_toupper(c); } bool error; @@ -453,6 +554,7 @@ const USHORT* const dstStart = dst; const USHORT* const dstEnd = dst + dstLen / sizeof(*dst); + ConversionICU& cIcu(getConversionICU()); for (ULONG i = 0; i < srcLen; ) { @@ -471,7 +573,7 @@ { *err_position = i - 1; - c = utf8_nextCharSafeBody(src, reinterpret_cast<int32_t*>(&i), srcLen, c, -1); + c = cIcu.utf8_nextCharSafeBody(src, reinterpret_cast<int32_t*>(&i), srcLen, c, -1); if (c < 0) { @@ -618,7 +720,7 @@ *error_flag = false; // safe casts - alignment not changed - int32_t cmp = u_strCompare(reinterpret_cast<const UChar*>(str1), len1 / sizeof(*str1), + int32_t cmp = getConversionICU().u_strCompare(reinterpret_cast<const UChar*>(str1), len1 / sizeof(*str1), reinterpret_cast<const UChar*>(str2), len2 / sizeof(*str2), true); return (cmp < 0 ? -1 : (cmp > 0 ? 1 : 0)); @@ -629,7 +731,7 @@ { fb_assert(len % sizeof(*str) == 0); // safe cast - alignment not changed - return u_countChar32(reinterpret_cast<const UChar*>(str), len / sizeof(*str)); + return getConversionICU().u_countChar32(reinterpret_cast<const UChar*>(str), len / sizeof(*str)); } @@ -687,6 +789,7 @@ { fb_assert(str != NULL); + ConversionICU& cIcu(getConversionICU()); for (ULONG i = 0; i < len; ) { UChar32 c = str[i++]; @@ -695,7 +798,7 @@ { const ULONG save_i = i - 1; - c = utf8_nextCharSafeBody(str, reinterpret_cast<int32_t*>(&i), len, c, -1); + c = cIcu.utf8_nextCharSafeBody(str, reinterpret_cast<int32_t*>(&i), len, c, -1); if (c < 0) { @@ -762,20 +865,6 @@ UnicodeUtil::ICU* UnicodeUtil::loadICU(const Firebird::string& icuVersion, const Firebird::string& configInfo) { -#if defined(WIN_NT) - const char* const inTemplate = "icuin%d%d.dll"; - const char* const ucTemplate = "icuuc%d%d.dll"; -#elif defined(DARWIN) - const char* const inTemplate = "/Library/Frameworks/Firebird.framework/Versions/A/Libraries/libicui18n.dylib"; - const char* const ucTemplate = "/Library/Frameworks/Firebird.framework/versions/A/Libraries/libicuuc.dylib"; -#elif defined(HPUX) - const char* const inTemplate = "libicui18n.sl.%d%d"; - const char* const ucTemplate = "libicuuc.sl.%d%d"; -#else - const char* const inTemplate = "libicui18n.so.%d%d"; - const char* const ucTemplate = "libicuuc.so.%d%d"; -#endif - ObjectsArray<string> versions; getVersions(configInfo, versions); @@ -916,6 +1005,56 @@ } +UnicodeUtil::ConversionICU& UnicodeUtil::getConversionICU() +{ + if (convIcu) + { + return *convIcu; + } + + MutexLockGuard g(convIcuMutex); + + if (convIcu) + { + return *convIcu; + } + + LocalStatus lastError; + string version; + int majorArray[] = {4, 3, 5, 6, 0}; + for (int* major = majorArray; *major; ++major) + { + for (int minor = 20; --minor; ) /* from 19 down to 0 */ + { + try + { + convIcu = FB_NEW(*getDefaultMemoryPool()) ImplementConversionICU(*major, minor); + return *convIcu; + } + catch (const LongJump&) { } + catch (const Exception& ex) + { + ex.stuffException(&lastError); + version.printf("Error loading ICU library version %d.%d", *major, minor); + } + } + } + + if (!lastError.isSuccess()) + { + (Arg::Gds(isc_random) << "Could not find acceptable ICU library" + << Arg::StatusVector(lastError.get())).raise(); + } + else + { + (Arg::Gds(isc_random) << "Could not find acceptable ICU library").raise(); + } + + // compiler warning silencer + return *convIcu; +} + + bool UnicodeUtil::getCollVersion(const Firebird::string& icuVersion, const Firebird::string& configInfo, Firebird::string& collVersion) { @@ -1128,6 +1267,7 @@ // Remove last bytes of key if they are start of a contraction // to correctly find in the index. + ConversionICU& cIcu(getConversionICU()); for (int i = 0; i < contractionsCount; ++i) { UChar str[10]; @@ -1140,7 +1280,7 @@ --len; // safe cast - alignment not changed - if (u_strCompare(str, len, reinterpret_cast<const UChar*>(src) + srcLen - len, len, true) == 0) + if (cIcu.u_strCompare(str, len, reinterpret_cast<const UChar*>(src) + srcLen - len, len, true) == 0) { srcLen -= len; break; Modified: firebird/trunk/src/common/unicode_util.h =================================================================== --- firebird/trunk/src/common/unicode_util.h 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/src/common/unicode_util.h 2011-08-02 11:54:30 UTC (rev 53367) @@ -30,6 +30,7 @@ #include "intlobj_new.h" #include "../common/IntlUtil.h" #include "../common/os/mod_loader.h" +#include <unicode/ucnv.h> struct UCollator; struct USet; @@ -42,9 +43,85 @@ struct ICU; public: + // encapsulate ICU conversion library + struct ConversionICU + { + UConverter* (U_EXPORT2* ucnv_open) (const char* converterName, UErrorCode* err); + void (U_EXPORT2* ucnv_close) (UConverter *converter); + int32_t (U_EXPORT2* ucnv_fromUChars) (UConverter *cnv, + char *dest, int32_t destCapacity, + const UChar *src, int32_t srcLength, + UErrorCode *pErrorCode); + + UChar32 (U_EXPORT2* u_tolower) (UChar32 c); + UChar32 (U_EXPORT2* u_toupper) (UChar32 c); + int32_t (U_EXPORT2* u_strCompare) (const UChar* s1, int32_t length1, + const UChar* s2, int32_t length2, UBool codePointOrder); + int32_t (U_EXPORT2* u_countChar32) (const UChar* s, int32_t length); + + UChar32 (U_EXPORT2* utf8_nextCharSafeBody) (const uint8_t* s, int32_t* pi, int32_t length, UChar32 c, UBool strict); + + void (U_EXPORT2* UCNV_FROM_U_CALLBACK_STOP) ( + const void *context, + UConverterFromUnicodeArgs *fromUArgs, + const UChar* codeUnits, + int32_t length, + UChar32 codePoint, + UConverterCallbackReason reason, + UErrorCode * err); + void (U_EXPORT2* UCNV_TO_U_CALLBACK_STOP) ( + const void *context, + UConverterToUnicodeArgs *toUArgs, + const char* codeUnits, + int32_t length, + UConverterCallbackReason reason, + UErrorCode * err); + + void (U_EXPORT2* ucnv_setToUCallBack) ( + UConverter * converter, + UConverterToUCallback newAction, + const void* newContext, + UConverterToUCallback *oldAction, + const void** oldContext, + UErrorCode * err); + void (U_EXPORT2* ucnv_setFromUCallBack) ( + UConverter * converter, + UConverterFromUCallback newAction, + const void *newContext, + UConverterFromUCallback *oldAction, + const void **oldContext, + UErrorCode * err); + + void (U_EXPORT2* ucnv_fromUnicode) ( + UConverter * converter, + char **target, + const char *targetLimit, + const UChar ** source, + const UChar * sourceLimit, + int32_t* offsets, + UBool flush, + UErrorCode * err); + void (U_EXPORT2* ucnv_toUnicode) ( + UConverter *converter, + UChar **target, + const UChar *targetLimit, + const char **source, + const char *sourceLimit, + int32_t *offsets, + UBool flush, + UErrorCode *err); + + void (U_EXPORT2* ucnv_getInvalidChars) ( + const UConverter *converter, + char *errBytes, + int8_t *len, + UErrorCode *err); + int8_t (U_EXPORT2* ucnv_getMaxCharSize) (const UConverter *converter); + int8_t (U_EXPORT2* ucnv_getMinCharSize) (const UConverter *converter); + }; + static const char* const DEFAULT_ICU_VERSION; -public: class ICUModules; // routines semantically equivalent with intlobj_new.h @@ -72,6 +149,7 @@ static INTL_BOOL utf16WellFormed(ULONG len, const USHORT* str, ULONG* offending_position); static INTL_BOOL utf32WellFormed(ULONG len, const ULONG* str, ULONG* offending_position); + static ConversionICU& getConversionICU(); static ICU* loadICU(const Firebird::string& icuVersion, const Firebird::string& configInfo); static bool getCollVersion(const Firebird::string& icuVersion, const Firebird::string& configInfo, Firebird::string& collVersion); Modified: firebird/trunk/src/intl/cs_icu.cpp =================================================================== --- firebird/trunk/src/intl/cs_icu.cpp 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/src/intl/cs_icu.cpp 2011-08-02 11:54:30 UTC (rev 53367) @@ -29,6 +29,7 @@ #include "cs_icu.h" #include "cv_icu.h" #include <unicode/ucnv.h> +#include "../common/unicode_util.h" static void charset_destroy(charset* cs) @@ -42,7 +43,8 @@ const ASCII* charSetName) { UErrorCode status = U_ZERO_ERROR; - UConverter* conv = ucnv_open(charSetName, &status); + Jrd::UnicodeUtil::ConversionICU& cIcu(Jrd::UnicodeUtil::getConversionICU()); + UConverter* conv = cIcu.ucnv_open(charSetName, &status); if (U_SUCCESS(status)) { @@ -53,8 +55,8 @@ cs->charset_version = CHARSET_VERSION_1; cs->charset_flags |= CHARSET_ASCII_BASED; - cs->charset_min_bytes_per_char = ucnv_getMinCharSize(conv); - cs->charset_max_bytes_per_char = ucnv_getMaxCharSize(conv); + cs->charset_min_bytes_per_char = cIcu.ucnv_getMinCharSize(conv); + cs->charset_max_bytes_per_char = cIcu.ucnv_getMaxCharSize(conv); cs->charset_fn_destroy = charset_destroy; cs->charset_fn_well_formed = NULL; @@ -62,11 +64,11 @@ BYTE* p2 = new BYTE[cs->charset_max_bytes_per_char]; cs->charset_space_character = p2; - cs->charset_space_length = ucnv_fromUChars(conv, reinterpret_cast<char*>(p2), + cs->charset_space_length = cIcu.ucnv_fromUChars(conv, reinterpret_cast<char*>(p2), cs->charset_max_bytes_per_char, &unicodeSpace, 1, &status); fb_assert(U_SUCCESS(status)); - ucnv_close(conv); + cIcu.ucnv_close(conv); CVICU_convert_init(cs); } Modified: firebird/trunk/src/intl/cv_icu.cpp =================================================================== --- firebird/trunk/src/intl/cv_icu.cpp 2011-08-02 09:26:49 UTC (rev 53366) +++ firebird/trunk/src/intl/cv_icu.cpp 2011-08-02 11:54:30 UTC (rev 53367) @@ -29,26 +29,28 @@ #include "ld_proto.h" #include "cv_icu.h" #include <unicode/ucnv.h> +#include "../common/unicode_util.h" static UConverter* create_converter(csconvert* cv, UErrorCode* status) { - UConverter* conv = ucnv_open(cv->csconvert_impl->cs->charset_name, status); + Jrd::UnicodeUtil::ConversionICU& cIcu(Jrd::UnicodeUtil::getConversionICU()); + UConverter* conv = cIcu.ucnv_open(cv->csconvert_impl->cs->charset_name, status); const void* oldContext; UConverterFromUCallback oldFromAction; - ucnv_setFromUCallBack( + cIcu.ucnv_setFromUCallBack( conv, - UCNV_FROM_U_CALLBACK_STOP, + cIcu.UCNV_FROM_U_CALLBACK_STOP, NULL, &oldFromAction, &oldContext, status); UConverterToUCallback oldToAction; - ucnv_setToUCallBack( + cIcu.ucnv_setToUCallBack( conv, - UCNV_TO_U_CALLBACK_STOP, + cIcu.UCNV_TO_U_CALLBACK_STOP, NULL, &oldToAction, &oldContext, @@ -88,7 +90,8 @@ Firebird::Aligner<UChar> alignedSource(src, srcLen); const UChar* source = alignedSource; char* target = reinterpret_cast<char*>(dst); - ucnv_fromUnicode(conv, &target, target + dstLen, &source, + Jrd::UnicodeUtil::ConversionICU& cIcu(Jrd::UnicodeUtil::getConversionICU()); + cIcu.ucnv_fromUnicode(conv, &target, target + dstLen, &source, source + srcLen / sizeof(UChar), NULL, TRUE, &status); *errPosition = (source - alignedSource) * sizeof(UChar); @@ -115,7 +118,7 @@ } } - ucnv_close(conv); + cIcu.ucnv_close(conv); return target - reinterpret_cast<char*>(dst); } @@ -143,7 +146,8 @@ const char* source = reinterpret_cast<const char*>(src); Firebird::OutAligner<UChar> alignedTarget(dst, dstLen); UChar* target = alignedTarget; - ucnv_toUnicode(conv, &target, target + dstLen / sizeof(UChar), &source, + Jrd::UnicodeUtil::ConversionICU& cIcu(Jrd::UnicodeUtil::getConversionICU()); + cIcu.ucnv_toUnicode(conv, &target, target + dstLen / sizeof(UChar), &source, source + srcLen, NULL, TRUE, &status); *errPosition = source - reinterpret_cast<const char*>(src); @@ -164,7 +168,7 @@ status = U_ZERO_ERROR; char errBytes[16]; int8_t errLen = sizeof(errBytes); - ucnv_getInvalidChars(conv, errBytes, &errLen, &status); + cIcu.ucnv_getInvalidChars(conv, errBytes, &errLen, &status); if (!U_SUCCESS(status)) *errCode = CS_CONVERT_ERROR; else @@ -184,7 +188,7 @@ } } - ucnv_close(conv); + cIcu.ucnv_close(conv); return (target - alignedTarget) * sizeof(UChar); } This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |