// Strange fiddlings required to use a nonstandard basic_string with g++ #include #include #include "ti_config.h" #include "string16.h" #if (defined(_AIX) && defined (__GNUC__) && __GNUC__ <= 2 && __GNUC_MINOR__ <= 95) // Why's this here? // C++ in its infinite complexity lets you perform a generic initialization // of static members of parametrized classes, e.g. // // template // int someclass::i = 666; // // but old versions of egcs, like the one they have on the SDSC SP/2, require // initialization of the instantiation instead: // int someclass::i = 666; string16::Rep string16::nilRep = { 0, 0, 1, false }; #elif (defined(_AIX) || defined(__osf__) || defined(hpux)) && \ defined (__GNUC__) && ((__GNUC__ >= 3 && __GNUC_MINOR__ <= 3) || \ (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)) // More bullshit for supporting g++'s perpetually broken string library const uint16 basic_string::_Rep::_S_terminal = uint16(); const basic_string::size_type basic_string::_Rep::_S_max_size = (((npos - sizeof(basic_string::_Rep))/sizeof(uint16)) - 1) / 4; #endif #if (defined (__GNUC__) && __GNUC__ >= 3 && __GNUC_MINOR__ >= 2 && __GNUC_MINOR__ < 4) || \ (defined(__xlC__) && !defined(_AIX)) /* xlc/Darwin */ #ifdef __xlC__ namespace std { #endif int char_traits::compare(const uint16* __s1, const uint16* __s2, size_t __n) { return memcmp(__s1, __s2, __n*sizeof(uint16)); } uint16* char_traits::move(uint16* __s1, const uint16* __s2, size_t __n) { return static_cast(memmove(__s1, __s2, __n*sizeof(uint16))); } uint16* char_traits::copy(uint16* __s1, const uint16* __s2, size_t __n) { return static_cast(memcpy(__s1, __s2, __n*sizeof(uint16))); } uint16* char_traits::assign(uint16* __s, size_t __n, uint16 __a) { for (size_t i = 0; i < __n; i++) __s[i] = __a; return __s; } #ifdef __xlC__ } #endif #endif // This representation is suitable for human viewing, // but cannot be fed into a C compiler. ostream &operator<<( ostream &os, const string16 &string ) { const ios::fmtflags flags = os.setf( ios::hex, ios::basefield | ios::showbase ); const char fill = os.fill( '0' ); os << '"'; for (unsigned pos = 0; pos < string.length(); ++pos) { const uint16 character = string[ pos ]; switch (character) { case '\b': os << "\\b"; break; case '\t': os << "\\t"; break; case '\n': os << "\\n"; break; case '\f': os << "\\f"; break; case '\r': os << "\\r"; break; case '"' : os << "\\\""; break; case '\\': os << "\\\\"; break; default: if (isascii( character ) && isprint( character )) os << (char) character; else os << "\\u" << setw( 4 ) << character; } } os << '"'; os.fill( fill ); os.flags( flags ); return os; } // This representation may be fed into a C compiler, // but is not as good for human viewing. void printEscaped( ostream &os, uint16 character ) { const ios::fmtflags flags = os.setf( ios::hex | ios::showbase, ios::basefield | ios::showbase ); const char fill = os.fill( '0' ); switch (character) { case '\b': os << "'\\b'"; break; case '\t': os << "'\\t'"; break; case '\n': os << "'\\n'"; break; case '\f': os << "'\\f'"; break; case '\r': os << "'\\r'"; break; case '\'': os << "'\\''"; break; case '"' : os << "'\\\"'"; break; case '\\': os << "'\\\\'"; break; default: if (isascii( character ) && isprint(character)) os << '\'' << char( character ) << '\''; else os << character; } os.fill( fill ); os.flags( flags ); } // This representation may be fed into a C compiler, // but is not as good for human viewing. void printEscaped( ostream &os, const string16 &string ) { os << "{"; bool first = true; for (unsigned pos = 0; pos < string.length(); ++pos) { if (first) first = false; else os << ","; printEscaped( os, string[ pos ] ); } os << "}"; }