X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/68482dc584054c65f2dee76def3927d338fc20a7..64b1cea09aac1077469090dc2dac9a139a509833:/src/common/string.cpp diff --git a/src/common/string.cpp b/src/common/string.cpp index c97125d2c4..d7a7c7d9f3 100644 --- a/src/common/string.cpp +++ b/src/common/string.cpp @@ -50,6 +50,18 @@ #define wxStringStrlen wxStrlen #endif +// ---------------------------------------------------------------------------- +// global variables +// ---------------------------------------------------------------------------- + +namespace wxPrivate +{ + +static UntypedBufferData s_untypedNullData(NULL); + +UntypedBufferData * const untypedNullDataPtr = &s_untypedNullData; + +} // namespace wxPrivate // --------------------------------------------------------------------------- // static class variables definition @@ -59,8 +71,36 @@ const size_t wxString::npos = (size_t) -1; #if wxUSE_STRING_POS_CACHE + +#ifdef wxHAS_COMPILER_TLS + wxTLS_TYPE(wxString::Cache) wxString::ms_cache; +#else // !wxHAS_COMPILER_TLS + +struct wxStrCacheInitializer +{ + wxStrCacheInitializer() + { + // calling this function triggers s_cache initialization in it, and + // from now on it becomes safe to call from multiple threads + wxString::GetCache(); + } +}; + +/* +wxString::Cache& wxString::GetCache() +{ + static wxTLS_TYPE(Cache) s_cache; + + return wxTLS_VALUE(s_cache); +} +*/ + +static wxStrCacheInitializer gs_stringCacheInit; + +#endif // wxHAS_COMPILER_TLS/!wxHAS_COMPILER_TLS + // gdb seems to be unable to display thread-local variables correctly, at least // not my 6.4.98 version under amd64, so provide this debugging helper to do it #ifdef __WXDEBUG__ @@ -73,11 +113,11 @@ struct wxStrCacheDumper for ( unsigned n = 0; n < wxString::Cache::SIZE; n++ ) { const wxString::Cache::Element& - c = wxString::ms_cache.cached[n]; + c = wxString::GetCacheBegin()[n]; printf("\t%u%s\t%p: pos=(%lu, %lu), len=%ld\n", n, - n == wxString::ms_cache.lastUsed ? " [*]" : "", + n == wxString::LastUsedCacheElement() ? " [*]" : "", c.str, (unsigned long)c.pos, (unsigned long)c.impl, @@ -94,12 +134,9 @@ void wxDumpStrCache() { wxStrCacheDumper::ShowAll(); } wxString::CacheStats wxString::ms_cacheStats; -namespace -{ - -struct ShowCacheStats +struct wxStrCacheStatsDumper { - ~ShowCacheStats() + ~wxStrCacheStatsDumper() { const wxString::CacheStats& stats = wxString::ms_cacheStats; @@ -124,9 +161,9 @@ struct ShowCacheStats stats.lentot, 100.*float(stats.lenhits)/stats.lentot); } } -} s_showCacheStats; +}; -} // anonymous namespace +static wxStrCacheStatsDumper s_showCacheStats; #endif // wxPROFILE_STRING_CACHE @@ -143,7 +180,13 @@ struct ShowCacheStats wxSTD ostream& operator<<(wxSTD ostream& os, const wxCStrData& str) { #if wxUSE_UNICODE && !wxUSE_UNICODE_UTF8 - return os << (const char *)str.AsCharBuf(); + const wxCharBuffer buf(str.AsCharBuf()); + if ( !buf ) + os.clear(wxSTD ios_base::failbit); + else + os << buf.data(); + + return os; #else return os << str.AsInternal(); #endif @@ -1251,7 +1294,7 @@ wxString wxString::Right(size_t nCount) const return dest; } -// get all characters after the last occurence of ch +// get all characters after the last occurrence of ch // (returns the whole string if ch not found) wxString wxString::AfterLast(wxUniChar ch) const { @@ -1260,7 +1303,7 @@ wxString wxString::AfterLast(wxUniChar ch) const if ( iPos == wxNOT_FOUND ) str = *this; else - str = wx_str() + iPos + 1; + str.assign(*this, iPos + 1, npos); return str; } @@ -1278,16 +1321,17 @@ wxString wxString::Left(size_t nCount) const return dest; } -// get all characters before the first occurence of ch +// get all characters before the first occurrence of ch // (returns the whole string if ch not found) wxString wxString::BeforeFirst(wxUniChar ch) const { int iPos = Find(ch); - if ( iPos == wxNOT_FOUND ) iPos = length(); + if ( iPos == wxNOT_FOUND ) + iPos = length(); return wxString(*this, 0, iPos); } -/// get all characters before the last occurence of ch +/// get all characters before the last occurrence of ch /// (returns empty string if ch not found) wxString wxString::BeforeLast(wxUniChar ch) const { @@ -1299,19 +1343,19 @@ wxString wxString::BeforeLast(wxUniChar ch) const return str; } -/// get all characters after the first occurence of ch +/// get all characters after the first occurrence of ch /// (returns empty string if ch not found) wxString wxString::AfterFirst(wxUniChar ch) const { wxString str; int iPos = Find(ch); if ( iPos != wxNOT_FOUND ) - str = wx_str() + iPos + 1; + str.assign(*this, iPos + 1, npos); return str; } -// replace first (or all) occurences of some substring with another one +// replace first (or all) occurrences of some substring with another one size_t wxString::Replace(const wxString& strOld, const wxString& strNew, bool bReplaceAll) { @@ -2065,43 +2109,3 @@ int wxString::Freq(wxUniChar ch) const return count; } -// ---------------------------------------------------------------------------- -// wxUTF8StringBuffer -// ---------------------------------------------------------------------------- - -#if wxUSE_UNICODE_WCHAR -wxUTF8StringBuffer::~wxUTF8StringBuffer() -{ - wxMBConvStrictUTF8 conv; - size_t wlen = conv.ToWChar(NULL, 0, m_buf); - wxCHECK_RET( wlen != wxCONV_FAILED, "invalid UTF-8 data in string buffer?" ); - - wxStringInternalBuffer wbuf(m_str, wlen); - conv.ToWChar(wbuf, wlen, m_buf); -} - -wxUTF8StringBufferLength::~wxUTF8StringBufferLength() -{ - wxCHECK_RET(m_lenSet, "length not set"); - - wxMBConvStrictUTF8 conv; - size_t wlen = conv.ToWChar(NULL, 0, m_buf, m_len); - wxCHECK_RET( wlen != wxCONV_FAILED, "invalid UTF-8 data in string buffer?" ); - - wxStringInternalBufferLength wbuf(m_str, wlen); - conv.ToWChar(wbuf, wlen, m_buf, m_len); - wbuf.SetLength(wlen); -} -#endif // wxUSE_UNICODE_WCHAR - -// ---------------------------------------------------------------------------- -// wxCharBufferType -// ---------------------------------------------------------------------------- - -template<> -wxCharTypeBuffer::Data -wxCharTypeBuffer::NullData(NULL); - -template<> -wxCharTypeBuffer::Data -wxCharTypeBuffer::NullData(NULL);