📄 charsetencoder.cpp
字号:
LogString::const_iterator& iter,
ByteBuffer& out) {
if(iter != in.end()) {
size_t requested = in.length() - (iter - in.begin());
if (requested > out.remaining()/sizeof(logchar)) {
requested = out.remaining()/sizeof(logchar);
}
memcpy(out.current(),
(const char*) in.data() + (iter - in.begin()),
requested * sizeof(logchar));
iter += requested;
out.position(out.position() + requested * sizeof(logchar));
}
return APR_SUCCESS;
}
private:
TrivialCharsetEncoder(const TrivialCharsetEncoder&);
TrivialCharsetEncoder& operator=(const TrivialCharsetEncoder&);
};
#if LOG4CXX_LOGCHAR_IS_UTF8
typedef TrivialCharsetEncoder UTF8CharsetEncoder;
#else
/**
* Converts a LogString to UTF-8.
*/
class UTF8CharsetEncoder : public CharsetEncoder {
public:
UTF8CharsetEncoder() {
}
virtual log4cxx_status_t encode(const LogString& in,
LogString::const_iterator& iter,
ByteBuffer& out) {
while(iter != in.end() && out.remaining() >= 8) {
unsigned int sv = Transcoder::decode(in, iter);
if (sv == 0xFFFF) {
return APR_BADARG;
}
Transcoder::encodeUTF8(sv, out);
}
return APR_SUCCESS;
}
private:
UTF8CharsetEncoder(const UTF8CharsetEncoder&);
UTF8CharsetEncoder& operator=(const UTF8CharsetEncoder&);
};
#endif
/**
* Encodes a LogString to UTF16-BE.
*/
class UTF16BECharsetEncoder : public CharsetEncoder {
public:
UTF16BECharsetEncoder() {
}
virtual log4cxx_status_t encode(const LogString& in,
LogString::const_iterator& iter,
ByteBuffer& out) {
while(iter != in.end() && out.remaining() >= 4) {
unsigned int sv = Transcoder::decode(in, iter);
if (sv == 0xFFFF) {
return APR_BADARG;
}
Transcoder::encodeUTF16BE(sv, out);
}
return APR_SUCCESS;
}
private:
UTF16BECharsetEncoder(const UTF16BECharsetEncoder&);
UTF16BECharsetEncoder& operator=(const UTF16BECharsetEncoder&);
};
/**
* Encodes a LogString to UTF16-LE.
*/
class UTF16LECharsetEncoder : public CharsetEncoder {
public:
UTF16LECharsetEncoder() {
}
virtual log4cxx_status_t encode(const LogString& in,
LogString::const_iterator& iter,
ByteBuffer& out) {
while(iter != in.end() && out.remaining() >= 4) {
unsigned int sv = Transcoder::decode(in, iter);
if (sv == 0xFFFF) {
return APR_BADARG;
}
Transcoder::encodeUTF16LE(sv, out);
}
return APR_SUCCESS;
}
private:
UTF16LECharsetEncoder(const UTF16LECharsetEncoder&);
UTF16LECharsetEncoder& operator=(const UTF16LECharsetEncoder&);
};
/**
* Charset encoder that uses an embedded CharsetEncoder consistent
* with current locale settings.
*/
class LocaleCharsetEncoder : public CharsetEncoder {
public:
LocaleCharsetEncoder() : pool(), mutex(pool), encoder(), encoding() {
}
virtual ~LocaleCharsetEncoder() {
}
virtual log4cxx_status_t encode(const LogString& in,
LogString::const_iterator& iter,
ByteBuffer& out) {
#if !LOG4CXX_CHARSET_EBCDIC
char* current = out.current();
size_t remain = out.remaining();
for(;
iter != in.end() && ((unsigned int) *iter) < 0x80 && remain > 0;
iter++, remain--, current++) {
*current = *iter;
}
out.position(current - out.data());
#endif
if (iter != in.end() && out.remaining() > 0) {
Pool subpool;
const char* enc = apr_os_locale_encoding(subpool.getAPRPool());
{
synchronized sync(mutex);
if (enc == 0) {
if (encoder == 0) {
encoding = "C";
encoder = new USASCIICharsetEncoder();
}
} else if (encoding != enc) {
encoding = enc;
LogString ename;
Transcoder::decode(encoding, ename);
try {
encoder = CharsetEncoder::getEncoder(ename);
} catch(IllegalArgumentException ex) {
encoder = new USASCIICharsetEncoder();
}
}
}
return encoder->encode(in, iter, out);
}
return APR_SUCCESS;
}
private:
LocaleCharsetEncoder(const LocaleCharsetEncoder&);
LocaleCharsetEncoder& operator=(const LocaleCharsetEncoder&);
Pool pool;
Mutex mutex;
CharsetEncoderPtr encoder;
std::string encoding;
};
} // namespace helpers
} //namespace log4cxx
CharsetEncoder::CharsetEncoder() {
}
CharsetEncoder::~CharsetEncoder() {
}
CharsetEncoderPtr CharsetEncoder::getDefaultEncoder() {
static CharsetEncoderPtr encoder(createDefaultEncoder());
//
// if invoked after static variable destruction
// (if logging is called in the destructor of a static object)
// then create a new decoder.
//
if (encoder == 0) {
return createDefaultEncoder();
}
return encoder;
}
CharsetEncoder* CharsetEncoder::createDefaultEncoder() {
#if LOG4CXX_CHARSET_UTF8
return new UTF8CharsetEncoder();
#elif LOG4CXX_CHARSET_ISO88591
return new ISOLatinCharsetEncoder();
#elif LOG4CXX_CHARSET_USASCII
return new USASCIICharsetEncoder();
#elif LOG4CXX_LOGCHAR_IS_WCHAR && LOG4CXX_HAS_WCSTOMBS
return new WcstombsCharsetEncoder();
#else
return new LocaleCharsetEncoder();
#endif
}
CharsetEncoderPtr CharsetEncoder::getUTF8Encoder() {
return new UTF8CharsetEncoder();
}
CharsetEncoderPtr CharsetEncoder::getEncoder(const LogString& charset) {
if (StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("UTF-8"), LOG4CXX_STR("utf-8"))) {
return new UTF8CharsetEncoder();
} else if (StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("C"), LOG4CXX_STR("c")) ||
charset == LOG4CXX_STR("646") ||
StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("US-ASCII"), LOG4CXX_STR("us-ascii")) ||
StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("ISO646-US"), LOG4CXX_STR("iso646-US")) ||
StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("ANSI_X3.4-1968"), LOG4CXX_STR("ansi_x3.4-1968"))) {
return new USASCIICharsetEncoder();
} else if (StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("ISO-8859-1"), LOG4CXX_STR("iso-8859-1")) ||
StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("ISO-LATIN-1"), LOG4CXX_STR("iso-latin-1"))) {
return new ISOLatinCharsetEncoder();
} else if (StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("UTF-16BE"), LOG4CXX_STR("utf-16be"))
|| StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("UTF-16"), LOG4CXX_STR("utf-16"))) {
return new UTF16BECharsetEncoder();
} else if (StringHelper::equalsIgnoreCase(charset, LOG4CXX_STR("UTF-16LE"), LOG4CXX_STR("utf-16le"))) {
return new UTF16LECharsetEncoder();
}
#if APR_HAS_XLATE || !defined(_WIN32)
return new APRCharsetEncoder(charset);
#else
throw IllegalArgumentException(charset);
#endif
}
void CharsetEncoder::reset() {
}
void CharsetEncoder::flush(ByteBuffer& /* out */ ) {
}
void CharsetEncoder::encode(CharsetEncoderPtr& enc,
const LogString& src,
LogString::const_iterator& iter,
ByteBuffer& dst) {
log4cxx_status_t stat = enc->encode(src, iter, dst);
if (stat != APR_SUCCESS && iter != src.end()) {
#if LOG4CXX_LOGCHAR_IS_WCHAR || LOG4CXX_LOGCHAR_IS_UNICHAR
iter++;
#elif LOG4CXX_LOGCHAR_IS_UTF8
// advance past this character and all continuation characters
while((*(++iter) & 0xC0) == 0x80);
#else
#error logchar is unrecognized
#endif
dst.put(Transcoder::LOSSCHAR);
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -