?? iconvgnutransservice.cpp
字號:
} return toReturn;}size_t IconvGNUWrapper::iconvFrom ( const char *fromPtr, size_t *fromLen, char **toPtr, size_t toLen ) const{ ICONV_LOCK; char ** tmpPtr = (char**)&fromPtr; return ::iconv (fCDFrom, tmpPtr, fromLen, toPtr, &toLen);}size_t IconvGNUWrapper::iconvTo ( const char *fromPtr, size_t *fromLen, char **toPtr, size_t toLen ) const{ ICONV_LOCK; char ** tmpPtr = (char**)&fromPtr; return ::iconv (fCDTo, tmpPtr, fromLen, toPtr, &toLen);}// ---------------------------------------------------------------------------// IconvGNUTransService: Constructors and Destructor// ---------------------------------------------------------------------------void reinitIconvGNUMutex(){ delete gIconvMutex; gIconvMutex = 0;}IconvGNUTransService::IconvGNUTransService() : IconvGNUWrapper(), fUnicodeCP(0){#if !defined(APP_NO_THREADS) // Create global lock object if (gIconvMutex == NULL) { gIconvMutex = new XMLMutex; if (gIconvMutex == NULL) XMLPlatformUtils::panic (PanicHandler::Panic_NoTransService); IconvGNUMutexCleanup.registerCleanup(reinitIconvGNUMutex); }#endif // Try to obtain local (host) characterset through the environment char* fLocalCP = setlocale (LC_CTYPE, ""); if (fLocalCP == NULL) fLocalCP = "iso-8859-1"; // fallback locale else { char *ptr = strchr (fLocalCP, '.'); if (ptr == NULL) fLocalCP = "iso-8859-1"; // fallback locale else fLocalCP = ptr + 1; } // Select the native unicode characters encoding schema const IconvGNUEncoding *eptr; // first - try to use the schema with character size, equil to XMLCh for (eptr = gIconvGNUEncodings; eptr->fSchema; eptr++) { if (eptr->fUChSize != sizeof(XMLCh)) continue; ICONV_LOCK; // try to create conversion descriptor iconv_t cd_to = iconv_open(fLocalCP, eptr->fSchema); if (cd_to == (iconv_t)-1) continue; iconv_t cd_from = iconv_open(eptr->fSchema, fLocalCP); if (cd_to == (iconv_t)-1) { iconv_close (cd_to); continue; } // got it setUChSize(eptr->fUChSize); setUBO(eptr->fUBO); setCDTo(cd_to); setCDFrom(cd_from); fUnicodeCP = eptr->fSchema; break; } if (fUnicodeCP == NULL) // try to use any known schema for (eptr = gIconvGNUEncodings; eptr->fSchema; eptr++) { // try to create conversion descriptor ICONV_LOCK; iconv_t cd_to = iconv_open(fLocalCP, eptr->fSchema); if (cd_to == (iconv_t)-1) continue; iconv_t cd_from = iconv_open(eptr->fSchema, fLocalCP); if (cd_to == (iconv_t)-1) { iconv_close (cd_to); continue; } // got it setUChSize(eptr->fUChSize); setUBO(eptr->fUBO); setCDTo(cd_to); setCDFrom(cd_from); fUnicodeCP = eptr->fSchema; break; } if (fUnicodeCP == NULL || cdTo() == (iconv_t)-1 || cdFrom() == (iconv_t)-1) XMLPlatformUtils::panic (PanicHandler::Panic_NoTransService);}IconvGNUTransService::~IconvGNUTransService(){ if (cdTo() != (iconv_t) -1) { iconv_close (cdTo()); setCDTo ((iconv_t)-1); } if (cdFrom() != (iconv_t) -1) { iconv_close (cdFrom()); setCDFrom ((iconv_t)-1); }}// ---------------------------------------------------------------------------// IconvGNUTransService: The virtual transcoding service API// ---------------------------------------------------------------------------int IconvGNUTransService::compareIString(const XMLCh* const comp1 , const XMLCh* const comp2){ const XMLCh* cptr1 = comp1; const XMLCh* cptr2 = comp2; XMLCh c1 = toUpper(*cptr1); XMLCh c2 = toUpper(*cptr2); while ( (*cptr1 != 0) && (*cptr2 != 0) ) { if (c1 != c2) break; c1 = toUpper(*(++cptr1)); c2 = toUpper(*(++cptr2)); } return (int) ( c1 - c2 );}int IconvGNUTransService::compareNIString(const XMLCh* const comp1 , const XMLCh* const comp2 , const unsigned int maxChars){ unsigned int n = 0; const XMLCh* cptr1 = comp1; const XMLCh* cptr2 = comp2; while (true && maxChars) { XMLCh c1 = toUpper(*cptr1); XMLCh c2 = toUpper(*cptr2); if (c1 != c2) return (int) (c1 - c2); // If either ended, then both ended, so equal if (!*cptr1 || !*cptr2) break; cptr1++; cptr2++; // Bump the count of chars done. If it equals the count then we // are equal for the requested count, so break out and return // equal. n++; if (n == maxChars) break; } return 0;}const XMLCh* IconvGNUTransService::getId() const{ return gMyServiceId;}bool IconvGNUTransService::isSpace(const XMLCh toCheck) const{ return IconvGNUWrapper::isSpace(toCheck);}XMLLCPTranscoder* IconvGNUTransService::makeNewLCPTranscoder(){ return new IconvGNULCPTranscoder (cdFrom(), cdTo(), uChSize(), UBO());}bool IconvGNUTransService::supportsSrcOfs() const{ return true;}// ---------------------------------------------------------------------------// IconvGNUTransService: The protected virtual transcoding service API// ---------------------------------------------------------------------------XMLTranscoder*IconvGNUTransService::makeNewXMLTranscoder( const XMLCh* const encodingName , XMLTransService::Codes& resValue , const unsigned int blockSize , MemoryManager* const manager){ resValue = XMLTransService::UnsupportedEncoding; IconvGNUTranscoder *newTranscoder = NULL; char *encLocal = XMLString::transcode(encodingName, manager); iconv_t cd_from, cd_to; { ICONV_LOCK; cd_from = iconv_open (fUnicodeCP, encLocal); if (cd_from == (iconv_t)-1) { resValue = XMLTransService::SupportFilesNotFound; if (encLocal) manager->deallocate(encLocal);//delete [] encLocal; return NULL; } cd_to = iconv_open (encLocal, fUnicodeCP); if (cd_to == (iconv_t)-1) { resValue = XMLTransService::SupportFilesNotFound; iconv_close (cd_from); if (encLocal) manager->deallocate(encLocal);//delete [] encLocal; return NULL; } newTranscoder = new (manager) IconvGNUTranscoder (encodingName, blockSize, cd_from, cd_to, uChSize(), UBO(), manager); } if (newTranscoder) resValue = XMLTransService::Ok; if (encLocal) manager->deallocate(encLocal);//delete [] encLocal; return newTranscoder;}void IconvGNUTransService::upperCase(XMLCh* const toUpperCase) const{ XMLCh* outPtr = toUpperCase; while (*outPtr) { *outPtr = toUpper(*outPtr); outPtr++; }}void IconvGNUTransService::lowerCase(XMLCh* const toLowerCase) const{ XMLCh* outPtr = toLowerCase; while (*outPtr) { *outPtr = toLower(*outPtr); outPtr++; }}// ---------------------------------------------------------------------------// IconvGNULCPTranscoder: The virtual transcoder API// ---------------------------------------------------------------------------unsigned intIconvGNULCPTranscoder::calcRequiredSize (const char* const srcText , MemoryManager* const manager){ if (!srcText) return 0; size_t len, srcLen; len = srcLen = strlen(srcText); if (len == 0) return 0; char tmpWideArr[gTempBuffArraySize]; size_t totalLen = 0; for (;;) { char *pTmpArr = tmpWideArr; const char *ptr = srcText + srcLen - len; size_t rc = iconvFrom(ptr, &len, &pTmpArr, gTempBuffArraySize); if (rc == (size_t) -1 && errno != E2BIG) { ThrowXMLwithMemMgr(TranscodingException, XMLExcepts::Trans_BadSrcSeq, manager); /* return 0; */ } rc = pTmpArr - (char *) tmpWideArr; totalLen += rc; if (rc == 0 || len == 0) break; } return totalLen / uChSize();}unsigned intIconvGNULCPTranscoder::calcRequiredSize(const XMLCh* const srcText , MemoryManager* const manager){ if (!srcText) return 0; unsigned int wLent = getWideCharLength(srcText); if (wLent == 0) return 0; char tmpWBuff[gTempBuffArraySize]; char *wBuf = 0; char *wBufPtr = 0; size_t len = wLent * uChSize(); if (uChSize() != sizeof(XMLCh) || UBO() != BYTE_ORDER) { if (len > gTempBuffArraySize) { wBufPtr = (char*) manager->allocate ( len * sizeof(char) );//new char[len]; if (wBufPtr == NULL) return 0; wBuf = wBufPtr; } else wBuf = tmpWBuff; xmlToMbs (srcText, wLent, wBuf, wLent); } else wBuf = (char *) srcText; char tmpBuff[gTempBuffArraySize]; size_t totalLen = 0; char *srcEnd = wBuf + wLent * uChSize(); for (;;) { char *pTmpArr = tmpBuff; const char *ptr = srcEnd - len; size_t rc = iconvTo(ptr, &len, &pTmpArr, gTempBuffArraySize); if (rc == (size_t) -1 && errno != E2BIG) { if (wBufPtr) manager->deallocate(wBufPtr);//delete [] wBufPtr; ThrowXMLwithMemMgr(TranscodingException, XMLExcepts::Trans_BadSrcSeq, manager); /* return 0; */ } rc = pTmpArr - tmpBuff; totalLen += rc; if (rc == 0 || len == 0) break; } if (wBufPtr) manager->deallocate(wBufPtr);//delete [] wBufPtr; return totalLen;}char* IconvGNULCPTranscoder::transcode(const XMLCh* const toTranscode){ if (!toTranscode) return 0; char* retVal = 0; if (*toTranscode) { unsigned int wLent = getWideCharLength(toTranscode); // Calc needed size. const size_t neededLen = calcRequiredSize (toTranscode); if (neededLen == 0) return 0; // allocate output buffer retVal = new char[neededLen + 1]; if (retVal == NULL) return 0; // prepare the original char tmpWBuff[gTempBuffArraySize]; char *wideCharBuf = 0; char *wBufPtr = 0; size_t len = wLent * uChSize(); if (uChSize() != sizeof(XMLCh) || UBO() != BYTE_ORDER) { if (len > gTempBuffArraySize) { wBufPtr = new char[len]; if (wBufPtr == NULL) return 0; wideCharBuf = wBufPtr; } else wideCharBuf = tmpWBuff; xmlToMbs (toTranscode, wLent, wideCharBuf, wLent); } else wideCharBuf = (char *) toTranscode; // perform conversion wLent *= uChSize(); char *ptr = retVal; size_t rc = iconvTo(wideCharBuf, (size_t *) &wLent, &ptr, neededLen); if (rc == (size_t)-1) { if (wBufPtr) delete [] wBufPtr; return 0; } if (wBufPtr) delete [] wBufPtr; retVal[neededLen] = 0; } else { retVal = new char[1]; if (retVal == NULL) return 0; retVal[0] = 0; } return retVal;}char* IconvGNULCPTranscoder::transcode(const XMLCh* const toTranscode, MemoryManager* const manager){ if (!toTranscode) return 0; char* retVal = 0; if (*toTranscode) { unsigned int wLent = getWideCharLength(toTranscode); // Calc needed size. const size_t neededLen = calcRequiredSize (toTranscode, manager); if (neededLen == 0) return 0; // allocate output buffer retVal = (char*) manager->allocate((neededLen + 1) * sizeof(char));//new char[neededLen + 1]; if (retVal == NULL) return 0; // prepare the original char tmpWBuff[gTempBuffArraySize]; char *wideCharBuf = 0; char *wBufPtr = 0; size_t len = wLent * uChSize(); if (uChSize() != sizeof(XMLCh) || UBO() != BYTE_ORDER) { if (len > gTempBuffArraySize) { wBufPtr = (char*) manager->allocate(len * sizeof(char));//new char[len]; if (wBufPtr == NULL) return 0; wideCharBuf = wBufPtr; } else wideCharBuf = tmpWBuff;
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -