if ( lenChunk == wxCONV_FAILED )
return wxCONV_FAILED;
- lenChunk++; // for the L'\0' at the end of this chunk
-
dstWritten += lenChunk;
+ if ( !srcEnd )
+ dstWritten++;
- if ( lenChunk == 1 )
+ if ( !lenChunk )
{
// nothing left in the input string, conversion succeeded
break;
if ( dstWritten > dstLen )
return wxCONV_FAILED;
- if ( MB2WC(dst, src, lenChunk) == wxCONV_FAILED )
+ // +1 is for trailing NUL
+ if ( MB2WC(dst, src, lenChunk + 1) == wxCONV_FAILED )
return wxCONV_FAILED;
dst += lenChunk;
+ if ( !srcEnd )
+ dst++;
}
if ( !srcEnd )
// the number of chars [which would be] written to dst [if it were not NULL]
size_t dstWritten = 0;
+ // if we don't know its length we have no choice but to assume that it is
+ // NUL-terminated (notice that it can still be NUL-terminated even if
+ // explicit length is given but it doesn't change our return value)
+ const bool isNulTerminated = srcLen == wxNO_LEN;
+
// make a copy of the input string unless it is already properly
// NUL-terminated
- //
- // if we don't know its length we have no choice but to assume that it is,
- // indeed, properly terminated
wxWCharBuffer bufTmp;
- if ( srcLen == wxNO_LEN )
+ if ( isNulTerminated )
{
srcLen = wxWcslen(src) + 1;
}
if ( lenChunk == wxCONV_FAILED )
return wxCONV_FAILED;
- lenChunk += lenNul;
dstWritten += lenChunk;
+ if ( isNulTerminated )
+ dstWritten += lenNul;
if ( dst )
{
if ( dstWritten > dstLen )
return wxCONV_FAILED;
- if ( WC2MB(dst, src, lenChunk) == wxCONV_FAILED )
+ if ( WC2MB(dst, src, lenChunk + lenNul) == wxCONV_FAILED )
return wxCONV_FAILED;
dst += lenChunk;
+ if ( isNulTerminated )
+ dst += lenNul;
}
}
// because we want the buffer to always be NUL-terminated, even if the
// input isn't (as otherwise the caller has no way to know its length)
wxWCharBuffer wbuf(dstLen);
- wbuf.data()[dstLen - 1] = L'\0';
+ wbuf.data()[dstLen] = L'\0';
if ( ToWChar(wbuf.data(), dstLen, inBuff, inLen) != wxCONV_FAILED )
{
if ( outLen )
{
*outLen = dstLen;
- if ( wbuf[dstLen - 1] == L'\0' )
+
+ // we also need to handle NUL-terminated input strings
+ // specially: for them the output is the length of the string
+ // excluding the trailing NUL, however if we're asked to
+ // convert a specific number of characters we return the length
+ // of the resulting output even if it's NUL-terminated
+ if ( inLen == wxNO_LEN )
(*outLen)--;
}
{
*outLen = dstLen;
- if ( dstLen >= nulLen &&
- !NotAllNULs(buf.data() + dstLen - nulLen, nulLen) )
+ if ( inLen == wxNO_LEN )
{
- // in this case the output is NUL-terminated and we're not
- // supposed to count NUL
+ // in this case both input and output are NUL-terminated
+ // and we're not supposed to count NUL
*outLen -= nulLen;
}
}
return m_convReal->ToWChar(dst, dstLen, src, srcLen);
// latin-1 (direct)
- return wxMBConv::ToWChar(dst, dstLen, src, srcLen);
-}
+ if ( srcLen == wxNO_LEN )
+ srcLen = strlen(src) + 1; // take trailing NUL too
-size_t wxCSConv::FromWChar(char *dst, size_t dstLen,
- const wchar_t *src, size_t srcLen) const
-{
- CreateConvIfNeeded();
+ if ( dst )
+ {
+ if ( dstLen < srcLen )
+ return wxCONV_FAILED;
- if (m_convReal)
- return m_convReal->FromWChar(dst, dstLen, src, srcLen);
+ for ( size_t n = 0; n < srcLen; n++ )
+ dst[n] = (unsigned char)(src[n]);
+ }
- // latin-1 (direct)
- return wxMBConv::FromWChar(dst, dstLen, src, srcLen);
+ return srcLen;
}
-size_t wxCSConv::MB2WC(wchar_t *buf, const char *psz, size_t n) const
+size_t wxCSConv::FromWChar(char *dst, size_t dstLen,
+ const wchar_t *src, size_t srcLen) const
{
CreateConvIfNeeded();
if (m_convReal)
- return m_convReal->MB2WC(buf, psz, n);
+ return m_convReal->FromWChar(dst, dstLen, src, srcLen);
// latin-1 (direct)
- size_t len = strlen(psz);
+ if ( srcLen == wxNO_LEN )
+ srcLen = wxWcslen(src) + 1;
- if (buf)
+ if ( dst )
{
- for (size_t c = 0; c <= len; c++)
- buf[c] = (unsigned char)(psz[c]);
- }
-
- return len;
-}
-
-size_t wxCSConv::WC2MB(char *buf, const wchar_t *psz, size_t n) const
-{
- CreateConvIfNeeded();
-
- if (m_convReal)
- return m_convReal->WC2MB(buf, psz, n);
+ if ( dstLen < srcLen )
+ return wxCONV_FAILED;
- // latin-1 (direct)
- const size_t len = wxWcslen(psz);
- if (buf)
- {
- for (size_t c = 0; c <= len; c++)
+ for ( size_t n = 0; n < srcLen; n++ )
{
- if (psz[c] > 0xFF)
+ if ( src[n] > 0xFF )
return wxCONV_FAILED;
- buf[c] = (char)psz[c];
+ dst[n] = (char)src[n];
}
+
}
- else
+ else // still need to check the input validity
{
- for (size_t c = 0; c <= len; c++)
+ for ( size_t n = 0; n < srcLen; n++ )
{
- if (psz[c] > 0xFF)
+ if ( src[n] > 0xFF )
return wxCONV_FAILED;
}
}
- return len;
+ return srcLen;
}
size_t wxCSConv::GetMBNulLen() const