#pragma once #include "../Base/Base.h" #include "../Base/SmartPtr.h" #if defined(_WIN32) || defined (_WIN64) #include #include #endif #include #ifndef _USE_NULLABLE_PROPERTY_ using namespace NSCommon; #endif namespace XmlUtils { static CString strInvalidValue = _T("x(-Jdl%^8sFGs@gkp14jJU(90dyjhjnb*EcfFf%#2124sf98hc"); //static _bstr_t g_cpszXML_TextExt = L"./text()"; // common AVSINLINE static int GetDigit (TCHAR c) { if (c >= '0' && c <= '9') return (int)(c - '0'); if (c >= 'a' && c <= 'f') return 10 + (int)(c - 'a'); if (c >= 'A' && c <= 'F') return 10 + (int)(c - 'A'); return 0; } AVSINLINE static bool IsDigit (TCHAR c) { if (c >= '0' && c <= '9') return true; return false; } AVSINLINE static __int64 GetHex (const CString& string) { __int64 nResult = 0; int nLen = string.GetLength(); for ( int nIndex = 0; nIndex < nLen; ++nIndex ) { nResult += GetDigit( string[nIndex] ) << ( 4 * ( nLen - 1 - nIndex ) ); } return nResult; } AVSINLINE static int GetColor (const CString& string) { // variables int blue = 0; int green = 0; int red = 0; CString color = string; color = color.Trim(); if (color.Find(_T("0x"))!=-1) color.Delete(0,2); if (color.Find(_T("#"))!=-1) color.Delete(0,1); while (color.GetLength() < 6) color = _T("0") + color; red = 16*GetDigit(color[0]) + GetDigit(color[1]); green = 16*GetDigit(color[2]) + GetDigit(color[3]); blue = 16*GetDigit(color[4]) + GetDigit(color[5]); return RGB(red, green, blue); } AVSINLINE static bool GetBoolean (const CString& string) { CString s = string; s.MakeLower(); return (s == _T("true")); } AVSINLINE static bool GetBoolean2(const CString& string) { CString sTemp = string; sTemp.MakeLower(); return ( _T("true") == sTemp || _T("1") == sTemp || _T("t") == sTemp || _T("on") == sTemp ); } AVSINLINE static int GetInteger (const CString& string) { if (string.GetLength() <1) return 0; try { return _ttoi(string); } catch(...) { } try { return static_cast(_wtoi64(string)); } catch(...) { return 0; } } AVSINLINE static size_t GetUInteger(const CString& string) { if (string.GetLength() <1) return 0; try { return (size_t) _ttoi(string); } catch(...) { } try { return (size_t) _wtoi64(string); } catch(...) { return 0; } } AVSINLINE static double GetDouble (const CString& string) { if (string.GetLength() <1) return 0; double d = 0; _stscanf(string, _T("%lf"), &d); return d; } AVSINLINE static float GetFloat (const CString& string) { if (string.GetLength() <1) return 0; float f = 0; _stscanf(string, _T("%f"), &f); return f; } #if defined(_WIN32) || defined (_WIN64) AVSINLINE static int GetInteger (BSTR string) { return _wtoi(string); } AVSINLINE static size_t GetUInteger(BSTR string) { return (size_t)_wtoi(string); } AVSINLINE static double GetDouble (BSTR string) { double d = 0; swscanf(string, _T("%lf"), &d); return d; } AVSINLINE static float GetFloat (BSTR string) { float f = 0; swscanf(string, _T("%f"), &f); return f; } AVSINLINE static void GetDouble (BSTR string, double* p) { *p = 0; swscanf(string, _T("%lf"), *p); } AVSINLINE static void GetFloat (BSTR string, float* p) { *p = 0; swscanf(string, _T("%f"), *p); } AVSINLINE static void GetInteger (BSTR string, int* p) { *p = 0; swscanf(string, _T("%d"), *p); } #endif AVSINLINE CString BoolToString (const bool & value) { CString sResult = ( value ? _T("true") : _T("false") ); return sResult; } AVSINLINE CString IntToString (const int & value) { CString str = _T(""); str.Format(_T("%d"), value); return str; } AVSINLINE CString UIntToString (const size_t & value) { CString str = _T(""); str.Format(_T("%u"), value); return str; } AVSINLINE CString FloatToString (const float & value) { CString str = _T(""); str.Format(_T("%f"), value); return str; } AVSINLINE CString DoubleToString(const double& value) { CString str = _T(""); str.Format(_T("%lf"), value); return str; } AVSINLINE static CString GetLower(const CString& string) { //CString s = string; s.MakeLower(); //return s; CString sResult; for( int nIndex = 0; nIndex < string.GetLength(); nIndex++) sResult += wchar_t( towlower(string[nIndex]) ); return sResult; } AVSINLINE static CString GetUpper(const CString& string) { CString sResult; for( int nIndex = 0; nIndex < string.GetLength(); nIndex++) sResult += wchar_t( towupper(string[nIndex]) ); return sResult; } AVSINLINE static bool IsUnicodeSymbol( WCHAR symbol ) { bool result = false; if ( ( 0x0009 == symbol ) || ( 0x000A == symbol ) || ( 0x000D == symbol ) || ( ( 0x0020 <= symbol ) && ( 0xD7FF >= symbol ) ) || ( ( 0xE000 <= symbol ) && ( symbol <= 0xFFFD ) ) || ( ( 0x10000 <= symbol ) && symbol ) ) { result = true; } return result; } AVSINLINE static CString EncodeXmlString(const CString& string, bool bDeleteNoUnicode = false) { CString sResult; if(bDeleteNoUnicode) { sResult = _T(""); for (unsigned int i = 0, length = string.GetLength(); i < length; ++i ) { WCHAR symbol = string.GetAt(i); if ( false == IsUnicodeSymbol( symbol ) ) { if(0xD800 <= symbol && symbol <= 0xDFFF && i + 1 < length) { i++; WCHAR symbol2 = string.GetAt(i); if (symbol < 0xDC00 && symbol2 >= 0xDC00 && symbol2 <= 0xDFFF) { sResult.AppendChar(symbol); sResult.AppendChar(symbol2); } } } else sResult.AppendChar(symbol); } } else { sResult = string; for (unsigned int i = 0, length = string.GetLength(); i < length; ++i ) { WCHAR symbol = string.GetAt(i); if ( false == IsUnicodeSymbol( symbol ) ) { if(0xD800 <= symbol && symbol <= 0xDFFF && i + 1 < length) { i++; WCHAR symbol2 = string.GetAt(i); if (!(symbol < 0xDC00 && symbol2 >= 0xDC00 && symbol2 <= 0xDFFF)) { sResult.SetAt(i - 1, ' '); sResult.SetAt(i, ' '); } } else sResult.SetAt(i, ' '); } } } sResult.Replace(_T("&"), _T("&")); sResult.Replace(_T("'"), _T("'")); sResult.Replace(_T("<"), _T("<")); sResult.Replace(_T(">"), _T(">")); sResult.Replace(_T("\""), _T(""")); return sResult; } //#ifndef _USE_LIBXML2_READER_ class CStringWriter { private: wchar_t* m_pData; size_t m_lSize; wchar_t* m_pDataCur; size_t m_lSizeCur; public: CStringWriter() { m_pData = NULL; m_lSize = 0; m_pDataCur = m_pData; m_lSizeCur = m_lSize; m_bInitTable = false; } ~CStringWriter() { RELEASEMEM(m_pData); } AVSINLINE void AddSize(size_t nSize) { if (NULL == m_pData) { m_lSize = (std::max)((int) nSize, 1000); m_pData = (wchar_t*)malloc(m_lSize * sizeof(wchar_t)); m_lSizeCur = 0; m_pDataCur = m_pData; return; } if ((m_lSizeCur + nSize) > m_lSize) { while ((m_lSizeCur + nSize) > m_lSize) { m_lSize *= 2; } wchar_t* pRealloc = (wchar_t*)realloc(m_pData, m_lSize * sizeof(wchar_t)); if (NULL != pRealloc) { // реаллок сработал m_pData = pRealloc; m_pDataCur = m_pData + m_lSizeCur; } else { wchar_t* pMalloc = (wchar_t*)malloc(m_lSize * sizeof(wchar_t)); memcpy(pMalloc, m_pData, m_lSizeCur * sizeof(wchar_t)); free(m_pData); m_pData = pMalloc; m_pDataCur = m_pData + m_lSizeCur; } } } public: AVSINLINE void WriteString(const wchar_t* pString, size_t nLen) { AddSize(nLen); memcpy(m_pDataCur, pString, nLen * sizeof(wchar_t)); m_pDataCur += nLen; m_lSizeCur += nLen; } #if defined(_WIN32) || defined (_WIN64) AVSINLINE void WriteString(_bstr_t& bsString) { size_t nLen = bsString.length(); WriteString(bsString.GetBSTR(), nLen); } #endif AVSINLINE void WriteString(const CString& sString) { size_t nLen = (size_t)sString.GetLength(); #ifdef _UNICODE CString str = sString; WriteString(str.GetBuffer(), nLen); #else CStringW str = (CStringW)sString; WriteString(str.GetBuffer(), nLen); #endif } AVSINLINE void AddCharSafe(const TCHAR& _c) { AddSize(1); *m_pDataCur++ = _c; ++m_lSizeCur; } AVSINLINE void AddChar2Safe(const TCHAR _c1, const TCHAR& _c2) { AddSize(2); *m_pDataCur++ = _c1; *m_pDataCur++ = _c2; m_lSizeCur += 2; } inline void WriteEncodeXmlString(const wchar_t* pString) { const wchar_t* pData = pString; while (*pData != 0) { BYTE _code = CheckCode(*pData); switch (_code) { case 1: AddCharSafe(*pData); break; case 0: AddCharSafe((WCHAR)' '); break; case 2: AddSize(5); *m_pDataCur++ = (WCHAR)('&'); *m_pDataCur++ = (WCHAR)('a'); *m_pDataCur++ = (WCHAR)('m'); *m_pDataCur++ = (WCHAR)('p'); *m_pDataCur++ = (WCHAR)(';'); m_lSizeCur += 5; break; case 3: AddSize(6); *m_pDataCur++ = (WCHAR)('&'); *m_pDataCur++ = (WCHAR)('a'); *m_pDataCur++ = (WCHAR)('p'); *m_pDataCur++ = (WCHAR)('o'); *m_pDataCur++ = (WCHAR)('s'); *m_pDataCur++ = (WCHAR)(';'); m_lSizeCur += 6; break; case 4: AddSize(4); *m_pDataCur++ = (WCHAR)('&'); *m_pDataCur++ = (WCHAR)('l'); *m_pDataCur++ = (WCHAR)('t'); *m_pDataCur++ = (WCHAR)(';'); m_lSizeCur += 4; break; case 5: AddSize(4); *m_pDataCur++ = (WCHAR)('&'); *m_pDataCur++ = (WCHAR)('g'); *m_pDataCur++ = (WCHAR)('t'); *m_pDataCur++ = (WCHAR)(';'); m_lSizeCur += 4; break; case 6: AddSize(6); *m_pDataCur++ = (WCHAR)('&'); *m_pDataCur++ = (WCHAR)('q'); *m_pDataCur++ = (WCHAR)('u'); *m_pDataCur++ = (WCHAR)('o'); *m_pDataCur++ = (WCHAR)('t'); *m_pDataCur++ = (WCHAR)(';'); m_lSizeCur += 6; break; default: break; } ++pData; } } AVSINLINE size_t GetCurSize() { return m_lSizeCur; } AVSINLINE void Write(CStringWriter& oWriter) { WriteString(oWriter.m_pData, oWriter.m_lSizeCur); } inline void Clear() { RELEASEMEM(m_pData); m_pData = NULL; m_lSize = 0; m_pDataCur = m_pData; m_lSizeCur = 0; } inline void ClearNoAttack() { m_pDataCur = m_pData; m_lSizeCur = 0; } CString GetData() { CString str(m_pData, (int)m_lSizeCur); return str; } protected: BYTE m_arTableUnicodes[65536]; bool m_bInitTable; protected: BYTE CheckCode(const WCHAR& c) { if (!m_bInitTable) { memset(m_arTableUnicodes, 0, 65536); m_arTableUnicodes[0x0009] = 1; m_arTableUnicodes[0x000A] = 1; m_arTableUnicodes[0x000D] = 1; memset(m_arTableUnicodes + 0x0020, 1, 0xD7FF - 0x0020 + 1); memset(m_arTableUnicodes + 0xE000, 1, 0xFFFD - 0xE000 + 1); m_arTableUnicodes['&'] = 2; m_arTableUnicodes['\''] = 3; m_arTableUnicodes['<'] = 4; m_arTableUnicodes['>'] = 5; m_arTableUnicodes['\"'] = 6; m_bInitTable = true; } #if !defined(_WIN32) && !defined (_WIN64) if (sizeof (wchar_t) == 4) { UTF16 c1=0; const UTF32 *pStr32 = (UTF32 *)&c; UTF16 *pStr16 = (UTF16 *)&c1; ConversionResult eUnicodeConversionResult = ConvertUTF32toUTF16(&pStr32,&pStr32[1], &pStr16, &pStr16[1],strictConversion); if (conversionOK != eUnicodeConversionResult) { return 1; //?? } return m_arTableUnicodes[c1]; } else #endif return m_arTableUnicodes[c]; } }; //#endif // ifndef _USE_LIBXML2_READER_ }