X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/6164d85e896743b16a0cf8b0610f5d17ceb47f36..7482b22003c03f7aa3335aec271b5fcb48e2693d:/src/common/string.cpp?ds=sidebyside diff --git a/src/common/string.cpp b/src/common/string.cpp index cb949eb688..5329f085e2 100644 --- a/src/common/string.cpp +++ b/src/common/string.cpp @@ -41,7 +41,11 @@ #include #include -#ifdef wxUSE_WCSRTOMBS +#ifdef __SALFORDC__ +#include +#endif + +#if wxUSE_WCSRTOMBS #include // for wcsrtombs(), see comments where it's used #endif // GNU @@ -58,9 +62,9 @@ // static class variables definition // --------------------------------------------------------------------------- -#ifdef STD_STRING_COMPATIBILITY +#ifdef wxSTD_STRING_COMPATIBILITY const size_t wxString::npos = STRING_MAXLEN; -#endif +#endif // wxSTD_STRING_COMPATIBILITY // ---------------------------------------------------------------------------- // static data @@ -76,13 +80,40 @@ static const struct } g_strEmpty = { {-1, 0, 0}, '\0' }; // empty C style string: points to 'string data' byte of g_strEmpty -extern const char *g_szNul = &g_strEmpty.dummy; +extern const char WXDLLEXPORT *g_szNul = &g_strEmpty.dummy; + +// ---------------------------------------------------------------------------- +// conditional compilation +// ---------------------------------------------------------------------------- + +// we want to find out if the current platform supports vsnprintf()-like +// function: for Unix this is done with configure, for Windows we test the +// compiler explicitly. +#ifdef __WXMSW__ + #ifdef _MSC_VER + #define wxVsprintf _vsnprintf + #endif +#else // !Windows + #ifdef HAVE_VSNPRINTF + #define wxVsprintf vsnprintf + #endif +#endif // Windows/!Windows + +#ifndef wxVsprintf + // in this case we'll use vsprintf() (which is ANSI and thus should be + // always available), but it's unsafe because it doesn't check for buffer + // size - so give a warning + #define wxVsprintf(buffer,len,format,argptr) vsprintf(buffer,format, argptr) +#ifndef __SC__ + #pragma message("Using sprintf() because no snprintf()-like function defined") +#endif +#endif // ---------------------------------------------------------------------------- // global functions // ---------------------------------------------------------------------------- -#ifdef STD_STRING_COMPATIBILITY +#ifdef wxSTD_STRING_COMPATIBILITY // MS Visual C++ version 5.0 provides the new STL headers as well as the old // iostream ones. @@ -101,6 +132,21 @@ extern const char *g_szNul = &g_strEmpty.dummy; #define NAMESPACE std:: #endif +#ifdef __WXMSW__ + #ifdef _MSC_VER + #define wxVsprintf _vsnprintf + #endif +#else + #if defined ( HAVE_VSNPRINTF ) + #define wxVsprintf vsnprintf + #endif +#endif + +#ifndef wxVsprintf + // vsprintf() is ANSI so we can always use it, but it's unsafe! + #define wxVsprintf(buffer,len,format,argptr) vsprintf(buffer,format, argptr) + #pragma message("Using sprintf() because no snprintf()-like function defined") +#endif NAMESPACE istream& operator>>(NAMESPACE istream& is, wxString& WXUNUSED(str)) { @@ -211,7 +257,7 @@ wxString::wxString(const unsigned char* psz, size_t nLength) InitWith((const char *)psz, 0, nLength); } -#ifdef STD_STRING_COMPATIBILITY +#ifdef wxSTD_STRING_COMPATIBILITY // poor man's iterators are "void *" pointers wxString::wxString(const void *pStart, const void *pEnd) @@ -229,7 +275,7 @@ wxString::wxString(const wchar_t *pwz) // NB: GNU libc5 wcstombs() is completely broken, don't use it (it doesn't // honor the 3rd parameter, thus it will happily crash here). -#ifdef wxUSE_WCSRTOMBS +#if wxUSE_WCSRTOMBS // don't know if it's really needed (or if we can pass NULL), but better safe // than quick mbstate_t mbstate; @@ -299,6 +345,10 @@ void wxString::AllocBeforeWrite(size_t nLen) pData->Unlock(); AllocBuffer(nLen); } + else { + // update the string length + pData->nDataLength = nLen; + } wxASSERT( !GetStringData()->IsShared() ); // we must be the only owner } @@ -626,11 +676,11 @@ wxString wxString::Right(size_t nCount) const // get all characters after the last occurence of ch // (returns the whole string if ch not found) -wxString wxString::Right(char ch) const +wxString wxString::AfterLast(char ch) const { wxString str; int iPos = Find(ch, TRUE); - if ( iPos == NOT_FOUND ) + if ( iPos == wxNOT_FOUND ) str = *this; else str = c_str() + iPos + 1; @@ -651,7 +701,7 @@ wxString wxString::Left(size_t nCount) const // get all characters before the first occurence of ch // (returns the whole string if ch not found) -wxString wxString::Left(char ch) const +wxString wxString::BeforeFirst(char ch) const { wxString str; for ( const char *pc = m_pchData; *pc != '\0' && *pc != ch; pc++ ) @@ -662,11 +712,11 @@ wxString wxString::Left(char ch) const /// get all characters before the last occurence of ch /// (returns empty string if ch not found) -wxString wxString::Before(char ch) const +wxString wxString::BeforeLast(char ch) const { wxString str; int iPos = Find(ch, TRUE); - if ( iPos != NOT_FOUND && iPos != 0 ) + if ( iPos != wxNOT_FOUND && iPos != 0 ) str = wxString(c_str(), iPos); return str; @@ -674,11 +724,11 @@ wxString wxString::Before(char ch) const /// get all characters after the first occurence of ch /// (returns empty string if ch not found) -wxString wxString::After(char ch) const +wxString wxString::AfterFirst(char ch) const { wxString str; int iPos = Find(ch); - if ( iPos != NOT_FOUND ) + if ( iPos != wxNOT_FOUND ) str = c_str() + iPos + 1; return str; @@ -825,7 +875,7 @@ wxString& wxString::Trim(bool bFromRight) psz++; // fix up data and length - int nDataLength = GetStringData()->nDataLength - (psz - m_pchData); + int nDataLength = GetStringData()->nDataLength - (psz - (const char*) m_pchData); memmove(m_pchData, psz, (nDataLength + 1)*sizeof(char)); GetStringData()->nDataLength = nDataLength; } @@ -853,14 +903,19 @@ wxString& wxString::Pad(size_t nCount, char chPad, bool bFromRight) // truncate the string wxString& wxString::Truncate(size_t uiLen) { - *(m_pchData + uiLen) = '\0'; - GetStringData()->nDataLength = uiLen; + if ( uiLen < Len() ) { + CopyBeforeWrite(); + + *(m_pchData + uiLen) = '\0'; + GetStringData()->nDataLength = uiLen; + } + //else: nothing to do, string is already short enough return *this; } // --------------------------------------------------------------------------- -// finding (return NOT_FOUND if not found and index otherwise) +// finding (return wxNOT_FOUND if not found and index otherwise) // --------------------------------------------------------------------------- // find a character @@ -868,7 +923,7 @@ int wxString::Find(char ch, bool bFromEnd) const { const char *psz = bFromEnd ? strrchr(m_pchData, ch) : strchr(m_pchData, ch); - return (psz == NULL) ? NOT_FOUND : psz - m_pchData; + return (psz == NULL) ? wxNOT_FOUND : psz - (const char*) m_pchData; } // find a sub-string (like strstr) @@ -876,7 +931,7 @@ int wxString::Find(const char *pszSub) const { const char *psz = strstr(m_pchData, pszSub); - return (psz == NULL) ? NOT_FOUND : psz - m_pchData; + return (psz == NULL) ? wxNOT_FOUND : psz - (const char*) m_pchData; } // --------------------------------------------------------------------------- @@ -923,35 +978,14 @@ int wxString::Printf(const char *pszFormat, ...) int wxString::PrintfV(const char* pszFormat, va_list argptr) { -#ifdef __BORLANDC__ - static char s_szScratch[1024]; - - int iLen = vsprintf(s_szScratch, pszFormat, argptr); - AllocBeforeWrite(iLen); - strcpy(m_pchData, s_szScratch); - - return iLen; -#else -#ifdef __WXMSW__ - #ifdef _MSC_VER - #define wxVsprintf _vsnprintf - #endif -#else // guess that any Unix has snprintf() - feel free to insert additional - // platform/compiler tests here if this is not the case for you - #define wxVsprintf vsnprintf -#endif - -#ifndef wxVsprintf - #pragma message("Using sprintf() because no snprintf()-like function defined") - #define wxVsprintf vsprintf -#endif - // static buffer to avoid dynamic memory allocation each time static char s_szScratch[1024]; + // NB: wxVsprintf() may return either less than the buffer size or -1 if there + // is not enough place depending on implementation int iLen = wxVsprintf(s_szScratch, WXSIZEOF(s_szScratch), pszFormat, argptr); char *buffer; - if ( (size_t)iLen < WXSIZEOF(s_szScratch) ) { + if ( iLen < (int)WXSIZEOF(s_szScratch) ) { buffer = s_szScratch; } else { @@ -981,7 +1015,6 @@ int wxString::PrintfV(const char* pszFormat, va_list argptr) free(buffer); return iLen; -#endif } // ---------------------------------------------------------------------------- @@ -1046,10 +1079,23 @@ bool wxString::Matches(const char *pszMask) const return *pszTxt == '\0'; } +// Count the number of chars +int wxString::Freq(char ch) const +{ + int count = 0; + int len = Len(); + for (int i = 0; i < len; i++) + { + if (GetChar(i) == ch) + count ++; + } + return count; +} + // --------------------------------------------------------------------------- // standard C++ library string functions // --------------------------------------------------------------------------- -#ifdef STD_STRING_COMPATIBILITY +#ifdef wxSTD_STRING_COMPATIBILITY wxString& wxString::insert(size_t nPos, const wxString& str) { @@ -1087,6 +1133,8 @@ size_t wxString::find(const char* sz, size_t nStart, size_t n) const } #endif +// Gives a duplicate symbol (presumably a case-insensitivity problem) +#if !defined(__BORLANDC__) size_t wxString::find(char ch, size_t nStart) const { wxASSERT( nStart <= Len() ); @@ -1095,6 +1143,7 @@ size_t wxString::find(char ch, size_t nStart) const return p == NULL ? npos : p - c_str(); } +#endif size_t wxString::rfind(const wxString& str, size_t nStart) const { @@ -1340,7 +1389,7 @@ int wxArrayString::Index(const char *sz, bool bCase, bool bFromEnd) const } } - return NOT_FOUND; + return wxNOT_FOUND; } // add item at the end @@ -1391,7 +1440,7 @@ void wxArrayString::Remove(const char *sz) { int iIndex = Index(sz); - wxCHECK_RET( iIndex != NOT_FOUND, + wxCHECK_RET( iIndex != wxNOT_FOUND, _("removing inexistent element in wxArrayString::Remove") ); Remove(iIndex);