Ich portiere gerade eine Lib von char* und ANSI auf wchar_t* und UTF16.
Dabei habe ich unter anderem eine Strinklasse vorliegen.
Diese hat, als sie noch char* benutzt hat, reibungslos mit ostream zusammengearbeitet, macht jetzt mit wchar_t aber Probleme.
Da die Klasse selbst ziemlich umfangrech ist (quasi eine Komplette C++ Reimplementation der Java Stringklasse + noch ein wenig mehr) habe ich mal zu Testzwecken alles rausgeschmissen, was für die Reproduktion des Issues unwichtig ist.
Es verbleibt diese zierliche kleine Klasse:
Code: Alles auswählen
class MyString
{
public:
MyString(void);
MyString(const char* Value);
MyString(const wchar_t* Value);
MyString(const MyString& Value);
~MyString();
operator wchar_t*(void) const;
operator const wchar_t*(void) const;
protected:
wchar_t* Buffer;
unsigned int BufferLen;
unsigned int Length;
void GetBuffer(unsigned int MaxStrLen);
};
Code: Alles auswählen
inline void MyString::GetBuffer(unsigned int MaxStrLen)
{
BufferLen = MaxStrLen;
//Buffer = new char[BufferLen + 1];
Buffer = (wchar_t*)MALLOC((BufferLen+1)*sizeof(wchar_t));
}
MyString::MyString(void): Buffer(NULL), BufferLen(0), Length(0)
{
const wchar_t* Value = L"";
GetBuffer(Length = WCSLEN(Value));
WCSCPY(Buffer, Value);
}
MyString::MyString(const char* Value): Buffer(NULL), BufferLen(0), Length(0)
{
DEBUG_ASSERT(Value);
int len = STRLEN(Value);
len++;
wchar_t* newBuf = (wchar_t*)MALLOC(sizeof(wchar_t)*len);
STRTOWSTR(const_cast<char*>(Value), newBuf, len);
GetBuffer(Length=len);
WCSCPY(Buffer, newBuf);
FREEIF(newBuf);
}
MyString::MyString(const wchar_t* Value): Buffer(NULL), BufferLen(0), Length(0)
{
DEBUG_ASSERT(Value);
GetBuffer(Length=WCSLEN(Value));
WCSCPY(Buffer, Value);
}
MyString::MyString(const MyString& Value): Buffer(NULL), BufferLen(0), Length(0)
{
GetBuffer(Length = Value.Length);
WCSCPY(Buffer, Value.Buffer);
}
MyString::~MyString()
{
FREE(Buffer);
}
MyString::operator wchar_t*(void) const
{
return Buffer;
}
MyString::operator const wchar_t*(void) const
{
return Buffer;
}
Code: Alles auswählen
MyString testStr(L"moep");
std::wcout << L"test - " << (const wchar_t*)testStr << std::endl;
Code: Alles auswählen
MyString testStr(L"moep");
std::wcout << L"test - " << testStr << std::endl;
Debugging ergibt nun folgendes:
Der Code springt in den Operator operator const wchar_t*(void) const und sollte entsprechend einen const wchar_t* zurückbekommen, welcher zum Aufruf von ostreams operator<< Überladung für const wchar_t* führen sollte. Das ist mit dem cast auch so der Fall, für const char* ist es auch ohne cast der Fall, für const wchar_t* ohne cast allerdings wird seltsamerweise ostreams operator<< Überladung für const void* aufgerufen, was erklärt, wieso die Speicheradresse ausgegeben wird. Die Frage ist nun, was läuft das schief, dass er ohne expliziten Cast nicht die const wchar_t* Überladung aufruft? Übergeber ich direkt einen const wchar_t*, funktioniert es auch, nur der ungecastete Rückgabewert meines operators wird irgendwie zum const void*